atomic.h
上传用户:lgb322
上传日期:2013-02-24
资源大小:30529k
文件大小:3k
源码类别:

嵌入式Linux

开发平台:

Unix_Linux

  1. /* $Id: atomic.h,v 1.3 2001/07/25 16:15:19 bjornw Exp $ */
  2. #ifndef __ASM_CRIS_ATOMIC__
  3. #define __ASM_CRIS_ATOMIC__
  4. #include <asm/system.h>
  5. /*
  6.  * Atomic operations that C can't guarantee us.  Useful for
  7.  * resource counting etc..
  8.  */
  9. /*
  10.  * Make sure gcc doesn't try to be clever and move things around
  11.  * on us. We need to use _exactly_ the address the user gave us,
  12.  * not some alias that contains the same information.
  13.  */
  14. #define __atomic_fool_gcc(x) (*(struct { int a[100]; } *)x)
  15. typedef struct { int counter; } atomic_t;
  16. #define ATOMIC_INIT(i)  { (i) }
  17. #define atomic_read(v) ((v)->counter)
  18. #define atomic_set(v,i) (((v)->counter) = (i))
  19. /* These should be written in asm but we do it in C for now. */
  20. static __inline__ void atomic_add(int i, volatile atomic_t *v)
  21. {
  22. unsigned long flags;
  23. save_flags(flags);
  24. cli();
  25. v->counter += i;
  26. restore_flags(flags);
  27. }
  28. static __inline__ void atomic_sub(int i, volatile atomic_t *v)
  29. {
  30. unsigned long flags;
  31. save_flags(flags);
  32. cli();
  33. v->counter -= i;
  34. restore_flags(flags);
  35. }
  36. static __inline__ int atomic_add_return(int i, volatile atomic_t *v)
  37. {
  38. unsigned long flags;
  39. int retval;
  40. save_flags(flags);
  41. cli();
  42. retval = (v->counter += i);
  43. restore_flags(flags);
  44. return retval;
  45. }
  46. static __inline__ int atomic_sub_return(int i, volatile atomic_t *v)
  47. {
  48. unsigned long flags;
  49. int retval;
  50. save_flags(flags);
  51. cli();
  52. retval = (v->counter -= i);
  53. restore_flags(flags);
  54. return retval;
  55. }
  56. static __inline__ int atomic_sub_and_test(int i, volatile atomic_t *v)
  57. {
  58. int retval;
  59. unsigned long flags;
  60. save_flags(flags);
  61. cli();
  62. retval = (v->counter -= i) == 0;
  63. restore_flags(flags);
  64. return retval;
  65. }
  66. static __inline__ void atomic_inc(volatile atomic_t *v)
  67. {
  68. unsigned long flags;
  69. save_flags(flags);
  70. cli();
  71. (v->counter)++;
  72. restore_flags(flags);
  73. }
  74. static __inline__ void atomic_dec(volatile atomic_t *v)
  75. {
  76. unsigned long flags;
  77. save_flags(flags);
  78. cli();
  79. (v->counter)--;
  80. restore_flags(flags);
  81. }
  82. static __inline__ int atomic_inc_return(volatile atomic_t *v)
  83. {
  84. unsigned long flags;
  85. int retval;
  86. save_flags(flags);
  87. cli();
  88. retval = (v->counter)++;
  89. restore_flags(flags);
  90. return retval;
  91. }
  92. static __inline__ int atomic_dec_return(volatile atomic_t *v)
  93. {
  94. unsigned long flags;
  95. int retval;
  96. save_flags(flags);
  97. cli();
  98. retval = (v->counter)--;
  99. restore_flags(flags);
  100. return retval;
  101. }
  102. static __inline__ int atomic_dec_and_test(volatile atomic_t *v)
  103. {
  104. int retval;
  105. unsigned long flags;
  106. save_flags(flags);
  107. cli();
  108. retval = --(v->counter) == 0;
  109. restore_flags(flags);
  110. return retval;
  111. }
  112. static __inline__ int atomic_inc_and_test(volatile atomic_t *v)
  113. {
  114. int retval;
  115. unsigned long flags;
  116. save_flags(flags);
  117. cli();
  118. retval = ++(v->counter) == 0;
  119. restore_flags(flags);
  120. return retval;
  121. }
  122. /* Atomic operations are already serializing */
  123. #define smp_mb__before_atomic_dec()    barrier()
  124. #define smp_mb__after_atomic_dec()     barrier()
  125. #define smp_mb__before_atomic_inc()    barrier()
  126. #define smp_mb__after_atomic_inc()     barrier()
  127. #endif