unordered atomics part 1

This commit is contained in:
IntegratedQuantum 2025-07-29 21:24:56 +02:00
parent 8abe239204
commit daf44c76d7

View File

@ -989,7 +989,7 @@ pub fn deinitDynamicIntArrayStorage() void {
pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIntArray pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIntArray
std.debug.assert(std.math.isPowerOfTwo(size)); std.debug.assert(std.math.isPowerOfTwo(size));
return struct { return struct {
data: []align(64) u32 = &.{}, data: []align(64) Atomic(u32) = &.{},
bitSize: u5 = 0, bitSize: u5 = 0,
const Self = @This(); const Self = @This();
@ -997,7 +997,7 @@ pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIn
pub fn initCapacity(bitSize: u5) Self { pub fn initCapacity(bitSize: u5) Self {
std.debug.assert(bitSize == 0 or bitSize & bitSize - 1 == 0); // Must be a power of 2 std.debug.assert(bitSize == 0 or bitSize & bitSize - 1 == 0); // Must be a power of 2
return .{ return .{
.data = dynamicIntArrayAllocator.allocator().alignedAlloc(u32, .@"64", @as(usize, @divExact(size, @bitSizeOf(u32)))*bitSize), .data = dynamicIntArrayAllocator.allocator().alignedAlloc(Atomic(u32), .@"64", @as(usize, @divExact(size, @bitSizeOf(u32)))*bitSize),
.bitSize = bitSize, .bitSize = bitSize,
}; };
} }
@ -1021,12 +1021,12 @@ pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIn
std.debug.assert(self.bitSize == newBitSize); std.debug.assert(self.bitSize == newBitSize);
switch(other.bitSize) { switch(other.bitSize) {
0 => @memset(self.data, 0), 0 => @memset(self.data, .init(0)),
inline 1, 2, 4, 8 => |bits| { inline 1, 2, 4, 8 => |bits| {
for(0..other.data.len) |i| { for(0..other.data.len) |i| {
const oldVal = other.data[i]; const oldVal = other.data[i].load(.unordered);
self.data[2*i] = bitInterleave(bits, oldVal & 0xffff); self.data[2*i].store(bitInterleave(bits, oldVal & 0xffff), .unordered);
self.data[2*i + 1] = bitInterleave(bits, oldVal >> 16); self.data[2*i + 1].store(bitInterleave(bits, oldVal >> 16), .unordered);
} }
}, },
else => unreachable, else => unreachable,
@ -1040,7 +1040,7 @@ pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIn
const intIndex = bitIndex >> 5; const intIndex = bitIndex >> 5;
const bitOffset: u5 = @intCast(bitIndex & 31); const bitOffset: u5 = @intCast(bitIndex & 31);
const bitMask = (@as(u32, 1) << self.bitSize) - 1; const bitMask = (@as(u32, 1) << self.bitSize) - 1;
return self.data[intIndex] >> bitOffset & bitMask; return self.data[intIndex].load(.unordered) >> bitOffset & bitMask;
} }
pub fn setValue(self: *Self, i: usize, value: u32) void { pub fn setValue(self: *Self, i: usize, value: u32) void {
@ -1051,9 +1051,9 @@ pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIn
const bitOffset: u5 = @intCast(bitIndex & 31); const bitOffset: u5 = @intCast(bitIndex & 31);
const bitMask = (@as(u32, 1) << self.bitSize) - 1; const bitMask = (@as(u32, 1) << self.bitSize) - 1;
std.debug.assert(value <= bitMask); std.debug.assert(value <= bitMask);
const ptr: *u32 = &self.data[intIndex]; const ptr: *Atomic(u32) = &self.data[intIndex];
ptr.* &= ~(bitMask << bitOffset); const newValue = (ptr.load(.unordered) & ~(bitMask << bitOffset)) | value << bitOffset;
ptr.* |= value << bitOffset; ptr.store(newValue, .unordered);
} }
pub fn setAndGetValue(self: *Self, i: usize, value: u32) u32 { pub fn setAndGetValue(self: *Self, i: usize, value: u32) u32 {
@ -1064,10 +1064,11 @@ pub fn DynamicPackedIntArray(size: comptime_int) type { // MARK: DynamicPackedIn
const bitOffset: u5 = @intCast(bitIndex & 31); const bitOffset: u5 = @intCast(bitIndex & 31);
const bitMask = (@as(u32, 1) << self.bitSize) - 1; const bitMask = (@as(u32, 1) << self.bitSize) - 1;
std.debug.assert(value <= bitMask); std.debug.assert(value <= bitMask);
const ptr: *u32 = &self.data[intIndex]; const ptr: *Atomic(u32) = &self.data[intIndex];
const result = ptr.* >> bitOffset & bitMask; const oldValue = ptr.load(.unordered);
ptr.* &= ~(bitMask << bitOffset); const result = oldValue >> bitOffset & bitMask;
ptr.* |= value << bitOffset; const newValue = (oldValue & ~(bitMask << bitOffset)) | value << bitOffset;
ptr.store(newValue, .unordered);
return result; return result;
} }
}; };
@ -1135,7 +1136,7 @@ pub fn PaletteCompressedRegion(T: type, size: comptime_int) type { // MARK: Pale
impl.palette[0] = std.mem.zeroes(T); impl.palette[0] = std.mem.zeroes(T);
impl.paletteOccupancy[0] = size; impl.paletteOccupancy[0] = size;
@memset(impl.paletteOccupancy[1..], 0); @memset(impl.paletteOccupancy[1..], 0);
@memset(impl.data.data, 0); @memset(impl.data.data, .init(0));
} }
fn privateDeinit(impl: *Impl, _: usize) void { fn privateDeinit(impl: *Impl, _: usize) void {