@@ -23,14 +23,28 @@ for (ityp,jtyp) ∈ [("i8", UInt8), ("i16", UInt16), ("i32", UInt32), ("i64", UI
23
23
end
24
24
end
25
25
end
26
- for op ∈ [" xchg" , " add" , " sub" , " and" , " nand" , " or" , " xor" , " max" , " min" , " umax" , " umin" ] # "fadd", "fsub"
26
+
27
+ """
28
+ Operations supported by `atomicrmw`.
29
+
30
+ - Julia v1.11 use [libLLVM-16](https://releases.llvm.org/16.0.0/docs/LangRef.html#atomicrmw-instruction)
31
+ """
32
+ const atomicrmw_ops = [
33
+ " xchg" , " add" , " sub" ,
34
+ " and" , " nand" , " or" , " xor" ,
35
+ " max" , " min" , " umax" , " umin" ,
36
+ # "fadd", "fsub",
37
+ # "fmax", "fmin",
38
+ # "uinc_wrap", "udec_wrap", # Need LLVM 16: VERSION >= v"1.11"
39
+ ]
40
+ for op ∈ atomicrmw_ops
27
41
f = Symbol (" _atomic_" , op, ' !' )
28
42
for (ityp,jtyp) ∈ [(" i8" , UInt8), (" i16" , UInt16), (" i32" , UInt32), (" i64" , UInt64), (" i128" , UInt128)]
29
43
@eval begin
44
+ # Do inplace `$(op)` for `*ptr` and `x` atomically, return the old value of `*ptr`.
30
45
@inline function $f (ptr:: Ptr{$jtyp} , x:: $jtyp )
31
46
Base. llvmcall ($ ("""
32
- %p = inttoptr i$(8 sizeof (Int)) %0 to $(ityp) *
33
- %v = atomicrmw $op $(ityp) * %p, $(ityp) %1 acq_rel
47
+ %v = atomicrmw $(op) ptr %0, $(ityp) %1 acq_rel
34
48
ret $(ityp) %v
35
49
""" ), $ jtyp, Tuple{Ptr{$ jtyp}, $ jtyp}, ptr, x)
36
50
end
@@ -42,9 +56,9 @@ for op ∈ ["xchg", "add", "sub", "and", "nand", "or", "xor", "max", "min", "uma
42
56
end
43
57
end
44
58
end
59
+
45
60
@inline _atomic_state (ptr:: Ptr{UInt} ) = reinterpret (ThreadState, _atomic_load (reinterpret (Ptr{UInt32}, ptr)))
46
61
@inline _atomic_store! (ptr:: Ptr{UInt} , x:: ThreadState ) = _atomic_store! (reinterpret (Ptr{UInt32}, ptr), reinterpret (UInt32, x))
47
62
@inline function _atomic_cas_cmp! (ptr:: Ptr{UInt} , cmp:: ThreadState , newval:: ThreadState )
48
63
_atomic_cas_cmp! (reinterpret (Ptr{UInt32}, ptr), reinterpret (UInt32, cmp), reinterpret (UInt32, newval))
49
64
end
50
-
0 commit comments