atomic64_386_32.S 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195
  1. /* SPDX-License-Identifier: GPL-2.0-or-later */
  2. /*
  3. * atomic64_t for 386/486
  4. *
  5. * Copyright © 2010 Luca Barbieri
  6. */
  7. #include <linux/linkage.h>
  8. #include <asm/alternative.h>
  9. /* if you want SMP support, implement these with real spinlocks */
  10. .macro IRQ_SAVE reg
  11. pushfl
  12. cli
  13. .endm
  14. .macro IRQ_RESTORE reg
  15. popfl
  16. .endm
  17. #define BEGIN_IRQ_SAVE(op) \
  18. .macro endp; \
  19. SYM_FUNC_END(atomic64_##op##_386); \
  20. .purgem endp; \
  21. .endm; \
  22. SYM_FUNC_START(atomic64_##op##_386); \
  23. IRQ_SAVE v;
  24. #define ENDP endp
  25. #define RET_IRQ_RESTORE \
  26. IRQ_RESTORE v; \
  27. RET
  28. #define v %ecx
  29. BEGIN_IRQ_SAVE(read)
  30. movl (v), %eax
  31. movl 4(v), %edx
  32. RET_IRQ_RESTORE
  33. ENDP
  34. #undef v
  35. #define v %esi
  36. BEGIN_IRQ_SAVE(set)
  37. movl %ebx, (v)
  38. movl %ecx, 4(v)
  39. RET_IRQ_RESTORE
  40. ENDP
  41. #undef v
  42. #define v %esi
  43. BEGIN_IRQ_SAVE(xchg)
  44. movl (v), %eax
  45. movl 4(v), %edx
  46. movl %ebx, (v)
  47. movl %ecx, 4(v)
  48. RET_IRQ_RESTORE
  49. ENDP
  50. #undef v
  51. #define v %ecx
  52. BEGIN_IRQ_SAVE(add)
  53. addl %eax, (v)
  54. adcl %edx, 4(v)
  55. RET_IRQ_RESTORE
  56. ENDP
  57. #undef v
  58. #define v %ecx
  59. BEGIN_IRQ_SAVE(add_return)
  60. addl (v), %eax
  61. adcl 4(v), %edx
  62. movl %eax, (v)
  63. movl %edx, 4(v)
  64. RET_IRQ_RESTORE
  65. ENDP
  66. #undef v
  67. #define v %ecx
  68. BEGIN_IRQ_SAVE(sub)
  69. subl %eax, (v)
  70. sbbl %edx, 4(v)
  71. RET_IRQ_RESTORE
  72. ENDP
  73. #undef v
  74. #define v %ecx
  75. BEGIN_IRQ_SAVE(sub_return)
  76. negl %edx
  77. negl %eax
  78. sbbl $0, %edx
  79. addl (v), %eax
  80. adcl 4(v), %edx
  81. movl %eax, (v)
  82. movl %edx, 4(v)
  83. RET_IRQ_RESTORE
  84. ENDP
  85. #undef v
  86. #define v %esi
  87. BEGIN_IRQ_SAVE(inc)
  88. addl $1, (v)
  89. adcl $0, 4(v)
  90. RET_IRQ_RESTORE
  91. ENDP
  92. #undef v
  93. #define v %esi
  94. BEGIN_IRQ_SAVE(inc_return)
  95. movl (v), %eax
  96. movl 4(v), %edx
  97. addl $1, %eax
  98. adcl $0, %edx
  99. movl %eax, (v)
  100. movl %edx, 4(v)
  101. RET_IRQ_RESTORE
  102. ENDP
  103. #undef v
  104. #define v %esi
  105. BEGIN_IRQ_SAVE(dec)
  106. subl $1, (v)
  107. sbbl $0, 4(v)
  108. RET_IRQ_RESTORE
  109. ENDP
  110. #undef v
  111. #define v %esi
  112. BEGIN_IRQ_SAVE(dec_return)
  113. movl (v), %eax
  114. movl 4(v), %edx
  115. subl $1, %eax
  116. sbbl $0, %edx
  117. movl %eax, (v)
  118. movl %edx, 4(v)
  119. RET_IRQ_RESTORE
  120. ENDP
  121. #undef v
  122. #define v %esi
  123. BEGIN_IRQ_SAVE(add_unless)
  124. addl %eax, %ecx
  125. adcl %edx, %edi
  126. addl (v), %eax
  127. adcl 4(v), %edx
  128. cmpl %eax, %ecx
  129. je 3f
  130. 1:
  131. movl %eax, (v)
  132. movl %edx, 4(v)
  133. movl $1, %eax
  134. 2:
  135. RET_IRQ_RESTORE
  136. 3:
  137. cmpl %edx, %edi
  138. jne 1b
  139. xorl %eax, %eax
  140. jmp 2b
  141. ENDP
  142. #undef v
  143. #define v %esi
  144. BEGIN_IRQ_SAVE(inc_not_zero)
  145. movl (v), %eax
  146. movl 4(v), %edx
  147. testl %eax, %eax
  148. je 3f
  149. 1:
  150. addl $1, %eax
  151. adcl $0, %edx
  152. movl %eax, (v)
  153. movl %edx, 4(v)
  154. movl $1, %eax
  155. 2:
  156. RET_IRQ_RESTORE
  157. 3:
  158. testl %edx, %edx
  159. jne 1b
  160. jmp 2b
  161. ENDP
  162. #undef v
  163. #define v %esi
  164. BEGIN_IRQ_SAVE(dec_if_positive)
  165. movl (v), %eax
  166. movl 4(v), %edx
  167. subl $1, %eax
  168. sbbl $0, %edx
  169. js 1f
  170. movl %eax, (v)
  171. movl %edx, 4(v)
  172. 1:
  173. RET_IRQ_RESTORE
  174. ENDP
  175. #undef v