Skip to content

Commit de39c5f

Browse files
authored
Merge pull request #24587 from jacobly0/x86_64
x86_64: fix some bugs
2 parents a51cdf3 + 3194a4d commit de39c5f

File tree

2 files changed

+40
-21
lines changed

2 files changed

+40
-21
lines changed

src/arch/x86_64/CodeGen.zig

Lines changed: 30 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1103,11 +1103,7 @@ const FormatAirData = struct {
11031103
inst: Air.Inst.Index,
11041104
};
11051105
fn formatAir(data: FormatAirData, w: *std.io.Writer) Writer.Error!void {
1106-
// not acceptable implementation because it ignores `w`:
1107-
//data.self.air.dumpInst(data.inst, data.self.pt, data.self.liveness);
1108-
_ = data;
1109-
_ = w;
1110-
@panic("TODO: unimplemented");
1106+
data.self.air.writeInst(w, data.inst, data.self.pt, data.self.liveness);
11111107
}
11121108
fn fmtAir(self: *CodeGen, inst: Air.Inst.Index) std.fmt.Formatter(FormatAirData, formatAir) {
11131109
return .{ .data = .{ .self = self, .inst = inst } };
@@ -179300,10 +179296,13 @@ fn lowerSwitchBr(
179300179296
} else undefined;
179301179297
const table_start: u31 = @intCast(cg.mir_table.items.len);
179302179298
{
179303-
const condition_index_reg = if (condition_index.isRegister())
179304-
condition_index.getReg().?
179305-
else
179306-
try cg.copyToTmpRegister(.usize, condition_index);
179299+
const condition_index_reg = condition_index_reg: {
179300+
if (condition_index.isRegister()) {
179301+
const condition_index_reg = condition_index.getReg().?;
179302+
if (condition_index_reg.isClass(.general_purpose)) break :condition_index_reg condition_index_reg;
179303+
}
179304+
break :condition_index_reg try cg.copyToTmpRegister(.usize, condition_index);
179305+
};
179307179306
const condition_index_lock = cg.register_manager.lockReg(condition_index_reg);
179308179307
defer if (condition_index_lock) |lock| cg.register_manager.unlockReg(lock);
179309179308
try cg.truncateRegister(condition_ty, condition_index_reg);
@@ -191921,18 +191920,15 @@ const Select = struct {
191921191920
error.InvalidInstruction => {
191922191921
const fixes = @tagName(mir_tag[0]);
191923191922
const fixes_blank = std.mem.indexOfScalar(u8, fixes, '_').?;
191924-
return s.cg.fail(
191925-
"invalid instruction: '{s}{s}{s} {s} {s} {s} {s}'",
191926-
.{
191927-
fixes[0..fixes_blank],
191928-
@tagName(mir_tag[1]),
191929-
fixes[fixes_blank + 1 ..],
191930-
@tagName(mir_ops[0]),
191931-
@tagName(mir_ops[1]),
191932-
@tagName(mir_ops[2]),
191933-
@tagName(mir_ops[3]),
191934-
},
191935-
);
191923+
return s.cg.fail("invalid instruction: '{s}{s}{s} {s} {s} {s} {s}'", .{
191924+
fixes[0..fixes_blank],
191925+
@tagName(mir_tag[1]),
191926+
fixes[fixes_blank + 1 ..],
191927+
@tagName(mir_ops[0]),
191928+
@tagName(mir_ops[1]),
191929+
@tagName(mir_ops[2]),
191930+
@tagName(mir_ops[3]),
191931+
});
191936191932
},
191937191933
else => |e| return e,
191938191934
};
@@ -194424,6 +194420,18 @@ fn select(
194424194420
while (true) for (pattern.src[0..src_temps.len], src_temps) |src_pattern, *src_temp| {
194425194421
if (try src_pattern.convert(src_temp, cg)) break;
194426194422
} else break;
194423+
var src_locks: [s_src_temps.len][2]?RegisterLock = @splat(@splat(null));
194424+
for (src_locks[0..src_temps.len], src_temps) |*locks, src_temp| {
194425+
const regs: [2]Register = switch (src_temp.tracking(cg).short) {
194426+
else => continue,
194427+
.register => |reg| .{ reg, .none },
194428+
.register_pair => |regs| regs,
194429+
};
194430+
for (regs, locks) |reg, *lock| {
194431+
if (reg == .none) continue;
194432+
lock.* = cg.register_manager.lockRegIndex(RegisterManager.indexOfRegIntoTracked(reg) orelse continue);
194433+
}
194434+
}
194427194435
@memcpy(s_src_temps[0..src_temps.len], src_temps);
194428194436
std.mem.swap(Temp, &s_src_temps[pattern.commute[0]], &s_src_temps[pattern.commute[1]]);
194429194437

@@ -194442,6 +194450,7 @@ fn select(
194442194450
}
194443194451
assert(s.top == 0);
194444194452

194453+
for (src_locks) |locks| for (locks) |lock| if (lock) |reg| cg.register_manager.unlockReg(reg);
194445194454
for (tmp_locks) |locks| for (locks) |lock| if (lock) |reg| cg.register_manager.unlockReg(reg);
194446194455
for (dst_locks) |locks| for (locks) |lock| if (lock) |reg| cg.register_manager.unlockReg(reg);
194447194456
caller_preserved: {

test/behavior/switch.zig

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1072,3 +1072,13 @@ test "switch on a signed value smaller than the smallest prong value" {
10721072
else => {},
10731073
}
10741074
}
1075+
1076+
test "switch on 8-bit mod result" {
1077+
var x: u8 = undefined;
1078+
x = 16;
1079+
switch (x % 4) {
1080+
0 => {},
1081+
1, 2, 3 => return error.TestFailed,
1082+
else => unreachable,
1083+
}
1084+
}

0 commit comments

Comments
 (0)