| ... | ... | @@ -3,6 +3,9 @@ |
| 3 | 3 | // This file is part of [zig](https://ziglang.org/), which is MIT licensed. |
| 4 | 4 | // The MIT license requires this copyright notice to be included in all copies |
| 5 | 5 | // and substantial portions of the software. |
| 6 | |
| 7 | const builtin = @import("std").builtin; |
| 8 | |
| 6 | 9 | /// Thread-safe, lock-free integer |
| 7 | 10 | pub fn Int(comptime T: type) type { |
| 8 | 11 | return struct { |
| ... | ... | @@ -14,30 +17,43 @@ pub fn Int(comptime T: type) type { |
| 14 | 17 | return Self{ .unprotected_value = init_val }; |
| 15 | 18 | } |
| 16 | 19 | |
| 20 | /// Read, Modify, Write |
| 21 | pub fn rmw(self: *Self, comptime op: builtin.AtomicRmwOp, operand: T, comptime ordering: builtin.AtomicOrder) T { |
| 22 | return @atomicRmw(T, &self.unprotected_value, operand, ordering); |
| 23 | } |
| 24 | |
| 25 | pub fn load(self: *Self, comptime ordering: builtin.AtomicOrder) T { |
| 26 | return @atomicLoad(T, &self.unprotected_value, ordering); |
| 27 | } |
| 28 | |
| 29 | pub fn store(self: *Self, value: T, comptime ordering: builtin.AtomicOrder) void { |
| 30 | @atomicStore(T, &self.unprotected_value, value, ordering); |
| 31 | } |
| 32 | |
| 17 | 33 | /// Returns previous value |
| 18 | 34 | pub fn incr(self: *Self) T { |
| 19 | | return @atomicRmw(T, &self.unprotected_value, .Add, 1, .SeqCst); |
| 35 | return self.rmw(.Add, 1, .SeqCst); |
| 20 | 36 | } |
| 21 | 37 | |
| 22 | 38 | /// Returns previous value |
| 23 | 39 | pub fn decr(self: *Self) T { |
| 24 | | return @atomicRmw(T, &self.unprotected_value, .Sub, 1, .SeqCst); |
| 40 | return self.rmw(.Sub, 1, .SeqCst); |
| 25 | 41 | } |
| 26 | 42 | |
| 27 | 43 | pub fn get(self: *Self) T { |
| 28 | | return @atomicLoad(T, &self.unprotected_value, .SeqCst); |
| 44 | return self.load(.SeqCst); |
| 29 | 45 | } |
| 30 | 46 | |
| 31 | 47 | pub fn set(self: *Self, new_value: T) void { |
| 32 | | _ = self.xchg(new_value); |
| 48 | self.store(new_value, .SeqCst); |
| 33 | 49 | } |
| 34 | 50 | |
| 35 | 51 | pub fn xchg(self: *Self, new_value: T) T { |
| 36 | | return @atomicRmw(T, &self.unprotected_value, .Xchg, new_value, .SeqCst); |
| 52 | return self.rmw(.Xchg, new_value, .SeqCst); |
| 37 | 53 | } |
| 38 | 54 | |
| 39 | 55 | pub fn fetchAdd(self: *Self, op: T) T { |
| 40 | | return @atomicRmw(T, &self.unprotected_value, .Add, op, .SeqCst); |
| 56 | return self.rmw(.Add, op, .SeqCst); |
| 41 | 57 | } |
| 42 | 58 | }; |
| 43 | 59 | } |