authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-01-24 21:28:12-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-01-24 21:29:04-07:00
log913d61ebb95567fe67b0bfad99694892aac841e2
tree5496f79e086292913a5ac166eff6f7d3ea5113d7
parent2e9ce6facd47189c4bbcd90a2a6ba1a689bfbde3

Revert "MultiArrayList: Fix error when struct is 0 sized"

This reverts commit 1f10cf4edf2b645e63dedc42f5d7475914bf2311. Re-opens #10618 I want to solve this a different way. `align(S)` where S is a 0-byte type should work in this context. This also caused issues such as https://github.com/Vexu/arocc/issues/221

2 files changed, 6 insertions(+), 86 deletions(-)

lib/std/array_hash_map.zig-29
...@@ -2215,35 +2215,6 @@ test "auto store_hash" {...@@ -2215,35 +2215,6 @@ test "auto store_hash" {
2215 try testing.expect(meta.fieldInfo(HasExpensiveEqlUn.Data, .hash).field_type != void);2215 try testing.expect(meta.fieldInfo(HasExpensiveEqlUn.Data, .hash).field_type != void);
2216}2216}
22172217
2218test "0 sized key" {
2219 var map = AutoArrayHashMap(u0, i32).init(std.testing.allocator);
2220 defer map.deinit();
2221
2222 try testing.expectEqual(map.get(0), null);
2223
2224 try map.put(0, 5);
2225 try testing.expectEqual(map.get(0), 5);
2226
2227 try map.put(0, 10);
2228 try testing.expectEqual(map.get(0), 10);
2229
2230 try testing.expectEqual(map.swapRemove(0), true);
2231 try testing.expectEqual(map.get(0), null);
2232}
2233
2234test "0 sized key and 0 sized value" {
2235 var map = AutoArrayHashMap(u0, u0).init(std.testing.allocator);
2236 defer map.deinit();
2237
2238 try testing.expectEqual(map.get(0), null);
2239
2240 try map.put(0, 0);
2241 try testing.expectEqual(map.get(0), 0);
2242
2243 try testing.expectEqual(map.swapRemove(0), true);
2244 try testing.expectEqual(map.get(0), null);
2245}
2246
2247pub fn getHashPtrAddrFn(comptime K: type, comptime Context: type) (fn (Context, K) u32) {2218pub fn getHashPtrAddrFn(comptime K: type, comptime Context: type) (fn (Context, K) u32) {
2248 return struct {2219 return struct {
2249 fn hash(ctx: Context, key: K) u32 {2220 fn hash(ctx: Context, key: K) u32 {
lib/std/multi_array_list.zig+6-57
...@@ -16,9 +16,7 @@ const testing = std.testing;...@@ -16,9 +16,7 @@ const testing = std.testing;
16/// `.items(.<field_name>)` to obtain a slice of field values.16/// `.items(.<field_name>)` to obtain a slice of field values.
17pub fn MultiArrayList(comptime S: type) type {17pub fn MultiArrayList(comptime S: type) type {
18 return struct {18 return struct {
19 const alignS = if (@alignOf(S) == 0) 1 else @alignOf(S);19 bytes: [*]align(@alignOf(S)) u8 = undefined,
20
21 bytes: [*]align(alignS) u8 = undefined,
22 len: usize = 0,20 len: usize = 0,
23 capacity: usize = 0,21 capacity: usize = 0,
2422
...@@ -52,8 +50,8 @@ pub fn MultiArrayList(comptime S: type) type {...@@ -52,8 +50,8 @@ pub fn MultiArrayList(comptime S: type) type {
52 return .{};50 return .{};
53 }51 }
54 const unaligned_ptr = self.ptrs[sizes.fields[0]];52 const unaligned_ptr = self.ptrs[sizes.fields[0]];
55 const aligned_ptr = @alignCast(alignS, unaligned_ptr);53 const aligned_ptr = @alignCast(@alignOf(S), unaligned_ptr);
56 const casted_ptr = @ptrCast([*]align(alignS) u8, aligned_ptr);54 const casted_ptr = @ptrCast([*]align(@alignOf(S)) u8, aligned_ptr);
57 return .{55 return .{
58 .bytes = casted_ptr,56 .bytes = casted_ptr,
59 .len = self.len,57 .len = self.len,
...@@ -263,7 +261,7 @@ pub fn MultiArrayList(comptime S: type) type {...@@ -263,7 +261,7 @@ pub fn MultiArrayList(comptime S: type) type {
263261
264 const other_bytes = gpa.allocAdvanced(262 const other_bytes = gpa.allocAdvanced(
265 u8,263 u8,
266 alignS,264 @alignOf(S),
267 capacityInBytes(new_len),265 capacityInBytes(new_len),
268 .exact,266 .exact,
269 ) catch {267 ) catch {
...@@ -341,7 +339,7 @@ pub fn MultiArrayList(comptime S: type) type {...@@ -341,7 +339,7 @@ pub fn MultiArrayList(comptime S: type) type {
341 assert(new_capacity >= self.len);339 assert(new_capacity >= self.len);
342 const new_bytes = try gpa.allocAdvanced(340 const new_bytes = try gpa.allocAdvanced(
343 u8,341 u8,
344 alignS,342 @alignOf(S),
345 capacityInBytes(new_capacity),343 capacityInBytes(new_capacity),
346 .exact,344 .exact,
347 );345 );
...@@ -400,7 +398,7 @@ pub fn MultiArrayList(comptime S: type) type {...@@ -400,7 +398,7 @@ pub fn MultiArrayList(comptime S: type) type {
400 return @reduce(.Add, capacity_vector * sizes_vector);398 return @reduce(.Add, capacity_vector * sizes_vector);
401 }399 }
402400
403 fn allocatedBytes(self: Self) []align(alignS) u8 {401 fn allocatedBytes(self: Self) []align(@alignOf(S)) u8 {
404 return self.bytes[0..capacityInBytes(self.capacity)];402 return self.bytes[0..capacityInBytes(self.capacity)];
405 }403 }
406404
...@@ -623,52 +621,3 @@ test "insert elements" {...@@ -623,52 +621,3 @@ test "insert elements" {
623 try testing.expectEqualSlices(u8, &[_]u8{ 1, 2 }, list.items(.a));621 try testing.expectEqualSlices(u8, &[_]u8{ 1, 2 }, list.items(.a));
624 try testing.expectEqualSlices(u32, &[_]u32{ 2, 3 }, list.items(.b));622 try testing.expectEqualSlices(u32, &[_]u32{ 2, 3 }, list.items(.b));
625}623}
626
627test "0 sized struct field" {
628 const ally = testing.allocator;
629
630 const Foo = struct {
631 a: u0,
632 b: f32,
633 };
634
635 var list = MultiArrayList(Foo){};
636 defer list.deinit(ally);
637
638 try testing.expectEqualSlices(u0, &[_]u0{}, list.items(.a));
639 try testing.expectEqualSlices(f32, &[_]f32{}, list.items(.b));
640
641 try list.append(ally, .{ .a = 0, .b = 42.0 });
642 try testing.expectEqualSlices(u0, &[_]u0{0}, list.items(.a));
643 try testing.expectEqualSlices(f32, &[_]f32{42.0}, list.items(.b));
644
645 try list.insert(ally, 0, .{ .a = 0, .b = -1.0 });
646 try testing.expectEqualSlices(u0, &[_]u0{ 0, 0 }, list.items(.a));
647 try testing.expectEqualSlices(f32, &[_]f32{ -1.0, 42.0 }, list.items(.b));
648
649 list.swapRemove(list.len - 1);
650 try testing.expectEqualSlices(u0, &[_]u0{0}, list.items(.a));
651 try testing.expectEqualSlices(f32, &[_]f32{-1.0}, list.items(.b));
652}
653
654test "0 sized struct" {
655 const ally = testing.allocator;
656
657 const Foo = struct {
658 a: u0,
659 };
660
661 var list = MultiArrayList(Foo){};
662 defer list.deinit(ally);
663
664 try testing.expectEqualSlices(u0, &[_]u0{}, list.items(.a));
665
666 try list.append(ally, .{ .a = 0 });
667 try testing.expectEqualSlices(u0, &[_]u0{0}, list.items(.a));
668
669 try list.insert(ally, 0, .{ .a = 0 });
670 try testing.expectEqualSlices(u0, &[_]u0{ 0, 0 }, list.items(.a));
671
672 list.swapRemove(list.len - 1);
673 try testing.expectEqualSlices(u0, &[_]u0{0}, list.items(.a));
674}