xref: /dflybsd-src/share/man/man9/atomic.9 (revision 2f45ab904bbc7cbcc4f624cb5512f60814fb7977)
1cb0ac91aSSascha Wildner.\" Copyright (c) 2000-2001 John H. Baldwin <jhb@FreeBSD.org>
2cb0ac91aSSascha Wildner.\" All rights reserved.
3cb0ac91aSSascha Wildner.\"
4cb0ac91aSSascha Wildner.\" Redistribution and use in source and binary forms, with or without
5cb0ac91aSSascha Wildner.\" modification, are permitted provided that the following conditions
6cb0ac91aSSascha Wildner.\" are met:
7cb0ac91aSSascha Wildner.\" 1. Redistributions of source code must retain the above copyright
8cb0ac91aSSascha Wildner.\"    notice, this list of conditions and the following disclaimer.
9cb0ac91aSSascha Wildner.\" 2. Redistributions in binary form must reproduce the above copyright
10cb0ac91aSSascha Wildner.\"    notice, this list of conditions and the following disclaimer in the
11cb0ac91aSSascha Wildner.\"    documentation and/or other materials provided with the distribution.
12cb0ac91aSSascha Wildner.\"
13cb0ac91aSSascha Wildner.\" THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY EXPRESS OR
14cb0ac91aSSascha Wildner.\" IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
15cb0ac91aSSascha Wildner.\" OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
16cb0ac91aSSascha Wildner.\" IN NO EVENT SHALL THE DEVELOPERS BE LIABLE FOR ANY DIRECT, INDIRECT,
17cb0ac91aSSascha Wildner.\" INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
18cb0ac91aSSascha Wildner.\" NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
19cb0ac91aSSascha Wildner.\" DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
20cb0ac91aSSascha Wildner.\" THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21cb0ac91aSSascha Wildner.\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
22cb0ac91aSSascha Wildner.\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23cb0ac91aSSascha Wildner.\"
24cb0ac91aSSascha Wildner.\" $FreeBSD: src/share/man/man9/atomic.9,v 1.17 2010/05/27 13:56:27 uqs Exp $
25cb0ac91aSSascha Wildner.\"
26d42a763bSAaron LI.Dd January 14, 2024
27cb0ac91aSSascha Wildner.Dt ATOMIC 9
28cb0ac91aSSascha Wildner.Os
29cb0ac91aSSascha Wildner.Sh NAME
30cb0ac91aSSascha Wildner.Nm atomic_add ,
31cb0ac91aSSascha Wildner.Nm atomic_clear ,
32cb0ac91aSSascha Wildner.Nm atomic_cmpset ,
33cb0ac91aSSascha Wildner.Nm atomic_fetchadd ,
34cb0ac91aSSascha Wildner.Nm atomic_load ,
35cb0ac91aSSascha Wildner.Nm atomic_readandclear ,
36cb0ac91aSSascha Wildner.Nm atomic_set ,
37cb0ac91aSSascha Wildner.Nm atomic_subtract ,
38cb0ac91aSSascha Wildner.Nm atomic_store
39cb0ac91aSSascha Wildner.Nd atomic operations
40cb0ac91aSSascha Wildner.Sh SYNOPSIS
41cb0ac91aSSascha Wildner.In sys/types.h
42cb0ac91aSSascha Wildner.In machine/atomic.h
43cb0ac91aSSascha Wildner.Ft void
44cb0ac91aSSascha Wildner.Fn atomic_add_[acq_|rel_]<type> "volatile <type> *p" "<type> v"
45cb0ac91aSSascha Wildner.Ft void
46cb0ac91aSSascha Wildner.Fn atomic_clear_[acq_|rel_]<type> "volatile <type> *p" "<type> v"
47cb0ac91aSSascha Wildner.Ft int
48cb0ac91aSSascha Wildner.Fo atomic_cmpset_[acq_|rel_]<type>
49cb0ac91aSSascha Wildner.Fa "volatile <type> *dst"
50cb0ac91aSSascha Wildner.Fa "<type> old"
51cb0ac91aSSascha Wildner.Fa "<type> new"
52cb0ac91aSSascha Wildner.Fc
53cb0ac91aSSascha Wildner.Ft <type>
54cb0ac91aSSascha Wildner.Fn atomic_fetchadd_<type> "volatile <type> *p" "<type> v"
55cb0ac91aSSascha Wildner.Ft <type>
56d42a763bSAaron LI.Fn atomic_load_[acq_]<type> "volatile <type> *p"
57cb0ac91aSSascha Wildner.Ft <type>
58cb0ac91aSSascha Wildner.Fn atomic_readandclear_<type> "volatile <type> *p"
59cb0ac91aSSascha Wildner.Ft void
60cb0ac91aSSascha Wildner.Fn atomic_set_[acq_|rel_]<type> "volatile <type> *p" "<type> v"
61cb0ac91aSSascha Wildner.Ft void
62cb0ac91aSSascha Wildner.Fn atomic_subtract_[acq_|rel_]<type> "volatile <type> *p" "<type> v"
63cb0ac91aSSascha Wildner.Ft void
64d42a763bSAaron LI.Fn atomic_store_[rel_]<type> "volatile <type> *p" "<type> v"
65cb0ac91aSSascha Wildner.Sh DESCRIPTION
66cb0ac91aSSascha WildnerEach of the atomic operations is guaranteed to be atomic in the presence of
67cb0ac91aSSascha Wildnerinterrupts.
68cb0ac91aSSascha WildnerThey can be used to implement reference counts or as building blocks for more
69*2f45ab90SAaron LIadvanced synchronization primitives, such as mutexes.
70*2f45ab90SAaron LI.Pp
71*2f45ab90SAaron LIOn all architectures supported by
72*2f45ab90SAaron LI. Dx ,
73*2f45ab90SAaron LIordinary loads and stores of integers in cache-coherent memory are
74*2f45ab90SAaron LIinherently atomic if the integer is naturally aligned and its size does
75*2f45ab90SAaron LInot exceed the processor's word size.
76*2f45ab90SAaron LIHowever, such loads and stores may be elided from the program by the
77*2f45ab90SAaron LIcompiler, whereas atomic operations are always performed.
78*2f45ab90SAaron LI.Pp
79*2f45ab90SAaron LIExcept as noted below, the semantics of these operations are almost
80*2f45ab90SAaron LIidentical to the semantics of similarly named C11 atomic operations.
81cb0ac91aSSascha Wildner.Ss Types
82cb0ac91aSSascha WildnerEach atomic operation operates on a specific
83cb0ac91aSSascha Wildner.Fa type .
84cb0ac91aSSascha WildnerThe type to use is indicated in the function name.
85*2f45ab90SAaron LIIn contrast to C11 atomic operations,
86*2f45ab90SAaron LI.Dx Ns 's
87*2f45ab90SAaron LIatomic operations are performed on ordinary integer types.
88*2f45ab90SAaron LIThe available types are:
89cb0ac91aSSascha Wildner.Pp
907cecd65aSzrj.Bl -tag -offset indent -width ".Li cpumask" -compact
91619596bfSSascha Wildner.It Li cpumask
92619596bfSSascha WildnerCPU mask (cpumask_t)
93cb0ac91aSSascha Wildner.It Li int
94cb0ac91aSSascha Wildnerunsigned integer
95cb0ac91aSSascha Wildner.It Li long
96cb0ac91aSSascha Wildnerunsigned long integer
97cb0ac91aSSascha Wildner.It Li ptr
98cb0ac91aSSascha Wildnerunsigned integer the size of a pointer
99cb0ac91aSSascha Wildner.It Li 32
100cb0ac91aSSascha Wildnerunsigned 32-bit integer
101*2f45ab90SAaron LI.It Li 64
102*2f45ab90SAaron LIunsigned 64-bit integer
103cb0ac91aSSascha Wildner.El
104cb0ac91aSSascha Wildner.Pp
105cb0ac91aSSascha WildnerFor example, the function to atomically add two integers is called
106cb0ac91aSSascha Wildner.Fn atomic_add_int .
107cb0ac91aSSascha Wildner.Pp
108cb0ac91aSSascha WildnerCertain architectures also provide operations for types smaller than
109cb0ac91aSSascha Wildner.Dq Li int .
110cb0ac91aSSascha Wildner.Pp
111cb0ac91aSSascha Wildner.Bl -tag -offset indent -width short -compact
112cb0ac91aSSascha Wildner.It Li char
113cb0ac91aSSascha Wildnerunsigned character
114cb0ac91aSSascha Wildner.It Li short
115cb0ac91aSSascha Wildnerunsigned short integer
116cb0ac91aSSascha Wildner.It Li 8
117cb0ac91aSSascha Wildnerunsigned 8-bit integer
118cb0ac91aSSascha Wildner.It Li 16
119cb0ac91aSSascha Wildnerunsigned 16-bit integer
120cb0ac91aSSascha Wildner.El
121cb0ac91aSSascha Wildner.Pp
122*2f45ab90SAaron LIThese must not be used in machine-independent code, because the instructions
123*2f45ab90SAaron LIto implement them efficiently may not be available.
124cb0ac91aSSascha Wildner.Ss Memory Barriers
125cb0ac91aSSascha WildnerMemory barriers are used to guarantee the order of data accesses in
126cb0ac91aSSascha Wildnertwo ways.
127cb0ac91aSSascha WildnerFirst, they specify hints to the compiler to not re-order or optimize the
128cb0ac91aSSascha Wildneroperations.
129cb0ac91aSSascha WildnerSecond, on architectures that do not guarantee ordered data accesses,
130cb0ac91aSSascha Wildnerspecial instructions or special variants of instructions are used to indicate
131cb0ac91aSSascha Wildnerto the processor that data accesses need to occur in a certain order.
132cb0ac91aSSascha WildnerAs a result, most of the atomic operations have three variants in order to
133cb0ac91aSSascha Wildnerinclude optional memory barriers.
134cb0ac91aSSascha WildnerThe first form just performs the operation without any explicit barriers.
135cb0ac91aSSascha WildnerThe second form uses a read memory barrier, and the third variant uses a write
136cb0ac91aSSascha Wildnermemory barrier.
137cb0ac91aSSascha Wildner.Pp
138cb0ac91aSSascha WildnerThe second variant of each operation includes a read memory barrier.
139cb0ac91aSSascha WildnerThis barrier ensures that the effects of this operation are completed before the
140cb0ac91aSSascha Wildnereffects of any later data accesses.
141cb0ac91aSSascha WildnerAs a result, the operation is said to have acquire semantics as it acquires a
142cb0ac91aSSascha Wildnerpseudo-lock requiring further operations to wait until it has completed.
143cb0ac91aSSascha WildnerTo denote this, the suffix
144cb0ac91aSSascha Wildner.Dq Li _acq
145cb0ac91aSSascha Wildneris inserted into the function name immediately prior to the
146cb0ac91aSSascha Wildner.Dq Li _ Ns Aq Fa type
147cb0ac91aSSascha Wildnersuffix.
148cb0ac91aSSascha WildnerFor example, to subtract two integers ensuring that any later writes will
149cb0ac91aSSascha Wildnerhappen after the subtraction is performed, use
150cb0ac91aSSascha Wildner.Fn atomic_subtract_acq_int .
151cb0ac91aSSascha Wildner.Pp
152cb0ac91aSSascha WildnerThe third variant of each operation includes a write memory barrier.
153cb0ac91aSSascha WildnerThis ensures that all effects of all previous data accesses are completed
154cb0ac91aSSascha Wildnerbefore this operation takes place.
155cb0ac91aSSascha WildnerAs a result, the operation is said to have release semantics as it releases
156cb0ac91aSSascha Wildnerany pending data accesses to be completed before its operation is performed.
157cb0ac91aSSascha WildnerTo denote this, the suffix
158cb0ac91aSSascha Wildner.Dq Li _rel
159cb0ac91aSSascha Wildneris inserted into the function name immediately prior to the
160cb0ac91aSSascha Wildner.Dq Li _ Ns Aq Fa type
161cb0ac91aSSascha Wildnersuffix.
162cb0ac91aSSascha WildnerFor example, to add two long integers ensuring that all previous
163cb0ac91aSSascha Wildnerwrites will happen first, use
164cb0ac91aSSascha Wildner.Fn atomic_add_rel_long .
165cb0ac91aSSascha Wildner.Pp
166cb0ac91aSSascha WildnerA practical example of using memory barriers is to ensure that data accesses
167cb0ac91aSSascha Wildnerthat are protected by a lock are all performed while the lock is held.
168cb0ac91aSSascha WildnerTo achieve this, one would use a read barrier when acquiring the lock to
169cb0ac91aSSascha Wildnerguarantee that the lock is held before any protected operations are performed.
170cb0ac91aSSascha WildnerFinally, one would use a write barrier when releasing the lock to ensure that
171cb0ac91aSSascha Wildnerall of the protected operations are completed before the lock is released.
172cb0ac91aSSascha Wildner.Ss Multiple Processors
173cb0ac91aSSascha WildnerThe current set of atomic operations do not necessarily guarantee atomicity
174cb0ac91aSSascha Wildneracross multiple processors.
175cb0ac91aSSascha WildnerTo guarantee atomicity across processors, not only does the individual
176cb0ac91aSSascha Wildneroperation need to be atomic on the processor performing the operation, but
177cb0ac91aSSascha Wildnerthe result of the operation needs to be pushed out to stable storage and the
178cb0ac91aSSascha Wildnercaches of all other processors on the system need to invalidate any cache
179cb0ac91aSSascha Wildnerlines that include the affected memory region.
180cb0ac91aSSascha Wildner.Ss Semantics
181cb0ac91aSSascha WildnerThis section describes the semantics of each operation using a C like notation.
182cb0ac91aSSascha Wildner.Bl -hang
183cb0ac91aSSascha Wildner.It Fn atomic_add p v
184cb0ac91aSSascha Wildner.Bd -literal -compact
185cb0ac91aSSascha Wildner*p += v;
186cb0ac91aSSascha Wildner.Ed
187619596bfSSascha Wildner.El
188619596bfSSascha Wildner.Pp
189619596bfSSascha WildnerThe
190619596bfSSascha Wildner.Fn atomic_add
191619596bfSSascha Wildnerfunctions are not implemented for the type
192619596bfSSascha Wildner.Dq Li cpumask .
193619596bfSSascha Wildner.Bl -hang
194cb0ac91aSSascha Wildner.It Fn atomic_clear p v
195cb0ac91aSSascha Wildner.Bd -literal -compact
196cb0ac91aSSascha Wildner*p &= ~v;
197cb0ac91aSSascha Wildner.Ed
198cb0ac91aSSascha Wildner.It Fn atomic_cmpset dst old new
199cb0ac91aSSascha Wildner.Bd -literal -compact
200cb0ac91aSSascha Wildnerif (*dst == old) {
201cb0ac91aSSascha Wildner	*dst = new;
202cb0ac91aSSascha Wildner	return 1;
2038dae8275SJoris GIOVANNANGELI} else {
204cb0ac91aSSascha Wildner	return 0;
2058dae8275SJoris GIOVANNANGELI}
206cb0ac91aSSascha Wildner.Ed
207cb0ac91aSSascha Wildner.El
208cb0ac91aSSascha Wildner.Pp
209cb0ac91aSSascha WildnerThe
210cb0ac91aSSascha Wildner.Fn atomic_cmpset
211cb0ac91aSSascha Wildnerfunctions are not implemented for the types
212cb0ac91aSSascha Wildner.Dq Li char ,
213cb0ac91aSSascha Wildner.Dq Li short ,
214cb0ac91aSSascha Wildner.Dq Li 8 ,
215cb0ac91aSSascha Wildnerand
216cb0ac91aSSascha Wildner.Dq Li 16 .
217cb0ac91aSSascha Wildner.Bl -hang
218cb0ac91aSSascha Wildner.It Fn atomic_fetchadd p v
219cb0ac91aSSascha Wildner.Bd -literal -compact
220cb0ac91aSSascha Wildnertmp = *p;
221cb0ac91aSSascha Wildner*p += v;
222cb0ac91aSSascha Wildnerreturn tmp;
223cb0ac91aSSascha Wildner.Ed
224cb0ac91aSSascha Wildner.El
225cb0ac91aSSascha Wildner.Pp
226cb0ac91aSSascha WildnerThe
227cb0ac91aSSascha Wildner.Fn atomic_fetchadd
228cb0ac91aSSascha Wildnerfunctions are only implemented for the types
229cb0ac91aSSascha Wildner.Dq Li int ,
230cb0ac91aSSascha Wildner.Dq Li long
231cb0ac91aSSascha Wildnerand
232cb0ac91aSSascha Wildner.Dq Li 32
233cb0ac91aSSascha Wildnerand do not have any variants with memory barriers at this time.
234cb0ac91aSSascha Wildner.Bl -hang
235cb0ac91aSSascha Wildner.It Fn atomic_load addr
236cb0ac91aSSascha Wildner.Bd -literal -compact
237cb0ac91aSSascha Wildnerreturn (*addr)
238cb0ac91aSSascha Wildner.Ed
239cb0ac91aSSascha Wildner.It Fn atomic_readandclear addr
240cb0ac91aSSascha Wildner.Bd -literal -compact
241cb0ac91aSSascha Wildnertemp = *addr;
242cb0ac91aSSascha Wildner*addr = 0;
243cb0ac91aSSascha Wildnerreturn (temp);
244cb0ac91aSSascha Wildner.Ed
245cb0ac91aSSascha Wildner.El
246cb0ac91aSSascha Wildner.Pp
247cb0ac91aSSascha WildnerThe
248cb0ac91aSSascha Wildner.Fn atomic_readandclear
249cb0ac91aSSascha Wildnerfunctions are not implemented for the types
250cb0ac91aSSascha Wildner.Dq Li char ,
251cb0ac91aSSascha Wildner.Dq Li short ,
252cb0ac91aSSascha Wildner.Dq Li ptr ,
253cb0ac91aSSascha Wildner.Dq Li 8 ,
254619596bfSSascha Wildner.Dq Li 16 ,
255cb0ac91aSSascha Wildnerand
256619596bfSSascha Wildner.Dq Li cpumask
257cb0ac91aSSascha Wildnerand do
258cb0ac91aSSascha Wildnernot have any variants with memory barriers at this time.
259cb0ac91aSSascha Wildner.Bl -hang
260cb0ac91aSSascha Wildner.It Fn atomic_set p v
261cb0ac91aSSascha Wildner.Bd -literal -compact
262cb0ac91aSSascha Wildner*p |= v;
263cb0ac91aSSascha Wildner.Ed
264cb0ac91aSSascha Wildner.It Fn atomic_subtract p v
265cb0ac91aSSascha Wildner.Bd -literal -compact
266cb0ac91aSSascha Wildner*p -= v;
267cb0ac91aSSascha Wildner.Ed
268619596bfSSascha Wildner.El
269619596bfSSascha Wildner.Pp
270619596bfSSascha WildnerThe
271619596bfSSascha Wildner.Fn atomic_subtract
272619596bfSSascha Wildnerfunctions are not implemented for the type
273619596bfSSascha Wildner.Dq Li cpumask .
274619596bfSSascha Wildner.Bl -hang
275cb0ac91aSSascha Wildner.It Fn atomic_store p v
276cb0ac91aSSascha Wildner.Bd -literal -compact
277cb0ac91aSSascha Wildner*p = v;
278cb0ac91aSSascha Wildner.Ed
279cb0ac91aSSascha Wildner.El
280cb0ac91aSSascha Wildner.Sh RETURN VALUES
281cb0ac91aSSascha WildnerThe
282cb0ac91aSSascha Wildner.Fn atomic_cmpset
283cb0ac91aSSascha Wildnerfunction
284cb0ac91aSSascha Wildnerreturns the result of the compare operation.
285cb0ac91aSSascha WildnerThe
286cb0ac91aSSascha Wildner.Fn atomic_fetchadd ,
287cb0ac91aSSascha Wildner.Fn atomic_load ,
288cb0ac91aSSascha Wildnerand
289cb0ac91aSSascha Wildner.Fn atomic_readandclear
290cb0ac91aSSascha Wildnerfunctions
291cb0ac91aSSascha Wildnerreturn the value at the specified address.
292cb0ac91aSSascha Wildner.\".Sh EXAMPLES
293cb0ac91aSSascha Wildner.\"This example uses the
294cb0ac91aSSascha Wildner.\".Fn atomic_cmpset_acq_ptr
295cb0ac91aSSascha Wildner.\"and
296cb0ac91aSSascha Wildner.\".Fn atomic_set_ptr
297cb0ac91aSSascha Wildner.\"functions to obtain a sleep mutex and handle recursion.
298cb0ac91aSSascha Wildner.\"Since the
299cb0ac91aSSascha Wildner.\".Va mtx_lock
300cb0ac91aSSascha Wildner.\"member of a
301cb0ac91aSSascha Wildner.\".Vt "struct mtx"
302cb0ac91aSSascha Wildner.\"is a pointer, the
303cb0ac91aSSascha Wildner.\".Dq Li ptr
304cb0ac91aSSascha Wildner.\"type is used.
305cb0ac91aSSascha Wildner.\".Bd -literal
306cb0ac91aSSascha Wildner.\"/* Try to obtain mtx_lock once. */
307cb0ac91aSSascha Wildner.\"#define _obtain_lock(mp, tid)						\\
308cb0ac91aSSascha Wildner.\"	atomic_cmpset_acq_ptr(&(mp)->mtx_lock, MTX_UNOWNED, (tid))
309cb0ac91aSSascha Wildner.\"
310cb0ac91aSSascha Wildner.\"/* Get a sleep lock, deal with recursion inline. */
311cb0ac91aSSascha Wildner.\"#define _get_sleep_lock(mp, tid, opts, file, line) do {			\\
312cb0ac91aSSascha Wildner.\"	uintptr_t _tid = (uintptr_t)(tid);				\\
313cb0ac91aSSascha Wildner.\"									\\
314cb0ac91aSSascha Wildner.\"	if (!_obtain_lock(mp, tid)) {					\\
315cb0ac91aSSascha Wildner.\"		if (((mp)->mtx_lock & MTX_FLAGMASK) != _tid)		\\
316cb0ac91aSSascha Wildner.\"			_mtx_lock_sleep((mp), _tid, (opts), (file), (line));\\
317cb0ac91aSSascha Wildner.\"		else {							\\
318cb0ac91aSSascha Wildner.\"			atomic_set_ptr(&(mp)->mtx_lock, MTX_RECURSE);	\\
319cb0ac91aSSascha Wildner.\"			(mp)->mtx_recurse++;				\\
320cb0ac91aSSascha Wildner.\"		}							\\
321cb0ac91aSSascha Wildner.\"	}								\\
322cb0ac91aSSascha Wildner.\"} while (0)
323cb0ac91aSSascha Wildner.\".Ed
324cb0ac91aSSascha Wildner.Sh HISTORY
325cb0ac91aSSascha WildnerThe
326cb0ac91aSSascha Wildner.Fn atomic_add ,
327cb0ac91aSSascha Wildner.Fn atomic_clear ,
328cb0ac91aSSascha Wildner.Fn atomic_set ,
329cb0ac91aSSascha Wildnerand
330cb0ac91aSSascha Wildner.Fn atomic_subtract
331cb0ac91aSSascha Wildneroperations were first introduced in
332cb0ac91aSSascha Wildner.Fx 3.0 .
333cb0ac91aSSascha WildnerThis first set only supported the types
334cb0ac91aSSascha Wildner.Dq Li char ,
335cb0ac91aSSascha Wildner.Dq Li short ,
336cb0ac91aSSascha Wildner.Dq Li int ,
337cb0ac91aSSascha Wildnerand
338cb0ac91aSSascha Wildner.Dq Li long .
339d42a763bSAaron LI.Pp
340cb0ac91aSSascha WildnerThe
341cb0ac91aSSascha Wildner.Fn atomic_cmpset ,
342cb0ac91aSSascha Wildner.Fn atomic_load ,
343cb0ac91aSSascha Wildner.Fn atomic_readandclear ,
344cb0ac91aSSascha Wildnerand
345cb0ac91aSSascha Wildner.Fn atomic_store
346cb0ac91aSSascha Wildneroperations were added in
347cb0ac91aSSascha Wildner.Fx 5.0 .
348cb0ac91aSSascha WildnerThe types
349cb0ac91aSSascha Wildner.Dq Li 8 ,
350cb0ac91aSSascha Wildner.Dq Li 16 ,
351cb0ac91aSSascha Wildner.Dq Li 32 ,
352*2f45ab90SAaron LI.Dq Li 64 ,
353cb0ac91aSSascha Wildnerand
354cb0ac91aSSascha Wildner.Dq Li ptr
355cb0ac91aSSascha Wildnerand all of the acquire and release variants
356cb0ac91aSSascha Wildnerwere added in
357cb0ac91aSSascha Wildner.Fx 5.0
358cb0ac91aSSascha Wildneras well.
359d42a763bSAaron LI.Pp
360cb0ac91aSSascha WildnerThe
361cb0ac91aSSascha Wildner.Fn atomic_fetchadd
362cb0ac91aSSascha Wildneroperations were added in
363cb0ac91aSSascha Wildner.Fx 6.0 .
364d42a763bSAaron LI.Pp
365d42a763bSAaron LIThe relaxed variants of
366d42a763bSAaron LI.Fn atomic_load
367d42a763bSAaron LIand
368d42a763bSAaron LI.Fn atomic_store
369d42a763bSAaron LIwere added in
370d42a763bSAaron LI.Fx 12.0
371d42a763bSAaron LIand
372d42a763bSAaron LI.Dx 6.5 .
373