xref: /openbmc/linux/tools/arch/x86/include/asm/atomic.h (revision a36954f5)
1 #ifndef _TOOLS_LINUX_ASM_X86_ATOMIC_H
2 #define _TOOLS_LINUX_ASM_X86_ATOMIC_H
3 
4 #include <linux/compiler.h>
5 #include <linux/types.h>
6 #include "rmwcc.h"
7 
8 #define LOCK_PREFIX "\n\tlock; "
9 
10 #include <asm/cmpxchg.h>
11 
12 /*
13  * Atomic operations that C can't guarantee us.  Useful for
14  * resource counting etc..
15  */
16 
17 #define ATOMIC_INIT(i)	{ (i) }
18 
19 /**
20  * atomic_read - read atomic variable
21  * @v: pointer of type atomic_t
22  *
23  * Atomically reads the value of @v.
24  */
25 static inline int atomic_read(const atomic_t *v)
26 {
27 	return ACCESS_ONCE((v)->counter);
28 }
29 
30 /**
31  * atomic_set - set atomic variable
32  * @v: pointer of type atomic_t
33  * @i: required value
34  *
35  * Atomically sets the value of @v to @i.
36  */
37 static inline void atomic_set(atomic_t *v, int i)
38 {
39 	v->counter = i;
40 }
41 
42 /**
43  * atomic_inc - increment atomic variable
44  * @v: pointer of type atomic_t
45  *
46  * Atomically increments @v by 1.
47  */
48 static inline void atomic_inc(atomic_t *v)
49 {
50 	asm volatile(LOCK_PREFIX "incl %0"
51 		     : "+m" (v->counter));
52 }
53 
54 /**
55  * atomic_dec_and_test - decrement and test
56  * @v: pointer of type atomic_t
57  *
58  * Atomically decrements @v by 1 and
59  * returns true if the result is 0, or false for all other
60  * cases.
61  */
62 static inline int atomic_dec_and_test(atomic_t *v)
63 {
64 	GEN_UNARY_RMWcc(LOCK_PREFIX "decl", v->counter, "%0", "e");
65 }
66 
67 static __always_inline int atomic_cmpxchg(atomic_t *v, int old, int new)
68 {
69 	return cmpxchg(&v->counter, old, new);
70 }
71 
72 #endif /* _TOOLS_LINUX_ASM_X86_ATOMIC_H */
73