| author | |
| committer | |
| log | 5806c386eb640247f6aa8983132c6b193195ea4a |
| tree | 08c05374dc59894c46f7578894a1f4c6af7d9489 |
| parent | e48d7bbb99a81d9e6058aa764266dcc3dbe71644 |
In some cases (such as bitcast), an operand may be the same MCValue as
the result. If that operand died and was a register, it was freed by
processDeath. We have to "re-allocate" the register.2 files changed, 30 insertions(+), 0 deletions(-)
src/codegen.zig+14| ... | @@ -973,6 +973,20 @@ fn Function(comptime arch: std.Target.Cpu.Arch) type { | ... | @@ -973,6 +973,20 @@ fn Function(comptime arch: std.Target.Cpu.Arch) type { |
| 973 | log.debug("%{d} => {}", .{ inst, result }); | 973 | log.debug("%{d} => {}", .{ inst, result }); |
| 974 | const branch = &self.branch_stack.items[self.branch_stack.items.len - 1]; | 974 | const branch = &self.branch_stack.items[self.branch_stack.items.len - 1]; |
| 975 | branch.inst_table.putAssumeCapacityNoClobber(inst, result); | 975 | branch.inst_table.putAssumeCapacityNoClobber(inst, result); |
| 976 | |||
| 977 | switch (result) { | ||
| 978 | .register => |reg| { | ||
| 979 | // In some cases (such as bitcast), an operand | ||
| 980 | // may be the same MCValue as the result. If | ||
| 981 | // that operand died and was a register, it | ||
| 982 | // was freed by processDeath. We have to | ||
| 983 | // "re-allocate" the register. | ||
| 984 | if (self.register_manager.isRegFree(reg)) { | ||
| 985 | self.register_manager.getRegAssumeFree(reg, inst); | ||
| 986 | } | ||
| 987 | }, | ||
| 988 | else => {}, | ||
| 989 | } | ||
| 976 | } | 990 | } |
| 977 | self.finishAirBookkeeping(); | 991 | self.finishAirBookkeeping(); |
| 978 | } | 992 | } |
test/stage2/arm.zig+16| ... | @@ -361,6 +361,22 @@ pub fn addCases(ctx: *TestContext) !void { | ... | @@ -361,6 +361,22 @@ pub fn addCases(ctx: *TestContext) !void { |
| 361 | , | 361 | , |
| 362 | "", | 362 | "", |
| 363 | ); | 363 | ); |
| 364 | |||
| 365 | case.addCompareOutput( | ||
| 366 | \\const Number = enum { one, two, three }; | ||
| 367 | \\ | ||
| 368 | \\pub fn main() void { | ||
| 369 | \\ var x: Number = .one; | ||
| 370 | \\ var y = Number.two; | ||
| 371 | \\ assert(@enumToInt(x) < @enumToInt(y)); | ||
| 372 | \\} | ||
| 373 | \\ | ||
| 374 | \\fn assert(ok: bool) void { | ||
| 375 | \\ if (!ok) unreachable; // assertion failure | ||
| 376 | \\} | ||
| 377 | , | ||
| 378 | "", | ||
| 379 | ); | ||
| 364 | } | 380 | } |
| 365 | 381 | ||
| 366 | { | 382 | { |