| ... | ... | @@ -795,11 +795,7 @@ fn spillCompareFlagsIfOccupied(self: *Self) !void { |
| 795 | 795 | assert(mcv == .compare_flags_signed or mcv == .compare_flags_unsigned); |
| 796 | 796 | |
| 797 | 797 | const new_mcv = try self.allocRegOrMem(inst_to_save, true); |
| 798 | | switch (new_mcv) { |
| 799 | | .register => |reg| try self.genSetReg(self.air.typeOfIndex(inst_to_save), reg, mcv), |
| 800 | | .stack_offset => |offset| try self.genSetStack(self.air.typeOfIndex(inst_to_save), offset, mcv), |
| 801 | | else => unreachable, |
| 802 | | } |
| 798 | try self.setRegOrMem(self.air.typeOfIndex(inst_to_save), new_mcv, mcv); |
| 803 | 799 | log.debug("spilling {d} to mcv {any}", .{ inst_to_save, new_mcv }); |
| 804 | 800 | |
| 805 | 801 | const branch = &self.branch_stack.items[self.branch_stack.items.len - 1]; |
| ... | ... | @@ -1172,9 +1168,14 @@ fn airSlicePtr(self: *Self, inst: Air.Inst.Index) !void { |
| 1172 | 1168 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 1173 | 1169 | const mcv = try self.resolveInst(ty_op.operand); |
| 1174 | 1170 | switch (mcv) { |
| 1171 | .dead, .unreach => unreachable, |
| 1172 | .register => unreachable, // a slice doesn't fit in one register |
| 1175 | 1173 | .stack_offset => |off| { |
| 1176 | 1174 | break :result MCValue{ .stack_offset = off }; |
| 1177 | 1175 | }, |
| 1176 | .memory => |addr| { |
| 1177 | break :result MCValue{ .memory = addr }; |
| 1178 | }, |
| 1178 | 1179 | else => return self.fail("TODO implement slice_ptr for {}", .{mcv}), |
| 1179 | 1180 | } |
| 1180 | 1181 | }; |
| ... | ... | @@ -1186,9 +1187,14 @@ fn airSliceLen(self: *Self, inst: Air.Inst.Index) !void { |
| 1186 | 1187 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 1187 | 1188 | const mcv = try self.resolveInst(ty_op.operand); |
| 1188 | 1189 | switch (mcv) { |
| 1190 | .dead, .unreach => unreachable, |
| 1191 | .register => unreachable, // a slice doesn't fit in one register |
| 1189 | 1192 | .stack_offset => |off| { |
| 1190 | 1193 | break :result MCValue{ .stack_offset = off + 4 }; |
| 1191 | 1194 | }, |
| 1195 | .memory => |addr| { |
| 1196 | break :result MCValue{ .memory = addr + 4 }; |
| 1197 | }, |
| 1192 | 1198 | else => return self.fail("TODO implement slice_len for {}", .{mcv}), |
| 1193 | 1199 | } |
| 1194 | 1200 | }; |
| ... | ... | @@ -1197,13 +1203,33 @@ fn airSliceLen(self: *Self, inst: Air.Inst.Index) !void { |
| 1197 | 1203 | |
| 1198 | 1204 | fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 1199 | 1205 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 1200 | | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else return self.fail("TODO implement ptr_slice_len_ptr for {}", .{self.target.cpu.arch}); |
| 1206 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 1207 | const mcv = try self.resolveInst(ty_op.operand); |
| 1208 | switch (mcv) { |
| 1209 | .dead, .unreach => unreachable, |
| 1210 | .register => unreachable, // a slice doesn't fit in one register |
| 1211 | .ptr_stack_offset => |off| { |
| 1212 | break :result MCValue{ .ptr_stack_offset = off + 4 }; |
| 1213 | }, |
| 1214 | else => return self.fail("TODO implement ptr_slice_len_ptr for {}", .{mcv}), |
| 1215 | } |
| 1216 | }; |
| 1201 | 1217 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 1202 | 1218 | } |
| 1203 | 1219 | |
| 1204 | 1220 | fn airPtrSlicePtrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 1205 | 1221 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 1206 | | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else return self.fail("TODO implement ptr_slice_ptr_ptr for {}", .{self.target.cpu.arch}); |
| 1222 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 1223 | const mcv = try self.resolveInst(ty_op.operand); |
| 1224 | switch (mcv) { |
| 1225 | .dead, .unreach => unreachable, |
| 1226 | .register => unreachable, // a slice doesn't fit in one register |
| 1227 | .ptr_stack_offset => |off| { |
| 1228 | break :result MCValue{ .ptr_stack_offset = off }; |
| 1229 | }, |
| 1230 | else => return self.fail("TODO implement ptr_slice_ptr_ptr for {}", .{mcv}), |
| 1231 | } |
| 1232 | }; |
| 1207 | 1233 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 1208 | 1234 | } |
| 1209 | 1235 | |