authorgravatar for mail@isaacfreund.comIsaac Freund <mail@isaacfreund.com> 2021-06-14 04:45:44+00:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2021-06-14 12:16:36-07:00
log4453f6a5ce40d2a8c1daeb3528c6c5466b9621dc
tree8caec9d83d797d42ce99c3541d8c78517599c6dd
parent7f6e7e3e5db5f8dc749e58b704eb0ff812a1cdbf

std: fix auto hash of tagged union with void field


1 files changed, 10 insertions(+), 2 deletions(-)

lib/std/hash/auto_hash.zig+10-2
......@@ -146,10 +146,12 @@ pub fn hash(hasher: anytype, key: anytype, comptime strat: HashStrategy) void {
146146 .Union => |info| {
147147 if (info.tag_type) |tag_type| {
148148 const tag = meta.activeTag(key);
149 const s = hash(hasher, tag, strat);
149 hash(hasher, tag, strat);
150150 inline for (info.fields) |field| {
151151 if (@field(tag_type, field.name) == tag) {
152 hash(hasher, @field(key, field.name), strat);
152 if (field.field_type != void) {
153 hash(hasher, @field(key, field.name), strat);
154 }
153155 // TODO use a labelled break when it does not crash the compiler. cf #2908
154156 // break :blk;
155157 return;
......@@ -385,17 +387,23 @@ test "testHash union" {
385387 A: u32,
386388 B: bool,
387389 C: u32,
390 D: void,
388391 };
389392
390393 const a = Foo{ .A = 18 };
391394 var b = Foo{ .B = true };
392395 const c = Foo{ .C = 18 };
396 const d: Foo = .D;
393397 try testing.expect(testHash(a) == testHash(a));
394398 try testing.expect(testHash(a) != testHash(b));
395399 try testing.expect(testHash(a) != testHash(c));
400 try testing.expect(testHash(a) != testHash(d));
396401
397402 b = Foo{ .A = 18 };
398403 try testing.expect(testHash(a) == testHash(b));
404
405 b = .D;
406 try testing.expect(testHash(d) == testHash(b));
399407}
400408
401409test "testHash vector" {