blob: 279d2a731f3fb57e9cdb061d1917df4ed7bb053e [file] [log] [blame]
H. Peter Anvin1965aae2008-10-22 22:26:29 -07001#ifndef _ASM_X86_ATOMIC_64_H
2#define _ASM_X86_ATOMIC_64_H
Linus Torvalds1da177e2005-04-16 15:20:36 -07003
Gerd Hoffmannd167a512006-06-26 13:56:16 +02004#include <asm/alternative.h>
Jeff Dikea436ed92007-05-08 00:35:02 -07005#include <asm/cmpxchg.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -07006
7/* atomic_t should be 32 bit signed type */
8
9/*
10 * Atomic operations that C can't guarantee us. Useful for
11 * resource counting etc..
12 */
13
Linus Torvalds1da177e2005-04-16 15:20:36 -070014/*
15 * Make sure gcc doesn't try to be clever and move things around
16 * on us. We need to use _exactly_ the address the user gave us,
17 * not some alias that contains the same information.
18 */
Joe Perches7edb3cd2008-03-23 01:01:42 -070019typedef struct {
20 int counter;
21} atomic_t;
Linus Torvalds1da177e2005-04-16 15:20:36 -070022
23#define ATOMIC_INIT(i) { (i) }
24
25/**
26 * atomic_read - read atomic variable
27 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -070028 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070029 * Atomically reads the value of @v.
Joe Perches7edb3cd2008-03-23 01:01:42 -070030 */
Linus Torvalds1da177e2005-04-16 15:20:36 -070031#define atomic_read(v) ((v)->counter)
32
33/**
34 * atomic_set - set atomic variable
35 * @v: pointer of type atomic_t
36 * @i: required value
Joe Perches7edb3cd2008-03-23 01:01:42 -070037 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070038 * Atomically sets the value of @v to @i.
Joe Perches7edb3cd2008-03-23 01:01:42 -070039 */
40#define atomic_set(v, i) (((v)->counter) = (i))
Linus Torvalds1da177e2005-04-16 15:20:36 -070041
42/**
43 * atomic_add - add integer to atomic variable
44 * @i: integer value to add
45 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -070046 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070047 * Atomically adds @i to @v.
48 */
Joe Perches7edb3cd2008-03-23 01:01:42 -070049static inline void atomic_add(int i, atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -070050{
Joe Perches7edb3cd2008-03-23 01:01:42 -070051 asm volatile(LOCK_PREFIX "addl %1,%0"
52 : "=m" (v->counter)
53 : "ir" (i), "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -070054}
55
56/**
57 * atomic_sub - subtract the atomic variable
58 * @i: integer value to subtract
59 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -070060 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070061 * Atomically subtracts @i from @v.
62 */
Joe Perches7edb3cd2008-03-23 01:01:42 -070063static inline void atomic_sub(int i, atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -070064{
Joe Perches7edb3cd2008-03-23 01:01:42 -070065 asm volatile(LOCK_PREFIX "subl %1,%0"
66 : "=m" (v->counter)
67 : "ir" (i), "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -070068}
69
70/**
71 * atomic_sub_and_test - subtract value from variable and test result
72 * @i: integer value to subtract
73 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -070074 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070075 * Atomically subtracts @i from @v and returns
76 * true if the result is zero, or false for all
77 * other cases.
78 */
Joe Perches7edb3cd2008-03-23 01:01:42 -070079static inline int atomic_sub_and_test(int i, atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -070080{
81 unsigned char c;
82
Joe Perches7edb3cd2008-03-23 01:01:42 -070083 asm volatile(LOCK_PREFIX "subl %2,%0; sete %1"
84 : "=m" (v->counter), "=qm" (c)
85 : "ir" (i), "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -070086 return c;
87}
88
89/**
90 * atomic_inc - increment atomic variable
91 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -070092 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070093 * Atomically increments @v by 1.
Joe Perches7edb3cd2008-03-23 01:01:42 -070094 */
95static inline void atomic_inc(atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -070096{
Joe Perches7edb3cd2008-03-23 01:01:42 -070097 asm volatile(LOCK_PREFIX "incl %0"
98 : "=m" (v->counter)
99 : "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700100}
101
102/**
103 * atomic_dec - decrement atomic variable
104 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -0700105 *
Linus Torvalds1da177e2005-04-16 15:20:36 -0700106 * Atomically decrements @v by 1.
Joe Perches7edb3cd2008-03-23 01:01:42 -0700107 */
108static inline void atomic_dec(atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700109{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700110 asm volatile(LOCK_PREFIX "decl %0"
111 : "=m" (v->counter)
112 : "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700113}
114
115/**
116 * atomic_dec_and_test - decrement and test
117 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -0700118 *
Linus Torvalds1da177e2005-04-16 15:20:36 -0700119 * Atomically decrements @v by 1 and
120 * returns true if the result is 0, or false for all other
121 * cases.
Joe Perches7edb3cd2008-03-23 01:01:42 -0700122 */
123static inline int atomic_dec_and_test(atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700124{
125 unsigned char c;
126
Joe Perches7edb3cd2008-03-23 01:01:42 -0700127 asm volatile(LOCK_PREFIX "decl %0; sete %1"
128 : "=m" (v->counter), "=qm" (c)
129 : "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700130 return c != 0;
131}
132
133/**
Joe Perches7edb3cd2008-03-23 01:01:42 -0700134 * atomic_inc_and_test - increment and test
Linus Torvalds1da177e2005-04-16 15:20:36 -0700135 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -0700136 *
Linus Torvalds1da177e2005-04-16 15:20:36 -0700137 * Atomically increments @v by 1
138 * and returns true if the result is zero, or false for all
139 * other cases.
Joe Perches7edb3cd2008-03-23 01:01:42 -0700140 */
141static inline int atomic_inc_and_test(atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700142{
143 unsigned char c;
144
Joe Perches7edb3cd2008-03-23 01:01:42 -0700145 asm volatile(LOCK_PREFIX "incl %0; sete %1"
146 : "=m" (v->counter), "=qm" (c)
147 : "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700148 return c != 0;
149}
150
151/**
152 * atomic_add_negative - add and test if negative
Linus Torvalds1da177e2005-04-16 15:20:36 -0700153 * @i: integer value to add
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800154 * @v: pointer of type atomic_t
Joe Perches7edb3cd2008-03-23 01:01:42 -0700155 *
Linus Torvalds1da177e2005-04-16 15:20:36 -0700156 * Atomically adds @i to @v and returns true
157 * if the result is negative, or false when
158 * result is greater than or equal to zero.
Joe Perches7edb3cd2008-03-23 01:01:42 -0700159 */
160static inline int atomic_add_negative(int i, atomic_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700161{
162 unsigned char c;
163
Joe Perches7edb3cd2008-03-23 01:01:42 -0700164 asm volatile(LOCK_PREFIX "addl %2,%0; sets %1"
165 : "=m" (v->counter), "=qm" (c)
166 : "ir" (i), "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700167 return c;
168}
169
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800170/**
171 * atomic_add_return - add and return
172 * @i: integer value to add
173 * @v: pointer of type atomic_t
174 *
175 * Atomically adds @i to @v and returns @i + @v
176 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700177static inline int atomic_add_return(int i, atomic_t *v)
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800178{
179 int __i = i;
Joe Perches7edb3cd2008-03-23 01:01:42 -0700180 asm volatile(LOCK_PREFIX "xaddl %0, %1"
181 : "+r" (i), "+m" (v->counter)
182 : : "memory");
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800183 return i + __i;
184}
185
Joe Perches7edb3cd2008-03-23 01:01:42 -0700186static inline int atomic_sub_return(int i, atomic_t *v)
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800187{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700188 return atomic_add_return(-i, v);
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800189}
190
Joe Perches7edb3cd2008-03-23 01:01:42 -0700191#define atomic_inc_return(v) (atomic_add_return(1, v))
192#define atomic_dec_return(v) (atomic_sub_return(1, v))
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800193
Linus Torvalds1da177e2005-04-16 15:20:36 -0700194/* An 64bit atomic type */
195
Joe Perches7edb3cd2008-03-23 01:01:42 -0700196typedef struct {
197 long counter;
198} atomic64_t;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700199
200#define ATOMIC64_INIT(i) { (i) }
201
202/**
203 * atomic64_read - read atomic64 variable
204 * @v: pointer of type atomic64_t
205 *
206 * Atomically reads the value of @v.
207 * Doesn't imply a read memory barrier.
208 */
209#define atomic64_read(v) ((v)->counter)
210
211/**
212 * atomic64_set - set atomic64 variable
213 * @v: pointer to type atomic64_t
214 * @i: required value
215 *
216 * Atomically sets the value of @v to @i.
217 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700218#define atomic64_set(v, i) (((v)->counter) = (i))
Linus Torvalds1da177e2005-04-16 15:20:36 -0700219
220/**
221 * atomic64_add - add integer to atomic64 variable
222 * @i: integer value to add
223 * @v: pointer to type atomic64_t
224 *
225 * Atomically adds @i to @v.
226 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700227static inline void atomic64_add(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700228{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700229 asm volatile(LOCK_PREFIX "addq %1,%0"
230 : "=m" (v->counter)
Mathieu Desnoyers3c3b5c32008-08-16 03:39:26 -0400231 : "er" (i), "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700232}
233
234/**
235 * atomic64_sub - subtract the atomic64 variable
236 * @i: integer value to subtract
237 * @v: pointer to type atomic64_t
238 *
239 * Atomically subtracts @i from @v.
240 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700241static inline void atomic64_sub(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700242{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700243 asm volatile(LOCK_PREFIX "subq %1,%0"
244 : "=m" (v->counter)
Mathieu Desnoyers3c3b5c32008-08-16 03:39:26 -0400245 : "er" (i), "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700246}
247
248/**
249 * atomic64_sub_and_test - subtract value from variable and test result
250 * @i: integer value to subtract
251 * @v: pointer to type atomic64_t
252 *
253 * Atomically subtracts @i from @v and returns
254 * true if the result is zero, or false for all
255 * other cases.
256 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700257static inline int atomic64_sub_and_test(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700258{
259 unsigned char c;
260
Joe Perches7edb3cd2008-03-23 01:01:42 -0700261 asm volatile(LOCK_PREFIX "subq %2,%0; sete %1"
262 : "=m" (v->counter), "=qm" (c)
Mathieu Desnoyers3c3b5c32008-08-16 03:39:26 -0400263 : "er" (i), "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700264 return c;
265}
266
267/**
268 * atomic64_inc - increment atomic64 variable
269 * @v: pointer to type atomic64_t
270 *
271 * Atomically increments @v by 1.
272 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700273static inline void atomic64_inc(atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700274{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700275 asm volatile(LOCK_PREFIX "incq %0"
276 : "=m" (v->counter)
277 : "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700278}
279
280/**
281 * atomic64_dec - decrement atomic64 variable
282 * @v: pointer to type atomic64_t
283 *
284 * Atomically decrements @v by 1.
285 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700286static inline void atomic64_dec(atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700287{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700288 asm volatile(LOCK_PREFIX "decq %0"
289 : "=m" (v->counter)
290 : "m" (v->counter));
Linus Torvalds1da177e2005-04-16 15:20:36 -0700291}
292
293/**
294 * atomic64_dec_and_test - decrement and test
295 * @v: pointer to type atomic64_t
296 *
297 * Atomically decrements @v by 1 and
298 * returns true if the result is 0, or false for all other
299 * cases.
300 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700301static inline int atomic64_dec_and_test(atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700302{
303 unsigned char c;
304
Joe Perches7edb3cd2008-03-23 01:01:42 -0700305 asm volatile(LOCK_PREFIX "decq %0; sete %1"
306 : "=m" (v->counter), "=qm" (c)
307 : "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700308 return c != 0;
309}
310
311/**
312 * atomic64_inc_and_test - increment and test
313 * @v: pointer to type atomic64_t
314 *
315 * Atomically increments @v by 1
316 * and returns true if the result is zero, or false for all
317 * other cases.
318 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700319static inline int atomic64_inc_and_test(atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700320{
321 unsigned char c;
322
Joe Perches7edb3cd2008-03-23 01:01:42 -0700323 asm volatile(LOCK_PREFIX "incq %0; sete %1"
324 : "=m" (v->counter), "=qm" (c)
325 : "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700326 return c != 0;
327}
328
329/**
330 * atomic64_add_negative - add and test if negative
Linus Torvalds1da177e2005-04-16 15:20:36 -0700331 * @i: integer value to add
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800332 * @v: pointer to type atomic64_t
Linus Torvalds1da177e2005-04-16 15:20:36 -0700333 *
334 * Atomically adds @i to @v and returns true
335 * if the result is negative, or false when
336 * result is greater than or equal to zero.
337 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700338static inline int atomic64_add_negative(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700339{
340 unsigned char c;
341
Joe Perches7edb3cd2008-03-23 01:01:42 -0700342 asm volatile(LOCK_PREFIX "addq %2,%0; sets %1"
343 : "=m" (v->counter), "=qm" (c)
Mathieu Desnoyers3c3b5c32008-08-16 03:39:26 -0400344 : "er" (i), "m" (v->counter) : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700345 return c;
346}
347
348/**
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800349 * atomic64_add_return - add and return
Linus Torvalds1da177e2005-04-16 15:20:36 -0700350 * @i: integer value to add
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800351 * @v: pointer to type atomic64_t
Linus Torvalds1da177e2005-04-16 15:20:36 -0700352 *
353 * Atomically adds @i to @v and returns @i + @v
354 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700355static inline long atomic64_add_return(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700356{
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800357 long __i = i;
Joe Perches7edb3cd2008-03-23 01:01:42 -0700358 asm volatile(LOCK_PREFIX "xaddq %0, %1;"
359 : "+r" (i), "+m" (v->counter)
360 : : "memory");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700361 return i + __i;
362}
363
Joe Perches7edb3cd2008-03-23 01:01:42 -0700364static inline long atomic64_sub_return(long i, atomic64_t *v)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700365{
Joe Perches7edb3cd2008-03-23 01:01:42 -0700366 return atomic64_add_return(-i, v);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700367}
368
Joe Perches7edb3cd2008-03-23 01:01:42 -0700369#define atomic64_inc_return(v) (atomic64_add_return(1, (v)))
370#define atomic64_dec_return(v) (atomic64_sub_return(1, (v)))
Hugh Dickins7c72aaf2005-11-23 13:37:40 -0800371
Joe Perches7edb3cd2008-03-23 01:01:42 -0700372#define atomic64_cmpxchg(v, old, new) (cmpxchg(&((v)->counter), (old), (new)))
Mathieu Desnoyers79d365a2007-05-08 00:34:36 -0700373#define atomic64_xchg(v, new) (xchg(&((v)->counter), new))
374
Joe Perches7edb3cd2008-03-23 01:01:42 -0700375#define atomic_cmpxchg(v, old, new) (cmpxchg(&((v)->counter), (old), (new)))
376#define atomic_xchg(v, new) (xchg(&((v)->counter), (new)))
Nick Piggin4a6dae62005-11-13 16:07:24 -0800377
Nick Piggin8426e1f2005-11-13 16:07:25 -0800378/**
379 * atomic_add_unless - add unless the number is a given value
380 * @v: pointer of type atomic_t
381 * @a: the amount to add to v...
382 * @u: ...unless v is equal to u.
383 *
384 * Atomically adds @a to @v, so long as it was not @u.
385 * Returns non-zero if @v was not @u, and zero otherwise.
386 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700387static inline int atomic_add_unless(atomic_t *v, int a, int u)
Mathieu Desnoyers2856f5e2007-05-08 00:34:38 -0700388{
389 int c, old;
390 c = atomic_read(v);
391 for (;;) {
392 if (unlikely(c == (u)))
393 break;
394 old = atomic_cmpxchg((v), c, c + (a));
395 if (likely(old == c))
396 break;
397 c = old;
398 }
399 return c != (u);
400}
401
Nick Piggin8426e1f2005-11-13 16:07:25 -0800402#define atomic_inc_not_zero(v) atomic_add_unless((v), 1, 0)
403
Mathieu Desnoyers79d365a2007-05-08 00:34:36 -0700404/**
405 * atomic64_add_unless - add unless the number is a given value
406 * @v: pointer of type atomic64_t
407 * @a: the amount to add to v...
408 * @u: ...unless v is equal to u.
409 *
410 * Atomically adds @a to @v, so long as it was not @u.
411 * Returns non-zero if @v was not @u, and zero otherwise.
412 */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700413static inline int atomic64_add_unless(atomic64_t *v, long a, long u)
Mathieu Desnoyers2856f5e2007-05-08 00:34:38 -0700414{
415 long c, old;
416 c = atomic64_read(v);
417 for (;;) {
418 if (unlikely(c == (u)))
419 break;
420 old = atomic64_cmpxchg((v), c, c + (a));
421 if (likely(old == c))
422 break;
423 c = old;
424 }
425 return c != (u);
426}
427
Cliff Wickman73e991f2008-06-04 15:33:17 -0500428/**
429 * atomic_inc_short - increment of a short integer
430 * @v: pointer to type int
431 *
432 * Atomically adds 1 to @v
433 * Returns the new value of @u
434 */
435static inline short int atomic_inc_short(short int *v)
436{
437 asm(LOCK_PREFIX "addw $1, %0" : "+m" (*v));
438 return *v;
439}
440
441/**
442 * atomic_or_long - OR of two long integers
443 * @v1: pointer to type unsigned long
444 * @v2: pointer to type unsigned long
445 *
446 * Atomically ORs @v1 and @v2
447 * Returns the result of the OR
448 */
449static inline void atomic_or_long(unsigned long *v1, unsigned long v2)
450{
451 asm(LOCK_PREFIX "orq %1, %0" : "+m" (*v1) : "r" (v2));
452}
453
Mathieu Desnoyers79d365a2007-05-08 00:34:36 -0700454#define atomic64_inc_not_zero(v) atomic64_add_unless((v), 1, 0)
455
Linus Torvalds1da177e2005-04-16 15:20:36 -0700456/* These are x86-specific, used by some header files */
Joe Perches7edb3cd2008-03-23 01:01:42 -0700457#define atomic_clear_mask(mask, addr) \
458 asm volatile(LOCK_PREFIX "andl %0,%1" \
459 : : "r" (~(mask)), "m" (*(addr)) : "memory")
Linus Torvalds1da177e2005-04-16 15:20:36 -0700460
Joe Perches7edb3cd2008-03-23 01:01:42 -0700461#define atomic_set_mask(mask, addr) \
462 asm volatile(LOCK_PREFIX "orl %0,%1" \
463 : : "r" ((unsigned)(mask)), "m" (*(addr)) \
464 : "memory")
Linus Torvalds1da177e2005-04-16 15:20:36 -0700465
466/* Atomic operations are already serializing on x86 */
467#define smp_mb__before_atomic_dec() barrier()
468#define smp_mb__after_atomic_dec() barrier()
469#define smp_mb__before_atomic_inc() barrier()
470#define smp_mb__after_atomic_inc() barrier()
471
Christoph Lameterd3cb4872006-01-06 00:11:20 -0800472#include <asm-generic/atomic.h>
H. Peter Anvin1965aae2008-10-22 22:26:29 -0700473#endif /* _ASM_X86_ATOMIC_64_H */