1 /* atomic operations */
2 
3 /*
4  * Copyright (c) 1997-2015, Wind River Systems, Inc.
5  * Copyright (c) 2023 Nordic Semiconductor ASA
6  *
7  * SPDX-License-Identifier: Apache-2.0
8  */
9 
10 #ifndef ZEPHYR_INCLUDE_SYS_ATOMIC_BUILTIN_H_
11 #define ZEPHYR_INCLUDE_SYS_ATOMIC_BUILTIN_H_
12 
13 #include <stdbool.h>
14 #include <stddef.h>
15 #include <zephyr/sys/atomic_types.h>
16 
17 #ifdef __cplusplus
18 extern "C" {
19 #endif
20 
21 /* Included from <atomic.h> */
22 
atomic_cas(atomic_t * target,atomic_val_t old_value,atomic_val_t new_value)23 static inline bool atomic_cas(atomic_t *target, atomic_val_t old_value,
24 			  atomic_val_t new_value)
25 {
26 	return __atomic_compare_exchange_n(target, &old_value, new_value,
27 					   0, __ATOMIC_SEQ_CST,
28 					   __ATOMIC_SEQ_CST);
29 }
30 
atomic_ptr_cas(atomic_ptr_t * target,atomic_ptr_val_t old_value,atomic_ptr_val_t new_value)31 static inline bool atomic_ptr_cas(atomic_ptr_t *target, atomic_ptr_val_t old_value,
32 				  atomic_ptr_val_t new_value)
33 {
34 	return __atomic_compare_exchange_n(target, &old_value, new_value,
35 					   0, __ATOMIC_SEQ_CST,
36 					   __ATOMIC_SEQ_CST);
37 }
38 
atomic_add(atomic_t * target,atomic_val_t value)39 static inline atomic_val_t atomic_add(atomic_t *target, atomic_val_t value)
40 {
41 	return __atomic_fetch_add(target, value, __ATOMIC_SEQ_CST);
42 }
43 
atomic_sub(atomic_t * target,atomic_val_t value)44 static inline atomic_val_t atomic_sub(atomic_t *target, atomic_val_t value)
45 {
46 	return __atomic_fetch_sub(target, value, __ATOMIC_SEQ_CST);
47 }
48 
atomic_inc(atomic_t * target)49 static inline atomic_val_t atomic_inc(atomic_t *target)
50 {
51 	return atomic_add(target, 1);
52 }
53 
atomic_dec(atomic_t * target)54 static inline atomic_val_t atomic_dec(atomic_t *target)
55 {
56 	return atomic_sub(target, 1);
57 }
58 
atomic_get(const atomic_t * target)59 static inline atomic_val_t atomic_get(const atomic_t *target)
60 {
61 	return __atomic_load_n(target, __ATOMIC_SEQ_CST);
62 }
63 
atomic_ptr_get(const atomic_ptr_t * target)64 static inline atomic_ptr_val_t atomic_ptr_get(const atomic_ptr_t *target)
65 {
66 	return __atomic_load_n(target, __ATOMIC_SEQ_CST);
67 }
68 
atomic_set(atomic_t * target,atomic_val_t value)69 static inline atomic_val_t atomic_set(atomic_t *target, atomic_val_t value)
70 {
71 	/* This builtin, as described by Intel, is not a traditional
72 	 * test-and-set operation, but rather an atomic exchange operation. It
73 	 * writes value into *ptr, and returns the previous contents of *ptr.
74 	 */
75 	return __atomic_exchange_n(target, value, __ATOMIC_SEQ_CST);
76 }
77 
atomic_ptr_set(atomic_ptr_t * target,atomic_ptr_val_t value)78 static inline atomic_ptr_val_t atomic_ptr_set(atomic_ptr_t *target, atomic_ptr_val_t value)
79 {
80 	return __atomic_exchange_n(target, value, __ATOMIC_SEQ_CST);
81 }
82 
atomic_clear(atomic_t * target)83 static inline atomic_val_t atomic_clear(atomic_t *target)
84 {
85 	return atomic_set(target, 0);
86 }
87 
atomic_ptr_clear(atomic_ptr_t * target)88 static inline atomic_ptr_val_t atomic_ptr_clear(atomic_ptr_t *target)
89 {
90 	return atomic_ptr_set(target, NULL);
91 }
92 
atomic_or(atomic_t * target,atomic_val_t value)93 static inline atomic_val_t atomic_or(atomic_t *target, atomic_val_t value)
94 {
95 	return __atomic_fetch_or(target, value, __ATOMIC_SEQ_CST);
96 }
97 
atomic_xor(atomic_t * target,atomic_val_t value)98 static inline atomic_val_t atomic_xor(atomic_t *target, atomic_val_t value)
99 {
100 	return __atomic_fetch_xor(target, value, __ATOMIC_SEQ_CST);
101 }
102 
atomic_and(atomic_t * target,atomic_val_t value)103 static inline atomic_val_t atomic_and(atomic_t *target, atomic_val_t value)
104 {
105 	return __atomic_fetch_and(target, value, __ATOMIC_SEQ_CST);
106 }
107 
atomic_nand(atomic_t * target,atomic_val_t value)108 static inline atomic_val_t atomic_nand(atomic_t *target, atomic_val_t value)
109 {
110 	return __atomic_fetch_nand(target, value, __ATOMIC_SEQ_CST);
111 }
112 
113 #ifdef __cplusplus
114 }
115 #endif
116 
117 #endif /* ZEPHYR_INCLUDE_SYS_ATOMIC_BUILTIN_H_ */
118