| ... | @@ -104,7 +104,7 @@ const Owner = union(enum) { | ... | @@ -104,7 +104,7 @@ const Owner = union(enum) { |
| 104 | nav_index: InternPool.Nav.Index, | 104 | nav_index: InternPool.Nav.Index, |
| 105 | lazy_sym: link.File.LazySymbol, | 105 | lazy_sym: link.File.LazySymbol, |
| 106 | | 106 | |
| 107 | fn getSymbolIndex(owner: Owner, ctx: *Self) !u32 { | 107 | fn getSymbolIndex(owner: Owner, ctx: *CodeGen) !u32 { |
| 108 | const pt = ctx.pt; | 108 | const pt = ctx.pt; |
| 109 | switch (owner) { | 109 | switch (owner) { |
| 110 | .nav_index => |nav_index| if (ctx.bin_file.cast(.elf)) |elf_file| { | 110 | .nav_index => |nav_index| if (ctx.bin_file.cast(.elf)) |elf_file| { |
| ... | @@ -394,7 +394,7 @@ pub const MCValue = union(enum) { | ... | @@ -394,7 +394,7 @@ pub const MCValue = union(enum) { |
| 394 | }; | 394 | }; |
| 395 | } | 395 | } |
| 396 | | 396 | |
| 397 | fn mem(mcv: MCValue, function: *Self, size: Memory.Size) !Memory { | 397 | fn mem(mcv: MCValue, function: *CodeGen, mod_rm: Memory.Mod.Rm) !Memory { |
| 398 | return switch (mcv) { | 398 | return switch (mcv) { |
| 399 | .none, | 399 | .none, |
| 400 | .unreach, | 400 | .unreach, |
| ... | @@ -420,22 +420,28 @@ pub const MCValue = union(enum) { | ... | @@ -420,22 +420,28 @@ pub const MCValue = union(enum) { |
| 420 | .memory => |addr| if (std.math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| .{ | 420 | .memory => |addr| if (std.math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| .{ |
| 421 | .base = .{ .reg = .ds }, | 421 | .base = .{ .reg = .ds }, |
| 422 | .mod = .{ .rm = .{ | 422 | .mod = .{ .rm = .{ |
| 423 | .size = size, | 423 | .size = mod_rm.size, |
| 424 | .disp = small_addr, | 424 | .index = mod_rm.index, |
| | 425 | .scale = mod_rm.scale, |
| | 426 | .disp = small_addr + mod_rm.disp, |
| 425 | } }, | 427 | } }, |
| 426 | } else .{ .base = .{ .reg = .ds }, .mod = .{ .off = addr } }, | 428 | } else .{ .base = .{ .reg = .ds }, .mod = .{ .off = addr } }, |
| 427 | .indirect => |reg_off| .{ | 429 | .indirect => |reg_off| .{ |
| 428 | .base = .{ .reg = reg_off.reg }, | 430 | .base = .{ .reg = reg_off.reg }, |
| 429 | .mod = .{ .rm = .{ | 431 | .mod = .{ .rm = .{ |
| 430 | .size = size, | 432 | .size = mod_rm.size, |
| 431 | .disp = reg_off.off, | 433 | .index = mod_rm.index, |
| | 434 | .scale = mod_rm.scale, |
| | 435 | .disp = reg_off.off + mod_rm.disp, |
| 432 | } }, | 436 | } }, |
| 433 | }, | 437 | }, |
| 434 | .load_frame => |frame_addr| .{ | 438 | .load_frame => |frame_addr| .{ |
| 435 | .base = .{ .frame = frame_addr.index }, | 439 | .base = .{ .frame = frame_addr.index }, |
| 436 | .mod = .{ .rm = .{ | 440 | .mod = .{ .rm = .{ |
| 437 | .size = size, | 441 | .size = mod_rm.size, |
| 438 | .disp = frame_addr.off, | 442 | .index = mod_rm.index, |
| | 443 | .scale = mod_rm.scale, |
| | 444 | .disp = frame_addr.off + mod_rm.disp, |
| 439 | } }, | 445 | } }, |
| 440 | }, | 446 | }, |
| 441 | .load_symbol => |sym_off| { | 447 | .load_symbol => |sym_off| { |
| ... | @@ -443,12 +449,14 @@ pub const MCValue = union(enum) { | ... | @@ -443,12 +449,14 @@ pub const MCValue = union(enum) { |
| 443 | return .{ | 449 | return .{ |
| 444 | .base = .{ .reloc = sym_off.sym_index }, | 450 | .base = .{ .reloc = sym_off.sym_index }, |
| 445 | .mod = .{ .rm = .{ | 451 | .mod = .{ .rm = .{ |
| 446 | .size = size, | 452 | .size = mod_rm.size, |
| 447 | .disp = sym_off.off, | 453 | .index = mod_rm.index, |
| | 454 | .scale = mod_rm.scale, |
| | 455 | .disp = sym_off.off + mod_rm.disp, |
| 448 | } }, | 456 | } }, |
| 449 | }; | 457 | }; |
| 450 | }, | 458 | }, |
| 451 | .air_ref => |ref| (try function.resolveInst(ref)).mem(function, size), | 459 | .air_ref => |ref| (try function.resolveInst(ref)).mem(function, mod_rm), |
| 452 | }; | 460 | }; |
| 453 | } | 461 | } |
| 454 | | 462 | |
| ... | @@ -537,7 +545,7 @@ const InstTracking = struct { | ... | @@ -537,7 +545,7 @@ const InstTracking = struct { |
| 537 | return self.short.getCondition(); | 545 | return self.short.getCondition(); |
| 538 | } | 546 | } |
| 539 | | 547 | |
| 540 | fn spill(self: *InstTracking, function: *Self, inst: Air.Inst.Index) !void { | 548 | fn spill(self: *InstTracking, function: *CodeGen, inst: Air.Inst.Index) !void { |
| 541 | if (std.meta.eql(self.long, self.short)) return; // Already spilled | 549 | if (std.meta.eql(self.long, self.short)) return; // Already spilled |
| 542 | // Allocate or reuse frame index | 550 | // Allocate or reuse frame index |
| 543 | switch (self.long) { | 551 | switch (self.long) { |
| ... | @@ -586,7 +594,7 @@ const InstTracking = struct { | ... | @@ -586,7 +594,7 @@ const InstTracking = struct { |
| 586 | }; | 594 | }; |
| 587 | } | 595 | } |
| 588 | | 596 | |
| 589 | fn trackSpill(self: *InstTracking, function: *Self, inst: Air.Inst.Index) !void { | 597 | fn trackSpill(self: *InstTracking, function: *CodeGen, inst: Air.Inst.Index) !void { |
| 590 | try function.freeValue(self.short); | 598 | try function.freeValue(self.short); |
| 591 | self.reuseFrame(); | 599 | self.reuseFrame(); |
| 592 | tracking_log.debug("{} => {} (spilled)", .{ inst, self.* }); | 600 | tracking_log.debug("{} => {} (spilled)", .{ inst, self.* }); |
| ... | @@ -633,7 +641,7 @@ const InstTracking = struct { | ... | @@ -633,7 +641,7 @@ const InstTracking = struct { |
| 633 | | 641 | |
| 634 | fn materialize( | 642 | fn materialize( |
| 635 | self: *InstTracking, | 643 | self: *InstTracking, |
| 636 | function: *Self, | 644 | function: *CodeGen, |
| 637 | inst: Air.Inst.Index, | 645 | inst: Air.Inst.Index, |
| 638 | target: InstTracking, | 646 | target: InstTracking, |
| 639 | ) !void { | 647 | ) !void { |
| ... | @@ -643,7 +651,7 @@ const InstTracking = struct { | ... | @@ -643,7 +651,7 @@ const InstTracking = struct { |
| 643 | | 651 | |
| 644 | fn materializeUnsafe( | 652 | fn materializeUnsafe( |
| 645 | self: InstTracking, | 653 | self: InstTracking, |
| 646 | function: *Self, | 654 | function: *CodeGen, |
| 647 | inst: Air.Inst.Index, | 655 | inst: Air.Inst.Index, |
| 648 | target: InstTracking, | 656 | target: InstTracking, |
| 649 | ) !void { | 657 | ) !void { |
| ... | @@ -675,7 +683,7 @@ const InstTracking = struct { | ... | @@ -675,7 +683,7 @@ const InstTracking = struct { |
| 675 | } | 683 | } |
| 676 | } | 684 | } |
| 677 | | 685 | |
| 678 | fn die(self: *InstTracking, function: *Self, inst: Air.Inst.Index) !void { | 686 | fn die(self: *InstTracking, function: *CodeGen, inst: Air.Inst.Index) !void { |
| 679 | if (self.short == .dead) return; | 687 | if (self.short == .dead) return; |
| 680 | try function.freeValue(self.short); | 688 | try function.freeValue(self.short); |
| 681 | self.short = .{ .dead = function.scope_generation }; | 689 | self.short = .{ .dead = function.scope_generation }; |
| ... | @@ -684,7 +692,7 @@ const InstTracking = struct { | ... | @@ -684,7 +692,7 @@ const InstTracking = struct { |
| 684 | | 692 | |
| 685 | fn reuse( | 693 | fn reuse( |
| 686 | self: *InstTracking, | 694 | self: *InstTracking, |
| 687 | function: *Self, | 695 | function: *CodeGen, |
| 688 | new_inst: ?Air.Inst.Index, | 696 | new_inst: ?Air.Inst.Index, |
| 689 | old_inst: Air.Inst.Index, | 697 | old_inst: Air.Inst.Index, |
| 690 | ) void { | 698 | ) void { |
| ... | @@ -692,7 +700,7 @@ const InstTracking = struct { | ... | @@ -692,7 +700,7 @@ const InstTracking = struct { |
| 692 | tracking_log.debug("{?} => {} (reuse {})", .{ new_inst, self.*, old_inst }); | 700 | tracking_log.debug("{?} => {} (reuse {})", .{ new_inst, self.*, old_inst }); |
| 693 | } | 701 | } |
| 694 | | 702 | |
| 695 | fn liveOut(self: *InstTracking, function: *Self, inst: Air.Inst.Index) void { | 703 | fn liveOut(self: *InstTracking, function: *CodeGen, inst: Air.Inst.Index) void { |
| 696 | for (self.getRegs()) |reg| { | 704 | for (self.getRegs()) |reg| { |
| 697 | if (function.register_manager.isRegFree(reg)) { | 705 | if (function.register_manager.isRegFree(reg)) { |
| 698 | tracking_log.debug("{} => {} (live-out)", .{ inst, self.* }); | 706 | tracking_log.debug("{} => {} (live-out)", .{ inst, self.* }); |
| ... | @@ -789,7 +797,7 @@ const BlockData = struct { | ... | @@ -789,7 +797,7 @@ const BlockData = struct { |
| 789 | } | 797 | } |
| 790 | }; | 798 | }; |
| 791 | | 799 | |
| 792 | const Self = @This(); | 800 | const CodeGen = @This(); |
| 793 | | 801 | |
| 794 | pub fn generate( | 802 | pub fn generate( |
| 795 | bin_file: *link.File, | 803 | bin_file: *link.File, |
| ... | @@ -809,7 +817,7 @@ pub fn generate( | ... | @@ -809,7 +817,7 @@ pub fn generate( |
| 809 | const fn_type: Type = .fromInterned(func.ty); | 817 | const fn_type: Type = .fromInterned(func.ty); |
| 810 | const mod = zcu.navFileScope(func.owner_nav).mod; | 818 | const mod = zcu.navFileScope(func.owner_nav).mod; |
| 811 | | 819 | |
| 812 | var function: Self = .{ | 820 | var function: CodeGen = .{ |
| 813 | .gpa = gpa, | 821 | .gpa = gpa, |
| 814 | .pt = pt, | 822 | .pt = pt, |
| 815 | .air = air, | 823 | .air = air, |
| ... | @@ -962,7 +970,7 @@ pub fn generateLazy( | ... | @@ -962,7 +970,7 @@ pub fn generateLazy( |
| 962 | const gpa = comp.gpa; | 970 | const gpa = comp.gpa; |
| 963 | // This function is for generating global code, so we use the root module. | 971 | // This function is for generating global code, so we use the root module. |
| 964 | const mod = comp.root_mod; | 972 | const mod = comp.root_mod; |
| 965 | var function: Self = .{ | 973 | var function: CodeGen = .{ |
| 966 | .gpa = gpa, | 974 | .gpa = gpa, |
| 967 | .pt = pt, | 975 | .pt = pt, |
| 968 | .air = undefined, | 976 | .air = undefined, |
| ... | @@ -1050,7 +1058,7 @@ fn fmtNav(nav_index: InternPool.Nav.Index, ip: *const InternPool) std.fmt.Format | ... | @@ -1050,7 +1058,7 @@ fn fmtNav(nav_index: InternPool.Nav.Index, ip: *const InternPool) std.fmt.Format |
| 1050 | } | 1058 | } |
| 1051 | | 1059 | |
| 1052 | const FormatAirData = struct { | 1060 | const FormatAirData = struct { |
| 1053 | self: *Self, | 1061 | self: *CodeGen, |
| 1054 | inst: Air.Inst.Index, | 1062 | inst: Air.Inst.Index, |
| 1055 | }; | 1063 | }; |
| 1056 | fn formatAir( | 1064 | fn formatAir( |
| ... | @@ -1066,12 +1074,12 @@ fn formatAir( | ... | @@ -1066,12 +1074,12 @@ fn formatAir( |
| 1066 | data.self.liveness, | 1074 | data.self.liveness, |
| 1067 | ); | 1075 | ); |
| 1068 | } | 1076 | } |
| 1069 | fn fmtAir(self: *Self, inst: Air.Inst.Index) std.fmt.Formatter(formatAir) { | 1077 | fn fmtAir(self: *CodeGen, inst: Air.Inst.Index) std.fmt.Formatter(formatAir) { |
| 1070 | return .{ .data = .{ .self = self, .inst = inst } }; | 1078 | return .{ .data = .{ .self = self, .inst = inst } }; |
| 1071 | } | 1079 | } |
| 1072 | | 1080 | |
| 1073 | const FormatWipMirData = struct { | 1081 | const FormatWipMirData = struct { |
| 1074 | self: *Self, | 1082 | self: *CodeGen, |
| 1075 | inst: Mir.Inst.Index, | 1083 | inst: Mir.Inst.Index, |
| 1076 | }; | 1084 | }; |
| 1077 | fn formatWipMir( | 1085 | fn formatWipMir( |
| ... | @@ -1192,12 +1200,12 @@ fn formatWipMir( | ... | @@ -1192,12 +1200,12 @@ fn formatWipMir( |
| 1192 | } | 1200 | } |
| 1193 | } | 1201 | } |
| 1194 | } | 1202 | } |
| 1195 | fn fmtWipMir(self: *Self, inst: Mir.Inst.Index) std.fmt.Formatter(formatWipMir) { | 1203 | fn fmtWipMir(self: *CodeGen, inst: Mir.Inst.Index) std.fmt.Formatter(formatWipMir) { |
| 1196 | return .{ .data = .{ .self = self, .inst = inst } }; | 1204 | return .{ .data = .{ .self = self, .inst = inst } }; |
| 1197 | } | 1205 | } |
| 1198 | | 1206 | |
| 1199 | const FormatTrackingData = struct { | 1207 | const FormatTrackingData = struct { |
| 1200 | self: *Self, | 1208 | self: *CodeGen, |
| 1201 | }; | 1209 | }; |
| 1202 | fn formatTracking( | 1210 | fn formatTracking( |
| 1203 | data: FormatTrackingData, | 1211 | data: FormatTrackingData, |
| ... | @@ -1208,26 +1216,26 @@ fn formatTracking( | ... | @@ -1208,26 +1216,26 @@ fn formatTracking( |
| 1208 | var it = data.self.inst_tracking.iterator(); | 1216 | var it = data.self.inst_tracking.iterator(); |
| 1209 | while (it.next()) |entry| try writer.print("\n{} = {}", .{ entry.key_ptr.*, entry.value_ptr.* }); | 1217 | while (it.next()) |entry| try writer.print("\n{} = {}", .{ entry.key_ptr.*, entry.value_ptr.* }); |
| 1210 | } | 1218 | } |
| 1211 | fn fmtTracking(self: *Self) std.fmt.Formatter(formatTracking) { | 1219 | fn fmtTracking(self: *CodeGen) std.fmt.Formatter(formatTracking) { |
| 1212 | return .{ .data = .{ .self = self } }; | 1220 | return .{ .data = .{ .self = self } }; |
| 1213 | } | 1221 | } |
| 1214 | | 1222 | |
| 1215 | fn addInst(self: *Self, inst: Mir.Inst) error{OutOfMemory}!Mir.Inst.Index { | 1223 | fn addInst(self: *CodeGen, inst: Mir.Inst) error{OutOfMemory}!Mir.Inst.Index { |
| 1216 | const gpa = self.gpa; | 1224 | const gpa = self.gpa; |
| 1217 | try self.mir_instructions.ensureUnusedCapacity(gpa, 1); | 1225 | try self.mir_instructions.ensureUnusedCapacity(gpa, 1); |
| 1218 | const result_index: Mir.Inst.Index = @intCast(self.mir_instructions.len); | 1226 | const result_index: Mir.Inst.Index = @intCast(self.mir_instructions.len); |
| 1219 | self.mir_instructions.appendAssumeCapacity(inst); | 1227 | self.mir_instructions.appendAssumeCapacity(inst); |
| 1220 | wip_mir_log.debug("{}", .{self.fmtWipMir(result_index)}); | 1228 | if (inst.ops != .pseudo_dead_none) wip_mir_log.debug("{}", .{self.fmtWipMir(result_index)}); |
| 1221 | return result_index; | 1229 | return result_index; |
| 1222 | } | 1230 | } |
| 1223 | | 1231 | |
| 1224 | fn addExtra(self: *Self, extra: anytype) Allocator.Error!u32 { | 1232 | fn addExtra(self: *CodeGen, extra: anytype) Allocator.Error!u32 { |
| 1225 | const fields = std.meta.fields(@TypeOf(extra)); | 1233 | const fields = std.meta.fields(@TypeOf(extra)); |
| 1226 | try self.mir_extra.ensureUnusedCapacity(self.gpa, fields.len); | 1234 | try self.mir_extra.ensureUnusedCapacity(self.gpa, fields.len); |
| 1227 | return self.addExtraAssumeCapacity(extra); | 1235 | return self.addExtraAssumeCapacity(extra); |
| 1228 | } | 1236 | } |
| 1229 | | 1237 | |
| 1230 | fn addExtraAssumeCapacity(self: *Self, extra: anytype) u32 { | 1238 | fn addExtraAssumeCapacity(self: *CodeGen, extra: anytype) u32 { |
| 1231 | const fields = std.meta.fields(@TypeOf(extra)); | 1239 | const fields = std.meta.fields(@TypeOf(extra)); |
| 1232 | const result: u32 = @intCast(self.mir_extra.items.len); | 1240 | const result: u32 = @intCast(self.mir_extra.items.len); |
| 1233 | inline for (fields) |field| { | 1241 | inline for (fields) |field| { |
| ... | @@ -1241,7 +1249,7 @@ fn addExtraAssumeCapacity(self: *Self, extra: anytype) u32 { | ... | @@ -1241,7 +1249,7 @@ fn addExtraAssumeCapacity(self: *Self, extra: anytype) u32 { |
| 1241 | return result; | 1249 | return result; |
| 1242 | } | 1250 | } |
| 1243 | | 1251 | |
| 1244 | fn asmOps(self: *Self, tag: Mir.Inst.FixedTag, ops: [4]Operand) !void { | 1252 | fn asmOps(self: *CodeGen, tag: Mir.Inst.FixedTag, ops: [4]Operand) !void { |
| 1245 | return switch (ops[0]) { | 1253 | return switch (ops[0]) { |
| 1246 | .none => self.asmOpOnly(tag), | 1254 | .none => self.asmOpOnly(tag), |
| 1247 | .reg => |reg0| switch (ops[1]) { | 1255 | .reg => |reg0| switch (ops[1]) { |
| ... | @@ -1316,7 +1324,7 @@ fn asmOps(self: *Self, tag: Mir.Inst.FixedTag, ops: [4]Operand) !void { | ... | @@ -1316,7 +1324,7 @@ fn asmOps(self: *Self, tag: Mir.Inst.FixedTag, ops: [4]Operand) !void { |
| 1316 | } | 1324 | } |
| 1317 | | 1325 | |
| 1318 | /// A `cc` of `.z_and_np` clobbers `reg2`! | 1326 | /// A `cc` of `.z_and_np` clobbers `reg2`! |
| 1319 | fn asmCmovccRegisterRegister(self: *Self, cc: Condition, reg1: Register, reg2: Register) !void { | 1327 | fn asmCmovccRegisterRegister(self: *CodeGen, cc: Condition, reg1: Register, reg2: Register) !void { |
| 1320 | _ = try self.addInst(.{ | 1328 | _ = try self.addInst(.{ |
| 1321 | .tag = switch (cc) { | 1329 | .tag = switch (cc) { |
| 1322 | else => .cmov, | 1330 | else => .cmov, |
| ... | @@ -1339,7 +1347,7 @@ fn asmCmovccRegisterRegister(self: *Self, cc: Condition, reg1: Register, reg2: R | ... | @@ -1339,7 +1347,7 @@ fn asmCmovccRegisterRegister(self: *Self, cc: Condition, reg1: Register, reg2: R |
| 1339 | } | 1347 | } |
| 1340 | | 1348 | |
| 1341 | /// A `cc` of `.z_and_np` is not supported by this encoding! | 1349 | /// A `cc` of `.z_and_np` is not supported by this encoding! |
| 1342 | fn asmCmovccRegisterMemory(self: *Self, cc: Condition, reg: Register, m: Memory) !void { | 1350 | fn asmCmovccRegisterMemory(self: *CodeGen, cc: Condition, reg: Register, m: Memory) !void { |
| 1343 | _ = try self.addInst(.{ | 1351 | _ = try self.addInst(.{ |
| 1344 | .tag = switch (cc) { | 1352 | .tag = switch (cc) { |
| 1345 | else => .cmov, | 1353 | else => .cmov, |
| ... | @@ -1363,7 +1371,7 @@ fn asmCmovccRegisterMemory(self: *Self, cc: Condition, reg: Register, m: Memory) | ... | @@ -1363,7 +1371,7 @@ fn asmCmovccRegisterMemory(self: *Self, cc: Condition, reg: Register, m: Memory) |
| 1363 | }); | 1371 | }); |
| 1364 | } | 1372 | } |
| 1365 | | 1373 | |
| 1366 | fn asmSetccRegister(self: *Self, cc: Condition, reg: Register) !void { | 1374 | fn asmSetccRegister(self: *CodeGen, cc: Condition, reg: Register) !void { |
| 1367 | _ = try self.addInst(.{ | 1375 | _ = try self.addInst(.{ |
| 1368 | .tag = switch (cc) { | 1376 | .tag = switch (cc) { |
| 1369 | else => .set, | 1377 | else => .set, |
| ... | @@ -1387,7 +1395,7 @@ fn asmSetccRegister(self: *Self, cc: Condition, reg: Register) !void { | ... | @@ -1387,7 +1395,7 @@ fn asmSetccRegister(self: *Self, cc: Condition, reg: Register) !void { |
| 1387 | }); | 1395 | }); |
| 1388 | } | 1396 | } |
| 1389 | | 1397 | |
| 1390 | fn asmSetccMemory(self: *Self, cc: Condition, m: Memory) !void { | 1398 | fn asmSetccMemory(self: *CodeGen, cc: Condition, m: Memory) !void { |
| 1391 | const payload = try self.addExtra(Mir.Memory.encode(m)); | 1399 | const payload = try self.addExtra(Mir.Memory.encode(m)); |
| 1392 | _ = try self.addInst(.{ | 1400 | _ = try self.addInst(.{ |
| 1393 | .tag = switch (cc) { | 1401 | .tag = switch (cc) { |
| ... | @@ -1412,7 +1420,7 @@ fn asmSetccMemory(self: *Self, cc: Condition, m: Memory) !void { | ... | @@ -1412,7 +1420,7 @@ fn asmSetccMemory(self: *Self, cc: Condition, m: Memory) !void { |
| 1412 | }); | 1420 | }); |
| 1413 | } | 1421 | } |
| 1414 | | 1422 | |
| 1415 | fn asmJmpReloc(self: *Self, target: Mir.Inst.Index) !Mir.Inst.Index { | 1423 | fn asmJmpReloc(self: *CodeGen, target: Mir.Inst.Index) !Mir.Inst.Index { |
| 1416 | return self.addInst(.{ | 1424 | return self.addInst(.{ |
| 1417 | .tag = .jmp, | 1425 | .tag = .jmp, |
| 1418 | .ops = .inst, | 1426 | .ops = .inst, |
| ... | @@ -1422,7 +1430,7 @@ fn asmJmpReloc(self: *Self, target: Mir.Inst.Index) !Mir.Inst.Index { | ... | @@ -1422,7 +1430,7 @@ fn asmJmpReloc(self: *Self, target: Mir.Inst.Index) !Mir.Inst.Index { |
| 1422 | }); | 1430 | }); |
| 1423 | } | 1431 | } |
| 1424 | | 1432 | |
| 1425 | fn asmJccReloc(self: *Self, cc: Condition, target: Mir.Inst.Index) !Mir.Inst.Index { | 1433 | fn asmJccReloc(self: *CodeGen, cc: Condition, target: Mir.Inst.Index) !Mir.Inst.Index { |
| 1426 | return self.addInst(.{ | 1434 | return self.addInst(.{ |
| 1427 | .tag = switch (cc) { | 1435 | .tag = switch (cc) { |
| 1428 | else => .j, | 1436 | else => .j, |
| ... | @@ -1443,7 +1451,7 @@ fn asmJccReloc(self: *Self, cc: Condition, target: Mir.Inst.Index) !Mir.Inst.Ind | ... | @@ -1443,7 +1451,7 @@ fn asmJccReloc(self: *Self, cc: Condition, target: Mir.Inst.Index) !Mir.Inst.Ind |
| 1443 | }); | 1451 | }); |
| 1444 | } | 1452 | } |
| 1445 | | 1453 | |
| 1446 | fn asmReloc(self: *Self, tag: Mir.Inst.FixedTag, target: Mir.Inst.Index) !void { | 1454 | fn asmReloc(self: *CodeGen, tag: Mir.Inst.FixedTag, target: Mir.Inst.Index) !void { |
| 1447 | _ = try self.addInst(.{ | 1455 | _ = try self.addInst(.{ |
| 1448 | .tag = tag[1], | 1456 | .tag = tag[1], |
| 1449 | .ops = .inst, | 1457 | .ops = .inst, |
| ... | @@ -1454,7 +1462,7 @@ fn asmReloc(self: *Self, tag: Mir.Inst.FixedTag, target: Mir.Inst.Index) !void { | ... | @@ -1454,7 +1462,7 @@ fn asmReloc(self: *Self, tag: Mir.Inst.FixedTag, target: Mir.Inst.Index) !void { |
| 1454 | }); | 1462 | }); |
| 1455 | } | 1463 | } |
| 1456 | | 1464 | |
| 1457 | fn asmPlaceholder(self: *Self) !Mir.Inst.Index { | 1465 | fn asmPlaceholder(self: *CodeGen) !Mir.Inst.Index { |
| 1458 | return self.addInst(.{ | 1466 | return self.addInst(.{ |
| 1459 | .tag = .pseudo, | 1467 | .tag = .pseudo, |
| 1460 | .ops = .pseudo_dead_none, | 1468 | .ops = .pseudo_dead_none, |
| ... | @@ -1464,7 +1472,7 @@ fn asmPlaceholder(self: *Self) !Mir.Inst.Index { | ... | @@ -1464,7 +1472,7 @@ fn asmPlaceholder(self: *Self) !Mir.Inst.Index { |
| 1464 | | 1472 | |
| 1465 | const MirTagAir = enum { dbg_local }; | 1473 | const MirTagAir = enum { dbg_local }; |
| 1466 | | 1474 | |
| 1467 | fn asmAir(self: *Self, tag: MirTagAir, inst: Air.Inst.Index) !void { | 1475 | fn asmAir(self: *CodeGen, tag: MirTagAir, inst: Air.Inst.Index) !void { |
| 1468 | _ = try self.addInst(.{ | 1476 | _ = try self.addInst(.{ |
| 1469 | .tag = .pseudo, | 1477 | .tag = .pseudo, |
| 1470 | .ops = switch (tag) { | 1478 | .ops = switch (tag) { |
| ... | @@ -1474,7 +1482,7 @@ fn asmAir(self: *Self, tag: MirTagAir, inst: Air.Inst.Index) !void { | ... | @@ -1474,7 +1482,7 @@ fn asmAir(self: *Self, tag: MirTagAir, inst: Air.Inst.Index) !void { |
| 1474 | }); | 1482 | }); |
| 1475 | } | 1483 | } |
| 1476 | | 1484 | |
| 1477 | fn asmAirImmediate(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, imm: Immediate) !void { | 1485 | fn asmAirImmediate(self: *CodeGen, tag: MirTagAir, inst: Air.Inst.Index, imm: Immediate) !void { |
| 1478 | switch (imm) { | 1486 | switch (imm) { |
| 1479 | .signed => |s| _ = try self.addInst(.{ | 1487 | .signed => |s| _ = try self.addInst(.{ |
| 1480 | .tag = .pseudo, | 1488 | .tag = .pseudo, |
| ... | @@ -1528,7 +1536,7 @@ fn asmAirImmediate(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, imm: Immed | ... | @@ -1528,7 +1536,7 @@ fn asmAirImmediate(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, imm: Immed |
| 1528 | } | 1536 | } |
| 1529 | | 1537 | |
| 1530 | fn asmAirRegisterImmediate( | 1538 | fn asmAirRegisterImmediate( |
| 1531 | self: *Self, | 1539 | self: *CodeGen, |
| 1532 | tag: MirTagAir, | 1540 | tag: MirTagAir, |
| 1533 | inst: Air.Inst.Index, | 1541 | inst: Air.Inst.Index, |
| 1534 | reg: Register, | 1542 | reg: Register, |
| ... | @@ -1550,7 +1558,7 @@ fn asmAirRegisterImmediate( | ... | @@ -1550,7 +1558,7 @@ fn asmAirRegisterImmediate( |
| 1550 | } | 1558 | } |
| 1551 | | 1559 | |
| 1552 | fn asmAirFrameAddress( | 1560 | fn asmAirFrameAddress( |
| 1553 | self: *Self, | 1561 | self: *CodeGen, |
| 1554 | tag: MirTagAir, | 1562 | tag: MirTagAir, |
| 1555 | inst: Air.Inst.Index, | 1563 | inst: Air.Inst.Index, |
| 1556 | frame_addr: bits.FrameAddr, | 1564 | frame_addr: bits.FrameAddr, |
| ... | @@ -1567,7 +1575,7 @@ fn asmAirFrameAddress( | ... | @@ -1567,7 +1575,7 @@ fn asmAirFrameAddress( |
| 1567 | }); | 1575 | }); |
| 1568 | } | 1576 | } |
| 1569 | | 1577 | |
| 1570 | fn asmAirMemory(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, m: Memory) !void { | 1578 | fn asmAirMemory(self: *CodeGen, tag: MirTagAir, inst: Air.Inst.Index, m: Memory) !void { |
| 1571 | _ = try self.addInst(.{ | 1579 | _ = try self.addInst(.{ |
| 1572 | .tag = .pseudo, | 1580 | .tag = .pseudo, |
| 1573 | .ops = switch (tag) { | 1581 | .ops = switch (tag) { |
| ... | @@ -1580,7 +1588,7 @@ fn asmAirMemory(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, m: Memory) !v | ... | @@ -1580,7 +1588,7 @@ fn asmAirMemory(self: *Self, tag: MirTagAir, inst: Air.Inst.Index, m: Memory) !v |
| 1580 | }); | 1588 | }); |
| 1581 | } | 1589 | } |
| 1582 | | 1590 | |
| 1583 | fn asmOpOnly(self: *Self, tag: Mir.Inst.FixedTag) !void { | 1591 | fn asmOpOnly(self: *CodeGen, tag: Mir.Inst.FixedTag) !void { |
| 1584 | _ = try self.addInst(.{ | 1592 | _ = try self.addInst(.{ |
| 1585 | .tag = tag[1], | 1593 | .tag = tag[1], |
| 1586 | .ops = .none, | 1594 | .ops = .none, |
| ... | @@ -1590,7 +1598,7 @@ fn asmOpOnly(self: *Self, tag: Mir.Inst.FixedTag) !void { | ... | @@ -1590,7 +1598,7 @@ fn asmOpOnly(self: *Self, tag: Mir.Inst.FixedTag) !void { |
| 1590 | }); | 1598 | }); |
| 1591 | } | 1599 | } |
| 1592 | | 1600 | |
| 1593 | fn asmPseudo(self: *Self, ops: Mir.Inst.Ops) !void { | 1601 | fn asmPseudo(self: *CodeGen, ops: Mir.Inst.Ops) !void { |
| 1594 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and | 1602 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and |
| 1595 | std.mem.endsWith(u8, @tagName(ops), "_none")); | 1603 | std.mem.endsWith(u8, @tagName(ops), "_none")); |
| 1596 | _ = try self.addInst(.{ | 1604 | _ = try self.addInst(.{ |
| ... | @@ -1600,7 +1608,7 @@ fn asmPseudo(self: *Self, ops: Mir.Inst.Ops) !void { | ... | @@ -1600,7 +1608,7 @@ fn asmPseudo(self: *Self, ops: Mir.Inst.Ops) !void { |
| 1600 | }); | 1608 | }); |
| 1601 | } | 1609 | } |
| 1602 | | 1610 | |
| 1603 | fn asmPseudoRegister(self: *Self, ops: Mir.Inst.Ops, reg: Register) !void { | 1611 | fn asmPseudoRegister(self: *CodeGen, ops: Mir.Inst.Ops, reg: Register) !void { |
| 1604 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and | 1612 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and |
| 1605 | std.mem.endsWith(u8, @tagName(ops), "_r")); | 1613 | std.mem.endsWith(u8, @tagName(ops), "_r")); |
| 1606 | _ = try self.addInst(.{ | 1614 | _ = try self.addInst(.{ |
| ... | @@ -1610,7 +1618,7 @@ fn asmPseudoRegister(self: *Self, ops: Mir.Inst.Ops, reg: Register) !void { | ... | @@ -1610,7 +1618,7 @@ fn asmPseudoRegister(self: *Self, ops: Mir.Inst.Ops, reg: Register) !void { |
| 1610 | }); | 1618 | }); |
| 1611 | } | 1619 | } |
| 1612 | | 1620 | |
| 1613 | fn asmPseudoImmediate(self: *Self, ops: Mir.Inst.Ops, imm: Immediate) !void { | 1621 | fn asmPseudoImmediate(self: *CodeGen, ops: Mir.Inst.Ops, imm: Immediate) !void { |
| 1614 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and | 1622 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and |
| 1615 | std.mem.endsWith(u8, @tagName(ops), "_i_s")); | 1623 | std.mem.endsWith(u8, @tagName(ops), "_i_s")); |
| 1616 | _ = try self.addInst(.{ | 1624 | _ = try self.addInst(.{ |
| ... | @@ -1620,7 +1628,7 @@ fn asmPseudoImmediate(self: *Self, ops: Mir.Inst.Ops, imm: Immediate) !void { | ... | @@ -1620,7 +1628,7 @@ fn asmPseudoImmediate(self: *Self, ops: Mir.Inst.Ops, imm: Immediate) !void { |
| 1620 | }); | 1628 | }); |
| 1621 | } | 1629 | } |
| 1622 | | 1630 | |
| 1623 | fn asmPseudoRegisterRegister(self: *Self, ops: Mir.Inst.Ops, reg1: Register, reg2: Register) !void { | 1631 | fn asmPseudoRegisterRegister(self: *CodeGen, ops: Mir.Inst.Ops, reg1: Register, reg2: Register) !void { |
| 1624 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and | 1632 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and |
| 1625 | std.mem.endsWith(u8, @tagName(ops), "_rr")); | 1633 | std.mem.endsWith(u8, @tagName(ops), "_rr")); |
| 1626 | _ = try self.addInst(.{ | 1634 | _ = try self.addInst(.{ |
| ... | @@ -1630,7 +1638,7 @@ fn asmPseudoRegisterRegister(self: *Self, ops: Mir.Inst.Ops, reg1: Register, reg | ... | @@ -1630,7 +1638,7 @@ fn asmPseudoRegisterRegister(self: *Self, ops: Mir.Inst.Ops, reg1: Register, reg |
| 1630 | }); | 1638 | }); |
| 1631 | } | 1639 | } |
| 1632 | | 1640 | |
| 1633 | fn asmPseudoRegisterImmediate(self: *Self, ops: Mir.Inst.Ops, reg: Register, imm: Immediate) !void { | 1641 | fn asmPseudoRegisterImmediate(self: *CodeGen, ops: Mir.Inst.Ops, reg: Register, imm: Immediate) !void { |
| 1634 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and | 1642 | assert(std.mem.startsWith(u8, @tagName(ops), "pseudo_") and |
| 1635 | std.mem.endsWith(u8, @tagName(ops), "_ri_s")); | 1643 | std.mem.endsWith(u8, @tagName(ops), "_ri_s")); |
| 1636 | _ = try self.addInst(.{ | 1644 | _ = try self.addInst(.{ |
| ... | @@ -1640,7 +1648,7 @@ fn asmPseudoRegisterImmediate(self: *Self, ops: Mir.Inst.Ops, reg: Register, imm | ... | @@ -1640,7 +1648,7 @@ fn asmPseudoRegisterImmediate(self: *Self, ops: Mir.Inst.Ops, reg: Register, imm |
| 1640 | }); | 1648 | }); |
| 1641 | } | 1649 | } |
| 1642 | | 1650 | |
| 1643 | fn asmRegister(self: *Self, tag: Mir.Inst.FixedTag, reg: Register) !void { | 1651 | fn asmRegister(self: *CodeGen, tag: Mir.Inst.FixedTag, reg: Register) !void { |
| 1644 | _ = try self.addInst(.{ | 1652 | _ = try self.addInst(.{ |
| 1645 | .tag = tag[1], | 1653 | .tag = tag[1], |
| 1646 | .ops = .r, | 1654 | .ops = .r, |
| ... | @@ -1651,7 +1659,7 @@ fn asmRegister(self: *Self, tag: Mir.Inst.FixedTag, reg: Register) !void { | ... | @@ -1651,7 +1659,7 @@ fn asmRegister(self: *Self, tag: Mir.Inst.FixedTag, reg: Register) !void { |
| 1651 | }); | 1659 | }); |
| 1652 | } | 1660 | } |
| 1653 | | 1661 | |
| 1654 | fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void { | 1662 | fn asmImmediate(self: *CodeGen, tag: Mir.Inst.FixedTag, imm: Immediate) !void { |
| 1655 | _ = try self.addInst(.{ | 1663 | _ = try self.addInst(.{ |
| 1656 | .tag = tag[1], | 1664 | .tag = tag[1], |
| 1657 | .ops = switch (imm) { | 1665 | .ops = switch (imm) { |
| ... | @@ -1676,7 +1684,7 @@ fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void { | ... | @@ -1676,7 +1684,7 @@ fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void { |
| 1676 | }); | 1684 | }); |
| 1677 | } | 1685 | } |
| 1678 | | 1686 | |
| 1679 | fn asmRegisterRegister(self: *Self, tag: Mir.Inst.FixedTag, reg1: Register, reg2: Register) !void { | 1687 | fn asmRegisterRegister(self: *CodeGen, tag: Mir.Inst.FixedTag, reg1: Register, reg2: Register) !void { |
| 1680 | _ = try self.addInst(.{ | 1688 | _ = try self.addInst(.{ |
| 1681 | .tag = tag[1], | 1689 | .tag = tag[1], |
| 1682 | .ops = .rr, | 1690 | .ops = .rr, |
| ... | @@ -1688,7 +1696,7 @@ fn asmRegisterRegister(self: *Self, tag: Mir.Inst.FixedTag, reg1: Register, reg2 | ... | @@ -1688,7 +1696,7 @@ fn asmRegisterRegister(self: *Self, tag: Mir.Inst.FixedTag, reg1: Register, reg2 |
| 1688 | }); | 1696 | }); |
| 1689 | } | 1697 | } |
| 1690 | | 1698 | |
| 1691 | fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm: Immediate) !void { | 1699 | fn asmRegisterImmediate(self: *CodeGen, tag: Mir.Inst.FixedTag, reg: Register, imm: Immediate) !void { |
| 1692 | const ops: Mir.Inst.Ops, const i: u32 = switch (imm) { | 1700 | const ops: Mir.Inst.Ops, const i: u32 = switch (imm) { |
| 1693 | .signed => |s| .{ .ri_s, @bitCast(s) }, | 1701 | .signed => |s| .{ .ri_s, @bitCast(s) }, |
| 1694 | .unsigned => |u| if (std.math.cast(u32, u)) |small| | 1702 | .unsigned => |u| if (std.math.cast(u32, u)) |small| |
| ... | @@ -1709,7 +1717,7 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm: | ... | @@ -1709,7 +1717,7 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm: |
| 1709 | } | 1717 | } |
| 1710 | | 1718 | |
| 1711 | fn asmRegisterRegisterRegister( | 1719 | fn asmRegisterRegisterRegister( |
| 1712 | self: *Self, | 1720 | self: *CodeGen, |
| 1713 | tag: Mir.Inst.FixedTag, | 1721 | tag: Mir.Inst.FixedTag, |
| 1714 | reg1: Register, | 1722 | reg1: Register, |
| 1715 | reg2: Register, | 1723 | reg2: Register, |
| ... | @@ -1728,7 +1736,7 @@ fn asmRegisterRegisterRegister( | ... | @@ -1728,7 +1736,7 @@ fn asmRegisterRegisterRegister( |
| 1728 | } | 1736 | } |
| 1729 | | 1737 | |
| 1730 | fn asmRegisterRegisterRegisterRegister( | 1738 | fn asmRegisterRegisterRegisterRegister( |
| 1731 | self: *Self, | 1739 | self: *CodeGen, |
| 1732 | tag: Mir.Inst.FixedTag, | 1740 | tag: Mir.Inst.FixedTag, |
| 1733 | reg1: Register, | 1741 | reg1: Register, |
| 1734 | reg2: Register, | 1742 | reg2: Register, |
| ... | @@ -1749,7 +1757,7 @@ fn asmRegisterRegisterRegisterRegister( | ... | @@ -1749,7 +1757,7 @@ fn asmRegisterRegisterRegisterRegister( |
| 1749 | } | 1757 | } |
| 1750 | | 1758 | |
| 1751 | fn asmRegisterRegisterRegisterImmediate( | 1759 | fn asmRegisterRegisterRegisterImmediate( |
| 1752 | self: *Self, | 1760 | self: *CodeGen, |
| 1753 | tag: Mir.Inst.FixedTag, | 1761 | tag: Mir.Inst.FixedTag, |
| 1754 | reg1: Register, | 1762 | reg1: Register, |
| 1755 | reg2: Register, | 1763 | reg2: Register, |
| ... | @@ -1774,7 +1782,7 @@ fn asmRegisterRegisterRegisterImmediate( | ... | @@ -1774,7 +1782,7 @@ fn asmRegisterRegisterRegisterImmediate( |
| 1774 | } | 1782 | } |
| 1775 | | 1783 | |
| 1776 | fn asmRegisterRegisterImmediate( | 1784 | fn asmRegisterRegisterImmediate( |
| 1777 | self: *Self, | 1785 | self: *CodeGen, |
| 1778 | tag: Mir.Inst.FixedTag, | 1786 | tag: Mir.Inst.FixedTag, |
| 1779 | reg1: Register, | 1787 | reg1: Register, |
| 1780 | reg2: Register, | 1788 | reg2: Register, |
| ... | @@ -1801,7 +1809,7 @@ fn asmRegisterRegisterImmediate( | ... | @@ -1801,7 +1809,7 @@ fn asmRegisterRegisterImmediate( |
| 1801 | } | 1809 | } |
| 1802 | | 1810 | |
| 1803 | fn asmRegisterRegisterMemory( | 1811 | fn asmRegisterRegisterMemory( |
| 1804 | self: *Self, | 1812 | self: *CodeGen, |
| 1805 | tag: Mir.Inst.FixedTag, | 1813 | tag: Mir.Inst.FixedTag, |
| 1806 | reg1: Register, | 1814 | reg1: Register, |
| 1807 | reg2: Register, | 1815 | reg2: Register, |
| ... | @@ -1820,7 +1828,7 @@ fn asmRegisterRegisterMemory( | ... | @@ -1820,7 +1828,7 @@ fn asmRegisterRegisterMemory( |
| 1820 | } | 1828 | } |
| 1821 | | 1829 | |
| 1822 | fn asmRegisterRegisterMemoryRegister( | 1830 | fn asmRegisterRegisterMemoryRegister( |
| 1823 | self: *Self, | 1831 | self: *CodeGen, |
| 1824 | tag: Mir.Inst.FixedTag, | 1832 | tag: Mir.Inst.FixedTag, |
| 1825 | reg1: Register, | 1833 | reg1: Register, |
| 1826 | reg2: Register, | 1834 | reg2: Register, |
| ... | @@ -1840,7 +1848,7 @@ fn asmRegisterRegisterMemoryRegister( | ... | @@ -1840,7 +1848,7 @@ fn asmRegisterRegisterMemoryRegister( |
| 1840 | }); | 1848 | }); |
| 1841 | } | 1849 | } |
| 1842 | | 1850 | |
| 1843 | fn asmMemory(self: *Self, tag: Mir.Inst.FixedTag, m: Memory) !void { | 1851 | fn asmMemory(self: *CodeGen, tag: Mir.Inst.FixedTag, m: Memory) !void { |
| 1844 | _ = try self.addInst(.{ | 1852 | _ = try self.addInst(.{ |
| 1845 | .tag = tag[1], | 1853 | .tag = tag[1], |
| 1846 | .ops = .m, | 1854 | .ops = .m, |
| ... | @@ -1851,7 +1859,7 @@ fn asmMemory(self: *Self, tag: Mir.Inst.FixedTag, m: Memory) !void { | ... | @@ -1851,7 +1859,7 @@ fn asmMemory(self: *Self, tag: Mir.Inst.FixedTag, m: Memory) !void { |
| 1851 | }); | 1859 | }); |
| 1852 | } | 1860 | } |
| 1853 | | 1861 | |
| 1854 | fn asmRegisterMemory(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, m: Memory) !void { | 1862 | fn asmRegisterMemory(self: *CodeGen, tag: Mir.Inst.FixedTag, reg: Register, m: Memory) !void { |
| 1855 | _ = try self.addInst(.{ | 1863 | _ = try self.addInst(.{ |
| 1856 | .tag = tag[1], | 1864 | .tag = tag[1], |
| 1857 | .ops = .rm, | 1865 | .ops = .rm, |
| ... | @@ -1864,7 +1872,7 @@ fn asmRegisterMemory(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, m: Memo | ... | @@ -1864,7 +1872,7 @@ fn asmRegisterMemory(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, m: Memo |
| 1864 | } | 1872 | } |
| 1865 | | 1873 | |
| 1866 | fn asmRegisterMemoryRegister( | 1874 | fn asmRegisterMemoryRegister( |
| 1867 | self: *Self, | 1875 | self: *CodeGen, |
| 1868 | tag: Mir.Inst.FixedTag, | 1876 | tag: Mir.Inst.FixedTag, |
| 1869 | reg1: Register, | 1877 | reg1: Register, |
| 1870 | m: Memory, | 1878 | m: Memory, |
| ... | @@ -1883,7 +1891,7 @@ fn asmRegisterMemoryRegister( | ... | @@ -1883,7 +1891,7 @@ fn asmRegisterMemoryRegister( |
| 1883 | } | 1891 | } |
| 1884 | | 1892 | |
| 1885 | fn asmRegisterMemoryImmediate( | 1893 | fn asmRegisterMemoryImmediate( |
| 1886 | self: *Self, | 1894 | self: *CodeGen, |
| 1887 | tag: Mir.Inst.FixedTag, | 1895 | tag: Mir.Inst.FixedTag, |
| 1888 | reg: Register, | 1896 | reg: Register, |
| 1889 | m: Memory, | 1897 | m: Memory, |
| ... | @@ -1928,7 +1936,7 @@ fn asmRegisterMemoryImmediate( | ... | @@ -1928,7 +1936,7 @@ fn asmRegisterMemoryImmediate( |
| 1928 | } | 1936 | } |
| 1929 | | 1937 | |
| 1930 | fn asmRegisterRegisterMemoryImmediate( | 1938 | fn asmRegisterRegisterMemoryImmediate( |
| 1931 | self: *Self, | 1939 | self: *CodeGen, |
| 1932 | tag: Mir.Inst.FixedTag, | 1940 | tag: Mir.Inst.FixedTag, |
| 1933 | reg1: Register, | 1941 | reg1: Register, |
| 1934 | reg2: Register, | 1942 | reg2: Register, |
| ... | @@ -1948,7 +1956,7 @@ fn asmRegisterRegisterMemoryImmediate( | ... | @@ -1948,7 +1956,7 @@ fn asmRegisterRegisterMemoryImmediate( |
| 1948 | }); | 1956 | }); |
| 1949 | } | 1957 | } |
| 1950 | | 1958 | |
| 1951 | fn asmMemoryRegister(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, reg: Register) !void { | 1959 | fn asmMemoryRegister(self: *CodeGen, tag: Mir.Inst.FixedTag, m: Memory, reg: Register) !void { |
| 1952 | _ = try self.addInst(.{ | 1960 | _ = try self.addInst(.{ |
| 1953 | .tag = tag[1], | 1961 | .tag = tag[1], |
| 1954 | .ops = .mr, | 1962 | .ops = .mr, |
| ... | @@ -1960,7 +1968,7 @@ fn asmMemoryRegister(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, reg: Regist | ... | @@ -1960,7 +1968,7 @@ fn asmMemoryRegister(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, reg: Regist |
| 1960 | }); | 1968 | }); |
| 1961 | } | 1969 | } |
| 1962 | | 1970 | |
| 1963 | fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immediate) !void { | 1971 | fn asmMemoryImmediate(self: *CodeGen, tag: Mir.Inst.FixedTag, m: Memory, imm: Immediate) !void { |
| 1964 | const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) { | 1972 | const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) { |
| 1965 | .signed => |s| @bitCast(s), | 1973 | .signed => |s| @bitCast(s), |
| 1966 | .unsigned => |u| @intCast(u), | 1974 | .unsigned => |u| @intCast(u), |
| ... | @@ -1982,7 +1990,7 @@ fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immed | ... | @@ -1982,7 +1990,7 @@ fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immed |
| 1982 | } | 1990 | } |
| 1983 | | 1991 | |
| 1984 | fn asmMemoryRegisterRegister( | 1992 | fn asmMemoryRegisterRegister( |
| 1985 | self: *Self, | 1993 | self: *CodeGen, |
| 1986 | tag: Mir.Inst.FixedTag, | 1994 | tag: Mir.Inst.FixedTag, |
| 1987 | m: Memory, | 1995 | m: Memory, |
| 1988 | reg1: Register, | 1996 | reg1: Register, |
| ... | @@ -2001,7 +2009,7 @@ fn asmMemoryRegisterRegister( | ... | @@ -2001,7 +2009,7 @@ fn asmMemoryRegisterRegister( |
| 2001 | } | 2009 | } |
| 2002 | | 2010 | |
| 2003 | fn asmMemoryRegisterImmediate( | 2011 | fn asmMemoryRegisterImmediate( |
| 2004 | self: *Self, | 2012 | self: *CodeGen, |
| 2005 | tag: Mir.Inst.FixedTag, | 2013 | tag: Mir.Inst.FixedTag, |
| 2006 | m: Memory, | 2014 | m: Memory, |
| 2007 | reg: Register, | 2015 | reg: Register, |
| ... | @@ -2019,7 +2027,7 @@ fn asmMemoryRegisterImmediate( | ... | @@ -2019,7 +2027,7 @@ fn asmMemoryRegisterImmediate( |
| 2019 | }); | 2027 | }); |
| 2020 | } | 2028 | } |
| 2021 | | 2029 | |
| 2022 | fn gen(self: *Self) InnerError!void { | 2030 | fn gen(self: *CodeGen) InnerError!void { |
| 2023 | const pt = self.pt; | 2031 | const pt = self.pt; |
| 2024 | const zcu = pt.zcu; | 2032 | const zcu = pt.zcu; |
| 2025 | const fn_info = zcu.typeToFunc(self.fn_type).?; | 2033 | const fn_info = zcu.typeToFunc(self.fn_type).?; |
| ... | @@ -2229,7 +2237,7 @@ fn gen(self: *Self) InnerError!void { | ... | @@ -2229,7 +2237,7 @@ fn gen(self: *Self) InnerError!void { |
| 2229 | }); | 2237 | }); |
| 2230 | } | 2238 | } |
| 2231 | | 2239 | |
| 2232 | fn checkInvariantsAfterAirInst(self: *Self) void { | 2240 | fn checkInvariantsAfterAirInst(self: *CodeGen) void { |
| 2233 | assert(!self.register_manager.lockedRegsExist()); | 2241 | assert(!self.register_manager.lockedRegsExist()); |
| 2234 | | 2242 | |
| 2235 | if (std.debug.runtime_safety) { | 2243 | if (std.debug.runtime_safety) { |
| ... | @@ -2245,13 +2253,13 @@ fn checkInvariantsAfterAirInst(self: *Self) void { | ... | @@ -2245,13 +2253,13 @@ fn checkInvariantsAfterAirInst(self: *Self) void { |
| 2245 | } | 2253 | } |
| 2246 | } | 2254 | } |
| 2247 | | 2255 | |
| 2248 | fn genBodyBlock(self: *Self, body: []const Air.Inst.Index) InnerError!void { | 2256 | fn genBodyBlock(self: *CodeGen, body: []const Air.Inst.Index) InnerError!void { |
| 2249 | try self.asmPseudo(.pseudo_dbg_enter_block_none); | 2257 | try self.asmPseudo(.pseudo_dbg_enter_block_none); |
| 2250 | try self.genBody(body); | 2258 | try self.genBody(body); |
| 2251 | try self.asmPseudo(.pseudo_dbg_leave_block_none); | 2259 | try self.asmPseudo(.pseudo_dbg_leave_block_none); |
| 2252 | } | 2260 | } |
| 2253 | | 2261 | |
| 2254 | fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | 2262 | fn genBody(self: *CodeGen, body: []const Air.Inst.Index) InnerError!void { |
| 2255 | const pt = self.pt; | 2263 | const pt = self.pt; |
| 2256 | const zcu = pt.zcu; | 2264 | const zcu = pt.zcu; |
| 2257 | const ip = &zcu.intern_pool; | 2265 | const ip = &zcu.intern_pool; |
| ... | @@ -2461,15 +2469,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2461,15 +2469,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2461 | try slot.moveTo(inst, self); | 2469 | try slot.moveTo(inst, self); |
| 2462 | }, | 2470 | }, |
| 2463 | .assembly => try self.airAsm(inst), | 2471 | .assembly => try self.airAsm(inst), |
| 2464 | inline .bit_and, .bit_or, .xor => |tag| if (use_old or self.typeOfIndex(inst).abiSize(zcu) > @as( | 2472 | inline .bit_and, .bit_or, .xor => |tag| if (use_old) try self.airBinOp(inst, tag) else { |
| 2465 | u64, | | |
| 2466 | if (!self.typeOfIndex(inst).isVector(zcu)) | | |
| 2467 | 8 | | |
| 2468 | else if (!self.hasFeature(.avx2)) | | |
| 2469 | 16 | | |
| 2470 | else | | |
| 2471 | 32, | | |
| 2472 | )) try self.airBinOp(inst, tag) else { | | |
| 2473 | const bin_op = air_datas[@intFromEnum(inst)].bin_op; | 2473 | const bin_op = air_datas[@intFromEnum(inst)].bin_op; |
| 2474 | var ops = try self.tempsFromOperands(inst, .{ bin_op.lhs, bin_op.rhs }); | 2474 | var ops = try self.tempsFromOperands(inst, .{ bin_op.lhs, bin_op.rhs }); |
| 2475 | try self.spillEflagsIfOccupied(); | 2475 | try self.spillEflagsIfOccupied(); |
| ... | @@ -2481,30 +2481,109 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2481,30 +2481,109 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2481 | }; | 2481 | }; |
| 2482 | var res: [1]Temp = undefined; | 2482 | var res: [1]Temp = undefined; |
| 2483 | try self.select(&res, &.{ &ops[0], &ops[1] }, &.{ | 2483 | try self.select(&res, &.{ &ops[0], &ops[1] }, &.{ |
| 2484 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .ymm, .ymm, .mem }, .features = &.{.avx2} }, | 2484 | .{ |
| 2485 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .ymm, .mem, .ymm }, .commute = .{ 1, 2 }, .features = &.{.avx2} }, | 2485 | .required_features = &.{.avx2}, |
| 2486 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .ymm, .ymm, .ymm }, .features = &.{.avx2} }, | 2486 | .mir_tag = .{ .vp_, mir_tag }, |
| 2487 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .xmm, .xmm, .mem }, .features = &.{.avx} }, | 2487 | .patterns = &.{ |
| 2488 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .xmm, .mem, .xmm }, .commute = .{ 1, 2 }, .features = &.{.avx} }, | 2488 | .{ .ops = &.{ .ymm, .ymm, .mem } }, |
| 2489 | .{ .tag = .{ .vp_, mir_tag }, .ops = &.{ .xmm, .xmm, .xmm }, .features = &.{.avx} }, | 2489 | .{ .ops = &.{ .ymm, .mem, .ymm }, .commute = .{ 1, 2 } }, |
| 2490 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .xmm, .{ .match = 0 }, .mem }, .features = &.{.sse2} }, | 2490 | .{ .ops = &.{ .ymm, .ymm, .ymm } }, |
| 2491 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .xmm, .mem, .{ .match = 0 } }, .features = &.{.sse2} }, | 2491 | }, |
| 2492 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .xmm, .{ .match = 0 }, .xmm }, .features = &.{.sse2} }, | 2492 | }, |
| 2493 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .xmm, .xmm, .{ .match = 0 } }, .features = &.{.sse2} }, | 2493 | .{ |
| 2494 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .mm, .{ .match = 0 }, .mem }, .features = &.{.mmx} }, | 2494 | .required_features = &.{.avx}, |
| 2495 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .mm, .mem, .{ .match = 0 } }, .features = &.{.mmx} }, | 2495 | .mir_tag = .{ .vp_, mir_tag }, |
| 2496 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .mm, .{ .match = 0 }, .mm }, .features = &.{.mmx} }, | 2496 | .patterns = &.{ |
| 2497 | .{ .tag = .{ .p_, mir_tag }, .ops = &.{ .mm, .mm, .{ .match = 0 } }, .features = &.{.mmx} }, | 2497 | .{ .ops = &.{ .xmm, .xmm, .mem } }, |
| 2498 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .mem, .{ .match = 0 }, .simm32 } }, | 2498 | .{ .ops = &.{ .xmm, .mem, .xmm }, .commute = .{ 1, 2 } }, |
| 2499 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .mem, .simm32, .{ .match = 0 } } }, | 2499 | .{ .ops = &.{ .xmm, .xmm, .xmm } }, |
| 2500 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .mem, .{ .match = 0 }, .gpr } }, | 2500 | }, |
| 2501 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .mem, .gpr, .{ .match = 0 } } }, | 2501 | }, |
| 2502 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .{ .match = 0 }, .simm32 } }, | 2502 | .{ |
| 2503 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .simm32, .{ .match = 0 } } }, | 2503 | .required_features = &.{.sse2}, |
| 2504 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .{ .match = 0 }, .mem } }, | 2504 | .mir_tag = .{ .p_, mir_tag }, |
| 2505 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .mem, .{ .match = 0 } } }, | 2505 | .patterns = &.{ |
| 2506 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .{ .match = 0 }, .gpr } }, | 2506 | .{ .ops = &.{ .xmm, .{ .implicit = 0 }, .mem } }, |
| 2507 | .{ .tag = .{ ._, mir_tag }, .ops = &.{ .gpr, .gpr, .{ .match = 0 } } }, | 2507 | .{ .ops = &.{ .xmm, .mem, .{ .implicit = 0 } } }, |
| | 2508 | .{ .ops = &.{ .xmm, .{ .implicit = 0 }, .xmm } }, |
| | 2509 | .{ .ops = &.{ .xmm, .xmm, .{ .implicit = 0 } } }, |
| | 2510 | }, |
| | 2511 | }, |
| | 2512 | .{ |
| | 2513 | .required_features = &.{.mmx}, |
| | 2514 | .mir_tag = .{ .p_, mir_tag }, |
| | 2515 | .patterns = &.{ |
| | 2516 | .{ .ops = &.{ .mm, .{ .implicit = 0 }, .mem } }, |
| | 2517 | .{ .ops = &.{ .mm, .mem, .{ .implicit = 0 } } }, |
| | 2518 | .{ .ops = &.{ .mm, .{ .implicit = 0 }, .mm } }, |
| | 2519 | .{ .ops = &.{ .mm, .mm, .{ .implicit = 0 } } }, |
| | 2520 | }, |
| | 2521 | }, |
| | 2522 | .{ |
| | 2523 | .mir_tag = .{ ._, mir_tag }, |
| | 2524 | .patterns = &.{ |
| | 2525 | .{ .ops = &.{ .mem, .{ .implicit = 0 }, .simm32 } }, |
| | 2526 | .{ .ops = &.{ .mem, .simm32, .{ .implicit = 0 } } }, |
| | 2527 | .{ .ops = &.{ .mem, .{ .implicit = 0 }, .gpr } }, |
| | 2528 | .{ .ops = &.{ .mem, .gpr, .{ .implicit = 0 } } }, |
| | 2529 | .{ .ops = &.{ .gpr, .{ .implicit = 0 }, .simm32 } }, |
| | 2530 | .{ .ops = &.{ .gpr, .simm32, .{ .implicit = 0 } } }, |
| | 2531 | .{ .ops = &.{ .gpr, .{ .implicit = 0 }, .mem } }, |
| | 2532 | .{ .ops = &.{ .gpr, .mem, .{ .implicit = 0 } } }, |
| | 2533 | .{ .ops = &.{ .gpr, .{ .implicit = 0 }, .gpr } }, |
| | 2534 | .{ .ops = &.{ .gpr, .gpr, .{ .implicit = 0 } } }, |
| | 2535 | }, |
| | 2536 | }, |
| | 2537 | |
| | 2538 | .{ |
| | 2539 | .required_features = &.{.avx2}, |
| | 2540 | .loop = .bitwise, |
| | 2541 | .mir_tag = .{ .vp_, mir_tag }, |
| | 2542 | .patterns = &.{ |
| | 2543 | .{ .ops = &.{ .ymm_limb, .{ .explicit = 0 }, .mem_limb } }, |
| | 2544 | .{ .ops = &.{ .ymm_limb, .mem_limb, .{ .explicit = 0 } }, .commute = .{ 1, 2 } }, |
| | 2545 | .{ .ops = &.{ .ymm_limb, .ymm_limb, .mem_limb } }, |
| | 2546 | }, |
| | 2547 | }, |
| | 2548 | .{ |
| | 2549 | .required_features = &.{.avx}, |
| | 2550 | .loop = .bitwise, |
| | 2551 | .mir_tag = .{ .vp_, mir_tag }, |
| | 2552 | .patterns = &.{ |
| | 2553 | .{ .ops = &.{ .xmm_limb, .{ .explicit = 0 }, .mem_limb } }, |
| | 2554 | .{ .ops = &.{ .xmm_limb, .mem_limb, .{ .explicit = 0 } }, .commute = .{ 1, 2 } }, |
| | 2555 | .{ .ops = &.{ .xmm_limb, .xmm_limb, .mem_limb } }, |
| | 2556 | }, |
| | 2557 | }, |
| | 2558 | .{ |
| | 2559 | .required_features = &.{.sse2}, |
| | 2560 | .loop = .bitwise, |
| | 2561 | .mir_tag = .{ .p_, mir_tag }, |
| | 2562 | .patterns = &.{ |
| | 2563 | .{ .ops = &.{ .xmm_limb, .{ .implicit = 0 }, .mem_limb } }, |
| | 2564 | .{ .ops = &.{ .xmm_limb, .mem_limb, .{ .implicit = 0 } } }, |
| | 2565 | }, |
| | 2566 | }, |
| | 2567 | .{ |
| | 2568 | .required_features = &.{.mmx}, |
| | 2569 | .loop = .bitwise, |
| | 2570 | .mir_tag = .{ .p_, mir_tag }, |
| | 2571 | .patterns = &.{ |
| | 2572 | .{ .ops = &.{ .mm_limb, .{ .implicit = 0 }, .mem_limb } }, |
| | 2573 | .{ .ops = &.{ .mm_limb, .mem_limb, .{ .implicit = 0 } } }, |
| | 2574 | }, |
| | 2575 | }, |
| | 2576 | .{ |
| | 2577 | .loop = .bitwise, |
| | 2578 | .mir_tag = .{ ._, mir_tag }, |
| | 2579 | .patterns = &.{ |
| | 2580 | .{ .ops = &.{ .mem_limb, .{ .implicit = 0 }, .gpr_limb } }, |
| | 2581 | .{ .ops = &.{ .mem_limb, .gpr_limb, .{ .implicit = 0 } } }, |
| | 2582 | .{ .ops = &.{ .gpr_limb, .{ .implicit = 0 }, .mem_limb } }, |
| | 2583 | .{ .ops = &.{ .gpr_limb, .mem_limb, .{ .implicit = 0 } } }, |
| | 2584 | .{ .ops = &.{ .gpr_limb, .{ .implicit = 0 }, .gpr_limb } }, |
| | 2585 | }, |
| | 2586 | }, |
| 2508 | }); | 2587 | }); |
| 2509 | if (ops[0].index != res[0].index) try ops[0].die(self); | 2588 | if (ops[0].index != res[0].index) try ops[0].die(self); |
| 2510 | if (ops[1].index != res[0].index) try ops[1].die(self); | 2589 | if (ops[1].index != res[0].index) try ops[1].die(self); |
| ... | @@ -2620,12 +2699,12 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2620,12 +2699,12 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2620 | while (try ops[0].toLea(self)) {} | 2699 | while (try ops[0].toLea(self)) {} |
| 2621 | try self.asmMemoryImmediate( | 2700 | try self.asmMemoryImmediate( |
| 2622 | .{ ._, .cmp }, | 2701 | .{ ._, .cmp }, |
| 2623 | try ops[0].tracking(self).short.deref().mem(self, if (!opt_repr_is_pl) | 2702 | try ops[0].tracking(self).short.deref().mem(self, .{ .size = if (!opt_repr_is_pl) |
| 2624 | .byte | 2703 | .byte |
| 2625 | else if (opt_child_ty.isSlice(zcu)) | 2704 | else if (opt_child_ty.isSlice(zcu)) |
| 2626 | .qword | 2705 | .qword |
| 2627 | else | 2706 | else |
| 2628 | .fromSize(opt_child_abi_size)), | 2707 | .fromSize(opt_child_abi_size) }), |
| 2629 | .u(0), | 2708 | .u(0), |
| 2630 | ); | 2709 | ); |
| 2631 | var is_null = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .e }); | 2710 | var is_null = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .e }); |
| ... | @@ -2643,12 +2722,12 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2643,12 +2722,12 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2643 | while (try ops[0].toLea(self)) {} | 2722 | while (try ops[0].toLea(self)) {} |
| 2644 | try self.asmMemoryImmediate( | 2723 | try self.asmMemoryImmediate( |
| 2645 | .{ ._, .cmp }, | 2724 | .{ ._, .cmp }, |
| 2646 | try ops[0].tracking(self).short.deref().mem(self, if (!opt_repr_is_pl) | 2725 | try ops[0].tracking(self).short.deref().mem(self, .{ .size = if (!opt_repr_is_pl) |
| 2647 | .byte | 2726 | .byte |
| 2648 | else if (opt_child_ty.isSlice(zcu)) | 2727 | else if (opt_child_ty.isSlice(zcu)) |
| 2649 | .qword | 2728 | .qword |
| 2650 | else | 2729 | else |
| 2651 | .fromSize(opt_child_abi_size)), | 2730 | .fromSize(opt_child_abi_size) }), |
| 2652 | .u(0), | 2731 | .u(0), |
| 2653 | ); | 2732 | ); |
| 2654 | var is_non_null = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .ne }); | 2733 | var is_non_null = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .ne }); |
| ... | @@ -2666,7 +2745,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2666,7 +2745,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2666 | while (try ops[0].toLea(self)) {} | 2745 | while (try ops[0].toLea(self)) {} |
| 2667 | try self.asmMemoryImmediate( | 2746 | try self.asmMemoryImmediate( |
| 2668 | .{ ._, .cmp }, | 2747 | .{ ._, .cmp }, |
| 2669 | try ops[0].tracking(self).short.deref().mem(self, self.memSize(eu_err_ty)), | 2748 | try ops[0].tracking(self).short.deref().mem(self, .{ .size = self.memSize(eu_err_ty) }), |
| 2670 | .u(0), | 2749 | .u(0), |
| 2671 | ); | 2750 | ); |
| 2672 | var is_err = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .ne }); | 2751 | var is_err = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .ne }); |
| ... | @@ -2684,7 +2763,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2684,7 +2763,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2684 | while (try ops[0].toLea(self)) {} | 2763 | while (try ops[0].toLea(self)) {} |
| 2685 | try self.asmMemoryImmediate( | 2764 | try self.asmMemoryImmediate( |
| 2686 | .{ ._, .cmp }, | 2765 | .{ ._, .cmp }, |
| 2687 | try ops[0].tracking(self).short.deref().mem(self, self.memSize(eu_err_ty)), | 2766 | try ops[0].tracking(self).short.deref().mem(self, .{ .size = self.memSize(eu_err_ty) }), |
| 2688 | .u(0), | 2767 | .u(0), |
| 2689 | ); | 2768 | ); |
| 2690 | var is_non_err = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .e }); | 2769 | var is_non_err = try self.tempFromValue(self.typeOfIndex(inst), .{ .eflags = .e }); |
| ... | @@ -2950,7 +3029,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { | ... | @@ -2950,7 +3029,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void { |
| 2950 | verbose_tracking_log.debug("{}", .{self.fmtTracking()}); | 3029 | verbose_tracking_log.debug("{}", .{self.fmtTracking()}); |
| 2951 | } | 3030 | } |
| 2952 | | 3031 | |
| 2953 | fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void { | 3032 | fn genLazy(self: *CodeGen, lazy_sym: link.File.LazySymbol) InnerError!void { |
| 2954 | const pt = self.pt; | 3033 | const pt = self.pt; |
| 2955 | const zcu = pt.zcu; | 3034 | const zcu = pt.zcu; |
| 2956 | const ip = &zcu.intern_pool; | 3035 | const ip = &zcu.intern_pool; |
| ... | @@ -3017,7 +3096,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void { | ... | @@ -3017,7 +3096,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void { |
| 3017 | } | 3096 | } |
| 3018 | } | 3097 | } |
| 3019 | | 3098 | |
| 3020 | fn getValue(self: *Self, value: MCValue, inst: ?Air.Inst.Index) !void { | 3099 | fn getValue(self: *CodeGen, value: MCValue, inst: ?Air.Inst.Index) !void { |
| 3021 | for (value.getRegs()) |reg| try self.register_manager.getReg(reg, inst); | 3100 | for (value.getRegs()) |reg| try self.register_manager.getReg(reg, inst); |
| 3022 | switch (value) { | 3101 | switch (value) { |
| 3023 | else => {}, | 3102 | else => {}, |
| ... | @@ -3025,21 +3104,23 @@ fn getValue(self: *Self, value: MCValue, inst: ?Air.Inst.Index) !void { | ... | @@ -3025,21 +3104,23 @@ fn getValue(self: *Self, value: MCValue, inst: ?Air.Inst.Index) !void { |
| 3025 | } | 3104 | } |
| 3026 | } | 3105 | } |
| 3027 | | 3106 | |
| 3028 | fn getValueIfFree(self: *Self, value: MCValue, inst: ?Air.Inst.Index) void { | 3107 | fn getValueIfFree(self: *CodeGen, value: MCValue, inst: ?Air.Inst.Index) void { |
| 3029 | for (value.getRegs()) |reg| if (self.register_manager.isRegFree(reg)) | 3108 | for (value.getRegs()) |reg| if (self.register_manager.isRegFree(reg)) |
| 3030 | self.register_manager.getRegAssumeFree(reg, inst); | 3109 | self.register_manager.getRegAssumeFree(reg, inst); |
| 3031 | } | 3110 | } |
| 3032 | | 3111 | |
| 3033 | fn freeValue(self: *Self, value: MCValue) !void { | 3112 | fn freeReg(self: *CodeGen, reg: Register) !void { |
| | 3113 | self.register_manager.freeReg(reg); |
| | 3114 | if (reg.class() == .x87) try self.asmRegister(.{ .f_, .free }, reg); |
| | 3115 | } |
| | 3116 | |
| | 3117 | fn freeValue(self: *CodeGen, value: MCValue) !void { |
| 3034 | switch (value) { | 3118 | switch (value) { |
| 3035 | .register => |reg| { | 3119 | .register => |reg| try self.freeReg(reg), |
| 3036 | self.register_manager.freeReg(reg); | 3120 | .register_pair => |regs| for (regs) |reg| try self.freeReg(reg), |
| 3037 | if (reg.class() == .x87) try self.asmRegister(.{ .f_, .free }, reg); | 3121 | .register_offset, .indirect => |reg_off| try self.freeReg(reg_off.reg), |
| 3038 | }, | | |
| 3039 | .register_pair => |regs| for (regs) |reg| self.register_manager.freeReg(reg), | | |
| 3040 | .register_offset => |reg_off| self.register_manager.freeReg(reg_off.reg), | | |
| 3041 | .register_overflow => |reg_ov| { | 3122 | .register_overflow => |reg_ov| { |
| 3042 | self.register_manager.freeReg(reg_ov.reg); | 3123 | try self.freeReg(reg_ov.reg); |
| 3043 | self.eflags_inst = null; | 3124 | self.eflags_inst = null; |
| 3044 | }, | 3125 | }, |
| 3045 | .eflags => self.eflags_inst = null, | 3126 | .eflags => self.eflags_inst = null, |
| ... | @@ -3047,16 +3128,16 @@ fn freeValue(self: *Self, value: MCValue) !void { | ... | @@ -3047,16 +3128,16 @@ fn freeValue(self: *Self, value: MCValue) !void { |
| 3047 | } | 3128 | } |
| 3048 | } | 3129 | } |
| 3049 | | 3130 | |
| 3050 | fn feed(self: *Self, bt: *Liveness.BigTomb, operand: Air.Inst.Ref) !void { | 3131 | fn feed(self: *CodeGen, bt: *Liveness.BigTomb, operand: Air.Inst.Ref) !void { |
| 3051 | if (bt.feed()) if (operand.toIndex()) |inst| try self.processDeath(inst); | 3132 | if (bt.feed()) if (operand.toIndex()) |inst| try self.processDeath(inst); |
| 3052 | } | 3133 | } |
| 3053 | | 3134 | |
| 3054 | /// Asserts there is already capacity to insert into top branch inst_table. | 3135 | /// Asserts there is already capacity to insert into top branch inst_table. |
| 3055 | fn processDeath(self: *Self, inst: Air.Inst.Index) !void { | 3136 | fn processDeath(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3056 | try self.inst_tracking.getPtr(inst).?.die(self, inst); | 3137 | try self.inst_tracking.getPtr(inst).?.die(self, inst); |
| 3057 | } | 3138 | } |
| 3058 | | 3139 | |
| 3059 | fn finishAirResult(self: *Self, inst: Air.Inst.Index, result: MCValue) void { | 3140 | fn finishAirResult(self: *CodeGen, inst: Air.Inst.Index, result: MCValue) void { |
| 3060 | if (self.liveness.isUnused(inst) and self.air.instructions.items(.tag)[@intFromEnum(inst)] != .arg) switch (result) { | 3141 | if (self.liveness.isUnused(inst) and self.air.instructions.items(.tag)[@intFromEnum(inst)] != .arg) switch (result) { |
| 3061 | .none, .dead, .unreach => {}, | 3142 | .none, .dead, .unreach => {}, |
| 3062 | else => unreachable, // Why didn't the result die? | 3143 | else => unreachable, // Why didn't the result die? |
| ... | @@ -3071,7 +3152,7 @@ fn finishAirResult(self: *Self, inst: Air.Inst.Index, result: MCValue) void { | ... | @@ -3071,7 +3152,7 @@ fn finishAirResult(self: *Self, inst: Air.Inst.Index, result: MCValue) void { |
| 3071 | } | 3152 | } |
| 3072 | | 3153 | |
| 3073 | fn finishAir( | 3154 | fn finishAir( |
| 3074 | self: *Self, | 3155 | self: *CodeGen, |
| 3075 | inst: Air.Inst.Index, | 3156 | inst: Air.Inst.Index, |
| 3076 | result: MCValue, | 3157 | result: MCValue, |
| 3077 | operands: [Liveness.bpi - 1]Air.Inst.Ref, | 3158 | operands: [Liveness.bpi - 1]Air.Inst.Ref, |
| ... | @@ -3092,7 +3173,7 @@ const FrameLayout = struct { | ... | @@ -3092,7 +3173,7 @@ const FrameLayout = struct { |
| 3092 | }; | 3173 | }; |
| 3093 | | 3174 | |
| 3094 | fn setFrameLoc( | 3175 | fn setFrameLoc( |
| 3095 | self: *Self, | 3176 | self: *CodeGen, |
| 3096 | frame_index: FrameIndex, | 3177 | frame_index: FrameIndex, |
| 3097 | base: Register, | 3178 | base: Register, |
| 3098 | offset: *i32, | 3179 | offset: *i32, |
| ... | @@ -3107,7 +3188,7 @@ fn setFrameLoc( | ... | @@ -3107,7 +3188,7 @@ fn setFrameLoc( |
| 3107 | offset.* += self.frame_allocs.items(.abi_size)[frame_i]; | 3188 | offset.* += self.frame_allocs.items(.abi_size)[frame_i]; |
| 3108 | } | 3189 | } |
| 3109 | | 3190 | |
| 3110 | fn computeFrameLayout(self: *Self, cc: std.builtin.CallingConvention) !FrameLayout { | 3191 | fn computeFrameLayout(self: *CodeGen, cc: std.builtin.CallingConvention) !FrameLayout { |
| 3111 | const frame_allocs_len = self.frame_allocs.len; | 3192 | const frame_allocs_len = self.frame_allocs.len; |
| 3112 | try self.frame_locs.resize(self.gpa, frame_allocs_len); | 3193 | try self.frame_locs.resize(self.gpa, frame_allocs_len); |
| 3113 | const stack_frame_order = try self.gpa.alloc(FrameIndex, frame_allocs_len - FrameIndex.named_count); | 3194 | const stack_frame_order = try self.gpa.alloc(FrameIndex, frame_allocs_len - FrameIndex.named_count); |
| ... | @@ -3173,16 +3254,16 @@ fn computeFrameLayout(self: *Self, cc: std.builtin.CallingConvention) !FrameLayo | ... | @@ -3173,16 +3254,16 @@ fn computeFrameLayout(self: *Self, cc: std.builtin.CallingConvention) !FrameLayo |
| 3173 | }; | 3254 | }; |
| 3174 | } | 3255 | } |
| 3175 | | 3256 | |
| 3176 | fn getFrameAddrAlignment(self: *Self, frame_addr: bits.FrameAddr) InternPool.Alignment { | 3257 | fn getFrameAddrAlignment(self: *CodeGen, frame_addr: bits.FrameAddr) InternPool.Alignment { |
| 3177 | const alloc_align = self.frame_allocs.get(@intFromEnum(frame_addr.index)).abi_align; | 3258 | const alloc_align = self.frame_allocs.get(@intFromEnum(frame_addr.index)).abi_align; |
| 3178 | return @enumFromInt(@min(@intFromEnum(alloc_align), @ctz(frame_addr.off))); | 3259 | return @enumFromInt(@min(@intFromEnum(alloc_align), @ctz(frame_addr.off))); |
| 3179 | } | 3260 | } |
| 3180 | | 3261 | |
| 3181 | fn getFrameAddrSize(self: *Self, frame_addr: bits.FrameAddr) u32 { | 3262 | fn getFrameAddrSize(self: *CodeGen, frame_addr: bits.FrameAddr) u32 { |
| 3182 | return self.frame_allocs.get(@intFromEnum(frame_addr.index)).abi_size - @as(u31, @intCast(frame_addr.off)); | 3263 | return self.frame_allocs.get(@intFromEnum(frame_addr.index)).abi_size - @as(u31, @intCast(frame_addr.off)); |
| 3183 | } | 3264 | } |
| 3184 | | 3265 | |
| 3185 | fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex { | 3266 | fn allocFrameIndex(self: *CodeGen, alloc: FrameAlloc) !FrameIndex { |
| 3186 | const frame_allocs_slice = self.frame_allocs.slice(); | 3267 | const frame_allocs_slice = self.frame_allocs.slice(); |
| 3187 | const frame_size = frame_allocs_slice.items(.abi_size); | 3268 | const frame_size = frame_allocs_slice.items(.abi_size); |
| 3188 | const frame_align = frame_allocs_slice.items(.abi_align); | 3269 | const frame_align = frame_allocs_slice.items(.abi_align); |
| ... | @@ -3205,7 +3286,7 @@ fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex { | ... | @@ -3205,7 +3286,7 @@ fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex { |
| 3205 | } | 3286 | } |
| 3206 | | 3287 | |
| 3207 | /// Use a pointer instruction as the basis for allocating stack memory. | 3288 | /// Use a pointer instruction as the basis for allocating stack memory. |
| 3208 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !FrameIndex { | 3289 | fn allocMemPtr(self: *CodeGen, inst: Air.Inst.Index) !FrameIndex { |
| 3209 | const pt = self.pt; | 3290 | const pt = self.pt; |
| 3210 | const zcu = pt.zcu; | 3291 | const zcu = pt.zcu; |
| 3211 | const ptr_ty = self.typeOfIndex(inst); | 3292 | const ptr_ty = self.typeOfIndex(inst); |
| ... | @@ -3218,15 +3299,15 @@ fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !FrameIndex { | ... | @@ -3218,15 +3299,15 @@ fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !FrameIndex { |
| 3218 | })); | 3299 | })); |
| 3219 | } | 3300 | } |
| 3220 | | 3301 | |
| 3221 | fn allocRegOrMem(self: *Self, inst: Air.Inst.Index, reg_ok: bool) !MCValue { | 3302 | fn allocRegOrMem(self: *CodeGen, inst: Air.Inst.Index, reg_ok: bool) !MCValue { |
| 3222 | return self.allocRegOrMemAdvanced(self.typeOfIndex(inst), inst, reg_ok); | 3303 | return self.allocRegOrMemAdvanced(self.typeOfIndex(inst), inst, reg_ok); |
| 3223 | } | 3304 | } |
| 3224 | | 3305 | |
| 3225 | fn allocTempRegOrMem(self: *Self, elem_ty: Type, reg_ok: bool) !MCValue { | 3306 | fn allocTempRegOrMem(self: *CodeGen, elem_ty: Type, reg_ok: bool) !MCValue { |
| 3226 | return self.allocRegOrMemAdvanced(elem_ty, null, reg_ok); | 3307 | return self.allocRegOrMemAdvanced(elem_ty, null, reg_ok); |
| 3227 | } | 3308 | } |
| 3228 | | 3309 | |
| 3229 | fn allocRegOrMemAdvanced(self: *Self, ty: Type, inst: ?Air.Inst.Index, reg_ok: bool) !MCValue { | 3310 | fn allocRegOrMemAdvanced(self: *CodeGen, ty: Type, inst: ?Air.Inst.Index, reg_ok: bool) !MCValue { |
| 3230 | const pt = self.pt; | 3311 | const pt = self.pt; |
| 3231 | const zcu = pt.zcu; | 3312 | const zcu = pt.zcu; |
| 3232 | const abi_size = std.math.cast(u32, ty.abiSize(zcu)) orelse { | 3313 | const abi_size = std.math.cast(u32, ty.abiSize(zcu)) orelse { |
| ... | @@ -3260,7 +3341,7 @@ fn allocRegOrMemAdvanced(self: *Self, ty: Type, inst: ?Air.Inst.Index, reg_ok: b | ... | @@ -3260,7 +3341,7 @@ fn allocRegOrMemAdvanced(self: *Self, ty: Type, inst: ?Air.Inst.Index, reg_ok: b |
| 3260 | return .{ .load_frame = .{ .index = frame_index } }; | 3341 | return .{ .load_frame = .{ .index = frame_index } }; |
| 3261 | } | 3342 | } |
| 3262 | | 3343 | |
| 3263 | fn regClassForType(self: *Self, ty: Type) Register.Class { | 3344 | fn regClassForType(self: *CodeGen, ty: Type) Register.Class { |
| 3264 | const pt = self.pt; | 3345 | const pt = self.pt; |
| 3265 | const zcu = pt.zcu; | 3346 | const zcu = pt.zcu; |
| 3266 | return switch (ty.zigTypeTag(zcu)) { | 3347 | return switch (ty.zigTypeTag(zcu)) { |
| ... | @@ -3289,7 +3370,7 @@ fn regSetForRegClass(rc: Register.Class) RegisterManager.RegisterBitSet { | ... | @@ -3289,7 +3370,7 @@ fn regSetForRegClass(rc: Register.Class) RegisterManager.RegisterBitSet { |
| 3289 | }; | 3370 | }; |
| 3290 | } | 3371 | } |
| 3291 | | 3372 | |
| 3292 | fn regSetForType(self: *Self, ty: Type) RegisterManager.RegisterBitSet { | 3373 | fn regSetForType(self: *CodeGen, ty: Type) RegisterManager.RegisterBitSet { |
| 3293 | return regSetForRegClass(self.regClassForType(ty)); | 3374 | return regSetForRegClass(self.regClassForType(ty)); |
| 3294 | } | 3375 | } |
| 3295 | | 3376 | |
| ... | @@ -3301,14 +3382,14 @@ const State = struct { | ... | @@ -3301,14 +3382,14 @@ const State = struct { |
| 3301 | scope_generation: u32, | 3382 | scope_generation: u32, |
| 3302 | }; | 3383 | }; |
| 3303 | | 3384 | |
| 3304 | fn initRetroactiveState(self: *Self) State { | 3385 | fn initRetroactiveState(self: *CodeGen) State { |
| 3305 | var state: State = undefined; | 3386 | var state: State = undefined; |
| 3306 | state.inst_tracking_len = @intCast(self.inst_tracking.count()); | 3387 | state.inst_tracking_len = @intCast(self.inst_tracking.count()); |
| 3307 | state.scope_generation = self.scope_generation; | 3388 | state.scope_generation = self.scope_generation; |
| 3308 | return state; | 3389 | return state; |
| 3309 | } | 3390 | } |
| 3310 | | 3391 | |
| 3311 | fn saveRetroactiveState(self: *Self, state: *State) !void { | 3392 | fn saveRetroactiveState(self: *CodeGen, state: *State) !void { |
| 3312 | try self.spillEflagsIfOccupied(); | 3393 | try self.spillEflagsIfOccupied(); |
| 3313 | const free_registers = self.register_manager.free_registers; | 3394 | const free_registers = self.register_manager.free_registers; |
| 3314 | var it = free_registers.iterator(.{ .kind = .unset }); | 3395 | var it = free_registers.iterator(.{ .kind = .unset }); |
| ... | @@ -3320,13 +3401,13 @@ fn saveRetroactiveState(self: *Self, state: *State) !void { | ... | @@ -3320,13 +3401,13 @@ fn saveRetroactiveState(self: *Self, state: *State) !void { |
| 3320 | state.free_registers = free_registers; | 3401 | state.free_registers = free_registers; |
| 3321 | } | 3402 | } |
| 3322 | | 3403 | |
| 3323 | fn saveState(self: *Self) !State { | 3404 | fn saveState(self: *CodeGen) !State { |
| 3324 | var state = self.initRetroactiveState(); | 3405 | var state = self.initRetroactiveState(); |
| 3325 | try self.saveRetroactiveState(&state); | 3406 | try self.saveRetroactiveState(&state); |
| 3326 | return state; | 3407 | return state; |
| 3327 | } | 3408 | } |
| 3328 | | 3409 | |
| 3329 | fn restoreState(self: *Self, state: State, deaths: []const Air.Inst.Index, comptime opts: struct { | 3410 | fn restoreState(self: *CodeGen, state: State, deaths: []const Air.Inst.Index, comptime opts: struct { |
| 3330 | emit_instructions: bool, | 3411 | emit_instructions: bool, |
| 3331 | update_tracking: bool, | 3412 | update_tracking: bool, |
| 3332 | resurrect: bool, | 3413 | resurrect: bool, |
| ... | @@ -3414,7 +3495,7 @@ fn restoreState(self: *Self, state: State, deaths: []const Air.Inst.Index, compt | ... | @@ -3414,7 +3495,7 @@ fn restoreState(self: *Self, state: State, deaths: []const Air.Inst.Index, compt |
| 3414 | } | 3495 | } |
| 3415 | } | 3496 | } |
| 3416 | | 3497 | |
| 3417 | pub fn spillInstruction(self: *Self, reg: Register, inst: Air.Inst.Index) !void { | 3498 | pub fn spillInstruction(self: *CodeGen, reg: Register, inst: Air.Inst.Index) !void { |
| 3418 | const tracking = self.inst_tracking.getPtr(inst) orelse return; | 3499 | const tracking = self.inst_tracking.getPtr(inst) orelse return; |
| 3419 | for (tracking.getRegs()) |tracked_reg| { | 3500 | for (tracking.getRegs()) |tracked_reg| { |
| 3420 | if (tracked_reg.id() == reg.id()) break; | 3501 | if (tracked_reg.id() == reg.id()) break; |
| ... | @@ -3423,7 +3504,7 @@ pub fn spillInstruction(self: *Self, reg: Register, inst: Air.Inst.Index) !void | ... | @@ -3423,7 +3504,7 @@ pub fn spillInstruction(self: *Self, reg: Register, inst: Air.Inst.Index) !void |
| 3423 | try tracking.trackSpill(self, inst); | 3504 | try tracking.trackSpill(self, inst); |
| 3424 | } | 3505 | } |
| 3425 | | 3506 | |
| 3426 | pub fn spillEflagsIfOccupied(self: *Self) !void { | 3507 | pub fn spillEflagsIfOccupied(self: *CodeGen) !void { |
| 3427 | if (self.eflags_inst) |inst| { | 3508 | if (self.eflags_inst) |inst| { |
| 3428 | self.eflags_inst = null; | 3509 | self.eflags_inst = null; |
| 3429 | const tracking = self.inst_tracking.getPtr(inst).?; | 3510 | const tracking = self.inst_tracking.getPtr(inst).?; |
| ... | @@ -3433,7 +3514,7 @@ pub fn spillEflagsIfOccupied(self: *Self) !void { | ... | @@ -3433,7 +3514,7 @@ pub fn spillEflagsIfOccupied(self: *Self) !void { |
| 3433 | } | 3514 | } |
| 3434 | } | 3515 | } |
| 3435 | | 3516 | |
| 3436 | pub fn spillCallerPreservedRegs(self: *Self, cc: std.builtin.CallingConvention) !void { | 3517 | pub fn spillCallerPreservedRegs(self: *CodeGen, cc: std.builtin.CallingConvention) !void { |
| 3437 | switch (cc) { | 3518 | switch (cc) { |
| 3438 | .x86_64_sysv => try self.spillRegisters(abi.getCallerPreservedRegs(.{ .x86_64_sysv = .{} })), | 3519 | .x86_64_sysv => try self.spillRegisters(abi.getCallerPreservedRegs(.{ .x86_64_sysv = .{} })), |
| 3439 | .x86_64_win => try self.spillRegisters(abi.getCallerPreservedRegs(.{ .x86_64_win = .{} })), | 3520 | .x86_64_win => try self.spillRegisters(abi.getCallerPreservedRegs(.{ .x86_64_win = .{} })), |
| ... | @@ -3441,14 +3522,14 @@ pub fn spillCallerPreservedRegs(self: *Self, cc: std.builtin.CallingConvention) | ... | @@ -3441,14 +3522,14 @@ pub fn spillCallerPreservedRegs(self: *Self, cc: std.builtin.CallingConvention) |
| 3441 | } | 3522 | } |
| 3442 | } | 3523 | } |
| 3443 | | 3524 | |
| 3444 | pub fn spillRegisters(self: *Self, comptime registers: []const Register) !void { | 3525 | pub fn spillRegisters(self: *CodeGen, comptime registers: []const Register) !void { |
| 3445 | inline for (registers) |reg| try self.register_manager.getKnownReg(reg, null); | 3526 | inline for (registers) |reg| try self.register_manager.getKnownReg(reg, null); |
| 3446 | } | 3527 | } |
| 3447 | | 3528 | |
| 3448 | /// Copies a value to a register without tracking the register. The register is not considered | 3529 | /// Copies a value to a register without tracking the register. The register is not considered |
| 3449 | /// allocated. A second call to `copyToTmpRegister` may return the same register. | 3530 | /// allocated. A second call to `copyToTmpRegister` may return the same register. |
| 3450 | /// This can have a side effect of spilling instructions to the stack to free up a register. | 3531 | /// This can have a side effect of spilling instructions to the stack to free up a register. |
| 3451 | fn copyToTmpRegister(self: *Self, ty: Type, mcv: MCValue) !Register { | 3532 | fn copyToTmpRegister(self: *CodeGen, ty: Type, mcv: MCValue) !Register { |
| 3452 | const reg = try self.register_manager.allocReg(null, self.regSetForType(ty)); | 3533 | const reg = try self.register_manager.allocReg(null, self.regSetForType(ty)); |
| 3453 | try self.genSetReg(reg, ty, mcv, .{}); | 3534 | try self.genSetReg(reg, ty, mcv, .{}); |
| 3454 | return reg; | 3535 | return reg; |
| ... | @@ -3459,7 +3540,7 @@ fn copyToTmpRegister(self: *Self, ty: Type, mcv: MCValue) !Register { | ... | @@ -3459,7 +3540,7 @@ fn copyToTmpRegister(self: *Self, ty: Type, mcv: MCValue) !Register { |
| 3459 | /// This can have a side effect of spilling instructions to the stack to free up a register. | 3540 | /// This can have a side effect of spilling instructions to the stack to free up a register. |
| 3460 | /// WARNING make sure that the allocated register matches the returned MCValue from an instruction! | 3541 | /// WARNING make sure that the allocated register matches the returned MCValue from an instruction! |
| 3461 | fn copyToRegisterWithInstTracking( | 3542 | fn copyToRegisterWithInstTracking( |
| 3462 | self: *Self, | 3543 | self: *CodeGen, |
| 3463 | reg_owner: Air.Inst.Index, | 3544 | reg_owner: Air.Inst.Index, |
| 3464 | ty: Type, | 3545 | ty: Type, |
| 3465 | mcv: MCValue, | 3546 | mcv: MCValue, |
| ... | @@ -3469,12 +3550,12 @@ fn copyToRegisterWithInstTracking( | ... | @@ -3469,12 +3550,12 @@ fn copyToRegisterWithInstTracking( |
| 3469 | return MCValue{ .register = reg }; | 3550 | return MCValue{ .register = reg }; |
| 3470 | } | 3551 | } |
| 3471 | | 3552 | |
| 3472 | fn airAlloc(self: *Self, inst: Air.Inst.Index) !void { | 3553 | fn airAlloc(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3473 | const result = MCValue{ .lea_frame = .{ .index = try self.allocMemPtr(inst) } }; | 3554 | const result = MCValue{ .lea_frame = .{ .index = try self.allocMemPtr(inst) } }; |
| 3474 | return self.finishAir(inst, result, .{ .none, .none, .none }); | 3555 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 3475 | } | 3556 | } |
| 3476 | | 3557 | |
| 3477 | fn airRetPtr(self: *Self, inst: Air.Inst.Index) !void { | 3558 | fn airRetPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3478 | const result: MCValue = switch (self.ret_mcv.long) { | 3559 | const result: MCValue = switch (self.ret_mcv.long) { |
| 3479 | else => unreachable, | 3560 | else => unreachable, |
| 3480 | .none => .{ .lea_frame = .{ .index = try self.allocMemPtr(inst) } }, | 3561 | .none => .{ .lea_frame = .{ .index = try self.allocMemPtr(inst) } }, |
| ... | @@ -3490,7 +3571,7 @@ fn airRetPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3490,7 +3571,7 @@ fn airRetPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 3490 | return self.finishAir(inst, result, .{ .none, .none, .none }); | 3571 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 3491 | } | 3572 | } |
| 3492 | | 3573 | |
| 3493 | fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { | 3574 | fn airFptrunc(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3494 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 3575 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 3495 | const dst_ty = self.typeOfIndex(inst); | 3576 | const dst_ty = self.typeOfIndex(inst); |
| 3496 | const dst_bits = dst_ty.floatBits(self.target.*); | 3577 | const dst_bits = dst_ty.floatBits(self.target.*); |
| ... | @@ -3562,7 +3643,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3562,7 +3643,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 3562 | .{ .v_ss, .cvtsd2 }, | 3643 | .{ .v_ss, .cvtsd2 }, |
| 3563 | dst_reg, | 3644 | dst_reg, |
| 3564 | dst_reg, | 3645 | dst_reg, |
| 3565 | try src_mcv.mem(self, .qword), | 3646 | try src_mcv.mem(self, .{ .size = .qword }), |
| 3566 | ) else try self.asmRegisterRegisterRegister( | 3647 | ) else try self.asmRegisterRegisterRegister( |
| 3567 | .{ .v_ss, .cvtsd2 }, | 3648 | .{ .v_ss, .cvtsd2 }, |
| 3568 | dst_reg, | 3649 | dst_reg, |
| ... | @@ -3574,7 +3655,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3574,7 +3655,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 3574 | ) else if (src_mcv.isMemory()) try self.asmRegisterMemory( | 3655 | ) else if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 3575 | .{ ._ss, .cvtsd2 }, | 3656 | .{ ._ss, .cvtsd2 }, |
| 3576 | dst_reg, | 3657 | dst_reg, |
| 3577 | try src_mcv.mem(self, .qword), | 3658 | try src_mcv.mem(self, .{ .size = .qword }), |
| 3578 | ) else try self.asmRegisterRegister( | 3659 | ) else try self.asmRegisterRegister( |
| 3579 | .{ ._ss, .cvtsd2 }, | 3660 | .{ ._ss, .cvtsd2 }, |
| 3580 | dst_reg, | 3661 | dst_reg, |
| ... | @@ -3589,7 +3670,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3589,7 +3670,7 @@ fn airFptrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 3589 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 3670 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 3590 | } | 3671 | } |
| 3591 | | 3672 | |
| 3592 | fn airFpext(self: *Self, inst: Air.Inst.Index) !void { | 3673 | fn airFpext(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3593 | const pt = self.pt; | 3674 | const pt = self.pt; |
| 3594 | const zcu = pt.zcu; | 3675 | const zcu = pt.zcu; |
| 3595 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 3676 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -3674,7 +3755,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3674,7 +3755,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { |
| 3674 | .{ .v_sd, .cvtss2 }, | 3755 | .{ .v_sd, .cvtss2 }, |
| 3675 | dst_alias, | 3756 | dst_alias, |
| 3676 | dst_alias, | 3757 | dst_alias, |
| 3677 | try src_mcv.mem(self, self.memSize(src_ty)), | 3758 | try src_mcv.mem(self, .{ .size = self.memSize(src_ty) }), |
| 3678 | ) else try self.asmRegisterRegisterRegister( | 3759 | ) else try self.asmRegisterRegisterRegister( |
| 3679 | .{ .v_sd, .cvtss2 }, | 3760 | .{ .v_sd, .cvtss2 }, |
| 3680 | dst_alias, | 3761 | dst_alias, |
| ... | @@ -3687,7 +3768,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3687,7 +3768,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { |
| 3687 | 2...4 => if (src_mcv.isMemory()) try self.asmRegisterMemory( | 3768 | 2...4 => if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 3688 | .{ .v_pd, .cvtps2 }, | 3769 | .{ .v_pd, .cvtps2 }, |
| 3689 | dst_alias, | 3770 | dst_alias, |
| 3690 | try src_mcv.mem(self, self.memSize(src_ty)), | 3771 | try src_mcv.mem(self, .{ .size = self.memSize(src_ty) }), |
| 3691 | ) else try self.asmRegisterRegister( | 3772 | ) else try self.asmRegisterRegister( |
| 3692 | .{ .v_pd, .cvtps2 }, | 3773 | .{ .v_pd, .cvtps2 }, |
| 3693 | dst_alias, | 3774 | dst_alias, |
| ... | @@ -3704,7 +3785,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3704,7 +3785,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { |
| 3704 | else => break :result null, | 3785 | else => break :result null, |
| 3705 | }, | 3786 | }, |
| 3706 | dst_alias, | 3787 | dst_alias, |
| 3707 | try src_mcv.mem(self, self.memSize(src_ty)), | 3788 | try src_mcv.mem(self, .{ .size = self.memSize(src_ty) }), |
| 3708 | ) else try self.asmRegisterRegister( | 3789 | ) else try self.asmRegisterRegister( |
| 3709 | switch (vec_len) { | 3790 | switch (vec_len) { |
| 3710 | 1 => .{ ._sd, .cvtss2 }, | 3791 | 1 => .{ ._sd, .cvtss2 }, |
| ... | @@ -3725,7 +3806,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3725,7 +3806,7 @@ fn airFpext(self: *Self, inst: Air.Inst.Index) !void { |
| 3725 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 3806 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 3726 | } | 3807 | } |
| 3727 | | 3808 | |
| 3728 | fn airIntCast(self: *Self, inst: Air.Inst.Index) !void { | 3809 | fn airIntCast(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3729 | const pt = self.pt; | 3810 | const pt = self.pt; |
| 3730 | const zcu = pt.zcu; | 3811 | const zcu = pt.zcu; |
| 3731 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 3812 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -3841,7 +3922,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3841,7 +3922,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void { |
| 3841 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 3922 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 3842 | mir_tag, | 3923 | mir_tag, |
| 3843 | dst_alias, | 3924 | dst_alias, |
| 3844 | try src_mcv.mem(self, self.memSize(src_ty)), | 3925 | try src_mcv.mem(self, .{ .size = self.memSize(src_ty) }), |
| 3845 | ) else try self.asmRegisterRegister( | 3926 | ) else try self.asmRegisterRegister( |
| 3846 | mir_tag, | 3927 | mir_tag, |
| 3847 | dst_alias, | 3928 | dst_alias, |
| ... | @@ -3984,7 +4065,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -3984,7 +4065,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void { |
| 3984 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 4065 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 3985 | } | 4066 | } |
| 3986 | | 4067 | |
| 3987 | fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { | 4068 | fn airTrunc(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 3988 | const pt = self.pt; | 4069 | const pt = self.pt; |
| 3989 | const zcu = pt.zcu; | 4070 | const zcu = pt.zcu; |
| 3990 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 4071 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -4080,7 +4161,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4080,7 +4161,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 4080 | .{ .vp_, .@"and" }, | 4161 | .{ .vp_, .@"and" }, |
| 4081 | dst_alias, | 4162 | dst_alias, |
| 4082 | dst_alias, | 4163 | dst_alias, |
| 4083 | try splat_addr_mcv.deref().mem(self, .fromSize(splat_abi_size)), | 4164 | try splat_addr_mcv.deref().mem(self, .{ .size = .fromSize(splat_abi_size) }), |
| 4084 | ); | 4165 | ); |
| 4085 | if (src_abi_size > 16) { | 4166 | if (src_abi_size > 16) { |
| 4086 | const temp_reg = try self.register_manager.allocReg(null, abi.RegisterClass.sse); | 4167 | const temp_reg = try self.register_manager.allocReg(null, abi.RegisterClass.sse); |
| ... | @@ -4104,7 +4185,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4104,7 +4185,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 4104 | try self.asmRegisterMemory( | 4185 | try self.asmRegisterMemory( |
| 4105 | .{ .p_, .@"and" }, | 4186 | .{ .p_, .@"and" }, |
| 4106 | dst_alias, | 4187 | dst_alias, |
| 4107 | try splat_addr_mcv.deref().mem(self, .fromSize(splat_abi_size)), | 4188 | try splat_addr_mcv.deref().mem(self, .{ .size = .fromSize(splat_abi_size) }), |
| 4108 | ); | 4189 | ); |
| 4109 | try self.asmRegisterRegister(mir_tag, dst_alias, dst_alias); | 4190 | try self.asmRegisterRegister(mir_tag, dst_alias, dst_alias); |
| 4110 | } | 4191 | } |
| ... | @@ -4130,7 +4211,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4130,7 +4211,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 4130 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 4211 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 4131 | } | 4212 | } |
| 4132 | | 4213 | |
| 4133 | fn airIntFromBool(self: *Self, inst: Air.Inst.Index) !void { | 4214 | fn airIntFromBool(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4134 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 4215 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 4135 | const ty = self.typeOfIndex(inst); | 4216 | const ty = self.typeOfIndex(inst); |
| 4136 | | 4217 | |
| ... | @@ -4143,7 +4224,7 @@ fn airIntFromBool(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4143,7 +4224,7 @@ fn airIntFromBool(self: *Self, inst: Air.Inst.Index) !void { |
| 4143 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); | 4224 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); |
| 4144 | } | 4225 | } |
| 4145 | | 4226 | |
| 4146 | fn airSlice(self: *Self, inst: Air.Inst.Index) !void { | 4227 | fn airSlice(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4147 | const zcu = self.pt.zcu; | 4228 | const zcu = self.pt.zcu; |
| 4148 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 4229 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 4149 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; | 4230 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| ... | @@ -4167,13 +4248,13 @@ fn airSlice(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4167,13 +4248,13 @@ fn airSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 4167 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 4248 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4168 | } | 4249 | } |
| 4169 | | 4250 | |
| 4170 | fn airUnOp(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | 4251 | fn airUnOp(self: *CodeGen, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 4171 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 4252 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 4172 | const dst_mcv = try self.genUnOp(inst, tag, ty_op.operand); | 4253 | const dst_mcv = try self.genUnOp(inst, tag, ty_op.operand); |
| 4173 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 4254 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 4174 | } | 4255 | } |
| 4175 | | 4256 | |
| 4176 | fn airBinOp(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | 4257 | fn airBinOp(self: *CodeGen, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 4177 | const pt = self.pt; | 4258 | const pt = self.pt; |
| 4178 | const zcu = pt.zcu; | 4259 | const zcu = pt.zcu; |
| 4179 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 4260 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -4208,14 +4289,14 @@ fn airBinOp(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | ... | @@ -4208,14 +4289,14 @@ fn airBinOp(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 4208 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); | 4289 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4209 | } | 4290 | } |
| 4210 | | 4291 | |
| 4211 | fn airPtrArithmetic(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | 4292 | fn airPtrArithmetic(self: *CodeGen, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 4212 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 4293 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 4213 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; | 4294 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 4214 | const dst_mcv = try self.genBinOp(inst, tag, bin_op.lhs, bin_op.rhs); | 4295 | const dst_mcv = try self.genBinOp(inst, tag, bin_op.lhs, bin_op.rhs); |
| 4215 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); | 4296 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4216 | } | 4297 | } |
| 4217 | | 4298 | |
| 4218 | fn activeIntBits(self: *Self, dst_air: Air.Inst.Ref) u16 { | 4299 | fn activeIntBits(self: *CodeGen, dst_air: Air.Inst.Ref) u16 { |
| 4219 | const pt = self.pt; | 4300 | const pt = self.pt; |
| 4220 | const zcu = pt.zcu; | 4301 | const zcu = pt.zcu; |
| 4221 | const air_tag = self.air.instructions.items(.tag); | 4302 | const air_tag = self.air.instructions.items(.tag); |
| ... | @@ -4250,7 +4331,7 @@ fn activeIntBits(self: *Self, dst_air: Air.Inst.Ref) u16 { | ... | @@ -4250,7 +4331,7 @@ fn activeIntBits(self: *Self, dst_air: Air.Inst.Ref) u16 { |
| 4250 | return dst_info.bits; | 4331 | return dst_info.bits; |
| 4251 | } | 4332 | } |
| 4252 | | 4333 | |
| 4253 | fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { | 4334 | fn airMulDivBinOp(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4254 | const pt = self.pt; | 4335 | const pt = self.pt; |
| 4255 | const zcu = pt.zcu; | 4336 | const zcu = pt.zcu; |
| 4256 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 4337 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -4314,7 +4395,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4314,7 +4395,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { |
| 4314 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( | 4395 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 4315 | .{ ._, .mov }, | 4396 | .{ ._, .mov }, |
| 4316 | tmp_reg, | 4397 | tmp_reg, |
| 4317 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .qword), | 4398 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 4318 | ) else try self.asmRegisterRegister( | 4399 | ) else try self.asmRegisterRegister( |
| 4319 | .{ ._, .mov }, | 4400 | .{ ._, .mov }, |
| 4320 | tmp_reg, | 4401 | tmp_reg, |
| ... | @@ -4338,7 +4419,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4338,7 +4419,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { |
| 4338 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( | 4419 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 4339 | .{ ._, .xor }, | 4420 | .{ ._, .xor }, |
| 4340 | tmp_reg, | 4421 | tmp_reg, |
| 4341 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .qword), | 4422 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 4342 | ) else try self.asmRegisterRegister( | 4423 | ) else try self.asmRegisterRegister( |
| 4343 | .{ ._, .xor }, | 4424 | .{ ._, .xor }, |
| 4344 | tmp_reg, | 4425 | tmp_reg, |
| ... | @@ -4441,12 +4522,12 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4441,12 +4522,12 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { |
| 4441 | try self.asmRegisterMemory( | 4522 | try self.asmRegisterMemory( |
| 4442 | .{ ._, .add }, | 4523 | .{ ._, .add }, |
| 4443 | tmp_regs[0], | 4524 | tmp_regs[0], |
| 4444 | try mat_rhs_mcv.mem(self, .qword), | 4525 | try mat_rhs_mcv.mem(self, .{ .size = .qword }), |
| 4445 | ); | 4526 | ); |
| 4446 | try self.asmRegisterMemory( | 4527 | try self.asmRegisterMemory( |
| 4447 | .{ ._, .adc }, | 4528 | .{ ._, .adc }, |
| 4448 | tmp_regs[1], | 4529 | tmp_regs[1], |
| 4449 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .qword), | 4530 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 4450 | ); | 4531 | ); |
| 4451 | } else for ( | 4532 | } else for ( |
| 4452 | [_]Mir.Inst.Tag{ .add, .adc }, | 4533 | [_]Mir.Inst.Tag{ .add, .adc }, |
| ... | @@ -4476,7 +4557,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4476,7 +4557,7 @@ fn airMulDivBinOp(self: *Self, inst: Air.Inst.Index) !void { |
| 4476 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 4557 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4477 | } | 4558 | } |
| 4478 | | 4559 | |
| 4479 | fn airAddSat(self: *Self, inst: Air.Inst.Index) !void { | 4560 | fn airAddSat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4480 | const pt = self.pt; | 4561 | const pt = self.pt; |
| 4481 | const zcu = pt.zcu; | 4562 | const zcu = pt.zcu; |
| 4482 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 4563 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -4577,7 +4658,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4577,7 +4658,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4577 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); | 4658 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4578 | } | 4659 | } |
| 4579 | | 4660 | |
| 4580 | fn airSubSat(self: *Self, inst: Air.Inst.Index) !void { | 4661 | fn airSubSat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4581 | const pt = self.pt; | 4662 | const pt = self.pt; |
| 4582 | const zcu = pt.zcu; | 4663 | const zcu = pt.zcu; |
| 4583 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 4664 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -4671,7 +4752,7 @@ fn airSubSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4671,7 +4752,7 @@ fn airSubSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4671 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); | 4752 | return self.finishAir(inst, dst_mcv, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4672 | } | 4753 | } |
| 4673 | | 4754 | |
| 4674 | fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { | 4755 | fn airMulSat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4675 | const pt = self.pt; | 4756 | const pt = self.pt; |
| 4676 | const zcu = pt.zcu; | 4757 | const zcu = pt.zcu; |
| 4677 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 4758 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -4715,7 +4796,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4715,7 +4796,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4715 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( | 4796 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 4716 | .{ ._, .mov }, | 4797 | .{ ._, .mov }, |
| 4717 | tmp_reg, | 4798 | tmp_reg, |
| 4718 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .qword), | 4799 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 4719 | ) else try self.asmRegisterRegister( | 4800 | ) else try self.asmRegisterRegister( |
| 4720 | .{ ._, .mov }, | 4801 | .{ ._, .mov }, |
| 4721 | tmp_reg, | 4802 | tmp_reg, |
| ... | @@ -4739,7 +4820,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4739,7 +4820,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4739 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( | 4820 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 4740 | .{ ._, .xor }, | 4821 | .{ ._, .xor }, |
| 4741 | tmp_reg, | 4822 | tmp_reg, |
| 4742 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .qword), | 4823 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 4743 | ) else try self.asmRegisterRegister( | 4824 | ) else try self.asmRegisterRegister( |
| 4744 | .{ ._, .xor }, | 4825 | .{ ._, .xor }, |
| 4745 | tmp_reg, | 4826 | tmp_reg, |
| ... | @@ -4748,7 +4829,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4748,7 +4829,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4748 | | 4829 | |
| 4749 | try self.asmRegisterImmediate(.{ ._r, .sa }, tmp_reg, .u(63)); | 4830 | try self.asmRegisterImmediate(.{ ._r, .sa }, tmp_reg, .u(63)); |
| 4750 | try self.asmRegister(.{ ._, .not }, tmp_reg); | 4831 | try self.asmRegister(.{ ._, .not }, tmp_reg); |
| 4751 | try self.asmMemoryImmediate(.{ ._, .cmp }, try overflow.mem(self, .dword), .s(0)); | 4832 | try self.asmMemoryImmediate(.{ ._, .cmp }, try overflow.mem(self, .{ .size = .dword }), .s(0)); |
| 4752 | try self.freeValue(overflow); | 4833 | try self.freeValue(overflow); |
| 4753 | try self.asmCmovccRegisterRegister(.ne, dst_mcv.register_pair[0], tmp_reg); | 4834 | try self.asmCmovccRegisterRegister(.ne, dst_mcv.register_pair[0], tmp_reg); |
| 4754 | try self.asmRegisterImmediate(.{ ._c, .bt }, tmp_reg, .u(63)); | 4835 | try self.asmRegisterImmediate(.{ ._c, .bt }, tmp_reg, .u(63)); |
| ... | @@ -4818,7 +4899,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4818,7 +4899,7 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void { |
| 4818 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 4899 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4819 | } | 4900 | } |
| 4820 | | 4901 | |
| 4821 | fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | 4902 | fn airAddSubWithOverflow(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4822 | const pt = self.pt; | 4903 | const pt = self.pt; |
| 4823 | const zcu = pt.zcu; | 4904 | const zcu = pt.zcu; |
| 4824 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 4905 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -4883,7 +4964,7 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4883,7 +4964,7 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 4883 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 4964 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 4884 | } | 4965 | } |
| 4885 | | 4966 | |
| 4886 | fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | 4967 | fn airShlWithOverflow(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 4887 | const pt = self.pt; | 4968 | const pt = self.pt; |
| 4888 | const zcu = pt.zcu; | 4969 | const zcu = pt.zcu; |
| 4889 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 4970 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -4961,7 +5042,7 @@ fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -4961,7 +5042,7 @@ fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 4961 | } | 5042 | } |
| 4962 | | 5043 | |
| 4963 | fn genSetFrameTruncatedOverflowCompare( | 5044 | fn genSetFrameTruncatedOverflowCompare( |
| 4964 | self: *Self, | 5045 | self: *CodeGen, |
| 4965 | tuple_ty: Type, | 5046 | tuple_ty: Type, |
| 4966 | frame_index: FrameIndex, | 5047 | frame_index: FrameIndex, |
| 4967 | src_mcv: MCValue, | 5048 | src_mcv: MCValue, |
| ... | @@ -5039,7 +5120,7 @@ fn genSetFrameTruncatedOverflowCompare( | ... | @@ -5039,7 +5120,7 @@ fn genSetFrameTruncatedOverflowCompare( |
| 5039 | ); | 5120 | ); |
| 5040 | } | 5121 | } |
| 5041 | | 5122 | |
| 5042 | fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | 5123 | fn airMulWithOverflow(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5043 | const pt = self.pt; | 5124 | const pt = self.pt; |
| 5044 | const zcu = pt.zcu; | 5125 | const zcu = pt.zcu; |
| 5045 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 5126 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -5214,7 +5295,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5214,7 +5295,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5214 | ); | 5295 | ); |
| 5215 | try self.asmMemoryImmediate( | 5296 | try self.asmMemoryImmediate( |
| 5216 | .{ ._, .cmp }, | 5297 | .{ ._, .cmp }, |
| 5217 | try overflow.mem(self, self.memSize(Type.c_int)), | 5298 | try overflow.mem(self, .{ .size = self.memSize(Type.c_int) }), |
| 5218 | .s(0), | 5299 | .s(0), |
| 5219 | ); | 5300 | ); |
| 5220 | try self.genSetMem( | 5301 | try self.genSetMem( |
| ... | @@ -5270,7 +5351,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5270,7 +5351,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5270 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( | 5351 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 5271 | .{ ._, .mov }, | 5352 | .{ ._, .mov }, |
| 5272 | .rax, | 5353 | .rax, |
| 5273 | try mat_lhs_mcv.mem(self, .qword), | 5354 | try mat_lhs_mcv.mem(self, .{ .size = .qword }), |
| 5274 | ) else try self.asmRegisterRegister( | 5355 | ) else try self.asmRegisterRegister( |
| 5275 | .{ ._, .mov }, | 5356 | .{ ._, .mov }, |
| 5276 | .rax, | 5357 | .rax, |
| ... | @@ -5279,7 +5360,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5279,7 +5360,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5279 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( | 5360 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 5280 | .{ ._, .mov }, | 5361 | .{ ._, .mov }, |
| 5281 | tmp_regs[0], | 5362 | tmp_regs[0], |
| 5282 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .qword), | 5363 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 5283 | ) else try self.asmRegisterRegister( | 5364 | ) else try self.asmRegisterRegister( |
| 5284 | .{ ._, .mov }, | 5365 | .{ ._, .mov }, |
| 5285 | tmp_regs[0], | 5366 | tmp_regs[0], |
| ... | @@ -5290,7 +5371,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5290,7 +5371,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5290 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_regs[0], .rax); | 5371 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_regs[0], .rax); |
| 5291 | try self.asmSetccRegister(.o, tmp_regs[2].to8()); | 5372 | try self.asmSetccRegister(.o, tmp_regs[2].to8()); |
| 5292 | if (mat_rhs_mcv.isMemory()) | 5373 | if (mat_rhs_mcv.isMemory()) |
| 5293 | try self.asmMemory(.{ ._, .mul }, try mat_rhs_mcv.mem(self, .qword)) | 5374 | try self.asmMemory(.{ ._, .mul }, try mat_rhs_mcv.mem(self, .{ .size = .qword })) |
| 5294 | else | 5375 | else |
| 5295 | try self.asmRegister(.{ ._, .mul }, mat_rhs_mcv.register_pair[0]); | 5376 | try self.asmRegister(.{ ._, .mul }, mat_rhs_mcv.register_pair[0]); |
| 5296 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_regs[0]); | 5377 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_regs[0]); |
| ... | @@ -5299,7 +5380,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5299,7 +5380,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5299 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( | 5380 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 5300 | .{ ._, .mov }, | 5381 | .{ ._, .mov }, |
| 5301 | tmp_regs[0], | 5382 | tmp_regs[0], |
| 5302 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .qword), | 5383 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 5303 | ) else try self.asmRegisterRegister( | 5384 | ) else try self.asmRegisterRegister( |
| 5304 | .{ ._, .mov }, | 5385 | .{ ._, .mov }, |
| 5305 | tmp_regs[0], | 5386 | tmp_regs[0], |
| ... | @@ -5316,7 +5397,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5316,7 +5397,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5316 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( | 5397 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 5317 | .{ .i_, .mul }, | 5398 | .{ .i_, .mul }, |
| 5318 | tmp_regs[0], | 5399 | tmp_regs[0], |
| 5319 | try mat_rhs_mcv.mem(self, .qword), | 5400 | try mat_rhs_mcv.mem(self, .{ .size = .qword }), |
| 5320 | ) else try self.asmRegisterRegister( | 5401 | ) else try self.asmRegisterRegister( |
| 5321 | .{ .i_, .mul }, | 5402 | .{ .i_, .mul }, |
| 5322 | tmp_regs[0], | 5403 | tmp_regs[0], |
| ... | @@ -5416,7 +5497,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5416,7 +5497,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 5416 | /// Generates signed or unsigned integer multiplication/division. | 5497 | /// Generates signed or unsigned integer multiplication/division. |
| 5417 | /// Clobbers .rax and .rdx registers. | 5498 | /// Clobbers .rax and .rdx registers. |
| 5418 | /// Quotient is saved in .rax and remainder in .rdx. | 5499 | /// Quotient is saved in .rax and remainder in .rdx. |
| 5419 | fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue, rhs: MCValue) !void { | 5500 | fn genIntMulDivOpMir(self: *CodeGen, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue, rhs: MCValue) !void { |
| 5420 | const pt = self.pt; | 5501 | const pt = self.pt; |
| 5421 | const abi_size: u32 = @intCast(ty.abiSize(pt.zcu)); | 5502 | const abi_size: u32 = @intCast(ty.abiSize(pt.zcu)); |
| 5422 | const bit_size: u32 = @intCast(self.regBitSize(ty)); | 5503 | const bit_size: u32 = @intCast(self.regBitSize(ty)); |
| ... | @@ -5455,7 +5536,10 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue | ... | @@ -5455,7 +5536,10 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue |
| 5455 | }; | 5536 | }; |
| 5456 | switch (mat_rhs) { | 5537 | switch (mat_rhs) { |
| 5457 | .register => |reg| try self.asmRegister(tag, registerAlias(reg, abi_size)), | 5538 | .register => |reg| try self.asmRegister(tag, registerAlias(reg, abi_size)), |
| 5458 | .memory, .indirect, .load_frame => try self.asmMemory(tag, try mat_rhs.mem(self, .fromSize(abi_size))), | 5539 | .memory, .indirect, .load_frame => try self.asmMemory( |
| | 5540 | tag, |
| | 5541 | try mat_rhs.mem(self, .{ .size = .fromSize(abi_size) }), |
| | 5542 | ), |
| 5459 | else => unreachable, | 5543 | else => unreachable, |
| 5460 | } | 5544 | } |
| 5461 | if (tag[1] == .div and bit_size == 8) try self.asmRegisterRegister(.{ ._, .mov }, .dl, .ah); | 5545 | if (tag[1] == .div and bit_size == 8) try self.asmRegisterRegister(.{ ._, .mov }, .dl, .ah); |
| ... | @@ -5463,7 +5547,7 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue | ... | @@ -5463,7 +5547,7 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue |
| 5463 | | 5547 | |
| 5464 | /// Always returns a register. | 5548 | /// Always returns a register. |
| 5465 | /// Clobbers .rax and .rdx registers. | 5549 | /// Clobbers .rax and .rdx registers. |
| 5466 | fn genInlineIntDivFloor(self: *Self, ty: Type, lhs: MCValue, rhs: MCValue) !MCValue { | 5550 | fn genInlineIntDivFloor(self: *CodeGen, ty: Type, lhs: MCValue, rhs: MCValue) !MCValue { |
| 5467 | const pt = self.pt; | 5551 | const pt = self.pt; |
| 5468 | const zcu = pt.zcu; | 5552 | const zcu = pt.zcu; |
| 5469 | const abi_size: u32 = @intCast(ty.abiSize(zcu)); | 5553 | const abi_size: u32 = @intCast(ty.abiSize(zcu)); |
| ... | @@ -5516,7 +5600,7 @@ fn genInlineIntDivFloor(self: *Self, ty: Type, lhs: MCValue, rhs: MCValue) !MCVa | ... | @@ -5516,7 +5600,7 @@ fn genInlineIntDivFloor(self: *Self, ty: Type, lhs: MCValue, rhs: MCValue) !MCVa |
| 5516 | return MCValue{ .register = divisor }; | 5600 | return MCValue{ .register = divisor }; |
| 5517 | } | 5601 | } |
| 5518 | | 5602 | |
| 5519 | fn airShlShrBinOp(self: *Self, inst: Air.Inst.Index) !void { | 5603 | fn airShlShrBinOp(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5520 | const pt = self.pt; | 5604 | const pt = self.pt; |
| 5521 | const zcu = pt.zcu; | 5605 | const zcu = pt.zcu; |
| 5522 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 5606 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -5784,14 +5868,14 @@ fn airShlShrBinOp(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5784,14 +5868,14 @@ fn airShlShrBinOp(self: *Self, inst: Air.Inst.Index) !void { |
| 5784 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 5868 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 5785 | } | 5869 | } |
| 5786 | | 5870 | |
| 5787 | fn airShlSat(self: *Self, inst: Air.Inst.Index) !void { | 5871 | fn airShlSat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5788 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 5872 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| 5789 | _ = bin_op; | 5873 | _ = bin_op; |
| 5790 | return self.fail("TODO implement shl_sat for {}", .{self.target.cpu.arch}); | 5874 | return self.fail("TODO implement shl_sat for {}", .{self.target.cpu.arch}); |
| 5791 | //return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 5875 | //return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 5792 | } | 5876 | } |
| 5793 | | 5877 | |
| 5794 | fn airOptionalPayload(self: *Self, inst: Air.Inst.Index) !void { | 5878 | fn airOptionalPayload(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5795 | const zcu = self.pt.zcu; | 5879 | const zcu = self.pt.zcu; |
| 5796 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 5880 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 5797 | const result: MCValue = result: { | 5881 | const result: MCValue = result: { |
| ... | @@ -5824,7 +5908,7 @@ fn airOptionalPayload(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5824,7 +5908,7 @@ fn airOptionalPayload(self: *Self, inst: Air.Inst.Index) !void { |
| 5824 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 5908 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 5825 | } | 5909 | } |
| 5826 | | 5910 | |
| 5827 | fn airOptionalPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { | 5911 | fn airOptionalPayloadPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5828 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 5912 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 5829 | | 5913 | |
| 5830 | const dst_ty = self.typeOfIndex(inst); | 5914 | const dst_ty = self.typeOfIndex(inst); |
| ... | @@ -5837,7 +5921,7 @@ fn airOptionalPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5837,7 +5921,7 @@ fn airOptionalPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 5837 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 5921 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 5838 | } | 5922 | } |
| 5839 | | 5923 | |
| 5840 | fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { | 5924 | fn airOptionalPayloadPtrSet(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5841 | const pt = self.pt; | 5925 | const pt = self.pt; |
| 5842 | const zcu = pt.zcu; | 5926 | const zcu = pt.zcu; |
| 5843 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 5927 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -5878,7 +5962,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5878,7 +5962,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { |
| 5878 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 5962 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 5879 | } | 5963 | } |
| 5880 | | 5964 | |
| 5881 | fn airUnwrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { | 5965 | fn airUnwrapErrUnionErr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5882 | const pt = self.pt; | 5966 | const pt = self.pt; |
| 5883 | const zcu = pt.zcu; | 5967 | const zcu = pt.zcu; |
| 5884 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 5968 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -5923,7 +6007,7 @@ fn airUnwrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5923,7 +6007,7 @@ fn airUnwrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { |
| 5923 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 6007 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 5924 | } | 6008 | } |
| 5925 | | 6009 | |
| 5926 | fn airUnwrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { | 6010 | fn airUnwrapErrUnionPayload(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5927 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6011 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 5928 | const operand_ty = self.typeOf(ty_op.operand); | 6012 | const operand_ty = self.typeOf(ty_op.operand); |
| 5929 | const operand = try self.resolveInst(ty_op.operand); | 6013 | const operand = try self.resolveInst(ty_op.operand); |
| ... | @@ -5932,7 +6016,7 @@ fn airUnwrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5932,7 +6016,7 @@ fn airUnwrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { |
| 5932 | } | 6016 | } |
| 5933 | | 6017 | |
| 5934 | // *(E!T) -> E | 6018 | // *(E!T) -> E |
| 5935 | fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void { | 6019 | fn airUnwrapErrUnionErrPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5936 | const pt = self.pt; | 6020 | const pt = self.pt; |
| 5937 | const zcu = pt.zcu; | 6021 | const zcu = pt.zcu; |
| 5938 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6022 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -5972,7 +6056,7 @@ fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5972,7 +6056,7 @@ fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 5972 | } | 6056 | } |
| 5973 | | 6057 | |
| 5974 | // *(E!T) -> *T | 6058 | // *(E!T) -> *T |
| 5975 | fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { | 6059 | fn airUnwrapErrUnionPayloadPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5976 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6060 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 5977 | const operand_ty = self.typeOf(ty_op.operand); | 6061 | const operand_ty = self.typeOf(ty_op.operand); |
| 5978 | const operand = try self.resolveInst(ty_op.operand); | 6062 | const operand = try self.resolveInst(ty_op.operand); |
| ... | @@ -5980,7 +6064,7 @@ fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -5980,7 +6064,7 @@ fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 5980 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 6064 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 5981 | } | 6065 | } |
| 5982 | | 6066 | |
| 5983 | fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { | 6067 | fn airErrUnionPayloadPtrSet(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 5984 | const pt = self.pt; | 6068 | const pt = self.pt; |
| 5985 | const zcu = pt.zcu; | 6069 | const zcu = pt.zcu; |
| 5986 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6070 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -6037,7 +6121,7 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6037,7 +6121,7 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { |
| 6037 | } | 6121 | } |
| 6038 | | 6122 | |
| 6039 | fn genUnwrapErrUnionPayloadMir( | 6123 | fn genUnwrapErrUnionPayloadMir( |
| 6040 | self: *Self, | 6124 | self: *CodeGen, |
| 6041 | maybe_inst: ?Air.Inst.Index, | 6125 | maybe_inst: ?Air.Inst.Index, |
| 6042 | err_union_ty: Type, | 6126 | err_union_ty: Type, |
| 6043 | err_union: MCValue, | 6127 | err_union: MCValue, |
| ... | @@ -6087,7 +6171,7 @@ fn genUnwrapErrUnionPayloadMir( | ... | @@ -6087,7 +6171,7 @@ fn genUnwrapErrUnionPayloadMir( |
| 6087 | } | 6171 | } |
| 6088 | | 6172 | |
| 6089 | fn genUnwrapErrUnionPayloadPtrMir( | 6173 | fn genUnwrapErrUnionPayloadPtrMir( |
| 6090 | self: *Self, | 6174 | self: *CodeGen, |
| 6091 | maybe_inst: ?Air.Inst.Index, | 6175 | maybe_inst: ?Air.Inst.Index, |
| 6092 | ptr_ty: Type, | 6176 | ptr_ty: Type, |
| 6093 | ptr_mcv: MCValue, | 6177 | ptr_mcv: MCValue, |
| ... | @@ -6110,23 +6194,23 @@ fn genUnwrapErrUnionPayloadPtrMir( | ... | @@ -6110,23 +6194,23 @@ fn genUnwrapErrUnionPayloadPtrMir( |
| 6110 | return result; | 6194 | return result; |
| 6111 | } | 6195 | } |
| 6112 | | 6196 | |
| 6113 | fn airErrReturnTrace(self: *Self, inst: Air.Inst.Index) !void { | 6197 | fn airErrReturnTrace(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6114 | _ = inst; | 6198 | _ = inst; |
| 6115 | return self.fail("TODO implement airErrReturnTrace for {}", .{self.target.cpu.arch}); | 6199 | return self.fail("TODO implement airErrReturnTrace for {}", .{self.target.cpu.arch}); |
| 6116 | //return self.finishAir(inst, result, .{ .none, .none, .none }); | 6200 | //return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 6117 | } | 6201 | } |
| 6118 | | 6202 | |
| 6119 | fn airSetErrReturnTrace(self: *Self, inst: Air.Inst.Index) !void { | 6203 | fn airSetErrReturnTrace(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6120 | _ = inst; | 6204 | _ = inst; |
| 6121 | return self.fail("TODO implement airSetErrReturnTrace for {}", .{self.target.cpu.arch}); | 6205 | return self.fail("TODO implement airSetErrReturnTrace for {}", .{self.target.cpu.arch}); |
| 6122 | } | 6206 | } |
| 6123 | | 6207 | |
| 6124 | fn airSaveErrReturnTraceIndex(self: *Self, inst: Air.Inst.Index) !void { | 6208 | fn airSaveErrReturnTraceIndex(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6125 | _ = inst; | 6209 | _ = inst; |
| 6126 | return self.fail("TODO implement airSaveErrReturnTraceIndex for {}", .{self.target.cpu.arch}); | 6210 | return self.fail("TODO implement airSaveErrReturnTraceIndex for {}", .{self.target.cpu.arch}); |
| 6127 | } | 6211 | } |
| 6128 | | 6212 | |
| 6129 | fn airWrapOptional(self: *Self, inst: Air.Inst.Index) !void { | 6213 | fn airWrapOptional(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6130 | const pt = self.pt; | 6214 | const pt = self.pt; |
| 6131 | const zcu = pt.zcu; | 6215 | const zcu = pt.zcu; |
| 6132 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6216 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -6181,7 +6265,7 @@ fn airWrapOptional(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6181,7 +6265,7 @@ fn airWrapOptional(self: *Self, inst: Air.Inst.Index) !void { |
| 6181 | } | 6265 | } |
| 6182 | | 6266 | |
| 6183 | /// T to E!T | 6267 | /// T to E!T |
| 6184 | fn airWrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { | 6268 | fn airWrapErrUnionPayload(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6185 | const pt = self.pt; | 6269 | const pt = self.pt; |
| 6186 | const zcu = pt.zcu; | 6270 | const zcu = pt.zcu; |
| 6187 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6271 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -6205,7 +6289,7 @@ fn airWrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6205,7 +6289,7 @@ fn airWrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void { |
| 6205 | } | 6289 | } |
| 6206 | | 6290 | |
| 6207 | /// E to E!T | 6291 | /// E to E!T |
| 6208 | fn airWrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { | 6292 | fn airWrapErrUnionErr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6209 | const pt = self.pt; | 6293 | const pt = self.pt; |
| 6210 | const zcu = pt.zcu; | 6294 | const zcu = pt.zcu; |
| 6211 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6295 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -6228,7 +6312,7 @@ fn airWrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6228,7 +6312,7 @@ fn airWrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void { |
| 6228 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 6312 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 6229 | } | 6313 | } |
| 6230 | | 6314 | |
| 6231 | fn airSlicePtr(self: *Self, inst: Air.Inst.Index) !void { | 6315 | fn airSlicePtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6232 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6316 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 6233 | const result = result: { | 6317 | const result = result: { |
| 6234 | const src_mcv = try self.resolveInst(ty_op.operand); | 6318 | const src_mcv = try self.resolveInst(ty_op.operand); |
| ... | @@ -6251,7 +6335,7 @@ fn airSlicePtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6251,7 +6335,7 @@ fn airSlicePtr(self: *Self, inst: Air.Inst.Index) !void { |
| 6251 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 6335 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 6252 | } | 6336 | } |
| 6253 | | 6337 | |
| 6254 | fn airSliceLen(self: *Self, inst: Air.Inst.Index) !void { | 6338 | fn airSliceLen(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6255 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6339 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 6256 | const result = result: { | 6340 | const result = result: { |
| 6257 | const src_mcv = try self.resolveInst(ty_op.operand); | 6341 | const src_mcv = try self.resolveInst(ty_op.operand); |
| ... | @@ -6279,7 +6363,7 @@ fn airSliceLen(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6279,7 +6363,7 @@ fn airSliceLen(self: *Self, inst: Air.Inst.Index) !void { |
| 6279 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 6363 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 6280 | } | 6364 | } |
| 6281 | | 6365 | |
| 6282 | fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void { | 6366 | fn airPtrSliceLenPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6283 | const pt = self.pt; | 6367 | const pt = self.pt; |
| 6284 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6368 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 6285 | | 6369 | |
| ... | @@ -6314,7 +6398,7 @@ fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6314,7 +6398,7 @@ fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 6314 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 6398 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 6315 | } | 6399 | } |
| 6316 | | 6400 | |
| 6317 | fn airPtrSlicePtrPtr(self: *Self, inst: Air.Inst.Index) !void { | 6401 | fn airPtrSlicePtrPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6318 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6402 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 6319 | | 6403 | |
| 6320 | const dst_ty = self.typeOfIndex(inst); | 6404 | const dst_ty = self.typeOfIndex(inst); |
| ... | @@ -6327,7 +6411,7 @@ fn airPtrSlicePtrPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6327,7 +6411,7 @@ fn airPtrSlicePtrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 6327 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 6411 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 6328 | } | 6412 | } |
| 6329 | | 6413 | |
| 6330 | fn elemOffset(self: *Self, index_ty: Type, index: MCValue, elem_size: u64) !Register { | 6414 | fn elemOffset(self: *CodeGen, index_ty: Type, index: MCValue, elem_size: u64) !Register { |
| 6331 | const reg: Register = blk: { | 6415 | const reg: Register = blk: { |
| 6332 | switch (index) { | 6416 | switch (index) { |
| 6333 | .immediate => |imm| { | 6417 | .immediate => |imm| { |
| ... | @@ -6347,7 +6431,7 @@ fn elemOffset(self: *Self, index_ty: Type, index: MCValue, elem_size: u64) !Regi | ... | @@ -6347,7 +6431,7 @@ fn elemOffset(self: *Self, index_ty: Type, index: MCValue, elem_size: u64) !Regi |
| 6347 | return reg; | 6431 | return reg; |
| 6348 | } | 6432 | } |
| 6349 | | 6433 | |
| 6350 | fn genSliceElemPtr(self: *Self, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref) !MCValue { | 6434 | fn genSliceElemPtr(self: *CodeGen, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref) !MCValue { |
| 6351 | const pt = self.pt; | 6435 | const pt = self.pt; |
| 6352 | const zcu = pt.zcu; | 6436 | const zcu = pt.zcu; |
| 6353 | const slice_ty = self.typeOf(lhs); | 6437 | const slice_ty = self.typeOf(lhs); |
| ... | @@ -6384,7 +6468,7 @@ fn genSliceElemPtr(self: *Self, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref) !MCValue { | ... | @@ -6384,7 +6468,7 @@ fn genSliceElemPtr(self: *Self, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref) !MCValue { |
| 6384 | return MCValue{ .register = addr_reg.to64() }; | 6468 | return MCValue{ .register = addr_reg.to64() }; |
| 6385 | } | 6469 | } |
| 6386 | | 6470 | |
| 6387 | fn airSliceElemVal(self: *Self, inst: Air.Inst.Index) !void { | 6471 | fn airSliceElemVal(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6388 | const pt = self.pt; | 6472 | const pt = self.pt; |
| 6389 | const zcu = pt.zcu; | 6473 | const zcu = pt.zcu; |
| 6390 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 6474 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -6403,14 +6487,14 @@ fn airSliceElemVal(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6403,14 +6487,14 @@ fn airSliceElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 6403 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 6487 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 6404 | } | 6488 | } |
| 6405 | | 6489 | |
| 6406 | fn airSliceElemPtr(self: *Self, inst: Air.Inst.Index) !void { | 6490 | fn airSliceElemPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6407 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 6491 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 6408 | const extra = self.air.extraData(Air.Bin, ty_pl.payload).data; | 6492 | const extra = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 6409 | const dst_mcv = try self.genSliceElemPtr(extra.lhs, extra.rhs); | 6493 | const dst_mcv = try self.genSliceElemPtr(extra.lhs, extra.rhs); |
| 6410 | return self.finishAir(inst, dst_mcv, .{ extra.lhs, extra.rhs, .none }); | 6494 | return self.finishAir(inst, dst_mcv, .{ extra.lhs, extra.rhs, .none }); |
| 6411 | } | 6495 | } |
| 6412 | | 6496 | |
| 6413 | fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { | 6497 | fn airArrayElemVal(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6414 | const pt = self.pt; | 6498 | const pt = self.pt; |
| 6415 | const zcu = pt.zcu; | 6499 | const zcu = pt.zcu; |
| 6416 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 6500 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -6463,7 +6547,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6463,7 +6547,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 6463 | }, | 6547 | }, |
| 6464 | .load_frame => try self.asmMemoryRegister( | 6548 | .load_frame => try self.asmMemoryRegister( |
| 6465 | .{ ._, .bt }, | 6549 | .{ ._, .bt }, |
| 6466 | try array_mcv.mem(self, .qword), | 6550 | try array_mcv.mem(self, .{ .size = .qword }), |
| 6467 | index_reg.to64(), | 6551 | index_reg.to64(), |
| 6468 | ), | 6552 | ), |
| 6469 | .memory, .load_symbol, .load_direct, .load_got, .load_tlv => try self.asmMemoryRegister( | 6553 | .memory, .load_symbol, .load_direct, .load_got, .load_tlv => try self.asmMemoryRegister( |
| ... | @@ -6540,7 +6624,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6540,7 +6624,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 6540 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 6624 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 6541 | } | 6625 | } |
| 6542 | | 6626 | |
| 6543 | fn airPtrElemVal(self: *Self, inst: Air.Inst.Index) !void { | 6627 | fn airPtrElemVal(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6544 | const pt = self.pt; | 6628 | const pt = self.pt; |
| 6545 | const zcu = pt.zcu; | 6629 | const zcu = pt.zcu; |
| 6546 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 6630 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -6591,7 +6675,7 @@ fn airPtrElemVal(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6591,7 +6675,7 @@ fn airPtrElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 6591 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 6675 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 6592 | } | 6676 | } |
| 6593 | | 6677 | |
| 6594 | fn airPtrElemPtr(self: *Self, inst: Air.Inst.Index) !void { | 6678 | fn airPtrElemPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6595 | const pt = self.pt; | 6679 | const pt = self.pt; |
| 6596 | const zcu = pt.zcu; | 6680 | const zcu = pt.zcu; |
| 6597 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 6681 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -6637,7 +6721,7 @@ fn airPtrElemPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6637,7 +6721,7 @@ fn airPtrElemPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 6637 | return self.finishAir(inst, result, .{ extra.lhs, extra.rhs, .none }); | 6721 | return self.finishAir(inst, result, .{ extra.lhs, extra.rhs, .none }); |
| 6638 | } | 6722 | } |
| 6639 | | 6723 | |
| 6640 | fn airSetUnionTag(self: *Self, inst: Air.Inst.Index) !void { | 6724 | fn airSetUnionTag(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6641 | const pt = self.pt; | 6725 | const pt = self.pt; |
| 6642 | const zcu = pt.zcu; | 6726 | const zcu = pt.zcu; |
| 6643 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 6727 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -6682,7 +6766,7 @@ fn airSetUnionTag(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6682,7 +6766,7 @@ fn airSetUnionTag(self: *Self, inst: Air.Inst.Index) !void { |
| 6682 | return self.finishAir(inst, .none, .{ bin_op.lhs, bin_op.rhs, .none }); | 6766 | return self.finishAir(inst, .none, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 6683 | } | 6767 | } |
| 6684 | | 6768 | |
| 6685 | fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void { | 6769 | fn airGetUnionTag(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6686 | const zcu = self.pt.zcu; | 6770 | const zcu = self.pt.zcu; |
| 6687 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6771 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 6688 | | 6772 | |
| ... | @@ -6739,7 +6823,7 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6739,7 +6823,7 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void { |
| 6739 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 6823 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 6740 | } | 6824 | } |
| 6741 | | 6825 | |
| 6742 | fn airClz(self: *Self, inst: Air.Inst.Index) !void { | 6826 | fn airClz(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6743 | const pt = self.pt; | 6827 | const pt = self.pt; |
| 6744 | const zcu = pt.zcu; | 6828 | const zcu = pt.zcu; |
| 6745 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 6829 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -6936,7 +7020,7 @@ fn airClz(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -6936,7 +7020,7 @@ fn airClz(self: *Self, inst: Air.Inst.Index) !void { |
| 6936 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 7020 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 6937 | } | 7021 | } |
| 6938 | | 7022 | |
| 6939 | fn airCtz(self: *Self, inst: Air.Inst.Index) !void { | 7023 | fn airCtz(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 6940 | const pt = self.pt; | 7024 | const pt = self.pt; |
| 6941 | const zcu = pt.zcu; | 7025 | const zcu = pt.zcu; |
| 6942 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 7026 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -7098,7 +7182,7 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7098,7 +7182,7 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void { |
| 7098 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 7182 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 7099 | } | 7183 | } |
| 7100 | | 7184 | |
| 7101 | fn airPopCount(self: *Self, inst: Air.Inst.Index) !void { | 7185 | fn airPopCount(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 7102 | const pt = self.pt; | 7186 | const pt = self.pt; |
| 7103 | const zcu = pt.zcu; | 7187 | const zcu = pt.zcu; |
| 7104 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 7188 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -7157,7 +7241,7 @@ fn airPopCount(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7157,7 +7241,7 @@ fn airPopCount(self: *Self, inst: Air.Inst.Index) !void { |
| 7157 | } | 7241 | } |
| 7158 | | 7242 | |
| 7159 | fn genPopCount( | 7243 | fn genPopCount( |
| 7160 | self: *Self, | 7244 | self: *CodeGen, |
| 7161 | dst_reg: Register, | 7245 | dst_reg: Register, |
| 7162 | src_ty: Type, | 7246 | src_ty: Type, |
| 7163 | src_mcv: MCValue, | 7247 | src_mcv: MCValue, |
| ... | @@ -7249,7 +7333,7 @@ fn genPopCount( | ... | @@ -7249,7 +7333,7 @@ fn genPopCount( |
| 7249 | } | 7333 | } |
| 7250 | | 7334 | |
| 7251 | fn genByteSwap( | 7335 | fn genByteSwap( |
| 7252 | self: *Self, | 7336 | self: *CodeGen, |
| 7253 | inst: Air.Inst.Index, | 7337 | inst: Air.Inst.Index, |
| 7254 | src_ty: Type, | 7338 | src_ty: Type, |
| 7255 | src_mcv: MCValue, | 7339 | src_mcv: MCValue, |
| ... | @@ -7308,7 +7392,7 @@ fn genByteSwap( | ... | @@ -7308,7 +7392,7 @@ fn genByteSwap( |
| 7308 | try self.asmRegisterMemory( | 7392 | try self.asmRegisterMemory( |
| 7309 | .{ ._, if (has_movbe) .movbe else .mov }, | 7393 | .{ ._, if (has_movbe) .movbe else .mov }, |
| 7310 | dst_reg.to64(), | 7394 | dst_reg.to64(), |
| 7311 | try src_mcv.address().offset(@intCast(limb_index * 8)).deref().mem(self, .qword), | 7395 | try src_mcv.address().offset(@intCast(limb_index * 8)).deref().mem(self, .{ .size = .qword }), |
| 7312 | ); | 7396 | ); |
| 7313 | if (!has_movbe) try self.asmRegister(.{ ._, .bswap }, dst_reg.to64()); | 7397 | if (!has_movbe) try self.asmRegister(.{ ._, .bswap }, dst_reg.to64()); |
| 7314 | } else { | 7398 | } else { |
| ... | @@ -7414,7 +7498,7 @@ fn genByteSwap( | ... | @@ -7414,7 +7498,7 @@ fn genByteSwap( |
| 7414 | return dst_mcv; | 7498 | return dst_mcv; |
| 7415 | } | 7499 | } |
| 7416 | | 7500 | |
| 7417 | fn airByteSwap(self: *Self, inst: Air.Inst.Index) !void { | 7501 | fn airByteSwap(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 7418 | const pt = self.pt; | 7502 | const pt = self.pt; |
| 7419 | const zcu = pt.zcu; | 7503 | const zcu = pt.zcu; |
| 7420 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 7504 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -7437,7 +7521,7 @@ fn airByteSwap(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7437,7 +7521,7 @@ fn airByteSwap(self: *Self, inst: Air.Inst.Index) !void { |
| 7437 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 7521 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 7438 | } | 7522 | } |
| 7439 | | 7523 | |
| 7440 | fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void { | 7524 | fn airBitReverse(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 7441 | const pt = self.pt; | 7525 | const pt = self.pt; |
| 7442 | const zcu = pt.zcu; | 7526 | const zcu = pt.zcu; |
| 7443 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 7527 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -7560,7 +7644,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7560,7 +7644,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void { |
| 7560 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 7644 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 7561 | } | 7645 | } |
| 7562 | | 7646 | |
| 7563 | fn floatSign(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) !void { | 7647 | fn floatSign(self: *CodeGen, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) !void { |
| 7564 | const pt = self.pt; | 7648 | const pt = self.pt; |
| 7565 | const zcu = pt.zcu; | 7649 | const zcu = pt.zcu; |
| 7566 | const tag = self.air.instructions.items(.tag)[@intFromEnum(inst)]; | 7650 | const tag = self.air.instructions.items(.tag)[@intFromEnum(inst)]; |
| ... | @@ -7623,7 +7707,7 @@ fn floatSign(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) | ... | @@ -7623,7 +7707,7 @@ fn floatSign(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) |
| 7623 | else => unreachable, | 7707 | else => unreachable, |
| 7624 | }); | 7708 | }); |
| 7625 | const sign_mem: Memory = if (sign_mcv.isMemory()) | 7709 | const sign_mem: Memory = if (sign_mcv.isMemory()) |
| 7626 | try sign_mcv.mem(self, .fromSize(abi_size)) | 7710 | try sign_mcv.mem(self, .{ .size = .fromSize(abi_size) }) |
| 7627 | else | 7711 | else |
| 7628 | .{ | 7712 | .{ |
| 7629 | .base = .{ .reg = try self.copyToTmpRegister(Type.usize, sign_mcv.address()) }, | 7713 | .base = .{ .reg = try self.copyToTmpRegister(Type.usize, sign_mcv.address()) }, |
| ... | @@ -7688,7 +7772,7 @@ fn floatSign(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) | ... | @@ -7688,7 +7772,7 @@ fn floatSign(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, ty: Type) |
| 7688 | return self.finishAir(inst, result, .{ operand, .none, .none }); | 7772 | return self.finishAir(inst, result, .{ operand, .none, .none }); |
| 7689 | } | 7773 | } |
| 7690 | | 7774 | |
| 7691 | fn airFloatSign(self: *Self, inst: Air.Inst.Index) !void { | 7775 | fn airFloatSign(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 7692 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 7776 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 7693 | const ty = self.typeOf(un_op); | 7777 | const ty = self.typeOf(un_op); |
| 7694 | return self.floatSign(inst, un_op, ty); | 7778 | return self.floatSign(inst, un_op, ty); |
| ... | @@ -7713,7 +7797,7 @@ const RoundMode = packed struct(u5) { | ... | @@ -7713,7 +7797,7 @@ const RoundMode = packed struct(u5) { |
| 7713 | } = .normal, | 7797 | } = .normal, |
| 7714 | }; | 7798 | }; |
| 7715 | | 7799 | |
| 7716 | fn airRound(self: *Self, inst: Air.Inst.Index, mode: RoundMode) !void { | 7800 | fn airRound(self: *CodeGen, inst: Air.Inst.Index, mode: RoundMode) !void { |
| 7717 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 7801 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 7718 | const ty = self.typeOf(un_op); | 7802 | const ty = self.typeOf(un_op); |
| 7719 | | 7803 | |
| ... | @@ -7737,7 +7821,7 @@ fn airRound(self: *Self, inst: Air.Inst.Index, mode: RoundMode) !void { | ... | @@ -7737,7 +7821,7 @@ fn airRound(self: *Self, inst: Air.Inst.Index, mode: RoundMode) !void { |
| 7737 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 7821 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 7738 | } | 7822 | } |
| 7739 | | 7823 | |
| 7740 | fn getRoundTag(self: *Self, ty: Type) ?Mir.Inst.FixedTag { | 7824 | fn getRoundTag(self: *CodeGen, ty: Type) ?Mir.Inst.FixedTag { |
| 7741 | const pt = self.pt; | 7825 | const pt = self.pt; |
| 7742 | const zcu = pt.zcu; | 7826 | const zcu = pt.zcu; |
| 7743 | return if (self.hasFeature(.sse4_1)) switch (ty.zigTypeTag(zcu)) { | 7827 | return if (self.hasFeature(.sse4_1)) switch (ty.zigTypeTag(zcu)) { |
| ... | @@ -7770,7 +7854,7 @@ fn getRoundTag(self: *Self, ty: Type) ?Mir.Inst.FixedTag { | ... | @@ -7770,7 +7854,7 @@ fn getRoundTag(self: *Self, ty: Type) ?Mir.Inst.FixedTag { |
| 7770 | } else null; | 7854 | } else null; |
| 7771 | } | 7855 | } |
| 7772 | | 7856 | |
| 7773 | fn genRoundLibcall(self: *Self, ty: Type, src_mcv: MCValue, mode: RoundMode) !MCValue { | 7857 | fn genRoundLibcall(self: *CodeGen, ty: Type, src_mcv: MCValue, mode: RoundMode) !MCValue { |
| 7774 | const pt = self.pt; | 7858 | const pt = self.pt; |
| 7775 | const zcu = pt.zcu; | 7859 | const zcu = pt.zcu; |
| 7776 | if (self.getRoundTag(ty)) |_| return .none; | 7860 | if (self.getRoundTag(ty)) |_| return .none; |
| ... | @@ -7795,7 +7879,7 @@ fn genRoundLibcall(self: *Self, ty: Type, src_mcv: MCValue, mode: RoundMode) !MC | ... | @@ -7795,7 +7879,7 @@ fn genRoundLibcall(self: *Self, ty: Type, src_mcv: MCValue, mode: RoundMode) !MC |
| 7795 | } }, &.{ty}, &.{src_mcv}); | 7879 | } }, &.{ty}, &.{src_mcv}); |
| 7796 | } | 7880 | } |
| 7797 | | 7881 | |
| 7798 | fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: RoundMode) !void { | 7882 | fn genRound(self: *CodeGen, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: RoundMode) !void { |
| 7799 | const pt = self.pt; | 7883 | const pt = self.pt; |
| 7800 | const mir_tag = self.getRoundTag(ty) orelse { | 7884 | const mir_tag = self.getRoundTag(ty) orelse { |
| 7801 | const result = try self.genRoundLibcall(ty, src_mcv, mode); | 7885 | const result = try self.genRoundLibcall(ty, src_mcv, mode); |
| ... | @@ -7808,7 +7892,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro | ... | @@ -7808,7 +7892,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro |
| 7808 | mir_tag, | 7892 | mir_tag, |
| 7809 | dst_alias, | 7893 | dst_alias, |
| 7810 | dst_alias, | 7894 | dst_alias, |
| 7811 | try src_mcv.mem(self, .fromSize(abi_size)), | 7895 | try src_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 7812 | .u(@as(u5, @bitCast(mode))), | 7896 | .u(@as(u5, @bitCast(mode))), |
| 7813 | ) else try self.asmRegisterRegisterRegisterImmediate( | 7897 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 7814 | mir_tag, | 7898 | mir_tag, |
| ... | @@ -7823,7 +7907,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro | ... | @@ -7823,7 +7907,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro |
| 7823 | else => if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 7907 | else => if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 7824 | mir_tag, | 7908 | mir_tag, |
| 7825 | dst_alias, | 7909 | dst_alias, |
| 7826 | try src_mcv.mem(self, .fromSize(abi_size)), | 7910 | try src_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 7827 | .u(@as(u5, @bitCast(mode))), | 7911 | .u(@as(u5, @bitCast(mode))), |
| 7828 | ) else try self.asmRegisterRegisterImmediate( | 7912 | ) else try self.asmRegisterRegisterImmediate( |
| 7829 | mir_tag, | 7913 | mir_tag, |
| ... | @@ -7837,7 +7921,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro | ... | @@ -7837,7 +7921,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: Ro |
| 7837 | } | 7921 | } |
| 7838 | } | 7922 | } |
| 7839 | | 7923 | |
| 7840 | fn airAbs(self: *Self, inst: Air.Inst.Index) !void { | 7924 | fn airAbs(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 7841 | const pt = self.pt; | 7925 | const pt = self.pt; |
| 7842 | const zcu = pt.zcu; | 7926 | const zcu = pt.zcu; |
| 7843 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 7927 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -7865,7 +7949,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7865,7 +7949,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { |
| 7865 | .memory, .indirect, .load_frame => try self.asmCmovccRegisterMemory( | 7949 | .memory, .indirect, .load_frame => try self.asmCmovccRegisterMemory( |
| 7866 | .l, | 7950 | .l, |
| 7867 | registerAlias(dst_mcv.register, cmov_abi_size), | 7951 | registerAlias(dst_mcv.register, cmov_abi_size), |
| 7868 | try src_mcv.mem(self, .fromSize(cmov_abi_size)), | 7952 | try src_mcv.mem(self, .{ .size = .fromSize(cmov_abi_size) }), |
| 7869 | ), | 7953 | ), |
| 7870 | else => { | 7954 | else => { |
| 7871 | const val_reg = try self.copyToTmpRegister(ty, src_mcv); | 7955 | const val_reg = try self.copyToTmpRegister(ty, src_mcv); |
| ... | @@ -7931,7 +8015,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -7931,7 +8015,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { |
| 7931 | | 8015 | |
| 7932 | try self.asmMemoryImmediate( | 8016 | try self.asmMemoryImmediate( |
| 7933 | .{ ._, .cmp }, | 8017 | .{ ._, .cmp }, |
| 7934 | try dst_mcv.address().offset((limb_len - 1) * 8).deref().mem(self, .qword), | 8018 | try dst_mcv.address().offset((limb_len - 1) * 8).deref().mem(self, .{ .size = .qword }), |
| 7935 | .u(0), | 8019 | .u(0), |
| 7936 | ); | 8020 | ); |
| 7937 | const positive = try self.asmJccReloc(.ns, undefined); | 8021 | const positive = try self.asmJccReloc(.ns, undefined); |
| ... | @@ -8024,7 +8108,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8024,7 +8108,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { |
| 8024 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 8108 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 8025 | mir_tag, | 8109 | mir_tag, |
| 8026 | dst_alias, | 8110 | dst_alias, |
| 8027 | try src_mcv.mem(self, self.memSize(ty)), | 8111 | try src_mcv.mem(self, .{ .size = self.memSize(ty) }), |
| 8028 | ) else try self.asmRegisterRegister( | 8112 | ) else try self.asmRegisterRegister( |
| 8029 | mir_tag, | 8113 | mir_tag, |
| 8030 | dst_alias, | 8114 | dst_alias, |
| ... | @@ -8038,7 +8122,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8038,7 +8122,7 @@ fn airAbs(self: *Self, inst: Air.Inst.Index) !void { |
| 8038 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 8122 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 8039 | } | 8123 | } |
| 8040 | | 8124 | |
| 8041 | fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { | 8125 | fn airSqrt(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 8042 | const pt = self.pt; | 8126 | const pt = self.pt; |
| 8043 | const zcu = pt.zcu; | 8127 | const zcu = pt.zcu; |
| 8044 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 8128 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| ... | @@ -8131,9 +8215,9 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8131,9 +8215,9 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 8131 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 8215 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 8132 | .{ .v_ps, .cvtph2 }, | 8216 | .{ .v_ps, .cvtph2 }, |
| 8133 | wide_reg, | 8217 | wide_reg, |
| 8134 | try src_mcv.mem(self, .fromSize( | 8218 | try src_mcv.mem(self, .{ .size = .fromSize( |
| 8135 | @intCast(@divExact(wide_reg.bitSize(), 16)), | 8219 | @intCast(@divExact(wide_reg.bitSize(), 16)), |
| 8136 | )), | 8220 | ) }), |
| 8137 | ) else try self.asmRegisterRegister( | 8221 | ) else try self.asmRegisterRegister( |
| 8138 | .{ .v_ps, .cvtph2 }, | 8222 | .{ .v_ps, .cvtph2 }, |
| 8139 | wide_reg, | 8223 | wide_reg, |
| ... | @@ -8177,7 +8261,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8177,7 +8261,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 8177 | mir_tag, | 8261 | mir_tag, |
| 8178 | dst_reg, | 8262 | dst_reg, |
| 8179 | dst_reg, | 8263 | dst_reg, |
| 8180 | try src_mcv.mem(self, .fromSize(abi_size)), | 8264 | try src_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 8181 | ) else try self.asmRegisterRegisterRegister( | 8265 | ) else try self.asmRegisterRegisterRegister( |
| 8182 | mir_tag, | 8266 | mir_tag, |
| 8183 | dst_reg, | 8267 | dst_reg, |
| ... | @@ -8190,7 +8274,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8190,7 +8274,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 8190 | else => if (src_mcv.isMemory()) try self.asmRegisterMemory( | 8274 | else => if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 8191 | mir_tag, | 8275 | mir_tag, |
| 8192 | dst_reg, | 8276 | dst_reg, |
| 8193 | try src_mcv.mem(self, .fromSize(abi_size)), | 8277 | try src_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 8194 | ) else try self.asmRegisterRegister( | 8278 | ) else try self.asmRegisterRegister( |
| 8195 | mir_tag, | 8279 | mir_tag, |
| 8196 | dst_reg, | 8280 | dst_reg, |
| ... | @@ -8205,7 +8289,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8205,7 +8289,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 8205 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 8289 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 8206 | } | 8290 | } |
| 8207 | | 8291 | |
| 8208 | fn airUnaryMath(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | 8292 | fn airUnaryMath(self: *CodeGen, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 8209 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 8293 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 8210 | const ty = self.typeOf(un_op); | 8294 | const ty = self.typeOf(un_op); |
| 8211 | var callee_buf: ["__round?".len]u8 = undefined; | 8295 | var callee_buf: ["__round?".len]u8 = undefined; |
| ... | @@ -8234,7 +8318,7 @@ fn airUnaryMath(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { | ... | @@ -8234,7 +8318,7 @@ fn airUnaryMath(self: *Self, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 8234 | } | 8318 | } |
| 8235 | | 8319 | |
| 8236 | fn reuseOperand( | 8320 | fn reuseOperand( |
| 8237 | self: *Self, | 8321 | self: *CodeGen, |
| 8238 | inst: Air.Inst.Index, | 8322 | inst: Air.Inst.Index, |
| 8239 | operand: Air.Inst.Ref, | 8323 | operand: Air.Inst.Ref, |
| 8240 | op_index: Liveness.OperandInt, | 8324 | op_index: Liveness.OperandInt, |
| ... | @@ -8244,7 +8328,7 @@ fn reuseOperand( | ... | @@ -8244,7 +8328,7 @@ fn reuseOperand( |
| 8244 | } | 8328 | } |
| 8245 | | 8329 | |
| 8246 | fn reuseOperandAdvanced( | 8330 | fn reuseOperandAdvanced( |
| 8247 | self: *Self, | 8331 | self: *CodeGen, |
| 8248 | inst: Air.Inst.Index, | 8332 | inst: Air.Inst.Index, |
| 8249 | operand: Air.Inst.Ref, | 8333 | operand: Air.Inst.Ref, |
| 8250 | op_index: Liveness.OperandInt, | 8334 | op_index: Liveness.OperandInt, |
| ... | @@ -8282,7 +8366,7 @@ fn reuseOperandAdvanced( | ... | @@ -8282,7 +8366,7 @@ fn reuseOperandAdvanced( |
| 8282 | return true; | 8366 | return true; |
| 8283 | } | 8367 | } |
| 8284 | | 8368 | |
| 8285 | fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { | 8369 | fn packedLoad(self: *CodeGen, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { |
| 8286 | const pt = self.pt; | 8370 | const pt = self.pt; |
| 8287 | const zcu = pt.zcu; | 8371 | const zcu = pt.zcu; |
| 8288 | | 8372 | |
| ... | @@ -8390,7 +8474,7 @@ fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) Inn | ... | @@ -8390,7 +8474,7 @@ fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) Inn |
| 8390 | try self.genCopy(val_ty, dst_mcv, .{ .register = dst_reg }, .{}); | 8474 | try self.genCopy(val_ty, dst_mcv, .{ .register = dst_reg }, .{}); |
| 8391 | } | 8475 | } |
| 8392 | | 8476 | |
| 8393 | fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { | 8477 | fn load(self: *CodeGen, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { |
| 8394 | const pt = self.pt; | 8478 | const pt = self.pt; |
| 8395 | const zcu = pt.zcu; | 8479 | const zcu = pt.zcu; |
| 8396 | const dst_ty = ptr_ty.childType(zcu); | 8480 | const dst_ty = ptr_ty.childType(zcu); |
| ... | @@ -8433,7 +8517,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro | ... | @@ -8433,7 +8517,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro |
| 8433 | } | 8517 | } |
| 8434 | } | 8518 | } |
| 8435 | | 8519 | |
| 8436 | fn airLoad(self: *Self, inst: Air.Inst.Index) !void { | 8520 | fn airLoad(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 8437 | const pt = self.pt; | 8521 | const pt = self.pt; |
| 8438 | const zcu = pt.zcu; | 8522 | const zcu = pt.zcu; |
| 8439 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 8523 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -8492,7 +8576,7 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8492,7 +8576,7 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 8492 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 8576 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 8493 | } | 8577 | } |
| 8494 | | 8578 | |
| 8495 | fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerError!void { | 8579 | fn packedStore(self: *CodeGen, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerError!void { |
| 8496 | const pt = self.pt; | 8580 | const pt = self.pt; |
| 8497 | const zcu = pt.zcu; | 8581 | const zcu = pt.zcu; |
| 8498 | const ptr_info = ptr_ty.ptrInfo(zcu); | 8582 | const ptr_info = ptr_ty.ptrInfo(zcu); |
| ... | @@ -8593,7 +8677,7 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In | ... | @@ -8593,7 +8677,7 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In |
| 8593 | } | 8677 | } |
| 8594 | | 8678 | |
| 8595 | fn store( | 8679 | fn store( |
| 8596 | self: *Self, | 8680 | self: *CodeGen, |
| 8597 | ptr_ty: Type, | 8681 | ptr_ty: Type, |
| 8598 | ptr_mcv: MCValue, | 8682 | ptr_mcv: MCValue, |
| 8599 | src_mcv: MCValue, | 8683 | src_mcv: MCValue, |
| ... | @@ -8641,7 +8725,7 @@ fn store( | ... | @@ -8641,7 +8725,7 @@ fn store( |
| 8641 | } | 8725 | } |
| 8642 | } | 8726 | } |
| 8643 | | 8727 | |
| 8644 | fn airStore(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | 8728 | fn airStore(self: *CodeGen, inst: Air.Inst.Index, safety: bool) !void { |
| 8645 | const pt = self.pt; | 8729 | const pt = self.pt; |
| 8646 | const zcu = pt.zcu; | 8730 | const zcu = pt.zcu; |
| 8647 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 8731 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -8667,20 +8751,20 @@ fn airStore(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | ... | @@ -8667,20 +8751,20 @@ fn airStore(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 8667 | return self.finishAir(inst, .none, .{ bin_op.lhs, bin_op.rhs, .none }); | 8751 | return self.finishAir(inst, .none, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 8668 | } | 8752 | } |
| 8669 | | 8753 | |
| 8670 | fn airStructFieldPtr(self: *Self, inst: Air.Inst.Index) !void { | 8754 | fn airStructFieldPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 8671 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 8755 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 8672 | const extra = self.air.extraData(Air.StructField, ty_pl.payload).data; | 8756 | const extra = self.air.extraData(Air.StructField, ty_pl.payload).data; |
| 8673 | const result = try self.fieldPtr(inst, extra.struct_operand, extra.field_index); | 8757 | const result = try self.fieldPtr(inst, extra.struct_operand, extra.field_index); |
| 8674 | return self.finishAir(inst, result, .{ extra.struct_operand, .none, .none }); | 8758 | return self.finishAir(inst, result, .{ extra.struct_operand, .none, .none }); |
| 8675 | } | 8759 | } |
| 8676 | | 8760 | |
| 8677 | fn airStructFieldPtrIndex(self: *Self, inst: Air.Inst.Index, field_index: u8) !void { | 8761 | fn airStructFieldPtrIndex(self: *CodeGen, inst: Air.Inst.Index, field_index: u8) !void { |
| 8678 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 8762 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 8679 | const result = try self.fieldPtr(inst, ty_op.operand, field_index); | 8763 | const result = try self.fieldPtr(inst, ty_op.operand, field_index); |
| 8680 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 8764 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 8681 | } | 8765 | } |
| 8682 | | 8766 | |
| 8683 | fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, field_index: u32) !MCValue { | 8767 | fn fieldPtr(self: *CodeGen, inst: Air.Inst.Index, operand: Air.Inst.Ref, field_index: u32) !MCValue { |
| 8684 | const ptr_field_ty = self.typeOfIndex(inst); | 8768 | const ptr_field_ty = self.typeOfIndex(inst); |
| 8685 | | 8769 | |
| 8686 | const src_mcv = try self.resolveInst(operand); | 8770 | const src_mcv = try self.resolveInst(operand); |
| ... | @@ -8692,7 +8776,7 @@ fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, field_inde | ... | @@ -8692,7 +8776,7 @@ fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, field_inde |
| 8692 | return dst_mcv.offset(self.fieldOffset(self.typeOf(operand), ptr_field_ty, field_index)); | 8776 | return dst_mcv.offset(self.fieldOffset(self.typeOf(operand), ptr_field_ty, field_index)); |
| 8693 | } | 8777 | } |
| 8694 | | 8778 | |
| 8695 | fn fieldOffset(self: *Self, ptr_agg_ty: Type, ptr_field_ty: Type, field_index: u32) i32 { | 8779 | fn fieldOffset(self: *CodeGen, ptr_agg_ty: Type, ptr_field_ty: Type, field_index: u32) i32 { |
| 8696 | const pt = self.pt; | 8780 | const pt = self.pt; |
| 8697 | const zcu = pt.zcu; | 8781 | const zcu = pt.zcu; |
| 8698 | const agg_ty = ptr_agg_ty.childType(zcu); | 8782 | const agg_ty = ptr_agg_ty.childType(zcu); |
| ... | @@ -8704,7 +8788,7 @@ fn fieldOffset(self: *Self, ptr_agg_ty: Type, ptr_field_ty: Type, field_index: u | ... | @@ -8704,7 +8788,7 @@ fn fieldOffset(self: *Self, ptr_agg_ty: Type, ptr_field_ty: Type, field_index: u |
| 8704 | }; | 8788 | }; |
| 8705 | } | 8789 | } |
| 8706 | | 8790 | |
| 8707 | fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void { | 8791 | fn airStructFieldVal(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 8708 | const pt = self.pt; | 8792 | const pt = self.pt; |
| 8709 | const zcu = pt.zcu; | 8793 | const zcu = pt.zcu; |
| 8710 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 8794 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -8993,7 +9077,7 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -8993,7 +9077,7 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void { |
| 8993 | return self.finishAir(inst, result, .{ extra.struct_operand, .none, .none }); | 9077 | return self.finishAir(inst, result, .{ extra.struct_operand, .none, .none }); |
| 8994 | } | 9078 | } |
| 8995 | | 9079 | |
| 8996 | fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { | 9080 | fn airFieldParentPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 8997 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 9081 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 8998 | const extra = self.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; | 9082 | const extra = self.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 8999 | | 9083 | |
| ... | @@ -9008,7 +9092,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -9008,7 +9092,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 9008 | return self.finishAir(inst, result, .{ extra.field_ptr, .none, .none }); | 9092 | return self.finishAir(inst, result, .{ extra.field_ptr, .none, .none }); |
| 9009 | } | 9093 | } |
| 9010 | | 9094 | |
| 9011 | fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air: Air.Inst.Ref) !MCValue { | 9095 | fn genUnOp(self: *CodeGen, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air: Air.Inst.Ref) !MCValue { |
| 9012 | const pt = self.pt; | 9096 | const pt = self.pt; |
| 9013 | const zcu = pt.zcu; | 9097 | const zcu = pt.zcu; |
| 9014 | const src_ty = self.typeOf(src_air); | 9098 | const src_ty = self.typeOf(src_air); |
| ... | @@ -9097,7 +9181,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air: | ... | @@ -9097,7 +9181,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air: |
| 9097 | return dst_mcv; | 9181 | return dst_mcv; |
| 9098 | } | 9182 | } |
| 9099 | | 9183 | |
| 9100 | fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MCValue) !void { | 9184 | fn genUnOpMir(self: *CodeGen, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MCValue) !void { |
| 9101 | const pt = self.pt; | 9185 | const pt = self.pt; |
| 9102 | const abi_size: u32 = @intCast(dst_ty.abiSize(pt.zcu)); | 9186 | const abi_size: u32 = @intCast(dst_ty.abiSize(pt.zcu)); |
| 9103 | if (abi_size > 8) return self.fail("TODO implement {} for {}", .{ mir_tag, dst_ty.fmt(pt) }); | 9187 | if (abi_size > 8) return self.fail("TODO implement {} for {}", .{ mir_tag, dst_ty.fmt(pt) }); |
| ... | @@ -9133,14 +9217,14 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC | ... | @@ -9133,14 +9217,14 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC |
| 9133 | }, | 9217 | }, |
| 9134 | .indirect, .load_frame => try self.asmMemory( | 9218 | .indirect, .load_frame => try self.asmMemory( |
| 9135 | mir_tag, | 9219 | mir_tag, |
| 9136 | try dst_mcv.mem(self, .fromSize(abi_size)), | 9220 | try dst_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 9137 | ), | 9221 | ), |
| 9138 | } | 9222 | } |
| 9139 | } | 9223 | } |
| 9140 | | 9224 | |
| 9141 | /// Clobbers .rcx for non-immediate shift value. | 9225 | /// Clobbers .rcx for non-immediate shift value. |
| 9142 | fn genShiftBinOpMir( | 9226 | fn genShiftBinOpMir( |
| 9143 | self: *Self, | 9227 | self: *CodeGen, |
| 9144 | tag: Mir.Inst.FixedTag, | 9228 | tag: Mir.Inst.FixedTag, |
| 9145 | lhs_ty: Type, | 9229 | lhs_ty: Type, |
| 9146 | lhs_mcv: MCValue, | 9230 | lhs_mcv: MCValue, |
| ... | @@ -9773,7 +9857,7 @@ fn genShiftBinOpMir( | ... | @@ -9773,7 +9857,7 @@ fn genShiftBinOpMir( |
| 9773 | /// Clobbers .rcx for non-immediate rhs, therefore care is needed to spill .rcx upfront. | 9857 | /// Clobbers .rcx for non-immediate rhs, therefore care is needed to spill .rcx upfront. |
| 9774 | /// Asserts .rcx is free. | 9858 | /// Asserts .rcx is free. |
| 9775 | fn genShiftBinOp( | 9859 | fn genShiftBinOp( |
| 9776 | self: *Self, | 9860 | self: *CodeGen, |
| 9777 | air_tag: Air.Inst.Tag, | 9861 | air_tag: Air.Inst.Tag, |
| 9778 | maybe_inst: ?Air.Inst.Index, | 9862 | maybe_inst: ?Air.Inst.Index, |
| 9779 | lhs_mcv: MCValue, | 9863 | lhs_mcv: MCValue, |
| ... | @@ -9832,7 +9916,7 @@ fn genShiftBinOp( | ... | @@ -9832,7 +9916,7 @@ fn genShiftBinOp( |
| 9832 | /// Clobbers .rax and .rdx therefore care is needed to spill .rax and .rdx upfront. | 9916 | /// Clobbers .rax and .rdx therefore care is needed to spill .rax and .rdx upfront. |
| 9833 | /// Asserts .rax and .rdx are free. | 9917 | /// Asserts .rax and .rdx are free. |
| 9834 | fn genMulDivBinOp( | 9918 | fn genMulDivBinOp( |
| 9835 | self: *Self, | 9919 | self: *CodeGen, |
| 9836 | tag: Air.Inst.Tag, | 9920 | tag: Air.Inst.Tag, |
| 9837 | maybe_inst: ?Air.Inst.Index, | 9921 | maybe_inst: ?Air.Inst.Index, |
| 9838 | dst_ty: Type, | 9922 | dst_ty: Type, |
| ... | @@ -9891,27 +9975,27 @@ fn genMulDivBinOp( | ... | @@ -9891,27 +9975,27 @@ fn genMulDivBinOp( |
| 9891 | defer self.register_manager.unlockReg(tmp_lock); | 9975 | defer self.register_manager.unlockReg(tmp_lock); |
| 9892 | | 9976 | |
| 9893 | if (mat_lhs_mcv.isMemory()) | 9977 | if (mat_lhs_mcv.isMemory()) |
| 9894 | try self.asmRegisterMemory(.{ ._, .mov }, .rax, try mat_lhs_mcv.mem(self, .qword)) | 9978 | try self.asmRegisterMemory(.{ ._, .mov }, .rax, try mat_lhs_mcv.mem(self, .{ .size = .qword })) |
| 9895 | else | 9979 | else |
| 9896 | try self.asmRegisterRegister(.{ ._, .mov }, .rax, mat_lhs_mcv.register_pair[0]); | 9980 | try self.asmRegisterRegister(.{ ._, .mov }, .rax, mat_lhs_mcv.register_pair[0]); |
| 9897 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( | 9981 | if (mat_rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 9898 | .{ ._, .mov }, | 9982 | .{ ._, .mov }, |
| 9899 | tmp_reg, | 9983 | tmp_reg, |
| 9900 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .qword), | 9984 | try mat_rhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 9901 | ) else try self.asmRegisterRegister(.{ ._, .mov }, tmp_reg, mat_rhs_mcv.register_pair[1]); | 9985 | ) else try self.asmRegisterRegister(.{ ._, .mov }, tmp_reg, mat_rhs_mcv.register_pair[1]); |
| 9902 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_reg, .rax); | 9986 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_reg, .rax); |
| 9903 | if (mat_rhs_mcv.isMemory()) | 9987 | if (mat_rhs_mcv.isMemory()) |
| 9904 | try self.asmMemory(.{ ._, .mul }, try mat_rhs_mcv.mem(self, .qword)) | 9988 | try self.asmMemory(.{ ._, .mul }, try mat_rhs_mcv.mem(self, .{ .size = .qword })) |
| 9905 | else | 9989 | else |
| 9906 | try self.asmRegister(.{ ._, .mul }, mat_rhs_mcv.register_pair[0]); | 9990 | try self.asmRegister(.{ ._, .mul }, mat_rhs_mcv.register_pair[0]); |
| 9907 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_reg); | 9991 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_reg); |
| 9908 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( | 9992 | if (mat_lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 9909 | .{ ._, .mov }, | 9993 | .{ ._, .mov }, |
| 9910 | tmp_reg, | 9994 | tmp_reg, |
| 9911 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .qword), | 9995 | try mat_lhs_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 9912 | ) else try self.asmRegisterRegister(.{ ._, .mov }, tmp_reg, mat_lhs_mcv.register_pair[1]); | 9996 | ) else try self.asmRegisterRegister(.{ ._, .mov }, tmp_reg, mat_lhs_mcv.register_pair[1]); |
| 9913 | if (mat_rhs_mcv.isMemory()) | 9997 | if (mat_rhs_mcv.isMemory()) |
| 9914 | try self.asmRegisterMemory(.{ .i_, .mul }, tmp_reg, try mat_rhs_mcv.mem(self, .qword)) | 9998 | try self.asmRegisterMemory(.{ .i_, .mul }, tmp_reg, try mat_rhs_mcv.mem(self, .{ .size = .qword })) |
| 9915 | else | 9999 | else |
| 9916 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_reg, mat_rhs_mcv.register_pair[0]); | 10000 | try self.asmRegisterRegister(.{ .i_, .mul }, tmp_reg, mat_rhs_mcv.register_pair[0]); |
| 9917 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_reg); | 10001 | try self.asmRegisterRegister(.{ ._, .add }, .rdx, tmp_reg); |
| ... | @@ -10238,7 +10322,7 @@ fn genMulDivBinOp( | ... | @@ -10238,7 +10322,7 @@ fn genMulDivBinOp( |
| 10238 | } | 10322 | } |
| 10239 | | 10323 | |
| 10240 | fn genBinOp( | 10324 | fn genBinOp( |
| 10241 | self: *Self, | 10325 | self: *CodeGen, |
| 10242 | maybe_inst: ?Air.Inst.Index, | 10326 | maybe_inst: ?Air.Inst.Index, |
| 10243 | air_tag: Air.Inst.Tag, | 10327 | air_tag: Air.Inst.Tag, |
| 10244 | lhs_air: Air.Inst.Ref, | 10328 | lhs_air: Air.Inst.Ref, |
| ... | @@ -10334,7 +10418,7 @@ fn genBinOp( | ... | @@ -10334,7 +10418,7 @@ fn genBinOp( |
| 10334 | .{ .vp_w, .insr }, | 10418 | .{ .vp_w, .insr }, |
| 10335 | dst_reg, | 10419 | dst_reg, |
| 10336 | dst_reg, | 10420 | dst_reg, |
| 10337 | try rhs_mcv.mem(self, .word), | 10421 | try rhs_mcv.mem(self, .{ .size = .word }), |
| 10338 | .u(1), | 10422 | .u(1), |
| 10339 | ) else try self.asmRegisterRegisterRegister( | 10423 | ) else try self.asmRegisterRegisterRegister( |
| 10340 | .{ .vp_, .unpcklwd }, | 10424 | .{ .vp_, .unpcklwd }, |
| ... | @@ -10359,7 +10443,7 @@ fn genBinOp( | ... | @@ -10359,7 +10443,7 @@ fn genBinOp( |
| 10359 | mir_tag, | 10443 | mir_tag, |
| 10360 | dst_reg, | 10444 | dst_reg, |
| 10361 | dst_reg, | 10445 | dst_reg, |
| 10362 | try src_mcv.mem(self, .fromBitSize(float_bits)), | 10446 | try src_mcv.mem(self, .{ .size = .fromBitSize(float_bits) }), |
| 10363 | ) else try self.asmRegisterRegisterRegister( | 10447 | ) else try self.asmRegisterRegisterRegister( |
| 10364 | mir_tag, | 10448 | mir_tag, |
| 10365 | dst_reg, | 10449 | dst_reg, |
| ... | @@ -10378,7 +10462,7 @@ fn genBinOp( | ... | @@ -10378,7 +10462,7 @@ fn genBinOp( |
| 10378 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 10462 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 10379 | mir_tag, | 10463 | mir_tag, |
| 10380 | dst_reg, | 10464 | dst_reg, |
| 10381 | try src_mcv.mem(self, .fromBitSize(float_bits)), | 10465 | try src_mcv.mem(self, .{ .size = .fromBitSize(float_bits) }), |
| 10382 | ) else try self.asmRegisterRegister( | 10466 | ) else try self.asmRegisterRegister( |
| 10383 | mir_tag, | 10467 | mir_tag, |
| 10384 | dst_reg, | 10468 | dst_reg, |
| ... | @@ -10651,22 +10735,22 @@ fn genBinOp( | ... | @@ -10651,22 +10735,22 @@ fn genBinOp( |
| 10651 | try self.asmRegisterMemory( | 10735 | try self.asmRegisterMemory( |
| 10652 | .{ ._, .cmp }, | 10736 | .{ ._, .cmp }, |
| 10653 | dst_regs[0], | 10737 | dst_regs[0], |
| 10654 | try src_mcv.mem(self, .qword), | 10738 | try src_mcv.mem(self, .{ .size = .qword }), |
| 10655 | ); | 10739 | ); |
| 10656 | try self.asmRegisterMemory( | 10740 | try self.asmRegisterMemory( |
| 10657 | .{ ._, .sbb }, | 10741 | .{ ._, .sbb }, |
| 10658 | tmp_reg, | 10742 | tmp_reg, |
| 10659 | try src_mcv.address().offset(8).deref().mem(self, .qword), | 10743 | try src_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 10660 | ); | 10744 | ); |
| 10661 | try self.asmCmovccRegisterMemory( | 10745 | try self.asmCmovccRegisterMemory( |
| 10662 | cc, | 10746 | cc, |
| 10663 | dst_regs[0], | 10747 | dst_regs[0], |
| 10664 | try src_mcv.mem(self, .qword), | 10748 | try src_mcv.mem(self, .{ .size = .qword }), |
| 10665 | ); | 10749 | ); |
| 10666 | try self.asmCmovccRegisterMemory( | 10750 | try self.asmCmovccRegisterMemory( |
| 10667 | cc, | 10751 | cc, |
| 10668 | dst_regs[1], | 10752 | dst_regs[1], |
| 10669 | try src_mcv.address().offset(8).deref().mem(self, .qword), | 10753 | try src_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 10670 | ); | 10754 | ); |
| 10671 | } else { | 10755 | } else { |
| 10672 | try self.asmRegisterRegister( | 10756 | try self.asmRegisterRegister( |
| ... | @@ -10829,7 +10913,7 @@ fn genBinOp( | ... | @@ -10829,7 +10913,7 @@ fn genBinOp( |
| 10829 | .{ .vp_w, .insr }, | 10913 | .{ .vp_w, .insr }, |
| 10830 | dst_reg, | 10914 | dst_reg, |
| 10831 | dst_reg, | 10915 | dst_reg, |
| 10832 | try src_mcv.mem(self, .word), | 10916 | try src_mcv.mem(self, .{ .size = .word }), |
| 10833 | .u(1), | 10917 | .u(1), |
| 10834 | ) else try self.asmRegisterRegisterRegister( | 10918 | ) else try self.asmRegisterRegisterRegister( |
| 10835 | .{ .vp_, .unpcklwd }, | 10919 | .{ .vp_, .unpcklwd }, |
| ... | @@ -11275,7 +11359,7 @@ fn genBinOp( | ... | @@ -11275,7 +11359,7 @@ fn genBinOp( |
| 11275 | .{ .vp_w, .insr }, | 11359 | .{ .vp_w, .insr }, |
| 11276 | dst_reg, | 11360 | dst_reg, |
| 11277 | dst_reg, | 11361 | dst_reg, |
| 11278 | try src_mcv.mem(self, .word), | 11362 | try src_mcv.mem(self, .{ .size = .word }), |
| 11279 | .u(1), | 11363 | .u(1), |
| 11280 | ) else try self.asmRegisterRegisterRegister( | 11364 | ) else try self.asmRegisterRegisterRegister( |
| 11281 | .{ .vp_, .unpcklwd }, | 11365 | .{ .vp_, .unpcklwd }, |
| ... | @@ -11321,7 +11405,7 @@ fn genBinOp( | ... | @@ -11321,7 +11405,7 @@ fn genBinOp( |
| 11321 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 11405 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 11322 | .{ .vp_d, .insr }, | 11406 | .{ .vp_d, .insr }, |
| 11323 | dst_reg, | 11407 | dst_reg, |
| 11324 | try src_mcv.mem(self, .dword), | 11408 | try src_mcv.mem(self, .{ .size = .dword }), |
| 11325 | .u(1), | 11409 | .u(1), |
| 11326 | ) else try self.asmRegisterRegisterRegister( | 11410 | ) else try self.asmRegisterRegisterRegister( |
| 11327 | .{ .v_ps, .unpckl }, | 11411 | .{ .v_ps, .unpckl }, |
| ... | @@ -11373,7 +11457,7 @@ fn genBinOp( | ... | @@ -11373,7 +11457,7 @@ fn genBinOp( |
| 11373 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 11457 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 11374 | .{ .v_ps, .cvtph2 }, | 11458 | .{ .v_ps, .cvtph2 }, |
| 11375 | tmp_reg, | 11459 | tmp_reg, |
| 11376 | try src_mcv.mem(self, .qword), | 11460 | try src_mcv.mem(self, .{ .size = .qword }), |
| 11377 | ) else try self.asmRegisterRegister( | 11461 | ) else try self.asmRegisterRegister( |
| 11378 | .{ .v_ps, .cvtph2 }, | 11462 | .{ .v_ps, .cvtph2 }, |
| 11379 | tmp_reg, | 11463 | tmp_reg, |
| ... | @@ -11416,7 +11500,7 @@ fn genBinOp( | ... | @@ -11416,7 +11500,7 @@ fn genBinOp( |
| 11416 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 11500 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 11417 | .{ .v_ps, .cvtph2 }, | 11501 | .{ .v_ps, .cvtph2 }, |
| 11418 | tmp_reg, | 11502 | tmp_reg, |
| 11419 | try src_mcv.mem(self, .xword), | 11503 | try src_mcv.mem(self, .{ .size = .xword }), |
| 11420 | ) else try self.asmRegisterRegister( | 11504 | ) else try self.asmRegisterRegister( |
| 11421 | .{ .v_ps, .cvtph2 }, | 11505 | .{ .v_ps, .cvtph2 }, |
| 11422 | tmp_reg, | 11506 | tmp_reg, |
| ... | @@ -11579,10 +11663,10 @@ fn genBinOp( | ... | @@ -11579,10 +11663,10 @@ fn genBinOp( |
| 11579 | mir_tag, | 11663 | mir_tag, |
| 11580 | dst_reg, | 11664 | dst_reg, |
| 11581 | lhs_reg, | 11665 | lhs_reg, |
| 11582 | try src_mcv.mem(self, switch (lhs_ty.zigTypeTag(zcu)) { | 11666 | try src_mcv.mem(self, .{ .size = switch (lhs_ty.zigTypeTag(zcu)) { |
| 11583 | else => .fromSize(abi_size), | 11667 | else => .fromSize(abi_size), |
| 11584 | .vector => .fromBitSize(dst_reg.bitSize()), | 11668 | .vector => .fromBitSize(dst_reg.bitSize()), |
| 11585 | }), | 11669 | } }), |
| 11586 | ) else try self.asmRegisterRegisterRegister( | 11670 | ) else try self.asmRegisterRegisterRegister( |
| 11587 | mir_tag, | 11671 | mir_tag, |
| 11588 | dst_reg, | 11672 | dst_reg, |
| ... | @@ -11597,10 +11681,10 @@ fn genBinOp( | ... | @@ -11597,10 +11681,10 @@ fn genBinOp( |
| 11597 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 11681 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 11598 | mir_tag, | 11682 | mir_tag, |
| 11599 | dst_reg, | 11683 | dst_reg, |
| 11600 | try src_mcv.mem(self, switch (lhs_ty.zigTypeTag(zcu)) { | 11684 | try src_mcv.mem(self, .{ .size = switch (lhs_ty.zigTypeTag(zcu)) { |
| 11601 | else => .fromSize(abi_size), | 11685 | else => .fromSize(abi_size), |
| 11602 | .vector => .fromBitSize(dst_reg.bitSize()), | 11686 | .vector => .fromBitSize(dst_reg.bitSize()), |
| 11603 | }), | 11687 | } }), |
| 11604 | ) else try self.asmRegisterRegister( | 11688 | ) else try self.asmRegisterRegister( |
| 11605 | mir_tag, | 11689 | mir_tag, |
| 11606 | dst_reg, | 11690 | dst_reg, |
| ... | @@ -11625,10 +11709,10 @@ fn genBinOp( | ... | @@ -11625,10 +11709,10 @@ fn genBinOp( |
| 11625 | mir_tag, | 11709 | mir_tag, |
| 11626 | dst_reg, | 11710 | dst_reg, |
| 11627 | lhs_reg, | 11711 | lhs_reg, |
| 11628 | try src_mcv.mem(self, switch (lhs_ty.zigTypeTag(zcu)) { | 11712 | try src_mcv.mem(self, .{ .size = switch (lhs_ty.zigTypeTag(zcu)) { |
| 11629 | else => .fromSize(abi_size), | 11713 | else => .fromSize(abi_size), |
| 11630 | .vector => .fromBitSize(dst_reg.bitSize()), | 11714 | .vector => .fromBitSize(dst_reg.bitSize()), |
| 11631 | }), | 11715 | } }), |
| 11632 | imm, | 11716 | imm, |
| 11633 | ) else try self.asmRegisterRegisterRegisterImmediate( | 11717 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 11634 | mir_tag, | 11718 | mir_tag, |
| ... | @@ -11645,10 +11729,10 @@ fn genBinOp( | ... | @@ -11645,10 +11729,10 @@ fn genBinOp( |
| 11645 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 11729 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 11646 | mir_tag, | 11730 | mir_tag, |
| 11647 | dst_reg, | 11731 | dst_reg, |
| 11648 | try src_mcv.mem(self, switch (lhs_ty.zigTypeTag(zcu)) { | 11732 | try src_mcv.mem(self, .{ .size = switch (lhs_ty.zigTypeTag(zcu)) { |
| 11649 | else => .fromSize(abi_size), | 11733 | else => .fromSize(abi_size), |
| 11650 | .vector => .fromBitSize(dst_reg.bitSize()), | 11734 | .vector => .fromBitSize(dst_reg.bitSize()), |
| 11651 | }), | 11735 | } }), |
| 11652 | imm, | 11736 | imm, |
| 11653 | ) else try self.asmRegisterRegisterImmediate( | 11737 | ) else try self.asmRegisterRegisterImmediate( |
| 11654 | mir_tag, | 11738 | mir_tag, |
| ... | @@ -11854,7 +11938,7 @@ fn genBinOp( | ... | @@ -11854,7 +11938,7 @@ fn genBinOp( |
| 11854 | const unsigned_ty = try lhs_ty.toUnsigned(pt); | 11938 | const unsigned_ty = try lhs_ty.toUnsigned(pt); |
| 11855 | const not_mcv = try self.genTypedValue(try unsigned_ty.maxInt(pt, unsigned_ty)); | 11939 | const not_mcv = try self.genTypedValue(try unsigned_ty.maxInt(pt, unsigned_ty)); |
| 11856 | const not_mem: Memory = if (not_mcv.isMemory()) | 11940 | const not_mem: Memory = if (not_mcv.isMemory()) |
| 11857 | try not_mcv.mem(self, .fromSize(abi_size)) | 11941 | try not_mcv.mem(self, .{ .size = .fromSize(abi_size) }) |
| 11858 | else | 11942 | else |
| 11859 | .{ .base = .{ | 11943 | .{ .base = .{ |
| 11860 | .reg = try self.copyToTmpRegister(Type.usize, not_mcv.address()), | 11944 | .reg = try self.copyToTmpRegister(Type.usize, not_mcv.address()), |
| ... | @@ -11915,7 +11999,7 @@ fn genBinOp( | ... | @@ -11915,7 +11999,7 @@ fn genBinOp( |
| 11915 | } | 11999 | } |
| 11916 | | 12000 | |
| 11917 | fn genBinOpMir( | 12001 | fn genBinOpMir( |
| 11918 | self: *Self, | 12002 | self: *CodeGen, |
| 11919 | mir_tag: Mir.Inst.FixedTag, | 12003 | mir_tag: Mir.Inst.FixedTag, |
| 11920 | ty: Type, | 12004 | ty: Type, |
| 11921 | dst_mcv: MCValue, | 12005 | dst_mcv: MCValue, |
| ... | @@ -12341,7 +12425,7 @@ fn genBinOpMir( | ... | @@ -12341,7 +12425,7 @@ fn genBinOpMir( |
| 12341 | | 12425 | |
| 12342 | /// Performs multi-operand integer multiplication between dst_mcv and src_mcv, storing the result in dst_mcv. | 12426 | /// Performs multi-operand integer multiplication between dst_mcv and src_mcv, storing the result in dst_mcv. |
| 12343 | /// Does not support byte-size operands. | 12427 | /// Does not support byte-size operands. |
| 12344 | fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError!void { | 12428 | fn genIntMulComplexOpMir(self: *CodeGen, dst_ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError!void { |
| 12345 | const pt = self.pt; | 12429 | const pt = self.pt; |
| 12346 | const abi_size: u32 = @intCast(dst_ty.abiSize(pt.zcu)); | 12430 | const abi_size: u32 = @intCast(dst_ty.abiSize(pt.zcu)); |
| 12347 | try self.spillEflagsIfOccupied(); | 12431 | try self.spillEflagsIfOccupied(); |
| ... | @@ -12468,7 +12552,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M | ... | @@ -12468,7 +12552,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M |
| 12468 | } | 12552 | } |
| 12469 | } | 12553 | } |
| 12470 | | 12554 | |
| 12471 | fn airArg(self: *Self, inst: Air.Inst.Index) !void { | 12555 | fn airArg(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 12472 | const pt = self.pt; | 12556 | const pt = self.pt; |
| 12473 | const zcu = pt.zcu; | 12557 | const zcu = pt.zcu; |
| 12474 | // skip zero-bit arguments as they don't have a corresponding arg instruction | 12558 | // skip zero-bit arguments as they don't have a corresponding arg instruction |
| ... | @@ -12522,7 +12606,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -12522,7 +12606,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { |
| 12522 | const dst_mcv = try self.allocRegOrMem(inst, false); | 12606 | const dst_mcv = try self.allocRegOrMem(inst, false); |
| 12523 | if (regs_frame_addr.regs > 0) try self.asmMemoryRegister( | 12607 | if (regs_frame_addr.regs > 0) try self.asmMemoryRegister( |
| 12524 | .{ ._, .mov }, | 12608 | .{ ._, .mov }, |
| 12525 | try dst_mcv.mem(self, .byte), | 12609 | try dst_mcv.mem(self, .{ .size = .byte }), |
| 12526 | prev_reg.to8(), | 12610 | prev_reg.to8(), |
| 12527 | ); | 12611 | ); |
| 12528 | try self.genInlineMemset( | 12612 | try self.genInlineMemset( |
| ... | @@ -12554,7 +12638,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -12554,7 +12638,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { |
| 12554 | const unset = try self.asmJccReloc(.e, undefined); | 12638 | const unset = try self.asmJccReloc(.e, undefined); |
| 12555 | try self.asmMemoryRegister( | 12639 | try self.asmMemoryRegister( |
| 12556 | .{ ._s, .bt }, | 12640 | .{ ._s, .bt }, |
| 12557 | try dst_mcv.mem(self, .dword), | 12641 | try dst_mcv.mem(self, .{ .size = .dword }), |
| 12558 | index_reg.to32(), | 12642 | index_reg.to32(), |
| 12559 | ); | 12643 | ); |
| 12560 | self.performReloc(unset); | 12644 | self.performReloc(unset); |
| ... | @@ -12578,7 +12662,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -12578,7 +12662,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { |
| 12578 | return self.finishAir(inst, result, .{ .none, .none, .none }); | 12662 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 12579 | } | 12663 | } |
| 12580 | | 12664 | |
| 12581 | fn airDbgArg(self: *Self, inst: Air.Inst.Index) !void { | 12665 | fn airDbgArg(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 12582 | // skip zero-bit arguments as they don't have a corresponding arg instruction | 12666 | // skip zero-bit arguments as they don't have a corresponding arg instruction |
| 12583 | var arg_index = self.arg_index; | 12667 | var arg_index = self.arg_index; |
| 12584 | while (self.args[arg_index] == .none) arg_index += 1; | 12668 | while (self.args[arg_index] == .none) arg_index += 1; |
| ... | @@ -12594,13 +12678,13 @@ fn airDbgArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -12594,13 +12678,13 @@ fn airDbgArg(self: *Self, inst: Air.Inst.Index) !void { |
| 12594 | } else try self.airDbgVarArgs(); | 12678 | } else try self.airDbgVarArgs(); |
| 12595 | } | 12679 | } |
| 12596 | | 12680 | |
| 12597 | fn airDbgVarArgs(self: *Self) !void { | 12681 | fn airDbgVarArgs(self: *CodeGen) !void { |
| 12598 | if (self.pt.zcu.typeToFunc(self.fn_type).?.is_var_args) | 12682 | if (self.pt.zcu.typeToFunc(self.fn_type).?.is_var_args) |
| 12599 | try self.asmPseudo(.pseudo_dbg_var_args_none); | 12683 | try self.asmPseudo(.pseudo_dbg_var_args_none); |
| 12600 | } | 12684 | } |
| 12601 | | 12685 | |
| 12602 | fn genLocalDebugInfo( | 12686 | fn genLocalDebugInfo( |
| 12603 | self: *Self, | 12687 | self: *CodeGen, |
| 12604 | inst: Air.Inst.Index, | 12688 | inst: Air.Inst.Index, |
| 12605 | mcv: MCValue, | 12689 | mcv: MCValue, |
| 12606 | ) !void { | 12690 | ) !void { |
| ... | @@ -12656,19 +12740,19 @@ fn genLocalDebugInfo( | ... | @@ -12656,19 +12740,19 @@ fn genLocalDebugInfo( |
| 12656 | } | 12740 | } |
| 12657 | } | 12741 | } |
| 12658 | | 12742 | |
| 12659 | fn airRetAddr(self: *Self, inst: Air.Inst.Index) !void { | 12743 | fn airRetAddr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 12660 | const dst_mcv = try self.allocRegOrMem(inst, true); | 12744 | const dst_mcv = try self.allocRegOrMem(inst, true); |
| 12661 | try self.genCopy(Type.usize, dst_mcv, .{ .load_frame = .{ .index = .ret_addr } }, .{}); | 12745 | try self.genCopy(Type.usize, dst_mcv, .{ .load_frame = .{ .index = .ret_addr } }, .{}); |
| 12662 | return self.finishAir(inst, dst_mcv, .{ .none, .none, .none }); | 12746 | return self.finishAir(inst, dst_mcv, .{ .none, .none, .none }); |
| 12663 | } | 12747 | } |
| 12664 | | 12748 | |
| 12665 | fn airFrameAddress(self: *Self, inst: Air.Inst.Index) !void { | 12749 | fn airFrameAddress(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 12666 | const dst_mcv = try self.allocRegOrMem(inst, true); | 12750 | const dst_mcv = try self.allocRegOrMem(inst, true); |
| 12667 | try self.genCopy(Type.usize, dst_mcv, .{ .lea_frame = .{ .index = .base_ptr } }, .{}); | 12751 | try self.genCopy(Type.usize, dst_mcv, .{ .lea_frame = .{ .index = .base_ptr } }, .{}); |
| 12668 | return self.finishAir(inst, dst_mcv, .{ .none, .none, .none }); | 12752 | return self.finishAir(inst, dst_mcv, .{ .none, .none, .none }); |
| 12669 | } | 12753 | } |
| 12670 | | 12754 | |
| 12671 | fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier) !void { | 12755 | fn airCall(self: *CodeGen, inst: Air.Inst.Index, modifier: std.builtin.CallModifier) !void { |
| 12672 | if (modifier == .always_tail) return self.fail("TODO implement tail calls for x86_64", .{}); | 12756 | if (modifier == .always_tail) return self.fail("TODO implement tail calls for x86_64", .{}); |
| 12673 | | 12757 | |
| 12674 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 12758 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| ... | @@ -12702,7 +12786,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier | ... | @@ -12702,7 +12786,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 12702 | return self.finishAirResult(inst, result); | 12786 | return self.finishAirResult(inst, result); |
| 12703 | } | 12787 | } |
| 12704 | | 12788 | |
| 12705 | fn genCall(self: *Self, info: union(enum) { | 12789 | fn genCall(self: *CodeGen, info: union(enum) { |
| 12706 | air: Air.Inst.Ref, | 12790 | air: Air.Inst.Ref, |
| 12707 | lib: struct { | 12791 | lib: struct { |
| 12708 | return_type: InternPool.Index, | 12792 | return_type: InternPool.Index, |
| ... | @@ -12808,7 +12892,7 @@ fn genCall(self: *Self, info: union(enum) { | ... | @@ -12808,7 +12892,7 @@ fn genCall(self: *Self, info: union(enum) { |
| 12808 | const index_lock = self.register_manager.lockRegAssumeUnused(index_reg); | 12892 | const index_lock = self.register_manager.lockRegAssumeUnused(index_reg); |
| 12809 | defer self.register_manager.unlockReg(index_lock); | 12893 | defer self.register_manager.unlockReg(index_lock); |
| 12810 | | 12894 | |
| 12811 | const src_mem: Memory = if (src_arg.isMemory()) try src_arg.mem(self, .dword) else .{ | 12895 | const src_mem: Memory = if (src_arg.isMemory()) try src_arg.mem(self, .{ .size = .dword }) else .{ |
| 12812 | .base = .{ .reg = try self.copyToTmpRegister( | 12896 | .base = .{ .reg = try self.copyToTmpRegister( |
| 12813 | Type.usize, | 12897 | Type.usize, |
| 12814 | switch (src_arg) { | 12898 | switch (src_arg) { |
| ... | @@ -12900,7 +12984,7 @@ fn genCall(self: *Self, info: union(enum) { | ... | @@ -12900,7 +12984,7 @@ fn genCall(self: *Self, info: union(enum) { |
| 12900 | .lea_frame = .{ .index = frame_index, .off = -reg_off.off }, | 12984 | .lea_frame = .{ .index = frame_index, .off = -reg_off.off }, |
| 12901 | }, .{}), | 12985 | }, .{}), |
| 12902 | .elementwise_regs_then_frame => |regs_frame_addr| { | 12986 | .elementwise_regs_then_frame => |regs_frame_addr| { |
| 12903 | const src_mem: Memory = if (src_arg.isMemory()) try src_arg.mem(self, .dword) else .{ | 12987 | const src_mem: Memory = if (src_arg.isMemory()) try src_arg.mem(self, .{ .size = .dword }) else .{ |
| 12904 | .base = .{ .reg = try self.copyToTmpRegister( | 12988 | .base = .{ .reg = try self.copyToTmpRegister( |
| 12905 | Type.usize, | 12989 | Type.usize, |
| 12906 | switch (src_arg) { | 12990 | switch (src_arg) { |
| ... | @@ -13006,7 +13090,7 @@ fn genCall(self: *Self, info: union(enum) { | ... | @@ -13006,7 +13090,7 @@ fn genCall(self: *Self, info: union(enum) { |
| 13006 | return call_info.return_value.short; | 13090 | return call_info.return_value.short; |
| 13007 | } | 13091 | } |
| 13008 | | 13092 | |
| 13009 | fn airRet(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | 13093 | fn airRet(self: *CodeGen, inst: Air.Inst.Index, safety: bool) !void { |
| 13010 | const pt = self.pt; | 13094 | const pt = self.pt; |
| 13011 | const zcu = pt.zcu; | 13095 | const zcu = pt.zcu; |
| 13012 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 13096 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| ... | @@ -13042,7 +13126,7 @@ fn airRet(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | ... | @@ -13042,7 +13126,7 @@ fn airRet(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 13042 | try self.exitlude_jump_relocs.append(self.gpa, jmp_reloc); | 13126 | try self.exitlude_jump_relocs.append(self.gpa, jmp_reloc); |
| 13043 | } | 13127 | } |
| 13044 | | 13128 | |
| 13045 | fn airRetLoad(self: *Self, inst: Air.Inst.Index) !void { | 13129 | fn airRetLoad(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13046 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 13130 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 13047 | const ptr = try self.resolveInst(un_op); | 13131 | const ptr = try self.resolveInst(un_op); |
| 13048 | | 13132 | |
| ... | @@ -13062,7 +13146,7 @@ fn airRetLoad(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13062,7 +13146,7 @@ fn airRetLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 13062 | try self.exitlude_jump_relocs.append(self.gpa, jmp_reloc); | 13146 | try self.exitlude_jump_relocs.append(self.gpa, jmp_reloc); |
| 13063 | } | 13147 | } |
| 13064 | | 13148 | |
| 13065 | fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void { | 13149 | fn airCmp(self: *CodeGen, inst: Air.Inst.Index, op: std.math.CompareOperator) !void { |
| 13066 | const pt = self.pt; | 13150 | const pt = self.pt; |
| 13067 | const zcu = pt.zcu; | 13151 | const zcu = pt.zcu; |
| 13068 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 13152 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -13145,7 +13229,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void | ... | @@ -13145,7 +13229,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void |
| 13145 | if (lhs_mcv.isMemory()) try self.asmRegisterMemory( | 13229 | if (lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 13146 | .{ ._, .mov }, | 13230 | .{ ._, .mov }, |
| 13147 | temp_lhs_reg.to8(), | 13231 | temp_lhs_reg.to8(), |
| 13148 | try lhs_mcv.address().offset(payload_abi_size).deref().mem(self, .byte), | 13232 | try lhs_mcv.address().offset(payload_abi_size).deref().mem(self, .{ .size = .byte }), |
| 13149 | ) else { | 13233 | ) else { |
| 13150 | try self.genSetReg(temp_lhs_reg, opt_ty, lhs_mcv, .{}); | 13234 | try self.genSetReg(temp_lhs_reg, opt_ty, lhs_mcv, .{}); |
| 13151 | try self.asmRegisterImmediate( | 13235 | try self.asmRegisterImmediate( |
| ... | @@ -13158,7 +13242,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void | ... | @@ -13158,7 +13242,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void |
| 13158 | const payload_compare = payload_compare: { | 13242 | const payload_compare = payload_compare: { |
| 13159 | if (rhs_mcv.isMemory()) { | 13243 | if (rhs_mcv.isMemory()) { |
| 13160 | const rhs_mem = | 13244 | const rhs_mem = |
| 13161 | try rhs_mcv.address().offset(payload_abi_size).deref().mem(self, .byte); | 13245 | try rhs_mcv.address().offset(payload_abi_size).deref().mem(self, .{ .size = .byte }); |
| 13162 | try self.asmMemoryRegister(.{ ._, .@"test" }, rhs_mem, temp_lhs_reg.to8()); | 13246 | try self.asmMemoryRegister(.{ ._, .@"test" }, rhs_mem, temp_lhs_reg.to8()); |
| 13163 | const payload_compare = try self.asmJccReloc(.nz, undefined); | 13247 | const payload_compare = try self.asmJccReloc(.nz, undefined); |
| 13164 | try self.asmRegisterMemory(.{ ._, .cmp }, temp_lhs_reg.to8(), rhs_mem); | 13248 | try self.asmRegisterMemory(.{ ._, .cmp }, temp_lhs_reg.to8(), rhs_mem); |
| ... | @@ -13459,7 +13543,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void | ... | @@ -13459,7 +13543,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void |
| 13459 | .{ .vp_w, .insr }, | 13543 | .{ .vp_w, .insr }, |
| 13460 | tmp1_reg, | 13544 | tmp1_reg, |
| 13461 | dst_reg.to128(), | 13545 | dst_reg.to128(), |
| 13462 | try src_mcv.mem(self, .word), | 13546 | try src_mcv.mem(self, .{ .size = .word }), |
| 13463 | .u(1), | 13547 | .u(1), |
| 13464 | ) else try self.asmRegisterRegisterRegister( | 13548 | ) else try self.asmRegisterRegisterRegister( |
| 13465 | .{ .vp_, .unpcklwd }, | 13549 | .{ .vp_, .unpcklwd }, |
| ... | @@ -13505,7 +13589,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void | ... | @@ -13505,7 +13589,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: std.math.CompareOperator) !void |
| 13505 | return self.finishAir(inst, .{ .eflags = result }, .{ bin_op.lhs, bin_op.rhs, .none }); | 13589 | return self.finishAir(inst, .{ .eflags = result }, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 13506 | } | 13590 | } |
| 13507 | | 13591 | |
| 13508 | fn airCmpVector(self: *Self, inst: Air.Inst.Index) !void { | 13592 | fn airCmpVector(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13509 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 13593 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 13510 | const extra = self.air.extraData(Air.VectorCmp, ty_pl.payload).data; | 13594 | const extra = self.air.extraData(Air.VectorCmp, ty_pl.payload).data; |
| 13511 | const dst_mcv = try self.genBinOp( | 13595 | const dst_mcv = try self.genBinOp( |
| ... | @@ -13517,7 +13601,7 @@ fn airCmpVector(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13517,7 +13601,7 @@ fn airCmpVector(self: *Self, inst: Air.Inst.Index) !void { |
| 13517 | return self.finishAir(inst, dst_mcv, .{ extra.lhs, extra.rhs, .none }); | 13601 | return self.finishAir(inst, dst_mcv, .{ extra.lhs, extra.rhs, .none }); |
| 13518 | } | 13602 | } |
| 13519 | | 13603 | |
| 13520 | fn airCmpLtErrorsLen(self: *Self, inst: Air.Inst.Index) !void { | 13604 | fn airCmpLtErrorsLen(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13521 | const pt = self.pt; | 13605 | const pt = self.pt; |
| 13522 | const zcu = pt.zcu; | 13606 | const zcu = pt.zcu; |
| 13523 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 13607 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| ... | @@ -13550,7 +13634,7 @@ fn airCmpLtErrorsLen(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13550,7 +13634,7 @@ fn airCmpLtErrorsLen(self: *Self, inst: Air.Inst.Index) !void { |
| 13550 | return self.finishAir(inst, .{ .eflags = .b }, .{ un_op, .none, .none }); | 13634 | return self.finishAir(inst, .{ .eflags = .b }, .{ un_op, .none, .none }); |
| 13551 | } | 13635 | } |
| 13552 | | 13636 | |
| 13553 | fn airTry(self: *Self, inst: Air.Inst.Index) !void { | 13637 | fn airTry(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13554 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 13638 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| 13555 | const extra = self.air.extraData(Air.Try, pl_op.payload); | 13639 | const extra = self.air.extraData(Air.Try, pl_op.payload); |
| 13556 | const body: []const Air.Inst.Index = @ptrCast(self.air.extra[extra.end..][0..extra.data.body_len]); | 13640 | const body: []const Air.Inst.Index = @ptrCast(self.air.extra[extra.end..][0..extra.data.body_len]); |
| ... | @@ -13559,7 +13643,7 @@ fn airTry(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13559,7 +13643,7 @@ fn airTry(self: *Self, inst: Air.Inst.Index) !void { |
| 13559 | return self.finishAir(inst, result, .{ .none, .none, .none }); | 13643 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 13560 | } | 13644 | } |
| 13561 | | 13645 | |
| 13562 | fn airTryPtr(self: *Self, inst: Air.Inst.Index) !void { | 13646 | fn airTryPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13563 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 13647 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 13564 | const extra = self.air.extraData(Air.TryPtr, ty_pl.payload); | 13648 | const extra = self.air.extraData(Air.TryPtr, ty_pl.payload); |
| 13565 | const body: []const Air.Inst.Index = @ptrCast(self.air.extra[extra.end..][0..extra.data.body_len]); | 13649 | const body: []const Air.Inst.Index = @ptrCast(self.air.extra[extra.end..][0..extra.data.body_len]); |
| ... | @@ -13569,7 +13653,7 @@ fn airTryPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13569,7 +13653,7 @@ fn airTryPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 13569 | } | 13653 | } |
| 13570 | | 13654 | |
| 13571 | fn genTry( | 13655 | fn genTry( |
| 13572 | self: *Self, | 13656 | self: *CodeGen, |
| 13573 | inst: Air.Inst.Index, | 13657 | inst: Air.Inst.Index, |
| 13574 | operand: Air.Inst.Ref, | 13658 | operand: Air.Inst.Ref, |
| 13575 | body: []const Air.Inst.Index, | 13659 | body: []const Air.Inst.Index, |
| ... | @@ -13615,7 +13699,7 @@ fn genTry( | ... | @@ -13615,7 +13699,7 @@ fn genTry( |
| 13615 | return result; | 13699 | return result; |
| 13616 | } | 13700 | } |
| 13617 | | 13701 | |
| 13618 | fn airDbgStmt(self: *Self, inst: Air.Inst.Index) !void { | 13702 | fn airDbgStmt(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13619 | const dbg_stmt = self.air.instructions.items(.data)[@intFromEnum(inst)].dbg_stmt; | 13703 | const dbg_stmt = self.air.instructions.items(.data)[@intFromEnum(inst)].dbg_stmt; |
| 13620 | _ = try self.addInst(.{ | 13704 | _ = try self.addInst(.{ |
| 13621 | .tag = .pseudo, | 13705 | .tag = .pseudo, |
| ... | @@ -13627,14 +13711,14 @@ fn airDbgStmt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13627,14 +13711,14 @@ fn airDbgStmt(self: *Self, inst: Air.Inst.Index) !void { |
| 13627 | }); | 13711 | }); |
| 13628 | } | 13712 | } |
| 13629 | | 13713 | |
| 13630 | fn airDbgEmptyStmt(self: *Self) !void { | 13714 | fn airDbgEmptyStmt(self: *CodeGen) !void { |
| 13631 | if (self.mir_instructions.len > 0 and | 13715 | if (self.mir_instructions.len > 0 and |
| 13632 | self.mir_instructions.items(.ops)[self.mir_instructions.len - 1] == .pseudo_dbg_line_stmt_line_column) | 13716 | self.mir_instructions.items(.ops)[self.mir_instructions.len - 1] == .pseudo_dbg_line_stmt_line_column) |
| 13633 | self.mir_instructions.items(.ops)[self.mir_instructions.len - 1] = .pseudo_dbg_line_line_column; | 13717 | self.mir_instructions.items(.ops)[self.mir_instructions.len - 1] = .pseudo_dbg_line_line_column; |
| 13634 | try self.asmOpOnly(.{ ._, .nop }); | 13718 | try self.asmOpOnly(.{ ._, .nop }); |
| 13635 | } | 13719 | } |
| 13636 | | 13720 | |
| 13637 | fn airDbgInlineBlock(self: *Self, inst: Air.Inst.Index) !void { | 13721 | fn airDbgInlineBlock(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13638 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 13722 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 13639 | const extra = self.air.extraData(Air.DbgInlineBlock, ty_pl.payload); | 13723 | const extra = self.air.extraData(Air.DbgInlineBlock, ty_pl.payload); |
| 13640 | const old_inline_func = self.inline_func; | 13724 | const old_inline_func = self.inline_func; |
| ... | @@ -13653,13 +13737,13 @@ fn airDbgInlineBlock(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13653,13 +13737,13 @@ fn airDbgInlineBlock(self: *Self, inst: Air.Inst.Index) !void { |
| 13653 | }); | 13737 | }); |
| 13654 | } | 13738 | } |
| 13655 | | 13739 | |
| 13656 | fn airDbgVar(self: *Self, inst: Air.Inst.Index) !void { | 13740 | fn airDbgVar(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13657 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 13741 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| 13658 | try self.genLocalDebugInfo(inst, try self.resolveInst(pl_op.operand)); | 13742 | try self.genLocalDebugInfo(inst, try self.resolveInst(pl_op.operand)); |
| 13659 | return self.finishAir(inst, .unreach, .{ pl_op.operand, .none, .none }); | 13743 | return self.finishAir(inst, .unreach, .{ pl_op.operand, .none, .none }); |
| 13660 | } | 13744 | } |
| 13661 | | 13745 | |
| 13662 | fn genCondBrMir(self: *Self, ty: Type, mcv: MCValue) !Mir.Inst.Index { | 13746 | fn genCondBrMir(self: *CodeGen, ty: Type, mcv: MCValue) !Mir.Inst.Index { |
| 13663 | const pt = self.pt; | 13747 | const pt = self.pt; |
| 13664 | const abi_size = ty.abiSize(pt.zcu); | 13748 | const abi_size = ty.abiSize(pt.zcu); |
| 13665 | switch (mcv) { | 13749 | switch (mcv) { |
| ... | @@ -13686,7 +13770,7 @@ fn genCondBrMir(self: *Self, ty: Type, mcv: MCValue) !Mir.Inst.Index { | ... | @@ -13686,7 +13770,7 @@ fn genCondBrMir(self: *Self, ty: Type, mcv: MCValue) !Mir.Inst.Index { |
| 13686 | } | 13770 | } |
| 13687 | } | 13771 | } |
| 13688 | | 13772 | |
| 13689 | fn airCondBr(self: *Self, inst: Air.Inst.Index) !void { | 13773 | fn airCondBr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 13690 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 13774 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| 13691 | const cond = try self.resolveInst(pl_op.operand); | 13775 | const cond = try self.resolveInst(pl_op.operand); |
| 13692 | const cond_ty = self.typeOf(pl_op.operand); | 13776 | const cond_ty = self.typeOf(pl_op.operand); |
| ... | @@ -13731,7 +13815,7 @@ fn airCondBr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -13731,7 +13815,7 @@ fn airCondBr(self: *Self, inst: Air.Inst.Index) !void { |
| 13731 | // We already took care of pl_op.operand earlier, so there's nothing left to do. | 13815 | // We already took care of pl_op.operand earlier, so there's nothing left to do. |
| 13732 | } | 13816 | } |
| 13733 | | 13817 | |
| 13734 | fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MCValue { | 13818 | fn isNull(self: *CodeGen, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MCValue { |
| 13735 | const pt = self.pt; | 13819 | const pt = self.pt; |
| 13736 | const zcu = pt.zcu; | 13820 | const zcu = pt.zcu; |
| 13737 | switch (opt_mcv) { | 13821 | switch (opt_mcv) { |
| ... | @@ -13862,7 +13946,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC | ... | @@ -13862,7 +13946,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC |
| 13862 | } | 13946 | } |
| 13863 | } | 13947 | } |
| 13864 | | 13948 | |
| 13865 | fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { | 13949 | fn isNullPtr(self: *CodeGen, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { |
| 13866 | const pt = self.pt; | 13950 | const pt = self.pt; |
| 13867 | const zcu = pt.zcu; | 13951 | const zcu = pt.zcu; |
| 13868 | const opt_ty = ptr_ty.childType(zcu); | 13952 | const opt_ty = ptr_ty.childType(zcu); |
| ... | @@ -13899,7 +13983,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) | ... | @@ -13899,7 +13983,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) |
| 13899 | return .{ .eflags = .e }; | 13983 | return .{ .eflags = .e }; |
| 13900 | } | 13984 | } |
| 13901 | | 13985 | |
| 13902 | fn isErr(self: *Self, maybe_inst: ?Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MCValue { | 13986 | fn isErr(self: *CodeGen, maybe_inst: ?Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MCValue { |
| 13903 | const pt = self.pt; | 13987 | const pt = self.pt; |
| 13904 | const zcu = pt.zcu; | 13988 | const zcu = pt.zcu; |
| 13905 | const err_ty = eu_ty.errorUnionSet(zcu); | 13989 | const err_ty = eu_ty.errorUnionSet(zcu); |
| ... | @@ -13948,7 +14032,7 @@ fn isErr(self: *Self, maybe_inst: ?Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) | ... | @@ -13948,7 +14032,7 @@ fn isErr(self: *Self, maybe_inst: ?Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) |
| 13948 | return MCValue{ .eflags = .a }; | 14032 | return MCValue{ .eflags = .a }; |
| 13949 | } | 14033 | } |
| 13950 | | 14034 | |
| 13951 | fn isErrPtr(self: *Self, maybe_inst: ?Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { | 14035 | fn isErrPtr(self: *CodeGen, maybe_inst: ?Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { |
| 13952 | const pt = self.pt; | 14036 | const pt = self.pt; |
| 13953 | const zcu = pt.zcu; | 14037 | const zcu = pt.zcu; |
| 13954 | const eu_ty = ptr_ty.childType(zcu); | 14038 | const eu_ty = ptr_ty.childType(zcu); |
| ... | @@ -13981,7 +14065,7 @@ fn isErrPtr(self: *Self, maybe_inst: ?Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCV | ... | @@ -13981,7 +14065,7 @@ fn isErrPtr(self: *Self, maybe_inst: ?Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCV |
| 13981 | return MCValue{ .eflags = .a }; | 14065 | return MCValue{ .eflags = .a }; |
| 13982 | } | 14066 | } |
| 13983 | | 14067 | |
| 13984 | fn isNonErr(self: *Self, inst: Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MCValue { | 14068 | fn isNonErr(self: *CodeGen, inst: Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MCValue { |
| 13985 | const is_err_res = try self.isErr(inst, eu_ty, eu_mcv); | 14069 | const is_err_res = try self.isErr(inst, eu_ty, eu_mcv); |
| 13986 | switch (is_err_res) { | 14070 | switch (is_err_res) { |
| 13987 | .eflags => |cc| { | 14071 | .eflags => |cc| { |
| ... | @@ -13996,7 +14080,7 @@ fn isNonErr(self: *Self, inst: Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MC | ... | @@ -13996,7 +14080,7 @@ fn isNonErr(self: *Self, inst: Air.Inst.Index, eu_ty: Type, eu_mcv: MCValue) !MC |
| 13996 | } | 14080 | } |
| 13997 | } | 14081 | } |
| 13998 | | 14082 | |
| 13999 | fn isNonErrPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { | 14083 | fn isNonErrPtr(self: *CodeGen, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) !MCValue { |
| 14000 | const is_err_res = try self.isErrPtr(inst, ptr_ty, ptr_mcv); | 14084 | const is_err_res = try self.isErrPtr(inst, ptr_ty, ptr_mcv); |
| 14001 | switch (is_err_res) { | 14085 | switch (is_err_res) { |
| 14002 | .eflags => |cc| { | 14086 | .eflags => |cc| { |
| ... | @@ -14011,7 +14095,7 @@ fn isNonErrPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue | ... | @@ -14011,7 +14095,7 @@ fn isNonErrPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue |
| 14011 | } | 14095 | } |
| 14012 | } | 14096 | } |
| 14013 | | 14097 | |
| 14014 | fn airIsNull(self: *Self, inst: Air.Inst.Index) !void { | 14098 | fn airIsNull(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14015 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14099 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14016 | const operand = try self.resolveInst(un_op); | 14100 | const operand = try self.resolveInst(un_op); |
| 14017 | const ty = self.typeOf(un_op); | 14101 | const ty = self.typeOf(un_op); |
| ... | @@ -14019,7 +14103,7 @@ fn airIsNull(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14019,7 +14103,7 @@ fn airIsNull(self: *Self, inst: Air.Inst.Index) !void { |
| 14019 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14103 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14020 | } | 14104 | } |
| 14021 | | 14105 | |
| 14022 | fn airIsNullPtr(self: *Self, inst: Air.Inst.Index) !void { | 14106 | fn airIsNullPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14023 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14107 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14024 | const operand = try self.resolveInst(un_op); | 14108 | const operand = try self.resolveInst(un_op); |
| 14025 | const ty = self.typeOf(un_op); | 14109 | const ty = self.typeOf(un_op); |
| ... | @@ -14027,7 +14111,7 @@ fn airIsNullPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14027,7 +14111,7 @@ fn airIsNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 14027 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14111 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14028 | } | 14112 | } |
| 14029 | | 14113 | |
| 14030 | fn airIsNonNull(self: *Self, inst: Air.Inst.Index) !void { | 14114 | fn airIsNonNull(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14031 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14115 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14032 | const operand = try self.resolveInst(un_op); | 14116 | const operand = try self.resolveInst(un_op); |
| 14033 | const ty = self.typeOf(un_op); | 14117 | const ty = self.typeOf(un_op); |
| ... | @@ -14039,7 +14123,7 @@ fn airIsNonNull(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14039,7 +14123,7 @@ fn airIsNonNull(self: *Self, inst: Air.Inst.Index) !void { |
| 14039 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14123 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14040 | } | 14124 | } |
| 14041 | | 14125 | |
| 14042 | fn airIsNonNullPtr(self: *Self, inst: Air.Inst.Index) !void { | 14126 | fn airIsNonNullPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14043 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14127 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14044 | const operand = try self.resolveInst(un_op); | 14128 | const operand = try self.resolveInst(un_op); |
| 14045 | const ty = self.typeOf(un_op); | 14129 | const ty = self.typeOf(un_op); |
| ... | @@ -14050,7 +14134,7 @@ fn airIsNonNullPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14050,7 +14134,7 @@ fn airIsNonNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 14050 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14134 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14051 | } | 14135 | } |
| 14052 | | 14136 | |
| 14053 | fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { | 14137 | fn airIsErr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14054 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14138 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14055 | const operand = try self.resolveInst(un_op); | 14139 | const operand = try self.resolveInst(un_op); |
| 14056 | const ty = self.typeOf(un_op); | 14140 | const ty = self.typeOf(un_op); |
| ... | @@ -14058,7 +14142,7 @@ fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14058,7 +14142,7 @@ fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { |
| 14058 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14142 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14059 | } | 14143 | } |
| 14060 | | 14144 | |
| 14061 | fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { | 14145 | fn airIsErrPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14062 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14146 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14063 | const operand = try self.resolveInst(un_op); | 14147 | const operand = try self.resolveInst(un_op); |
| 14064 | const ty = self.typeOf(un_op); | 14148 | const ty = self.typeOf(un_op); |
| ... | @@ -14066,7 +14150,7 @@ fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14066,7 +14150,7 @@ fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 14066 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14150 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14067 | } | 14151 | } |
| 14068 | | 14152 | |
| 14069 | fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { | 14153 | fn airIsNonErr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14070 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14154 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14071 | const operand = try self.resolveInst(un_op); | 14155 | const operand = try self.resolveInst(un_op); |
| 14072 | const ty = self.typeOf(un_op); | 14156 | const ty = self.typeOf(un_op); |
| ... | @@ -14074,7 +14158,7 @@ fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14074,7 +14158,7 @@ fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { |
| 14074 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14158 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14075 | } | 14159 | } |
| 14076 | | 14160 | |
| 14077 | fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { | 14161 | fn airIsNonErrPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14078 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 14162 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 14079 | const operand = try self.resolveInst(un_op); | 14163 | const operand = try self.resolveInst(un_op); |
| 14080 | const ty = self.typeOf(un_op); | 14164 | const ty = self.typeOf(un_op); |
| ... | @@ -14082,7 +14166,7 @@ fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14082,7 +14166,7 @@ fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 14082 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 14166 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14083 | } | 14167 | } |
| 14084 | | 14168 | |
| 14085 | fn airLoop(self: *Self, inst: Air.Inst.Index) !void { | 14169 | fn airLoop(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14086 | // A loop is a setup to be able to jump back to the beginning. | 14170 | // A loop is a setup to be able to jump back to the beginning. |
| 14087 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 14171 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 14088 | const loop = self.air.extraData(Air.Block, ty_pl.payload); | 14172 | const loop = self.air.extraData(Air.Block, ty_pl.payload); |
| ... | @@ -14100,7 +14184,7 @@ fn airLoop(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14100,7 +14184,7 @@ fn airLoop(self: *Self, inst: Air.Inst.Index) !void { |
| 14100 | try self.genBodyBlock(body); | 14184 | try self.genBodyBlock(body); |
| 14101 | } | 14185 | } |
| 14102 | | 14186 | |
| 14103 | fn airBlock(self: *Self, inst: Air.Inst.Index) !void { | 14187 | fn airBlock(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14104 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 14188 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 14105 | const extra = self.air.extraData(Air.Block, ty_pl.payload); | 14189 | const extra = self.air.extraData(Air.Block, ty_pl.payload); |
| 14106 | try self.asmPseudo(.pseudo_dbg_enter_block_none); | 14190 | try self.asmPseudo(.pseudo_dbg_enter_block_none); |
| ... | @@ -14108,7 +14192,7 @@ fn airBlock(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14108,7 +14192,7 @@ fn airBlock(self: *Self, inst: Air.Inst.Index) !void { |
| 14108 | try self.asmPseudo(.pseudo_dbg_leave_block_none); | 14192 | try self.asmPseudo(.pseudo_dbg_leave_block_none); |
| 14109 | } | 14193 | } |
| 14110 | | 14194 | |
| 14111 | fn lowerBlock(self: *Self, inst: Air.Inst.Index, body: []const Air.Inst.Index) !void { | 14195 | fn lowerBlock(self: *CodeGen, inst: Air.Inst.Index, body: []const Air.Inst.Index) !void { |
| 14112 | // A block is a setup to be able to jump to the end. | 14196 | // A block is a setup to be able to jump to the end. |
| 14113 | const inst_tracking_i = self.inst_tracking.count(); | 14197 | const inst_tracking_i = self.inst_tracking.count(); |
| 14114 | self.inst_tracking.putAssumeCapacityNoClobber(inst, .init(.unreach)); | 14198 | self.inst_tracking.putAssumeCapacityNoClobber(inst, .init(.unreach)); |
| ... | @@ -14137,7 +14221,7 @@ fn lowerBlock(self: *Self, inst: Air.Inst.Index, body: []const Air.Inst.Index) ! | ... | @@ -14137,7 +14221,7 @@ fn lowerBlock(self: *Self, inst: Air.Inst.Index, body: []const Air.Inst.Index) ! |
| 14137 | self.getValueIfFree(tracking.short, inst); | 14221 | self.getValueIfFree(tracking.short, inst); |
| 14138 | } | 14222 | } |
| 14139 | | 14223 | |
| 14140 | fn lowerSwitchBr(self: *Self, inst: Air.Inst.Index, switch_br: Air.UnwrappedSwitch, condition: MCValue) !void { | 14224 | fn lowerSwitchBr(self: *CodeGen, inst: Air.Inst.Index, switch_br: Air.UnwrappedSwitch, condition: MCValue) !void { |
| 14141 | const zcu = self.pt.zcu; | 14225 | const zcu = self.pt.zcu; |
| 14142 | const condition_ty = self.typeOf(switch_br.operand); | 14226 | const condition_ty = self.typeOf(switch_br.operand); |
| 14143 | const liveness = try self.liveness.getSwitchBr(self.gpa, inst, switch_br.cases_len + 1); | 14227 | const liveness = try self.liveness.getSwitchBr(self.gpa, inst, switch_br.cases_len + 1); |
| ... | @@ -14255,7 +14339,7 @@ fn lowerSwitchBr(self: *Self, inst: Air.Inst.Index, switch_br: Air.UnwrappedSwit | ... | @@ -14255,7 +14339,7 @@ fn lowerSwitchBr(self: *Self, inst: Air.Inst.Index, switch_br: Air.UnwrappedSwit |
| 14255 | } | 14339 | } |
| 14256 | } | 14340 | } |
| 14257 | | 14341 | |
| 14258 | fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void { | 14342 | fn airSwitchBr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14259 | const switch_br = self.air.unwrapSwitch(inst); | 14343 | const switch_br = self.air.unwrapSwitch(inst); |
| 14260 | const condition = try self.resolveInst(switch_br.operand); | 14344 | const condition = try self.resolveInst(switch_br.operand); |
| 14261 | | 14345 | |
| ... | @@ -14271,7 +14355,7 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14271,7 +14355,7 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void { |
| 14271 | // We already took care of pl_op.operand earlier, so there's nothing left to do | 14355 | // We already took care of pl_op.operand earlier, so there's nothing left to do |
| 14272 | } | 14356 | } |
| 14273 | | 14357 | |
| 14274 | fn airLoopSwitchBr(self: *Self, inst: Air.Inst.Index) !void { | 14358 | fn airLoopSwitchBr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14275 | const switch_br = self.air.unwrapSwitch(inst); | 14359 | const switch_br = self.air.unwrapSwitch(inst); |
| 14276 | const condition = try self.resolveInst(switch_br.operand); | 14360 | const condition = try self.resolveInst(switch_br.operand); |
| 14277 | | 14361 | |
| ... | @@ -14309,7 +14393,7 @@ fn airLoopSwitchBr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14309,7 +14393,7 @@ fn airLoopSwitchBr(self: *Self, inst: Air.Inst.Index) !void { |
| 14309 | try self.processDeath(inst); | 14393 | try self.processDeath(inst); |
| 14310 | } | 14394 | } |
| 14311 | | 14395 | |
| 14312 | fn airSwitchDispatch(self: *Self, inst: Air.Inst.Index) !void { | 14396 | fn airSwitchDispatch(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14313 | const br = self.air.instructions.items(.data)[@intFromEnum(inst)].br; | 14397 | const br = self.air.instructions.items(.data)[@intFromEnum(inst)].br; |
| 14314 | | 14398 | |
| 14315 | const block_ty = self.typeOfIndex(br.block_inst); | 14399 | const block_ty = self.typeOfIndex(br.block_inst); |
| ... | @@ -14354,7 +14438,7 @@ fn airSwitchDispatch(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14354,7 +14438,7 @@ fn airSwitchDispatch(self: *Self, inst: Air.Inst.Index) !void { |
| 14354 | try self.freeValue(block_tracking.short); | 14438 | try self.freeValue(block_tracking.short); |
| 14355 | } | 14439 | } |
| 14356 | | 14440 | |
| 14357 | fn performReloc(self: *Self, reloc: Mir.Inst.Index) void { | 14441 | fn performReloc(self: *CodeGen, reloc: Mir.Inst.Index) void { |
| 14358 | const next_inst: u32 = @intCast(self.mir_instructions.len); | 14442 | const next_inst: u32 = @intCast(self.mir_instructions.len); |
| 14359 | switch (self.mir_instructions.items(.tag)[reloc]) { | 14443 | switch (self.mir_instructions.items(.tag)[reloc]) { |
| 14360 | .j, .jmp => {}, | 14444 | .j, .jmp => {}, |
| ... | @@ -14367,7 +14451,7 @@ fn performReloc(self: *Self, reloc: Mir.Inst.Index) void { | ... | @@ -14367,7 +14451,7 @@ fn performReloc(self: *Self, reloc: Mir.Inst.Index) void { |
| 14367 | self.mir_instructions.items(.data)[reloc].inst.inst = next_inst; | 14451 | self.mir_instructions.items(.data)[reloc].inst.inst = next_inst; |
| 14368 | } | 14452 | } |
| 14369 | | 14453 | |
| 14370 | fn airBr(self: *Self, inst: Air.Inst.Index) !void { | 14454 | fn airBr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14371 | const zcu = self.pt.zcu; | 14455 | const zcu = self.pt.zcu; |
| 14372 | const br = self.air.instructions.items(.data)[@intFromEnum(inst)].br; | 14456 | const br = self.air.instructions.items(.data)[@intFromEnum(inst)].br; |
| 14373 | | 14457 | |
| ... | @@ -14426,7 +14510,7 @@ fn airBr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14426,7 +14510,7 @@ fn airBr(self: *Self, inst: Air.Inst.Index) !void { |
| 14426 | try self.freeValue(block_tracking.short); | 14510 | try self.freeValue(block_tracking.short); |
| 14427 | } | 14511 | } |
| 14428 | | 14512 | |
| 14429 | fn airRepeat(self: *Self, inst: Air.Inst.Index) !void { | 14513 | fn airRepeat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14430 | const loop_inst = self.air.instructions.items(.data)[@intFromEnum(inst)].repeat.loop_inst; | 14514 | const loop_inst = self.air.instructions.items(.data)[@intFromEnum(inst)].repeat.loop_inst; |
| 14431 | const repeat_info = self.loops.get(loop_inst).?; | 14515 | const repeat_info = self.loops.get(loop_inst).?; |
| 14432 | try self.restoreState(repeat_info.state, &.{}, .{ | 14516 | try self.restoreState(repeat_info.state, &.{}, .{ |
| ... | @@ -14438,7 +14522,7 @@ fn airRepeat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -14438,7 +14522,7 @@ fn airRepeat(self: *Self, inst: Air.Inst.Index) !void { |
| 14438 | _ = try self.asmJmpReloc(repeat_info.target); | 14522 | _ = try self.asmJmpReloc(repeat_info.target); |
| 14439 | } | 14523 | } |
| 14440 | | 14524 | |
| 14441 | fn airAsm(self: *Self, inst: Air.Inst.Index) !void { | 14525 | fn airAsm(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14442 | const pt = self.pt; | 14526 | const pt = self.pt; |
| 14443 | const zcu = pt.zcu; | 14527 | const zcu = pt.zcu; |
| 14444 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 14528 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -15110,7 +15194,7 @@ const MoveStrategy = union(enum) { | ... | @@ -15110,7 +15194,7 @@ const MoveStrategy = union(enum) { |
| 15110 | extract: Mir.Inst.FixedTag, | 15194 | extract: Mir.Inst.FixedTag, |
| 15111 | }; | 15195 | }; |
| 15112 | | 15196 | |
| 15113 | pub fn read(strat: MoveStrategy, self: *Self, dst_reg: Register, src_mem: Memory) !void { | 15197 | pub fn read(strat: MoveStrategy, self: *CodeGen, dst_reg: Register, src_mem: Memory) !void { |
| 15114 | switch (strat) { | 15198 | switch (strat) { |
| 15115 | .move => |tag| try self.asmRegisterMemory(tag, switch (tag[1]) { | 15199 | .move => |tag| try self.asmRegisterMemory(tag, switch (tag[1]) { |
| 15116 | else => dst_reg, | 15200 | else => dst_reg, |
| ... | @@ -15136,7 +15220,7 @@ const MoveStrategy = union(enum) { | ... | @@ -15136,7 +15220,7 @@ const MoveStrategy = union(enum) { |
| 15136 | ), | 15220 | ), |
| 15137 | } | 15221 | } |
| 15138 | } | 15222 | } |
| 15139 | pub fn write(strat: MoveStrategy, self: *Self, dst_mem: Memory, src_reg: Register) !void { | 15223 | pub fn write(strat: MoveStrategy, self: *CodeGen, dst_mem: Memory, src_reg: Register) !void { |
| 15140 | switch (strat) { | 15224 | switch (strat) { |
| 15141 | .move => |tag| try self.asmMemoryRegister(tag, dst_mem, src_reg), | 15225 | .move => |tag| try self.asmMemoryRegister(tag, dst_mem, src_reg), |
| 15142 | .x87_load_store => { | 15226 | .x87_load_store => { |
| ... | @@ -15152,7 +15236,7 @@ const MoveStrategy = union(enum) { | ... | @@ -15152,7 +15236,7 @@ const MoveStrategy = union(enum) { |
| 15152 | } | 15236 | } |
| 15153 | } | 15237 | } |
| 15154 | }; | 15238 | }; |
| 15155 | fn moveStrategy(self: *Self, ty: Type, class: Register.Class, aligned: bool) !MoveStrategy { | 15239 | fn moveStrategy(self: *CodeGen, ty: Type, class: Register.Class, aligned: bool) !MoveStrategy { |
| 15156 | const pt = self.pt; | 15240 | const pt = self.pt; |
| 15157 | const zcu = pt.zcu; | 15241 | const zcu = pt.zcu; |
| 15158 | switch (class) { | 15242 | switch (class) { |
| ... | @@ -15383,7 +15467,7 @@ const CopyOptions = struct { | ... | @@ -15383,7 +15467,7 @@ const CopyOptions = struct { |
| 15383 | safety: bool = false, | 15467 | safety: bool = false, |
| 15384 | }; | 15468 | }; |
| 15385 | | 15469 | |
| 15386 | fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: CopyOptions) InnerError!void { | 15470 | fn genCopy(self: *CodeGen, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: CopyOptions) InnerError!void { |
| 15387 | const pt = self.pt; | 15471 | const pt = self.pt; |
| 15388 | | 15472 | |
| 15389 | const src_lock = if (src_mcv.getReg()) |reg| self.register_manager.lockReg(reg) else null; | 15473 | const src_lock = if (src_mcv.getReg()) |reg| self.register_manager.lockReg(reg) else null; |
| ... | @@ -15496,7 +15580,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: Copy | ... | @@ -15496,7 +15580,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: Copy |
| 15496 | } | 15580 | } |
| 15497 | | 15581 | |
| 15498 | fn genSetReg( | 15582 | fn genSetReg( |
| 15499 | self: *Self, | 15583 | self: *CodeGen, |
| 15500 | dst_reg: Register, | 15584 | dst_reg: Register, |
| 15501 | ty: Type, | 15585 | ty: Type, |
| 15502 | src_mcv: MCValue, | 15586 | src_mcv: MCValue, |
| ... | @@ -15781,7 +15865,7 @@ fn genSetReg( | ... | @@ -15781,7 +15865,7 @@ fn genSetReg( |
| 15781 | } | 15865 | } |
| 15782 | | 15866 | |
| 15783 | fn genSetMem( | 15867 | fn genSetMem( |
| 15784 | self: *Self, | 15868 | self: *CodeGen, |
| 15785 | base: Memory.Base, | 15869 | base: Memory.Base, |
| 15786 | disp: i32, | 15870 | disp: i32, |
| 15787 | ty: Type, | 15871 | ty: Type, |
| ... | @@ -16012,7 +16096,7 @@ fn genSetMem( | ... | @@ -16012,7 +16096,7 @@ fn genSetMem( |
| 16012 | } | 16096 | } |
| 16013 | } | 16097 | } |
| 16014 | | 16098 | |
| 16015 | fn genInlineMemcpy(self: *Self, dst_ptr: MCValue, src_ptr: MCValue, len: MCValue) InnerError!void { | 16099 | fn genInlineMemcpy(self: *CodeGen, dst_ptr: MCValue, src_ptr: MCValue, len: MCValue) InnerError!void { |
| 16016 | try self.spillRegisters(&.{ .rsi, .rdi, .rcx }); | 16100 | try self.spillRegisters(&.{ .rsi, .rdi, .rcx }); |
| 16017 | try self.genSetReg(.rsi, Type.usize, src_ptr, .{}); | 16101 | try self.genSetReg(.rsi, Type.usize, src_ptr, .{}); |
| 16018 | try self.genSetReg(.rdi, Type.usize, dst_ptr, .{}); | 16102 | try self.genSetReg(.rdi, Type.usize, dst_ptr, .{}); |
| ... | @@ -16021,7 +16105,7 @@ fn genInlineMemcpy(self: *Self, dst_ptr: MCValue, src_ptr: MCValue, len: MCValue | ... | @@ -16021,7 +16105,7 @@ fn genInlineMemcpy(self: *Self, dst_ptr: MCValue, src_ptr: MCValue, len: MCValue |
| 16021 | } | 16105 | } |
| 16022 | | 16106 | |
| 16023 | fn genInlineMemset( | 16107 | fn genInlineMemset( |
| 16024 | self: *Self, | 16108 | self: *CodeGen, |
| 16025 | dst_ptr: MCValue, | 16109 | dst_ptr: MCValue, |
| 16026 | value: MCValue, | 16110 | value: MCValue, |
| 16027 | len: MCValue, | 16111 | len: MCValue, |
| ... | @@ -16035,7 +16119,7 @@ fn genInlineMemset( | ... | @@ -16035,7 +16119,7 @@ fn genInlineMemset( |
| 16035 | } | 16119 | } |
| 16036 | | 16120 | |
| 16037 | fn genExternSymbolRef( | 16121 | fn genExternSymbolRef( |
| 16038 | self: *Self, | 16122 | self: *CodeGen, |
| 16039 | comptime tag: Mir.Inst.Tag, | 16123 | comptime tag: Mir.Inst.Tag, |
| 16040 | lib: ?[]const u8, | 16124 | lib: ?[]const u8, |
| 16041 | callee: []const u8, | 16125 | callee: []const u8, |
| ... | @@ -16061,7 +16145,7 @@ fn genExternSymbolRef( | ... | @@ -16061,7 +16145,7 @@ fn genExternSymbolRef( |
| 16061 | } | 16145 | } |
| 16062 | | 16146 | |
| 16063 | fn genLazySymbolRef( | 16147 | fn genLazySymbolRef( |
| 16064 | self: *Self, | 16148 | self: *CodeGen, |
| 16065 | comptime tag: Mir.Inst.Tag, | 16149 | comptime tag: Mir.Inst.Tag, |
| 16066 | reg: Register, | 16150 | reg: Register, |
| 16067 | lazy_sym: link.File.LazySymbol, | 16151 | lazy_sym: link.File.LazySymbol, |
| ... | @@ -16159,7 +16243,7 @@ fn genLazySymbolRef( | ... | @@ -16159,7 +16243,7 @@ fn genLazySymbolRef( |
| 16159 | } | 16243 | } |
| 16160 | } | 16244 | } |
| 16161 | | 16245 | |
| 16162 | fn airIntFromPtr(self: *Self, inst: Air.Inst.Index) !void { | 16246 | fn airIntFromPtr(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16163 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 16247 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 16164 | const result = result: { | 16248 | const result = result: { |
| 16165 | // TODO: handle case where the operand is a slice not a raw pointer | 16249 | // TODO: handle case where the operand is a slice not a raw pointer |
| ... | @@ -16174,7 +16258,7 @@ fn airIntFromPtr(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16174,7 +16258,7 @@ fn airIntFromPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 16174 | return self.finishAir(inst, result, .{ un_op, .none, .none }); | 16258 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 16175 | } | 16259 | } |
| 16176 | | 16260 | |
| 16177 | fn airBitCast(self: *Self, inst: Air.Inst.Index) !void { | 16261 | fn airBitCast(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16178 | const pt = self.pt; | 16262 | const pt = self.pt; |
| 16179 | const zcu = pt.zcu; | 16263 | const zcu = pt.zcu; |
| 16180 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 16264 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -16239,7 +16323,7 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16239,7 +16323,7 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void { |
| 16239 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 16323 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 16240 | } | 16324 | } |
| 16241 | | 16325 | |
| 16242 | fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { | 16326 | fn airArrayToSlice(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16243 | const pt = self.pt; | 16327 | const pt = self.pt; |
| 16244 | const zcu = pt.zcu; | 16328 | const zcu = pt.zcu; |
| 16245 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 16329 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -16264,7 +16348,7 @@ fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16264,7 +16348,7 @@ fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 16264 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 16348 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 16265 | } | 16349 | } |
| 16266 | | 16350 | |
| 16267 | fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void { | 16351 | fn airFloatFromInt(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16268 | const pt = self.pt; | 16352 | const pt = self.pt; |
| 16269 | const zcu = pt.zcu; | 16353 | const zcu = pt.zcu; |
| 16270 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 16354 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -16344,7 +16428,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16344,7 +16428,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void { |
| 16344 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 16428 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 16345 | } | 16429 | } |
| 16346 | | 16430 | |
| 16347 | fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void { | 16431 | fn airIntFromFloat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16348 | const pt = self.pt; | 16432 | const pt = self.pt; |
| 16349 | const zcu = pt.zcu; | 16433 | const zcu = pt.zcu; |
| 16350 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 16434 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -16416,7 +16500,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16416,7 +16500,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void { |
| 16416 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 16500 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 16417 | } | 16501 | } |
| 16418 | | 16502 | |
| 16419 | fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void { | 16503 | fn airCmpxchg(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16420 | const pt = self.pt; | 16504 | const pt = self.pt; |
| 16421 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 16505 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| 16422 | const extra = self.air.extraData(Air.Cmpxchg, ty_pl.payload).data; | 16506 | const extra = self.air.extraData(Air.Cmpxchg, ty_pl.payload).data; |
| ... | @@ -16463,7 +16547,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16463,7 +16547,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void { |
| 16463 | const ptr_mcv = try self.resolveInst(extra.ptr); | 16547 | const ptr_mcv = try self.resolveInst(extra.ptr); |
| 16464 | const mem_size: Memory.Size = .fromSize(val_abi_size); | 16548 | const mem_size: Memory.Size = .fromSize(val_abi_size); |
| 16465 | const ptr_mem: Memory = switch (ptr_mcv) { | 16549 | const ptr_mem: Memory = switch (ptr_mcv) { |
| 16466 | .immediate, .register, .register_offset, .lea_frame => try ptr_mcv.deref().mem(self, mem_size), | 16550 | .immediate, .register, .register_offset, .lea_frame => try ptr_mcv.deref().mem(self, .{ .size = mem_size }), |
| 16467 | else => .{ | 16551 | else => .{ |
| 16468 | .base = .{ .reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv) }, | 16552 | .base = .{ .reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv) }, |
| 16469 | .mod = .{ .rm = .{ .size = mem_size } }, | 16553 | .mod = .{ .rm = .{ .size = mem_size } }, |
| ... | @@ -16504,7 +16588,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16504,7 +16588,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void { |
| 16504 | } | 16588 | } |
| 16505 | | 16589 | |
| 16506 | fn atomicOp( | 16590 | fn atomicOp( |
| 16507 | self: *Self, | 16591 | self: *CodeGen, |
| 16508 | ptr_mcv: MCValue, | 16592 | ptr_mcv: MCValue, |
| 16509 | val_mcv: MCValue, | 16593 | val_mcv: MCValue, |
| 16510 | ptr_ty: Type, | 16594 | ptr_ty: Type, |
| ... | @@ -16530,7 +16614,7 @@ fn atomicOp( | ... | @@ -16530,7 +16614,7 @@ fn atomicOp( |
| 16530 | const val_abi_size: u32 = @intCast(val_ty.abiSize(zcu)); | 16614 | const val_abi_size: u32 = @intCast(val_ty.abiSize(zcu)); |
| 16531 | const mem_size: Memory.Size = .fromSize(val_abi_size); | 16615 | const mem_size: Memory.Size = .fromSize(val_abi_size); |
| 16532 | const ptr_mem: Memory = switch (ptr_mcv) { | 16616 | const ptr_mem: Memory = switch (ptr_mcv) { |
| 16533 | .immediate, .register, .register_offset, .lea_frame => try ptr_mcv.deref().mem(self, mem_size), | 16617 | .immediate, .register, .register_offset, .lea_frame => try ptr_mcv.deref().mem(self, .{ .size = mem_size }), |
| 16534 | else => .{ | 16618 | else => .{ |
| 16535 | .base = .{ .reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv) }, | 16619 | .base = .{ .reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv) }, |
| 16536 | .mod = .{ .rm = .{ .size = mem_size } }, | 16620 | .mod = .{ .rm = .{ .size = mem_size } }, |
| ... | @@ -16649,7 +16733,7 @@ fn atomicOp( | ... | @@ -16649,7 +16733,7 @@ fn atomicOp( |
| 16649 | mir_tag, | 16733 | mir_tag, |
| 16650 | sse_reg.to128(), | 16734 | sse_reg.to128(), |
| 16651 | sse_reg.to128(), | 16735 | sse_reg.to128(), |
| 16652 | try val_mcv.mem(self, self.memSize(val_ty)), | 16736 | try val_mcv.mem(self, .{ .size = self.memSize(val_ty) }), |
| 16653 | ) else try self.asmRegisterRegisterRegister( | 16737 | ) else try self.asmRegisterRegisterRegister( |
| 16654 | mir_tag, | 16738 | mir_tag, |
| 16655 | sse_reg.to128(), | 16739 | sse_reg.to128(), |
| ... | @@ -16662,7 +16746,7 @@ fn atomicOp( | ... | @@ -16662,7 +16746,7 @@ fn atomicOp( |
| 16662 | ._ss, ._sd => if (val_mcv.isMemory()) try self.asmRegisterMemory( | 16746 | ._ss, ._sd => if (val_mcv.isMemory()) try self.asmRegisterMemory( |
| 16663 | mir_tag, | 16747 | mir_tag, |
| 16664 | sse_reg.to128(), | 16748 | sse_reg.to128(), |
| 16665 | try val_mcv.mem(self, self.memSize(val_ty)), | 16749 | try val_mcv.mem(self, .{ .size = self.memSize(val_ty) }), |
| 16666 | ) else try self.asmRegisterRegister( | 16750 | ) else try self.asmRegisterRegister( |
| 16667 | mir_tag, | 16751 | mir_tag, |
| 16668 | sse_reg.to128(), | 16752 | sse_reg.to128(), |
| ... | @@ -16717,7 +16801,7 @@ fn atomicOp( | ... | @@ -16717,7 +16801,7 @@ fn atomicOp( |
| 16717 | try self.asmCmovccRegisterMemory( | 16801 | try self.asmCmovccRegisterMemory( |
| 16718 | cc, | 16802 | cc, |
| 16719 | registerAlias(tmp_reg, cmov_abi_size), | 16803 | registerAlias(tmp_reg, cmov_abi_size), |
| 16720 | try val_mcv.mem(self, .fromSize(cmov_abi_size)), | 16804 | try val_mcv.mem(self, .{ .size = .fromSize(cmov_abi_size) }), |
| 16721 | ); | 16805 | ); |
| 16722 | }, | 16806 | }, |
| 16723 | else => { | 16807 | else => { |
| ... | @@ -16773,8 +16857,8 @@ fn atomicOp( | ... | @@ -16773,8 +16857,8 @@ fn atomicOp( |
| 16773 | .reg = try self.copyToTmpRegister(Type.usize, val_mcv.address()), | 16857 | .reg = try self.copyToTmpRegister(Type.usize, val_mcv.address()), |
| 16774 | } }, | 16858 | } }, |
| 16775 | }; | 16859 | }; |
| 16776 | const val_lo_mem = try val_mem_mcv.mem(self, .qword); | 16860 | const val_lo_mem = try val_mem_mcv.mem(self, .{ .size = .qword }); |
| 16777 | const val_hi_mem = try val_mem_mcv.address().offset(8).deref().mem(self, .qword); | 16861 | const val_hi_mem = try val_mem_mcv.address().offset(8).deref().mem(self, .{ .size = .qword }); |
| 16778 | if (rmw_op != std.builtin.AtomicRmwOp.Xchg) { | 16862 | if (rmw_op != std.builtin.AtomicRmwOp.Xchg) { |
| 16779 | try self.asmRegisterRegister(.{ ._, .mov }, .rbx, .rax); | 16863 | try self.asmRegisterRegister(.{ ._, .mov }, .rbx, .rax); |
| 16780 | try self.asmRegisterRegister(.{ ._, .mov }, .rcx, .rdx); | 16864 | try self.asmRegisterRegister(.{ ._, .mov }, .rcx, .rdx); |
| ... | @@ -16862,7 +16946,7 @@ fn atomicOp( | ... | @@ -16862,7 +16946,7 @@ fn atomicOp( |
| 16862 | } | 16946 | } |
| 16863 | } | 16947 | } |
| 16864 | | 16948 | |
| 16865 | fn airAtomicRmw(self: *Self, inst: Air.Inst.Index) !void { | 16949 | fn airAtomicRmw(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16866 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 16950 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| 16867 | const extra = self.air.extraData(Air.AtomicRmw, pl_op.payload).data; | 16951 | const extra = self.air.extraData(Air.AtomicRmw, pl_op.payload).data; |
| 16868 | | 16952 | |
| ... | @@ -16883,7 +16967,7 @@ fn airAtomicRmw(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16883,7 +16967,7 @@ fn airAtomicRmw(self: *Self, inst: Air.Inst.Index) !void { |
| 16883 | return self.finishAir(inst, result, .{ pl_op.operand, extra.operand, .none }); | 16967 | return self.finishAir(inst, result, .{ pl_op.operand, extra.operand, .none }); |
| 16884 | } | 16968 | } |
| 16885 | | 16969 | |
| 16886 | fn airAtomicLoad(self: *Self, inst: Air.Inst.Index) !void { | 16970 | fn airAtomicLoad(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 16887 | const atomic_load = self.air.instructions.items(.data)[@intFromEnum(inst)].atomic_load; | 16971 | const atomic_load = self.air.instructions.items(.data)[@intFromEnum(inst)].atomic_load; |
| 16888 | | 16972 | |
| 16889 | const ptr_ty = self.typeOf(atomic_load.ptr); | 16973 | const ptr_ty = self.typeOf(atomic_load.ptr); |
| ... | @@ -16904,7 +16988,7 @@ fn airAtomicLoad(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -16904,7 +16988,7 @@ fn airAtomicLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 16904 | return self.finishAir(inst, dst_mcv, .{ atomic_load.ptr, .none, .none }); | 16988 | return self.finishAir(inst, dst_mcv, .{ atomic_load.ptr, .none, .none }); |
| 16905 | } | 16989 | } |
| 16906 | | 16990 | |
| 16907 | fn airAtomicStore(self: *Self, inst: Air.Inst.Index, order: std.builtin.AtomicOrder) !void { | 16991 | fn airAtomicStore(self: *CodeGen, inst: Air.Inst.Index, order: std.builtin.AtomicOrder) !void { |
| 16908 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 16992 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| 16909 | | 16993 | |
| 16910 | const ptr_ty = self.typeOf(bin_op.lhs); | 16994 | const ptr_ty = self.typeOf(bin_op.lhs); |
| ... | @@ -16917,7 +17001,7 @@ fn airAtomicStore(self: *Self, inst: Air.Inst.Index, order: std.builtin.AtomicOr | ... | @@ -16917,7 +17001,7 @@ fn airAtomicStore(self: *Self, inst: Air.Inst.Index, order: std.builtin.AtomicOr |
| 16917 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); | 17001 | return self.finishAir(inst, result, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 16918 | } | 17002 | } |
| 16919 | | 17003 | |
| 16920 | fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | 17004 | fn airMemset(self: *CodeGen, inst: Air.Inst.Index, safety: bool) !void { |
| 16921 | const pt = self.pt; | 17005 | const pt = self.pt; |
| 16922 | const zcu = pt.zcu; | 17006 | const zcu = pt.zcu; |
| 16923 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 17007 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -17059,7 +17143,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { | ... | @@ -17059,7 +17143,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 17059 | return self.finishAir(inst, .unreach, .{ bin_op.lhs, bin_op.rhs, .none }); | 17143 | return self.finishAir(inst, .unreach, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 17060 | } | 17144 | } |
| 17061 | | 17145 | |
| 17062 | fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { | 17146 | fn airMemcpy(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17063 | const pt = self.pt; | 17147 | const pt = self.pt; |
| 17064 | const zcu = pt.zcu; | 17148 | const zcu = pt.zcu; |
| 17065 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; | 17149 | const bin_op = self.air.instructions.items(.data)[@intFromEnum(inst)].bin_op; |
| ... | @@ -17107,7 +17191,7 @@ fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17107,7 +17191,7 @@ fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { |
| 17107 | else => try self.asmRegisterMemoryImmediate( | 17191 | else => try self.asmRegisterMemoryImmediate( |
| 17108 | .{ .i_, .mul }, | 17192 | .{ .i_, .mul }, |
| 17109 | len_reg, | 17193 | len_reg, |
| 17110 | try dst.address().offset(8).deref().mem(self, .qword), | 17194 | try dst.address().offset(8).deref().mem(self, .{ .size = .qword }), |
| 17111 | .s(@intCast(dst_ty.childType(zcu).abiSize(zcu))), | 17195 | .s(@intCast(dst_ty.childType(zcu).abiSize(zcu))), |
| 17112 | ), | 17196 | ), |
| 17113 | } | 17197 | } |
| ... | @@ -17139,7 +17223,7 @@ fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17139,7 +17223,7 @@ fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { |
| 17139 | return self.finishAir(inst, .unreach, .{ bin_op.lhs, bin_op.rhs, .none }); | 17223 | return self.finishAir(inst, .unreach, .{ bin_op.lhs, bin_op.rhs, .none }); |
| 17140 | } | 17224 | } |
| 17141 | | 17225 | |
| 17142 | fn airTagName(self: *Self, inst: Air.Inst.Index) !void { | 17226 | fn airTagName(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17143 | const pt = self.pt; | 17227 | const pt = self.pt; |
| 17144 | const zcu = pt.zcu; | 17228 | const zcu = pt.zcu; |
| 17145 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 17229 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| ... | @@ -17179,7 +17263,7 @@ fn airTagName(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17179,7 +17263,7 @@ fn airTagName(self: *Self, inst: Air.Inst.Index) !void { |
| 17179 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); | 17263 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); |
| 17180 | } | 17264 | } |
| 17181 | | 17265 | |
| 17182 | fn airErrorName(self: *Self, inst: Air.Inst.Index) !void { | 17266 | fn airErrorName(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17183 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 17267 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 17184 | | 17268 | |
| 17185 | const err_ty = self.typeOf(un_op); | 17269 | const err_ty = self.typeOf(un_op); |
| ... | @@ -17281,7 +17365,7 @@ fn airErrorName(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17281,7 +17365,7 @@ fn airErrorName(self: *Self, inst: Air.Inst.Index) !void { |
| 17281 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); | 17365 | return self.finishAir(inst, dst_mcv, .{ un_op, .none, .none }); |
| 17282 | } | 17366 | } |
| 17283 | | 17367 | |
| 17284 | fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | 17368 | fn airSplat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17285 | const pt = self.pt; | 17369 | const pt = self.pt; |
| 17286 | const zcu = pt.zcu; | 17370 | const zcu = pt.zcu; |
| 17287 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 17371 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -17318,7 +17402,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17318,7 +17402,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17318 | else => cc: { | 17402 | else => cc: { |
| 17319 | try self.asmMemoryImmediate( | 17403 | try self.asmMemoryImmediate( |
| 17320 | .{ ._, .@"test" }, | 17404 | .{ ._, .@"test" }, |
| 17321 | try src_mcv.mem(self, .byte), | 17405 | try src_mcv.mem(self, .{ .size = .byte }), |
| 17322 | .u(1), | 17406 | .u(1), |
| 17323 | ); | 17407 | ); |
| 17324 | break :cc .nz; | 17408 | break :cc .nz; |
| ... | @@ -17362,7 +17446,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17362,7 +17446,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17362 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17446 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17363 | mir_tag, | 17447 | mir_tag, |
| 17364 | registerAlias(dst_reg, @intCast(vector_ty.abiSize(zcu))), | 17448 | registerAlias(dst_reg, @intCast(vector_ty.abiSize(zcu))), |
| 17365 | try src_mcv.mem(self, self.memSize(scalar_ty)), | 17449 | try src_mcv.mem(self, .{ .size = self.memSize(scalar_ty) }), |
| 17366 | ) else { | 17450 | ) else { |
| 17367 | if (mir_tag[0] == .v_i128) break :avx2; | 17451 | if (mir_tag[0] == .v_i128) break :avx2; |
| 17368 | try self.genSetReg(dst_reg, scalar_ty, src_mcv, .{}); | 17452 | try self.genSetReg(dst_reg, scalar_ty, src_mcv, .{}); |
| ... | @@ -17438,7 +17522,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17438,7 +17522,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17438 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17522 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17439 | .{ .v_ss, .broadcast }, | 17523 | .{ .v_ss, .broadcast }, |
| 17440 | dst_reg.to128(), | 17524 | dst_reg.to128(), |
| 17441 | try src_mcv.mem(self, .dword), | 17525 | try src_mcv.mem(self, .{ .size = .dword }), |
| 17442 | ) else { | 17526 | ) else { |
| 17443 | const src_reg = if (src_mcv.isRegister()) | 17527 | const src_reg = if (src_mcv.isRegister()) |
| 17444 | src_mcv.getReg().? | 17528 | src_mcv.getReg().? |
| ... | @@ -17475,7 +17559,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17475,7 +17559,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17475 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17559 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17476 | .{ .v_ss, .broadcast }, | 17560 | .{ .v_ss, .broadcast }, |
| 17477 | dst_reg.to256(), | 17561 | dst_reg.to256(), |
| 17478 | try src_mcv.mem(self, .dword), | 17562 | try src_mcv.mem(self, .{ .size = .dword }), |
| 17479 | ) else { | 17563 | ) else { |
| 17480 | const src_reg = if (src_mcv.isRegister()) | 17564 | const src_reg = if (src_mcv.isRegister()) |
| 17481 | src_mcv.getReg().? | 17565 | src_mcv.getReg().? |
| ... | @@ -17521,7 +17605,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17521,7 +17605,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17521 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17605 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17522 | if (self.hasFeature(.avx)) .{ .v_, .movddup } else .{ ._, .movddup }, | 17606 | if (self.hasFeature(.avx)) .{ .v_, .movddup } else .{ ._, .movddup }, |
| 17523 | dst_reg.to128(), | 17607 | dst_reg.to128(), |
| 17524 | try src_mcv.mem(self, .qword), | 17608 | try src_mcv.mem(self, .{ .size = .qword }), |
| 17525 | ) else try self.asmRegisterRegister( | 17609 | ) else try self.asmRegisterRegister( |
| 17526 | if (self.hasFeature(.avx)) .{ .v_, .movddup } else .{ ._, .movddup }, | 17610 | if (self.hasFeature(.avx)) .{ .v_, .movddup } else .{ ._, .movddup }, |
| 17527 | dst_reg.to128(), | 17611 | dst_reg.to128(), |
| ... | @@ -17546,7 +17630,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17546,7 +17630,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17546 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17630 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17547 | .{ .v_sd, .broadcast }, | 17631 | .{ .v_sd, .broadcast }, |
| 17548 | dst_reg.to256(), | 17632 | dst_reg.to256(), |
| 17549 | try src_mcv.mem(self, .qword), | 17633 | try src_mcv.mem(self, .{ .size = .qword }), |
| 17550 | ) else { | 17634 | ) else { |
| 17551 | const src_reg = if (src_mcv.isRegister()) | 17635 | const src_reg = if (src_mcv.isRegister()) |
| 17552 | src_mcv.getReg().? | 17636 | src_mcv.getReg().? |
| ... | @@ -17589,7 +17673,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17589,7 +17673,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17589 | if (src_mcv.isMemory()) try self.asmRegisterMemory( | 17673 | if (src_mcv.isMemory()) try self.asmRegisterMemory( |
| 17590 | .{ .v_f128, .broadcast }, | 17674 | .{ .v_f128, .broadcast }, |
| 17591 | dst_reg.to256(), | 17675 | dst_reg.to256(), |
| 17592 | try src_mcv.mem(self, .xword), | 17676 | try src_mcv.mem(self, .{ .size = .xword }), |
| 17593 | ) else { | 17677 | ) else { |
| 17594 | const src_reg = if (src_mcv.isRegister()) | 17678 | const src_reg = if (src_mcv.isRegister()) |
| 17595 | src_mcv.getReg().? | 17679 | src_mcv.getReg().? |
| ... | @@ -17616,7 +17700,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17616,7 +17700,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 17616 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 17700 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 17617 | } | 17701 | } |
| 17618 | | 17702 | |
| 17619 | fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | 17703 | fn airSelect(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17620 | const pt = self.pt; | 17704 | const pt = self.pt; |
| 17621 | const zcu = pt.zcu; | 17705 | const zcu = pt.zcu; |
| 17622 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 17706 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| ... | @@ -17695,7 +17779,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17695,7 +17779,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { |
| 17695 | else => unreachable, | 17779 | else => unreachable, |
| 17696 | }, .broadcast }, | 17780 | }, .broadcast }, |
| 17697 | mask_alias, | 17781 | mask_alias, |
| 17698 | if (pred_mcv.isMemory()) try pred_mcv.mem(self, .byte) else .{ | 17782 | if (pred_mcv.isMemory()) try pred_mcv.mem(self, .{ .size = .byte }) else .{ |
| 17699 | .base = .{ .reg = (try self.copyToTmpRegister( | 17783 | .base = .{ .reg = (try self.copyToTmpRegister( |
| 17700 | Type.usize, | 17784 | Type.usize, |
| 17701 | pred_mcv.address(), | 17785 | pred_mcv.address(), |
| ... | @@ -17893,7 +17977,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17893,7 +17977,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { |
| 17893 | mir_tag, | 17977 | mir_tag, |
| 17894 | dst_alias, | 17978 | dst_alias, |
| 17895 | rhs_alias, | 17979 | rhs_alias, |
| 17896 | try lhs_mcv.mem(self, self.memSize(ty)), | 17980 | try lhs_mcv.mem(self, .{ .size = self.memSize(ty) }), |
| 17897 | mask_alias, | 17981 | mask_alias, |
| 17898 | ) else try self.asmRegisterRegisterRegisterRegister( | 17982 | ) else try self.asmRegisterRegisterRegisterRegister( |
| 17899 | mir_tag, | 17983 | mir_tag, |
| ... | @@ -17908,7 +17992,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17908,7 +17992,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { |
| 17908 | } else if (has_blend) if (lhs_mcv.isMemory()) try self.asmRegisterMemoryRegister( | 17992 | } else if (has_blend) if (lhs_mcv.isMemory()) try self.asmRegisterMemoryRegister( |
| 17909 | mir_tag, | 17993 | mir_tag, |
| 17910 | dst_alias, | 17994 | dst_alias, |
| 17911 | try lhs_mcv.mem(self, self.memSize(ty)), | 17995 | try lhs_mcv.mem(self, .{ .size = self.memSize(ty) }), |
| 17912 | mask_alias, | 17996 | mask_alias, |
| 17913 | ) else try self.asmRegisterRegisterRegister( | 17997 | ) else try self.asmRegisterRegisterRegister( |
| 17914 | mir_tag, | 17998 | mir_tag, |
| ... | @@ -17933,7 +18017,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17933,7 +18017,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { |
| 17933 | if (rhs_mcv.isMemory()) try self.asmRegisterMemory( | 18017 | if (rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 17934 | .{ mir_fixes, .andn }, | 18018 | .{ mir_fixes, .andn }, |
| 17935 | mask_alias, | 18019 | mask_alias, |
| 17936 | try rhs_mcv.mem(self, .fromSize(abi_size)), | 18020 | try rhs_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 17937 | ) else try self.asmRegisterRegister( | 18021 | ) else try self.asmRegisterRegister( |
| 17938 | .{ mir_fixes, .andn }, | 18022 | .{ mir_fixes, .andn }, |
| 17939 | mask_alias, | 18023 | mask_alias, |
| ... | @@ -17949,7 +18033,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -17949,7 +18033,7 @@ fn airSelect(self: *Self, inst: Air.Inst.Index) !void { |
| 17949 | return self.finishAir(inst, result, .{ pl_op.operand, extra.lhs, extra.rhs }); | 18033 | return self.finishAir(inst, result, .{ pl_op.operand, extra.lhs, extra.rhs }); |
| 17950 | } | 18034 | } |
| 17951 | | 18035 | |
| 17952 | fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | 18036 | fn airShuffle(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 17953 | const pt = self.pt; | 18037 | const pt = self.pt; |
| 17954 | const zcu = pt.zcu; | 18038 | const zcu = pt.zcu; |
| 17955 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; | 18039 | const ty_pl = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_pl; |
| ... | @@ -18074,7 +18158,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18074,7 +18158,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18074 | mir_tag, | 18158 | mir_tag, |
| 18075 | dst_alias, | 18159 | dst_alias, |
| 18076 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), | 18160 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), |
| 18077 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18161 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18078 | ) else try self.asmRegisterRegisterRegister( | 18162 | ) else try self.asmRegisterRegisterRegister( |
| 18079 | mir_tag, | 18163 | mir_tag, |
| 18080 | dst_alias, | 18164 | dst_alias, |
| ... | @@ -18086,7 +18170,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18086,7 +18170,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18086 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemory( | 18170 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 18087 | mir_tag, | 18171 | mir_tag, |
| 18088 | dst_alias, | 18172 | dst_alias, |
| 18089 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18173 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18090 | ) else try self.asmRegisterRegister( | 18174 | ) else try self.asmRegisterRegister( |
| 18091 | mir_tag, | 18175 | mir_tag, |
| 18092 | dst_alias, | 18176 | dst_alias, |
| ... | @@ -18135,7 +18219,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18135,7 +18219,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18135 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 18219 | if (src_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 18136 | .{ if (has_avx) .vp_d else .p_d, .shuf }, | 18220 | .{ if (has_avx) .vp_d else .p_d, .shuf }, |
| 18137 | dst_alias, | 18221 | dst_alias, |
| 18138 | try src_mcv.mem(self, .fromSize(max_abi_size)), | 18222 | try src_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18139 | .u(control), | 18223 | .u(control), |
| 18140 | ) else try self.asmRegisterRegisterImmediate( | 18224 | ) else try self.asmRegisterRegisterImmediate( |
| 18141 | .{ if (has_avx) .vp_d else .p_d, .shuf }, | 18225 | .{ if (has_avx) .vp_d else .p_d, .shuf }, |
| ... | @@ -18192,7 +18276,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18192,7 +18276,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18192 | .{ .v_ps, .shuf }, | 18276 | .{ .v_ps, .shuf }, |
| 18193 | dst_alias, | 18277 | dst_alias, |
| 18194 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), | 18278 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), |
| 18195 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18279 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18196 | .u(control), | 18280 | .u(control), |
| 18197 | ) else try self.asmRegisterRegisterRegisterImmediate( | 18281 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 18198 | .{ .v_ps, .shuf }, | 18282 | .{ .v_ps, .shuf }, |
| ... | @@ -18206,7 +18290,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18206,7 +18290,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18206 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 18290 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 18207 | .{ ._ps, .shuf }, | 18291 | .{ ._ps, .shuf }, |
| 18208 | dst_alias, | 18292 | dst_alias, |
| 18209 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18293 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18210 | .u(control), | 18294 | .u(control), |
| 18211 | ) else try self.asmRegisterRegisterImmediate( | 18295 | ) else try self.asmRegisterRegisterImmediate( |
| 18212 | .{ ._ps, .shuf }, | 18296 | .{ ._ps, .shuf }, |
| ... | @@ -18259,7 +18343,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18259,7 +18343,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18259 | .{ .v_pd, .shuf }, | 18343 | .{ .v_pd, .shuf }, |
| 18260 | dst_alias, | 18344 | dst_alias, |
| 18261 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), | 18345 | registerAlias(lhs_mcv.getReg() orelse dst_reg, max_abi_size), |
| 18262 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18346 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18263 | .u(control), | 18347 | .u(control), |
| 18264 | ) else try self.asmRegisterRegisterRegisterImmediate( | 18348 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 18265 | .{ .v_pd, .shuf }, | 18349 | .{ .v_pd, .shuf }, |
| ... | @@ -18273,7 +18357,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18273,7 +18357,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18273 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 18357 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 18274 | .{ ._pd, .shuf }, | 18358 | .{ ._pd, .shuf }, |
| 18275 | dst_alias, | 18359 | dst_alias, |
| 18276 | try rhs_mcv.mem(self, .fromSize(max_abi_size)), | 18360 | try rhs_mcv.mem(self, .{ .size = .fromSize(max_abi_size) }), |
| 18277 | .u(control), | 18361 | .u(control), |
| 18278 | ) else try self.asmRegisterRegisterImmediate( | 18362 | ) else try self.asmRegisterRegisterImmediate( |
| 18279 | .{ ._pd, .shuf }, | 18363 | .{ ._pd, .shuf }, |
| ... | @@ -18329,7 +18413,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18329,7 +18413,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18329 | .{ .vp_d, .blend }, | 18413 | .{ .vp_d, .blend }, |
| 18330 | registerAlias(dst_reg, dst_abi_size), | 18414 | registerAlias(dst_reg, dst_abi_size), |
| 18331 | registerAlias(lhs_reg, dst_abi_size), | 18415 | registerAlias(lhs_reg, dst_abi_size), |
| 18332 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18416 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18333 | .u(expanded_control), | 18417 | .u(expanded_control), |
| 18334 | ) else try self.asmRegisterRegisterRegisterImmediate( | 18418 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 18335 | .{ .vp_d, .blend }, | 18419 | .{ .vp_d, .blend }, |
| ... | @@ -18384,7 +18468,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18384,7 +18468,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18384 | lhs_mcv.getReg().? | 18468 | lhs_mcv.getReg().? |
| 18385 | else | 18469 | else |
| 18386 | dst_reg, dst_abi_size), | 18470 | dst_reg, dst_abi_size), |
| 18387 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18471 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18388 | .u(expanded_control), | 18472 | .u(expanded_control), |
| 18389 | ) else try self.asmRegisterRegisterRegisterImmediate( | 18473 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 18390 | .{ .vp_w, .blend }, | 18474 | .{ .vp_w, .blend }, |
| ... | @@ -18401,7 +18485,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18401,7 +18485,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18401 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( | 18485 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryImmediate( |
| 18402 | .{ .p_w, .blend }, | 18486 | .{ .p_w, .blend }, |
| 18403 | registerAlias(dst_reg, dst_abi_size), | 18487 | registerAlias(dst_reg, dst_abi_size), |
| 18404 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18488 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18405 | .u(expanded_control), | 18489 | .u(expanded_control), |
| 18406 | ) else try self.asmRegisterRegisterImmediate( | 18490 | ) else try self.asmRegisterRegisterImmediate( |
| 18407 | .{ .p_w, .blend }, | 18491 | .{ .p_w, .blend }, |
| ... | @@ -18445,7 +18529,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18445,7 +18529,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18445 | lhs_mcv.getReg().? | 18529 | lhs_mcv.getReg().? |
| 18446 | else | 18530 | else |
| 18447 | dst_reg, dst_abi_size), | 18531 | dst_reg, dst_abi_size), |
| 18448 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18532 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18449 | .u(expanded_control), | 18533 | .u(expanded_control), |
| 18450 | ) else try self.asmRegisterRegisterRegisterImmediate( | 18534 | ) else try self.asmRegisterRegisterRegisterImmediate( |
| 18451 | switch (elem_abi_size) { | 18535 | switch (elem_abi_size) { |
| ... | @@ -18470,7 +18554,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18470,7 +18554,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18470 | else => unreachable, | 18554 | else => unreachable, |
| 18471 | }, | 18555 | }, |
| 18472 | registerAlias(dst_reg, dst_abi_size), | 18556 | registerAlias(dst_reg, dst_abi_size), |
| 18473 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18557 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18474 | .u(expanded_control), | 18558 | .u(expanded_control), |
| 18475 | ) else try self.asmRegisterRegisterImmediate( | 18559 | ) else try self.asmRegisterRegisterImmediate( |
| 18476 | switch (elem_abi_size) { | 18560 | switch (elem_abi_size) { |
| ... | @@ -18560,7 +18644,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18560,7 +18644,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18560 | registerAlias(lhs_mcv.getReg().?, dst_abi_size) | 18644 | registerAlias(lhs_mcv.getReg().?, dst_abi_size) |
| 18561 | else | 18645 | else |
| 18562 | dst_alias, | 18646 | dst_alias, |
| 18563 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18647 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18564 | select_mask_alias, | 18648 | select_mask_alias, |
| 18565 | ) else try self.asmRegisterRegisterRegisterRegister( | 18649 | ) else try self.asmRegisterRegisterRegisterRegister( |
| 18566 | mir_tag, | 18650 | mir_tag, |
| ... | @@ -18577,7 +18661,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18577,7 +18661,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18577 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryRegister( | 18661 | ) else if (rhs_mcv.isMemory()) try self.asmRegisterMemoryRegister( |
| 18578 | mir_tag, | 18662 | mir_tag, |
| 18579 | dst_alias, | 18663 | dst_alias, |
| 18580 | try rhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18664 | try rhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18581 | select_mask_alias, | 18665 | select_mask_alias, |
| 18582 | ) else try self.asmRegisterRegisterRegister( | 18666 | ) else try self.asmRegisterRegisterRegister( |
| 18583 | mir_tag, | 18667 | mir_tag, |
| ... | @@ -18620,7 +18704,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18620,7 +18704,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18620 | if (lhs_mcv.isMemory()) try self.asmRegisterMemory( | 18704 | if (lhs_mcv.isMemory()) try self.asmRegisterMemory( |
| 18621 | .{ mir_fixes, .andn }, | 18705 | .{ mir_fixes, .andn }, |
| 18622 | mask_alias, | 18706 | mask_alias, |
| 18623 | try lhs_mcv.mem(self, .fromSize(dst_abi_size)), | 18707 | try lhs_mcv.mem(self, .{ .size = .fromSize(dst_abi_size) }), |
| 18624 | ) else try self.asmRegisterRegister( | 18708 | ) else try self.asmRegisterRegister( |
| 18625 | .{ mir_fixes, .andn }, | 18709 | .{ mir_fixes, .andn }, |
| 18626 | mask_alias, | 18710 | mask_alias, |
| ... | @@ -18757,7 +18841,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18757,7 +18841,7 @@ fn airShuffle(self: *Self, inst: Air.Inst.Index) !void { |
| 18757 | return self.finishAir(inst, result, .{ extra.a, extra.b, .none }); | 18841 | return self.finishAir(inst, result, .{ extra.a, extra.b, .none }); |
| 18758 | } | 18842 | } |
| 18759 | | 18843 | |
| 18760 | fn airReduce(self: *Self, inst: Air.Inst.Index) !void { | 18844 | fn airReduce(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 18761 | const pt = self.pt; | 18845 | const pt = self.pt; |
| 18762 | const zcu = pt.zcu; | 18846 | const zcu = pt.zcu; |
| 18763 | const reduce = self.air.instructions.items(.data)[@intFromEnum(inst)].reduce; | 18847 | const reduce = self.air.instructions.items(.data)[@intFromEnum(inst)].reduce; |
| ... | @@ -18776,7 +18860,7 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18776,7 +18860,7 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 18776 | .Or => { | 18860 | .Or => { |
| 18777 | if (operand_mcv.isMemory()) try self.asmMemoryImmediate( | 18861 | if (operand_mcv.isMemory()) try self.asmMemoryImmediate( |
| 18778 | .{ ._, .@"test" }, | 18862 | .{ ._, .@"test" }, |
| 18779 | try operand_mcv.mem(self, .fromSize(abi_size)), | 18863 | try operand_mcv.mem(self, .{ .size = .fromSize(abi_size) }), |
| 18780 | .u(mask), | 18864 | .u(mask), |
| 18781 | ) else { | 18865 | ) else { |
| 18782 | const operand_reg = registerAlias(if (operand_mcv.isRegister()) | 18866 | const operand_reg = registerAlias(if (operand_mcv.isRegister()) |
| ... | @@ -18815,7 +18899,7 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -18815,7 +18899,7 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 18815 | return self.finishAir(inst, result, .{ reduce.operand, .none, .none }); | 18899 | return self.finishAir(inst, result, .{ reduce.operand, .none, .none }); |
| 18816 | } | 18900 | } |
| 18817 | | 18901 | |
| 18818 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { | 18902 | fn airAggregateInit(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 18819 | const pt = self.pt; | 18903 | const pt = self.pt; |
| 18820 | const zcu = pt.zcu; | 18904 | const zcu = pt.zcu; |
| 18821 | const result_ty = self.typeOfIndex(inst); | 18905 | const result_ty = self.typeOfIndex(inst); |
| ... | @@ -19007,7 +19091,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19007,7 +19091,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 19007 | return self.finishAirResult(inst, result); | 19091 | return self.finishAirResult(inst, result); |
| 19008 | } | 19092 | } |
| 19009 | | 19093 | |
| 19010 | fn airUnionInit(self: *Self, inst: Air.Inst.Index) !void { | 19094 | fn airUnionInit(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19011 | const pt = self.pt; | 19095 | const pt = self.pt; |
| 19012 | const zcu = pt.zcu; | 19096 | const zcu = pt.zcu; |
| 19013 | const ip = &zcu.intern_pool; | 19097 | const ip = &zcu.intern_pool; |
| ... | @@ -19053,12 +19137,12 @@ fn airUnionInit(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19053,12 +19137,12 @@ fn airUnionInit(self: *Self, inst: Air.Inst.Index) !void { |
| 19053 | return self.finishAir(inst, result, .{ extra.init, .none, .none }); | 19137 | return self.finishAir(inst, result, .{ extra.init, .none, .none }); |
| 19054 | } | 19138 | } |
| 19055 | | 19139 | |
| 19056 | fn airPrefetch(self: *Self, inst: Air.Inst.Index) !void { | 19140 | fn airPrefetch(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19057 | const prefetch = self.air.instructions.items(.data)[@intFromEnum(inst)].prefetch; | 19141 | const prefetch = self.air.instructions.items(.data)[@intFromEnum(inst)].prefetch; |
| 19058 | return self.finishAir(inst, .unreach, .{ prefetch.ptr, .none, .none }); | 19142 | return self.finishAir(inst, .unreach, .{ prefetch.ptr, .none, .none }); |
| 19059 | } | 19143 | } |
| 19060 | | 19144 | |
| 19061 | fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { | 19145 | fn airMulAdd(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19062 | const pt = self.pt; | 19146 | const pt = self.pt; |
| 19063 | const zcu = pt.zcu; | 19147 | const zcu = pt.zcu; |
| 19064 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; | 19148 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| ... | @@ -19219,14 +19303,14 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19219,14 +19303,14 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { |
| 19219 | mir_tag, | 19303 | mir_tag, |
| 19220 | mop1_reg, | 19304 | mop1_reg, |
| 19221 | mop2_reg, | 19305 | mop2_reg, |
| 19222 | try mops[2].mem(self, .fromSize(abi_size)), | 19306 | try mops[2].mem(self, .{ .size = .fromSize(abi_size) }), |
| 19223 | ); | 19307 | ); |
| 19224 | break :result mops[0]; | 19308 | break :result mops[0]; |
| 19225 | }; | 19309 | }; |
| 19226 | return self.finishAir(inst, result, ops); | 19310 | return self.finishAir(inst, result, ops); |
| 19227 | } | 19311 | } |
| 19228 | | 19312 | |
| 19229 | fn airVaStart(self: *Self, inst: Air.Inst.Index) !void { | 19313 | fn airVaStart(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19230 | const pt = self.pt; | 19314 | const pt = self.pt; |
| 19231 | const zcu = pt.zcu; | 19315 | const zcu = pt.zcu; |
| 19232 | const va_list_ty = self.air.instructions.items(.data)[@intFromEnum(inst)].ty; | 19316 | const va_list_ty = self.air.instructions.items(.data)[@intFromEnum(inst)].ty; |
| ... | @@ -19284,7 +19368,7 @@ fn airVaStart(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19284,7 +19368,7 @@ fn airVaStart(self: *Self, inst: Air.Inst.Index) !void { |
| 19284 | return self.finishAir(inst, result, .{ .none, .none, .none }); | 19368 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 19285 | } | 19369 | } |
| 19286 | | 19370 | |
| 19287 | fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { | 19371 | fn airVaArg(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19288 | const pt = self.pt; | 19372 | const pt = self.pt; |
| 19289 | const zcu = pt.zcu; | 19373 | const zcu = pt.zcu; |
| 19290 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 19374 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| ... | @@ -19451,7 +19535,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19451,7 +19535,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { |
| 19451 | .{ .v_ss, .cvtsd2 }, | 19535 | .{ .v_ss, .cvtsd2 }, |
| 19452 | dst_reg, | 19536 | dst_reg, |
| 19453 | dst_reg, | 19537 | dst_reg, |
| 19454 | try promote_mcv.mem(self, .qword), | 19538 | try promote_mcv.mem(self, .{ .size = .qword }), |
| 19455 | ) else try self.asmRegisterRegisterRegister( | 19539 | ) else try self.asmRegisterRegisterRegister( |
| 19456 | .{ .v_ss, .cvtsd2 }, | 19540 | .{ .v_ss, .cvtsd2 }, |
| 19457 | dst_reg, | 19541 | dst_reg, |
| ... | @@ -19463,7 +19547,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19463,7 +19547,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { |
| 19463 | ) else if (promote_mcv.isMemory()) try self.asmRegisterMemory( | 19547 | ) else if (promote_mcv.isMemory()) try self.asmRegisterMemory( |
| 19464 | .{ ._ss, .cvtsd2 }, | 19548 | .{ ._ss, .cvtsd2 }, |
| 19465 | dst_reg, | 19549 | dst_reg, |
| 19466 | try promote_mcv.mem(self, .qword), | 19550 | try promote_mcv.mem(self, .{ .size = .qword }), |
| 19467 | ) else try self.asmRegisterRegister( | 19551 | ) else try self.asmRegisterRegister( |
| 19468 | .{ ._ss, .cvtsd2 }, | 19552 | .{ ._ss, .cvtsd2 }, |
| 19469 | dst_reg, | 19553 | dst_reg, |
| ... | @@ -19480,7 +19564,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19480,7 +19564,7 @@ fn airVaArg(self: *Self, inst: Air.Inst.Index) !void { |
| 19480 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); | 19564 | return self.finishAir(inst, result, .{ ty_op.operand, .none, .none }); |
| 19481 | } | 19565 | } |
| 19482 | | 19566 | |
| 19483 | fn airVaCopy(self: *Self, inst: Air.Inst.Index) !void { | 19567 | fn airVaCopy(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19484 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; | 19568 | const ty_op = self.air.instructions.items(.data)[@intFromEnum(inst)].ty_op; |
| 19485 | const ptr_va_list_ty = self.typeOf(ty_op.operand); | 19569 | const ptr_va_list_ty = self.typeOf(ty_op.operand); |
| 19486 | | 19570 | |
| ... | @@ -19489,12 +19573,12 @@ fn airVaCopy(self: *Self, inst: Air.Inst.Index) !void { | ... | @@ -19489,12 +19573,12 @@ fn airVaCopy(self: *Self, inst: Air.Inst.Index) !void { |
| 19489 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); | 19573 | return self.finishAir(inst, dst_mcv, .{ ty_op.operand, .none, .none }); |
| 19490 | } | 19574 | } |
| 19491 | | 19575 | |
| 19492 | fn airVaEnd(self: *Self, inst: Air.Inst.Index) !void { | 19576 | fn airVaEnd(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19493 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; | 19577 | const un_op = self.air.instructions.items(.data)[@intFromEnum(inst)].un_op; |
| 19494 | return self.finishAir(inst, .unreach, .{ un_op, .none, .none }); | 19578 | return self.finishAir(inst, .unreach, .{ un_op, .none, .none }); |
| 19495 | } | 19579 | } |
| 19496 | | 19580 | |
| 19497 | fn resolveInst(self: *Self, ref: Air.Inst.Ref) InnerError!MCValue { | 19581 | fn resolveInst(self: *CodeGen, ref: Air.Inst.Ref) InnerError!MCValue { |
| 19498 | const zcu = self.pt.zcu; | 19582 | const zcu = self.pt.zcu; |
| 19499 | const ty = self.typeOf(ref); | 19583 | const ty = self.typeOf(ref); |
| 19500 | | 19584 | |
| ... | @@ -19543,7 +19627,7 @@ fn resolveInst(self: *Self, ref: Air.Inst.Ref) InnerError!MCValue { | ... | @@ -19543,7 +19627,7 @@ fn resolveInst(self: *Self, ref: Air.Inst.Ref) InnerError!MCValue { |
| 19543 | } | 19627 | } |
| 19544 | } | 19628 | } |
| 19545 | | 19629 | |
| 19546 | fn getResolvedInstValue(self: *Self, inst: Air.Inst.Index) *InstTracking { | 19630 | fn getResolvedInstValue(self: *CodeGen, inst: Air.Inst.Index) *InstTracking { |
| 19547 | const tracking = self.inst_tracking.getPtr(inst).?; | 19631 | const tracking = self.inst_tracking.getPtr(inst).?; |
| 19548 | return switch (tracking.short) { | 19632 | return switch (tracking.short) { |
| 19549 | .none, .unreach, .dead => unreachable, | 19633 | .none, .unreach, .dead => unreachable, |
| ... | @@ -19556,7 +19640,7 @@ fn getResolvedInstValue(self: *Self, inst: Air.Inst.Index) *InstTracking { | ... | @@ -19556,7 +19640,7 @@ fn getResolvedInstValue(self: *Self, inst: Air.Inst.Index) *InstTracking { |
| 19556 | /// A potential opportunity for future optimization here would be keeping track | 19640 | /// A potential opportunity for future optimization here would be keeping track |
| 19557 | /// of the fact that the instruction is available both as an immediate | 19641 | /// of the fact that the instruction is available both as an immediate |
| 19558 | /// and as a register. | 19642 | /// and as a register. |
| 19559 | fn limitImmediateType(self: *Self, operand: Air.Inst.Ref, comptime T: type) !MCValue { | 19643 | fn limitImmediateType(self: *CodeGen, operand: Air.Inst.Ref, comptime T: type) !MCValue { |
| 19560 | const mcv = try self.resolveInst(operand); | 19644 | const mcv = try self.resolveInst(operand); |
| 19561 | const ti = @typeInfo(T).int; | 19645 | const ti = @typeInfo(T).int; |
| 19562 | switch (mcv) { | 19646 | switch (mcv) { |
| ... | @@ -19572,7 +19656,7 @@ fn limitImmediateType(self: *Self, operand: Air.Inst.Ref, comptime T: type) !MCV | ... | @@ -19572,7 +19656,7 @@ fn limitImmediateType(self: *Self, operand: Air.Inst.Ref, comptime T: type) !MCV |
| 19572 | return mcv; | 19656 | return mcv; |
| 19573 | } | 19657 | } |
| 19574 | | 19658 | |
| 19575 | fn genTypedValue(self: *Self, val: Value) InnerError!MCValue { | 19659 | fn genTypedValue(self: *CodeGen, val: Value) InnerError!MCValue { |
| 19576 | const pt = self.pt; | 19660 | const pt = self.pt; |
| 19577 | return switch (try codegen.genTypedValue(self.bin_file, pt, self.src_loc, val, self.target.*)) { | 19661 | return switch (try codegen.genTypedValue(self.bin_file, pt, self.src_loc, val, self.target.*)) { |
| 19578 | .mcv => |mcv| switch (mcv) { | 19662 | .mcv => |mcv| switch (mcv) { |
| ... | @@ -19599,7 +19683,7 @@ const CallMCValues = struct { | ... | @@ -19599,7 +19683,7 @@ const CallMCValues = struct { |
| 19599 | gp_count: u32, | 19683 | gp_count: u32, |
| 19600 | fp_count: u32, | 19684 | fp_count: u32, |
| 19601 | | 19685 | |
| 19602 | fn deinit(self: *CallMCValues, func: *Self) void { | 19686 | fn deinit(self: *CallMCValues, func: *CodeGen) void { |
| 19603 | func.gpa.free(self.args); | 19687 | func.gpa.free(self.args); |
| 19604 | self.* = undefined; | 19688 | self.* = undefined; |
| 19605 | } | 19689 | } |
| ... | @@ -19607,7 +19691,7 @@ const CallMCValues = struct { | ... | @@ -19607,7 +19691,7 @@ const CallMCValues = struct { |
| 19607 | | 19691 | |
| 19608 | /// Caller must call `CallMCValues.deinit`. | 19692 | /// Caller must call `CallMCValues.deinit`. |
| 19609 | fn resolveCallingConventionValues( | 19693 | fn resolveCallingConventionValues( |
| 19610 | self: *Self, | 19694 | self: *CodeGen, |
| 19611 | fn_info: InternPool.Key.FuncType, | 19695 | fn_info: InternPool.Key.FuncType, |
| 19612 | var_args: []const Type, | 19696 | var_args: []const Type, |
| 19613 | stack_frame_base: FrameIndex, | 19697 | stack_frame_base: FrameIndex, |
| ... | @@ -19889,7 +19973,7 @@ fn resolveCallingConventionValues( | ... | @@ -19889,7 +19973,7 @@ fn resolveCallingConventionValues( |
| 19889 | return result; | 19973 | return result; |
| 19890 | } | 19974 | } |
| 19891 | | 19975 | |
| 19892 | fn fail(self: *Self, comptime format: []const u8, args: anytype) error{ OutOfMemory, CodegenFail } { | 19976 | fn fail(self: *CodeGen, comptime format: []const u8, args: anytype) error{ OutOfMemory, CodegenFail } { |
| 19893 | @branchHint(.cold); | 19977 | @branchHint(.cold); |
| 19894 | const zcu = self.pt.zcu; | 19978 | const zcu = self.pt.zcu; |
| 19895 | switch (self.owner) { | 19979 | switch (self.owner) { |
| ... | @@ -19899,7 +19983,7 @@ fn fail(self: *Self, comptime format: []const u8, args: anytype) error{ OutOfMem | ... | @@ -19899,7 +19983,7 @@ fn fail(self: *Self, comptime format: []const u8, args: anytype) error{ OutOfMem |
| 19899 | return error.CodegenFail; | 19983 | return error.CodegenFail; |
| 19900 | } | 19984 | } |
| 19901 | | 19985 | |
| 19902 | fn failMsg(self: *Self, msg: *Zcu.ErrorMsg) error{ OutOfMemory, CodegenFail } { | 19986 | fn failMsg(self: *CodeGen, msg: *Zcu.ErrorMsg) error{ OutOfMemory, CodegenFail } { |
| 19903 | @branchHint(.cold); | 19987 | @branchHint(.cold); |
| 19904 | const zcu = self.pt.zcu; | 19988 | const zcu = self.pt.zcu; |
| 19905 | switch (self.owner) { | 19989 | switch (self.owner) { |
| ... | @@ -19960,7 +20044,7 @@ fn registerAlias(reg: Register, size_bytes: u32) Register { | ... | @@ -19960,7 +20044,7 @@ fn registerAlias(reg: Register, size_bytes: u32) Register { |
| 19960 | }; | 20044 | }; |
| 19961 | } | 20045 | } |
| 19962 | | 20046 | |
| 19963 | fn memSize(self: *Self, ty: Type) Memory.Size { | 20047 | fn memSize(self: *CodeGen, ty: Type) Memory.Size { |
| 19964 | const zcu = self.pt.zcu; | 20048 | const zcu = self.pt.zcu; |
| 19965 | return switch (ty.zigTypeTag(zcu)) { | 20049 | return switch (ty.zigTypeTag(zcu)) { |
| 19966 | .float => .fromBitSize(ty.floatBits(self.target.*)), | 20050 | .float => .fromBitSize(ty.floatBits(self.target.*)), |
| ... | @@ -19968,7 +20052,7 @@ fn memSize(self: *Self, ty: Type) Memory.Size { | ... | @@ -19968,7 +20052,7 @@ fn memSize(self: *Self, ty: Type) Memory.Size { |
| 19968 | }; | 20052 | }; |
| 19969 | } | 20053 | } |
| 19970 | | 20054 | |
| 19971 | fn splitType(self: *Self, ty: Type) ![2]Type { | 20055 | fn splitType(self: *CodeGen, ty: Type) ![2]Type { |
| 19972 | const pt = self.pt; | 20056 | const pt = self.pt; |
| 19973 | const zcu = pt.zcu; | 20057 | const zcu = pt.zcu; |
| 19974 | const classes = std.mem.sliceTo(&abi.classifySystemV(ty, zcu, self.target.*, .other), .none); | 20058 | const classes = std.mem.sliceTo(&abi.classifySystemV(ty, zcu, self.target.*, .other), .none); |
| ... | @@ -19998,7 +20082,7 @@ fn splitType(self: *Self, ty: Type) ![2]Type { | ... | @@ -19998,7 +20082,7 @@ fn splitType(self: *Self, ty: Type) ![2]Type { |
| 19998 | | 20082 | |
| 19999 | /// Truncates the value in the register in place. | 20083 | /// Truncates the value in the register in place. |
| 20000 | /// Clobbers any remaining bits. | 20084 | /// Clobbers any remaining bits. |
| 20001 | fn truncateRegister(self: *Self, ty: Type, reg: Register) !void { | 20085 | fn truncateRegister(self: *CodeGen, ty: Type, reg: Register) !void { |
| 20002 | const pt = self.pt; | 20086 | const pt = self.pt; |
| 20003 | const zcu = pt.zcu; | 20087 | const zcu = pt.zcu; |
| 20004 | const int_info = if (ty.isAbiInt(zcu)) ty.intInfo(zcu) else std.builtin.Type.Int{ | 20088 | const int_info = if (ty.isAbiInt(zcu)) ty.intInfo(zcu) else std.builtin.Type.Int{ |
| ... | @@ -20046,7 +20130,7 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void { | ... | @@ -20046,7 +20130,7 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void { |
| 20046 | } | 20130 | } |
| 20047 | } | 20131 | } |
| 20048 | | 20132 | |
| 20049 | fn regBitSize(self: *Self, ty: Type) u64 { | 20133 | fn regBitSize(self: *CodeGen, ty: Type) u64 { |
| 20050 | const zcu = self.pt.zcu; | 20134 | const zcu = self.pt.zcu; |
| 20051 | const abi_size = ty.abiSize(zcu); | 20135 | const abi_size = ty.abiSize(zcu); |
| 20052 | return switch (ty.zigTypeTag(zcu)) { | 20136 | return switch (ty.zigTypeTag(zcu)) { |
| ... | @@ -20065,27 +20149,27 @@ fn regBitSize(self: *Self, ty: Type) u64 { | ... | @@ -20065,27 +20149,27 @@ fn regBitSize(self: *Self, ty: Type) u64 { |
| 20065 | }; | 20149 | }; |
| 20066 | } | 20150 | } |
| 20067 | | 20151 | |
| 20068 | fn regExtraBits(self: *Self, ty: Type) u64 { | 20152 | fn regExtraBits(self: *CodeGen, ty: Type) u64 { |
| 20069 | return self.regBitSize(ty) - ty.bitSize(self.pt.zcu); | 20153 | return self.regBitSize(ty) - ty.bitSize(self.pt.zcu); |
| 20070 | } | 20154 | } |
| 20071 | | 20155 | |
| 20072 | fn hasFeature(self: *Self, feature: std.Target.x86.Feature) bool { | 20156 | fn hasFeature(self: *CodeGen, feature: std.Target.x86.Feature) bool { |
| 20073 | return std.Target.x86.featureSetHas(self.target.cpu.features, feature); | 20157 | return std.Target.x86.featureSetHas(self.target.cpu.features, feature); |
| 20074 | } | 20158 | } |
| 20075 | fn hasAnyFeatures(self: *Self, features: anytype) bool { | 20159 | fn hasAnyFeatures(self: *CodeGen, features: anytype) bool { |
| 20076 | return std.Target.x86.featureSetHasAny(self.target.cpu.features, features); | 20160 | return std.Target.x86.featureSetHasAny(self.target.cpu.features, features); |
| 20077 | } | 20161 | } |
| 20078 | fn hasAllFeatures(self: *Self, features: anytype) bool { | 20162 | fn hasAllFeatures(self: *CodeGen, features: anytype) bool { |
| 20079 | return std.Target.x86.featureSetHasAll(self.target.cpu.features, features); | 20163 | return std.Target.x86.featureSetHasAll(self.target.cpu.features, features); |
| 20080 | } | 20164 | } |
| 20081 | | 20165 | |
| 20082 | fn typeOf(self: *Self, inst: Air.Inst.Ref) Type { | 20166 | fn typeOf(self: *CodeGen, inst: Air.Inst.Ref) Type { |
| 20083 | const pt = self.pt; | 20167 | const pt = self.pt; |
| 20084 | const zcu = pt.zcu; | 20168 | const zcu = pt.zcu; |
| 20085 | return self.air.typeOf(inst, &zcu.intern_pool); | 20169 | return self.air.typeOf(inst, &zcu.intern_pool); |
| 20086 | } | 20170 | } |
| 20087 | | 20171 | |
| 20088 | fn typeOfIndex(self: *Self, inst: Air.Inst.Index) Type { | 20172 | fn typeOfIndex(self: *CodeGen, inst: Air.Inst.Index) Type { |
| 20089 | const pt = self.pt; | 20173 | const pt = self.pt; |
| 20090 | const zcu = pt.zcu; | 20174 | const zcu = pt.zcu; |
| 20091 | const temp: Temp = .{ .index = inst }; | 20175 | const temp: Temp = .{ .index = inst }; |
| ... | @@ -20118,7 +20202,7 @@ fn floatCompilerRtAbiName(float_bits: u32) u8 { | ... | @@ -20118,7 +20202,7 @@ fn floatCompilerRtAbiName(float_bits: u32) u8 { |
| 20118 | }; | 20202 | }; |
| 20119 | } | 20203 | } |
| 20120 | | 20204 | |
| 20121 | fn floatCompilerRtAbiType(self: *Self, ty: Type, other_ty: Type) Type { | 20205 | fn floatCompilerRtAbiType(self: *CodeGen, ty: Type, other_ty: Type) Type { |
| 20122 | if (ty.toIntern() == .f16_type and | 20206 | if (ty.toIntern() == .f16_type and |
| 20123 | (other_ty.toIntern() == .f32_type or other_ty.toIntern() == .f64_type) and | 20207 | (other_ty.toIntern() == .f32_type or other_ty.toIntern() == .f64_type) and |
| 20124 | self.target.isDarwin()) return Type.u16; | 20208 | self.target.isDarwin()) return Type.u16; |
| ... | @@ -20145,7 +20229,7 @@ fn floatLibcAbiSuffix(ty: Type) []const u8 { | ... | @@ -20145,7 +20229,7 @@ fn floatLibcAbiSuffix(ty: Type) []const u8 { |
| 20145 | }; | 20229 | }; |
| 20146 | } | 20230 | } |
| 20147 | | 20231 | |
| 20148 | fn promoteInt(self: *Self, ty: Type) Type { | 20232 | fn promoteInt(self: *CodeGen, ty: Type) Type { |
| 20149 | const pt = self.pt; | 20233 | const pt = self.pt; |
| 20150 | const zcu = pt.zcu; | 20234 | const zcu = pt.zcu; |
| 20151 | const int_info: InternPool.Key.IntType = switch (ty.toIntern()) { | 20235 | const int_info: InternPool.Key.IntType = switch (ty.toIntern()) { |
| ... | @@ -20165,7 +20249,7 @@ fn promoteInt(self: *Self, ty: Type) Type { | ... | @@ -20165,7 +20249,7 @@ fn promoteInt(self: *Self, ty: Type) Type { |
| 20165 | return ty; | 20249 | return ty; |
| 20166 | } | 20250 | } |
| 20167 | | 20251 | |
| 20168 | fn promoteVarArg(self: *Self, ty: Type) Type { | 20252 | fn promoteVarArg(self: *CodeGen, ty: Type) Type { |
| 20169 | if (!ty.isRuntimeFloat()) return self.promoteInt(ty); | 20253 | if (!ty.isRuntimeFloat()) return self.promoteInt(ty); |
| 20170 | switch (ty.floatBits(self.target.*)) { | 20254 | switch (ty.floatBits(self.target.*)) { |
| 20171 | 32, 64 => return Type.f64, | 20255 | 32, 64 => return Type.f64, |
| ... | @@ -20181,7 +20265,7 @@ fn promoteVarArg(self: *Self, ty: Type) Type { | ... | @@ -20181,7 +20265,7 @@ fn promoteVarArg(self: *Self, ty: Type) Type { |
| 20181 | const Temp = struct { | 20265 | const Temp = struct { |
| 20182 | index: Air.Inst.Index, | 20266 | index: Air.Inst.Index, |
| 20183 | | 20267 | |
| 20184 | fn unwrap(temp: Temp, self: *Self) union(enum) { | 20268 | fn unwrap(temp: Temp, cg: *CodeGen) union(enum) { |
| 20185 | ref: Air.Inst.Ref, | 20269 | ref: Air.Inst.Ref, |
| 20186 | temp: Index, | 20270 | temp: Index, |
| 20187 | } { | 20271 | } { |
| ... | @@ -20189,38 +20273,69 @@ const Temp = struct { | ... | @@ -20189,38 +20273,69 @@ const Temp = struct { |
| 20189 | .ref => |ref| return .{ .ref = ref }, | 20273 | .ref => |ref| return .{ .ref = ref }, |
| 20190 | .target => |target_index| { | 20274 | .target => |target_index| { |
| 20191 | const temp_index: Index = @enumFromInt(target_index); | 20275 | const temp_index: Index = @enumFromInt(target_index); |
| 20192 | assert(temp_index.isValid(self)); | 20276 | assert(temp_index.isValid(cg)); |
| 20193 | return .{ .temp = temp_index }; | 20277 | return .{ .temp = temp_index }; |
| 20194 | }, | 20278 | }, |
| 20195 | } | 20279 | } |
| 20196 | } | 20280 | } |
| 20197 | | 20281 | |
| 20198 | fn typeOf(temp: Temp, self: *Self) Type { | 20282 | fn typeOf(temp: Temp, cg: *CodeGen) Type { |
| 20199 | return switch (temp.unwrap(self)) { | 20283 | return switch (temp.unwrap(cg)) { |
| 20200 | .ref => |ref| self.typeOf(ref), | 20284 | .ref => |ref| cg.typeOf(ref), |
| 20201 | .temp => |temp_index| temp_index.typeOf(self), | 20285 | .temp => |temp_index| temp_index.typeOf(cg), |
| 20202 | }; | 20286 | }; |
| 20203 | } | 20287 | } |
| 20204 | | 20288 | |
| 20205 | fn isMut(temp: Temp, self: *Self) bool { | 20289 | fn isMut(temp: Temp, cg: *CodeGen) bool { |
| 20206 | return temp.unwrap(self) == .temp; | 20290 | return switch (temp.unwrap(cg)) { |
| | 20291 | .ref => false, |
| | 20292 | .temp => |temp_index| switch (temp_index.tracking(cg).short) { |
| | 20293 | .none, |
| | 20294 | .unreach, |
| | 20295 | .dead, |
| | 20296 | .undef, |
| | 20297 | .immediate, |
| | 20298 | .eflags, |
| | 20299 | .register_offset, |
| | 20300 | .memory, |
| | 20301 | .load_symbol, |
| | 20302 | .lea_symbol, |
| | 20303 | .indirect, |
| | 20304 | .load_direct, |
| | 20305 | .lea_direct, |
| | 20306 | .load_got, |
| | 20307 | .lea_got, |
| | 20308 | .load_tlv, |
| | 20309 | .lea_tlv, |
| | 20310 | .lea_frame, |
| | 20311 | .elementwise_regs_then_frame, |
| | 20312 | .reserved_frame, |
| | 20313 | .air_ref, |
| | 20314 | => false, |
| | 20315 | .register, |
| | 20316 | .register_pair, |
| | 20317 | .register_overflow, |
| | 20318 | => true, |
| | 20319 | .load_frame => |frame_addr| !frame_addr.index.isNamed(), |
| | 20320 | }, |
| | 20321 | }; |
| 20207 | } | 20322 | } |
| 20208 | | 20323 | |
| 20209 | fn tracking(temp: Temp, self: *Self) InstTracking { | 20324 | fn tracking(temp: Temp, cg: *CodeGen) InstTracking { |
| 20210 | return self.inst_tracking.get(temp.index).?; | 20325 | return cg.inst_tracking.get(temp.index).?; |
| 20211 | } | 20326 | } |
| 20212 | | 20327 | |
| 20213 | fn getOffset(temp: Temp, off: i32, self: *Self) !Temp { | 20328 | fn getOffset(temp: Temp, off: i32, cg: *CodeGen) !Temp { |
| 20214 | const new_temp_index = self.next_temp_index; | 20329 | const new_temp_index = cg.next_temp_index; |
| 20215 | self.temp_type[@intFromEnum(new_temp_index)] = Type.usize; | 20330 | cg.temp_type[@intFromEnum(new_temp_index)] = Type.usize; |
| 20216 | self.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); | 20331 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| 20217 | switch (temp.tracking(self).short) { | 20332 | switch (temp.tracking(cg).short) { |
| 20218 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20333 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| 20219 | .register => |reg| { | 20334 | .register => |reg| { |
| 20220 | const new_reg = | 20335 | const new_reg = |
| 20221 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20336 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20222 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20337 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20223 | try self.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ | 20338 | try cg.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ |
| 20224 | .base = .{ .reg = reg.to64() }, | 20339 | .base = .{ .reg = reg.to64() }, |
| 20225 | .mod = .{ .rm = .{ | 20340 | .mod = .{ .rm = .{ |
| 20226 | .size = .qword, | 20341 | .size = .qword, |
| ... | @@ -20230,9 +20345,9 @@ const Temp = struct { | ... | @@ -20230,9 +20345,9 @@ const Temp = struct { |
| 20230 | }, | 20345 | }, |
| 20231 | .register_offset => |reg_off| { | 20346 | .register_offset => |reg_off| { |
| 20232 | const new_reg = | 20347 | const new_reg = |
| 20233 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20348 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20234 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20349 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20235 | try self.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ | 20350 | try cg.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ |
| 20236 | .base = .{ .reg = reg_off.reg.to64() }, | 20351 | .base = .{ .reg = reg_off.reg.to64() }, |
| 20237 | .mod = .{ .rm = .{ | 20352 | .mod = .{ .rm = .{ |
| 20238 | .size = .qword, | 20353 | .size = .qword, |
| ... | @@ -20240,18 +20355,18 @@ const Temp = struct { | ... | @@ -20240,18 +20355,18 @@ const Temp = struct { |
| 20240 | } }, | 20355 | } }, |
| 20241 | }); | 20356 | }); |
| 20242 | }, | 20357 | }, |
| 20243 | .lea_symbol => |sym_off| new_temp_index.tracking(self).* = .init(.{ .lea_symbol = .{ | 20358 | .lea_symbol => |sym_off| new_temp_index.tracking(cg).* = .init(.{ .lea_symbol = .{ |
| 20244 | .sym_index = sym_off.sym_index, | 20359 | .sym_index = sym_off.sym_index, |
| 20245 | .off = sym_off.off + off, | 20360 | .off = sym_off.off + off, |
| 20246 | } }), | 20361 | } }), |
| 20247 | .load_frame => |frame_addr| { | 20362 | .load_frame => |frame_addr| { |
| 20248 | const new_reg = | 20363 | const new_reg = |
| 20249 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20364 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20250 | new_temp_index.tracking(self).* = .init(.{ .register_offset = .{ | 20365 | new_temp_index.tracking(cg).* = .init(.{ .register_offset = .{ |
| 20251 | .reg = new_reg, | 20366 | .reg = new_reg, |
| 20252 | .off = off, | 20367 | .off = off, |
| 20253 | } }); | 20368 | } }); |
| 20254 | try self.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ | 20369 | try cg.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ |
| 20255 | .base = .{ .frame = frame_addr.index }, | 20370 | .base = .{ .frame = frame_addr.index }, |
| 20256 | .mod = .{ .rm = .{ | 20371 | .mod = .{ .rm = .{ |
| 20257 | .size = .qword, | 20372 | .size = .qword, |
| ... | @@ -20259,7 +20374,7 @@ const Temp = struct { | ... | @@ -20259,7 +20374,7 @@ const Temp = struct { |
| 20259 | } }, | 20374 | } }, |
| 20260 | }); | 20375 | }); |
| 20261 | }, | 20376 | }, |
| 20262 | .lea_frame => |frame_addr| new_temp_index.tracking(self).* = .init(.{ .lea_frame = .{ | 20377 | .lea_frame => |frame_addr| new_temp_index.tracking(cg).* = .init(.{ .lea_frame = .{ |
| 20263 | .index = frame_addr.index, | 20378 | .index = frame_addr.index, |
| 20264 | .off = frame_addr.off + off, | 20379 | .off = frame_addr.off + off, |
| 20265 | } }), | 20380 | } }), |
| ... | @@ -20267,16 +20382,16 @@ const Temp = struct { | ... | @@ -20267,16 +20382,16 @@ const Temp = struct { |
| 20267 | return .{ .index = new_temp_index.toIndex() }; | 20382 | return .{ .index = new_temp_index.toIndex() }; |
| 20268 | } | 20383 | } |
| 20269 | | 20384 | |
| 20270 | fn toOffset(temp: *Temp, off: i32, self: *Self) !void { | 20385 | fn toOffset(temp: *Temp, off: i32, cg: *CodeGen) !void { |
| 20271 | if (off == 0) return; | 20386 | if (off == 0) return; |
| 20272 | switch (temp.unwrap(self)) { | 20387 | switch (temp.unwrap(cg)) { |
| 20273 | .ref => {}, | 20388 | .ref => {}, |
| 20274 | .temp => |temp_index| { | 20389 | .temp => |temp_index| { |
| 20275 | const temp_tracking = temp_index.tracking(self); | 20390 | const temp_tracking = temp_index.tracking(cg); |
| 20276 | switch (temp_tracking.short) { | 20391 | switch (temp_tracking.short) { |
| 20277 | else => {}, | 20392 | else => {}, |
| 20278 | .register => |reg| { | 20393 | .register => |reg| { |
| 20279 | try self.freeValue(temp_tracking.long); | 20394 | try cg.freeValue(temp_tracking.long); |
| 20280 | temp_tracking.* = .init(.{ .register_offset = .{ | 20395 | temp_tracking.* = .init(.{ .register_offset = .{ |
| 20281 | .reg = reg, | 20396 | .reg = reg, |
| 20282 | .off = off, | 20397 | .off = off, |
| ... | @@ -20284,7 +20399,7 @@ const Temp = struct { | ... | @@ -20284,7 +20399,7 @@ const Temp = struct { |
| 20284 | return; | 20399 | return; |
| 20285 | }, | 20400 | }, |
| 20286 | .register_offset => |reg_off| { | 20401 | .register_offset => |reg_off| { |
| 20287 | try self.freeValue(temp_tracking.long); | 20402 | try cg.freeValue(temp_tracking.long); |
| 20288 | temp_tracking.* = .init(.{ .register_offset = .{ | 20403 | temp_tracking.* = .init(.{ .register_offset = .{ |
| 20289 | .reg = reg_off.reg, | 20404 | .reg = reg_off.reg, |
| 20290 | .off = reg_off.off + off, | 20405 | .off = reg_off.off + off, |
| ... | @@ -20310,39 +20425,39 @@ const Temp = struct { | ... | @@ -20310,39 +20425,39 @@ const Temp = struct { |
| 20310 | } | 20425 | } |
| 20311 | }, | 20426 | }, |
| 20312 | } | 20427 | } |
| 20313 | const new_temp = try temp.getOffset(off, self); | 20428 | const new_temp = try temp.getOffset(off, cg); |
| 20314 | try temp.die(self); | 20429 | try temp.die(cg); |
| 20315 | temp.* = new_temp; | 20430 | temp.* = new_temp; |
| 20316 | } | 20431 | } |
| 20317 | | 20432 | |
| 20318 | fn getLimb(temp: Temp, limb_index: u28, self: *Self) !Temp { | 20433 | fn getLimb(temp: Temp, limb_index: u28, cg: *CodeGen) !Temp { |
| 20319 | const new_temp_index = self.next_temp_index; | 20434 | const new_temp_index = cg.next_temp_index; |
| 20320 | self.temp_type[@intFromEnum(new_temp_index)] = Type.usize; | 20435 | cg.temp_type[@intFromEnum(new_temp_index)] = Type.usize; |
| 20321 | switch (temp.tracking(self).short) { | 20436 | switch (temp.tracking(cg).short) { |
| 20322 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20437 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| 20323 | .immediate => |imm| { | 20438 | .immediate => |imm| { |
| 20324 | assert(limb_index == 0); | 20439 | assert(limb_index == 0); |
| 20325 | new_temp_index.tracking(self).* = .init(.{ .immediate = imm }); | 20440 | new_temp_index.tracking(cg).* = .init(.{ .immediate = imm }); |
| 20326 | }, | 20441 | }, |
| 20327 | .register => |reg| { | 20442 | .register => |reg| { |
| 20328 | assert(limb_index == 0); | 20443 | assert(limb_index == 0); |
| 20329 | const new_reg = | 20444 | const new_reg = |
| 20330 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20445 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20331 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20446 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20332 | try self.asmRegisterRegister(.{ ._, .mov }, new_reg.to64(), reg.to64()); | 20447 | try cg.asmRegisterRegister(.{ ._, .mov }, new_reg.to64(), reg.to64()); |
| 20333 | }, | 20448 | }, |
| 20334 | .register_pair => |regs| { | 20449 | .register_pair => |regs| { |
| 20335 | const new_reg = | 20450 | const new_reg = |
| 20336 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20451 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20337 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20452 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20338 | try self.asmRegisterRegister(.{ ._, .mov }, new_reg.to64(), regs[limb_index].to64()); | 20453 | try cg.asmRegisterRegister(.{ ._, .mov }, new_reg.to64(), regs[limb_index].to64()); |
| 20339 | }, | 20454 | }, |
| 20340 | .register_offset => |reg_off| { | 20455 | .register_offset => |reg_off| { |
| 20341 | assert(limb_index == 0); | 20456 | assert(limb_index == 0); |
| 20342 | const new_reg = | 20457 | const new_reg = |
| 20343 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20458 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20344 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20459 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20345 | try self.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ | 20460 | try cg.asmRegisterMemory(.{ ._, .lea }, new_reg.to64(), .{ |
| 20346 | .base = .{ .reg = reg_off.reg.to64() }, | 20461 | .base = .{ .reg = reg_off.reg.to64() }, |
| 20347 | .mod = .{ .rm = .{ | 20462 | .mod = .{ .rm = .{ |
| 20348 | .size = .qword, | 20463 | .size = .qword, |
| ... | @@ -20352,9 +20467,9 @@ const Temp = struct { | ... | @@ -20352,9 +20467,9 @@ const Temp = struct { |
| 20352 | }, | 20467 | }, |
| 20353 | .load_symbol => |sym_off| { | 20468 | .load_symbol => |sym_off| { |
| 20354 | const new_reg = | 20469 | const new_reg = |
| 20355 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20470 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20356 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20471 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20357 | try self.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ | 20472 | try cg.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ |
| 20358 | .base = .{ .reloc = sym_off.sym_index }, | 20473 | .base = .{ .reloc = sym_off.sym_index }, |
| 20359 | .mod = .{ .rm = .{ | 20474 | .mod = .{ .rm = .{ |
| 20360 | .size = .qword, | 20475 | .size = .qword, |
| ... | @@ -20364,13 +20479,13 @@ const Temp = struct { | ... | @@ -20364,13 +20479,13 @@ const Temp = struct { |
| 20364 | }, | 20479 | }, |
| 20365 | .lea_symbol => |sym_off| { | 20480 | .lea_symbol => |sym_off| { |
| 20366 | assert(limb_index == 0); | 20481 | assert(limb_index == 0); |
| 20367 | new_temp_index.tracking(self).* = .init(.{ .lea_symbol = sym_off }); | 20482 | new_temp_index.tracking(cg).* = .init(.{ .lea_symbol = sym_off }); |
| 20368 | }, | 20483 | }, |
| 20369 | .load_frame => |frame_addr| { | 20484 | .load_frame => |frame_addr| { |
| 20370 | const new_reg = | 20485 | const new_reg = |
| 20371 | try self.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); | 20486 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| 20372 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20487 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20373 | try self.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ | 20488 | try cg.asmRegisterMemory(.{ ._, .mov }, new_reg.to64(), .{ |
| 20374 | .base = .{ .frame = frame_addr.index }, | 20489 | .base = .{ .frame = frame_addr.index }, |
| 20375 | .mod = .{ .rm = .{ | 20490 | .mod = .{ .rm = .{ |
| 20376 | .size = .qword, | 20491 | .size = .qword, |
| ... | @@ -20380,23 +20495,23 @@ const Temp = struct { | ... | @@ -20380,23 +20495,23 @@ const Temp = struct { |
| 20380 | }, | 20495 | }, |
| 20381 | .lea_frame => |frame_addr| { | 20496 | .lea_frame => |frame_addr| { |
| 20382 | assert(limb_index == 0); | 20497 | assert(limb_index == 0); |
| 20383 | new_temp_index.tracking(self).* = .init(.{ .lea_frame = frame_addr }); | 20498 | new_temp_index.tracking(cg).* = .init(.{ .lea_frame = frame_addr }); |
| 20384 | }, | 20499 | }, |
| 20385 | } | 20500 | } |
| 20386 | self.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); | 20501 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| 20387 | return .{ .index = new_temp_index.toIndex() }; | 20502 | return .{ .index = new_temp_index.toIndex() }; |
| 20388 | } | 20503 | } |
| 20389 | | 20504 | |
| 20390 | fn toLimb(temp: *Temp, limb_index: u28, self: *Self) !void { | 20505 | fn toLimb(temp: *Temp, limb_index: u28, cg: *CodeGen) !void { |
| 20391 | switch (temp.unwrap(self)) { | 20506 | switch (temp.unwrap(cg)) { |
| 20392 | .ref => {}, | 20507 | .ref => {}, |
| 20393 | .temp => |temp_index| { | 20508 | .temp => |temp_index| { |
| 20394 | const temp_tracking = temp_index.tracking(self); | 20509 | const temp_tracking = temp_index.tracking(cg); |
| 20395 | switch (temp_tracking.short) { | 20510 | switch (temp_tracking.short) { |
| 20396 | else => {}, | 20511 | else => {}, |
| 20397 | .register, .lea_symbol, .lea_frame => { | 20512 | .register, .lea_symbol, .lea_frame => { |
| 20398 | assert(limb_index == 0); | 20513 | assert(limb_index == 0); |
| 20399 | self.temp_type[@intFromEnum(temp_index)] = Type.usize; | 20514 | cg.temp_type[@intFromEnum(temp_index)] = Type.usize; |
| 20400 | return; | 20515 | return; |
| 20401 | }, | 20516 | }, |
| 20402 | .register_pair => |regs| { | 20517 | .register_pair => |regs| { |
| ... | @@ -20406,9 +20521,9 @@ const Temp = struct { | ... | @@ -20406,9 +20521,9 @@ const Temp = struct { |
| 20406 | temp_tracking.long.address().offset(@as(u31, limb_index) * 8).deref(), | 20521 | temp_tracking.long.address().offset(@as(u31, limb_index) * 8).deref(), |
| 20407 | } | 20522 | } |
| 20408 | for (regs, 0..) |reg, reg_index| if (reg_index != limb_index) | 20523 | for (regs, 0..) |reg, reg_index| if (reg_index != limb_index) |
| 20409 | self.register_manager.freeReg(reg); | 20524 | cg.register_manager.freeReg(reg); |
| 20410 | temp_tracking.* = .init(.{ .register = regs[limb_index] }); | 20525 | temp_tracking.* = .init(.{ .register = regs[limb_index] }); |
| 20411 | self.temp_type[@intFromEnum(temp_index)] = Type.usize; | 20526 | cg.temp_type[@intFromEnum(temp_index)] = Type.usize; |
| 20412 | return; | 20527 | return; |
| 20413 | }, | 20528 | }, |
| 20414 | .load_symbol => |sym_off| { | 20529 | .load_symbol => |sym_off| { |
| ... | @@ -20417,7 +20532,7 @@ const Temp = struct { | ... | @@ -20417,7 +20532,7 @@ const Temp = struct { |
| 20417 | .sym_index = sym_off.sym_index, | 20532 | .sym_index = sym_off.sym_index, |
| 20418 | .off = sym_off.off + @as(u31, limb_index) * 8, | 20533 | .off = sym_off.off + @as(u31, limb_index) * 8, |
| 20419 | } }); | 20534 | } }); |
| 20420 | self.temp_type[@intFromEnum(temp_index)] = Type.usize; | 20535 | cg.temp_type[@intFromEnum(temp_index)] = Type.usize; |
| 20421 | return; | 20536 | return; |
| 20422 | }, | 20537 | }, |
| 20423 | .load_frame => |frame_addr| if (!frame_addr.index.isNamed()) { | 20538 | .load_frame => |frame_addr| if (!frame_addr.index.isNamed()) { |
| ... | @@ -20426,102 +20541,102 @@ const Temp = struct { | ... | @@ -20426,102 +20541,102 @@ const Temp = struct { |
| 20426 | .index = frame_addr.index, | 20541 | .index = frame_addr.index, |
| 20427 | .off = frame_addr.off + @as(u31, limb_index) * 8, | 20542 | .off = frame_addr.off + @as(u31, limb_index) * 8, |
| 20428 | } }); | 20543 | } }); |
| 20429 | self.temp_type[@intFromEnum(temp_index)] = Type.usize; | 20544 | cg.temp_type[@intFromEnum(temp_index)] = Type.usize; |
| 20430 | return; | 20545 | return; |
| 20431 | }, | 20546 | }, |
| 20432 | } | 20547 | } |
| 20433 | }, | 20548 | }, |
| 20434 | } | 20549 | } |
| 20435 | const new_temp = try temp.getLimb(limb_index, self); | 20550 | const new_temp = try temp.getLimb(limb_index, cg); |
| 20436 | try temp.die(self); | 20551 | try temp.die(cg); |
| 20437 | temp.* = new_temp; | 20552 | temp.* = new_temp; |
| 20438 | } | 20553 | } |
| 20439 | | 20554 | |
| 20440 | fn toReg(temp: *Temp, new_reg: Register, self: *Self) !bool { | 20555 | fn toReg(temp: *Temp, new_reg: Register, cg: *CodeGen) !bool { |
| 20441 | const val, const ty = switch (temp.unwrap(self)) { | 20556 | const val, const ty = val_ty: switch (temp.unwrap(cg)) { |
| 20442 | .ref => |ref| .{ temp.tracking(self).short, self.typeOf(ref) }, | 20557 | .ref => |ref| .{ temp.tracking(cg).short, cg.typeOf(ref) }, |
| 20443 | .temp => |temp_index| val: { | 20558 | .temp => |temp_index| { |
| 20444 | const temp_tracking = temp_index.tracking(self); | 20559 | const temp_tracking = temp_index.tracking(cg); |
| 20445 | if (temp_tracking.short == .register and | 20560 | if (temp_tracking.short == .register and |
| 20446 | temp_tracking.short.register == new_reg) return false; | 20561 | temp_tracking.short.register == new_reg) return false; |
| 20447 | break :val .{ temp_tracking.short, temp_index.typeOf(self) }; | 20562 | break :val_ty .{ temp_tracking.short, temp_index.typeOf(cg) }; |
| 20448 | }, | 20563 | }, |
| 20449 | }; | 20564 | }; |
| 20450 | const new_temp_index = self.next_temp_index; | 20565 | const new_temp_index = cg.next_temp_index; |
| 20451 | self.temp_type[@intFromEnum(new_temp_index)] = ty; | 20566 | cg.temp_type[@intFromEnum(new_temp_index)] = ty; |
| 20452 | try self.genSetReg(new_reg, ty, val, .{}); | 20567 | try cg.genSetReg(new_reg, ty, val, .{}); |
| 20453 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20568 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20454 | try temp.die(self); | 20569 | try temp.die(cg); |
| 20455 | self.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); | 20570 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| 20456 | temp.* = .{ .index = new_temp_index.toIndex() }; | 20571 | temp.* = .{ .index = new_temp_index.toIndex() }; |
| 20457 | return true; | 20572 | return true; |
| 20458 | } | 20573 | } |
| 20459 | | 20574 | |
| 20460 | fn toAnyReg(temp: *Temp, self: *Self) !bool { | 20575 | fn toAnyReg(temp: *Temp, cg: *CodeGen) !bool { |
| 20461 | const val, const ty = switch (temp.unwrap(self)) { | 20576 | const val, const ty = switch (temp.unwrap(cg)) { |
| 20462 | .ref => |ref| .{ temp.tracking(self).short, self.typeOf(ref) }, | 20577 | .ref => |ref| .{ temp.tracking(cg).short, cg.typeOf(ref) }, |
| 20463 | .temp => |temp_index| val: { | 20578 | .temp => |temp_index| val: { |
| 20464 | const temp_tracking = temp_index.tracking(self); | 20579 | const temp_tracking = temp_index.tracking(cg); |
| 20465 | if (temp_tracking.short == .register) return false; | 20580 | if (temp_tracking.short == .register) return false; |
| 20466 | break :val .{ temp_tracking.short, temp_index.typeOf(self) }; | 20581 | break :val .{ temp_tracking.short, temp_index.typeOf(cg) }; |
| 20467 | }, | 20582 | }, |
| 20468 | }; | 20583 | }; |
| 20469 | const new_temp_index = self.next_temp_index; | 20584 | const new_temp_index = cg.next_temp_index; |
| 20470 | self.temp_type[@intFromEnum(new_temp_index)] = ty; | 20585 | cg.temp_type[@intFromEnum(new_temp_index)] = ty; |
| 20471 | const new_reg = | 20586 | const new_reg = |
| 20472 | try self.register_manager.allocReg(new_temp_index.toIndex(), self.regSetForType(ty)); | 20587 | try cg.register_manager.allocReg(new_temp_index.toIndex(), cg.regSetForType(ty)); |
| 20473 | try self.genSetReg(new_reg, ty, val, .{}); | 20588 | try cg.genSetReg(new_reg, ty, val, .{}); |
| 20474 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20589 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20475 | try temp.die(self); | 20590 | try temp.die(cg); |
| 20476 | self.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); | 20591 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| 20477 | temp.* = .{ .index = new_temp_index.toIndex() }; | 20592 | temp.* = .{ .index = new_temp_index.toIndex() }; |
| 20478 | return true; | 20593 | return true; |
| 20479 | } | 20594 | } |
| 20480 | | 20595 | |
| 20481 | fn toRegClass(temp: *Temp, rc: Register.Class, self: *Self) !bool { | 20596 | fn toRegClass(temp: *Temp, rc: Register.Class, cg: *CodeGen) !bool { |
| 20482 | const val, const ty = switch (temp.unwrap(self)) { | 20597 | const val, const ty = switch (temp.unwrap(cg)) { |
| 20483 | .ref => |ref| .{ temp.tracking(self).short, self.typeOf(ref) }, | 20598 | .ref => |ref| .{ temp.tracking(cg).short, cg.typeOf(ref) }, |
| 20484 | .temp => |temp_index| val: { | 20599 | .temp => |temp_index| val: { |
| 20485 | const temp_tracking = temp_index.tracking(self); | 20600 | const temp_tracking = temp_index.tracking(cg); |
| 20486 | switch (temp_tracking.short) { | 20601 | switch (temp_tracking.short) { |
| 20487 | else => {}, | 20602 | else => {}, |
| 20488 | .register => |reg| if (reg.class() == rc) return false, | 20603 | .register => |reg| if (reg.class() == rc) return false, |
| 20489 | } | 20604 | } |
| 20490 | break :val .{ temp_tracking.short, temp_index.typeOf(self) }; | 20605 | break :val .{ temp_tracking.short, temp_index.typeOf(cg) }; |
| 20491 | }, | 20606 | }, |
| 20492 | }; | 20607 | }; |
| 20493 | const new_temp_index = self.next_temp_index; | 20608 | const new_temp_index = cg.next_temp_index; |
| 20494 | self.temp_type[@intFromEnum(new_temp_index)] = ty; | 20609 | cg.temp_type[@intFromEnum(new_temp_index)] = ty; |
| 20495 | const new_reg = try self.register_manager.allocReg(new_temp_index.toIndex(), regSetForRegClass(rc)); | 20610 | const new_reg = try cg.register_manager.allocReg(new_temp_index.toIndex(), regSetForRegClass(rc)); |
| 20496 | try self.genSetReg(new_reg, ty, val, .{}); | 20611 | try cg.genSetReg(new_reg, ty, val, .{}); |
| 20497 | new_temp_index.tracking(self).* = .init(.{ .register = new_reg }); | 20612 | new_temp_index.tracking(cg).* = .init(.{ .register = new_reg }); |
| 20498 | try temp.die(self); | 20613 | try temp.die(cg); |
| 20499 | self.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); | 20614 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| 20500 | temp.* = .{ .index = new_temp_index.toIndex() }; | 20615 | temp.* = .{ .index = new_temp_index.toIndex() }; |
| 20501 | return true; | 20616 | return true; |
| 20502 | } | 20617 | } |
| 20503 | | 20618 | |
| 20504 | fn toPair(first_temp: *Temp, second_temp: *Temp, self: *Self) !void { | 20619 | fn toPair(first_temp: *Temp, second_temp: *Temp, cg: *CodeGen) !void { |
| 20505 | while (true) for ([_]*Temp{ first_temp, second_temp }) |part_temp| { | 20620 | while (true) for ([_]*Temp{ first_temp, second_temp }) |part_temp| { |
| 20506 | if (try part_temp.toAnyReg(self)) break; | 20621 | if (try part_temp.toAnyReg(cg)) break; |
| 20507 | } else break; | 20622 | } else break; |
| 20508 | const first_temp_tracking = first_temp.unwrap(self).temp.tracking(self); | 20623 | const first_temp_tracking = first_temp.unwrap(cg).temp.tracking(cg); |
| 20509 | const second_temp_tracking = second_temp.unwrap(self).temp.tracking(self); | 20624 | const second_temp_tracking = second_temp.unwrap(cg).temp.tracking(cg); |
| 20510 | const result: MCValue = .{ .register_pair = .{ | 20625 | const result: MCValue = .{ .register_pair = .{ |
| 20511 | first_temp_tracking.short.register, | 20626 | first_temp_tracking.short.register, |
| 20512 | second_temp_tracking.short.register, | 20627 | second_temp_tracking.short.register, |
| 20513 | } }; | 20628 | } }; |
| 20514 | const result_temp_index = self.next_temp_index; | 20629 | const result_temp_index = cg.next_temp_index; |
| 20515 | const result_temp: Temp = .{ .index = result_temp_index.toIndex() }; | 20630 | const result_temp: Temp = .{ .index = result_temp_index.toIndex() }; |
| 20516 | assert(self.reuseTemp(result_temp.index, first_temp.index, first_temp_tracking)); | 20631 | assert(cg.reuseTemp(result_temp.index, first_temp.index, first_temp_tracking)); |
| 20517 | assert(self.reuseTemp(result_temp.index, second_temp.index, second_temp_tracking)); | 20632 | assert(cg.reuseTemp(result_temp.index, second_temp.index, second_temp_tracking)); |
| 20518 | self.temp_type[@intFromEnum(result_temp_index)] = Type.slice_const_u8; | 20633 | cg.temp_type[@intFromEnum(result_temp_index)] = Type.slice_const_u8; |
| 20519 | result_temp_index.tracking(self).* = .init(result); | 20634 | result_temp_index.tracking(cg).* = .init(result); |
| 20520 | first_temp.* = result_temp; | 20635 | first_temp.* = result_temp; |
| 20521 | } | 20636 | } |
| 20522 | | 20637 | |
| 20523 | fn toLea(temp: *Temp, self: *Self) !bool { | 20638 | fn toLea(temp: *Temp, cg: *CodeGen) !bool { |
| 20524 | switch (temp.tracking(self).short) { | 20639 | switch (temp.tracking(cg).short) { |
| 20525 | .none, | 20640 | .none, |
| 20526 | .unreach, | 20641 | .unreach, |
| 20527 | .dead, | 20642 | .dead, |
| ... | @@ -20548,65 +20663,83 @@ const Temp = struct { | ... | @@ -20548,65 +20663,83 @@ const Temp = struct { |
| 20548 | .load_got, | 20663 | .load_got, |
| 20549 | .load_tlv, | 20664 | .load_tlv, |
| 20550 | .load_frame, | 20665 | .load_frame, |
| 20551 | => return temp.toAnyReg(self), | 20666 | => return temp.toAnyReg(cg), |
| 20552 | .lea_symbol => |sym_off| { | 20667 | .lea_symbol => |sym_off| { |
| 20553 | const off = sym_off.off; | 20668 | const off = sym_off.off; |
| 20554 | if (off == 0) return false; | 20669 | if (off == 0) return false; |
| 20555 | try temp.toOffset(-off, self); | 20670 | try temp.toOffset(-off, cg); |
| 20556 | while (try temp.toAnyReg(self)) {} | 20671 | while (try temp.toAnyReg(cg)) {} |
| 20557 | try temp.toOffset(off, self); | 20672 | try temp.toOffset(off, cg); |
| 20558 | return true; | 20673 | return true; |
| 20559 | }, | 20674 | }, |
| 20560 | } | 20675 | } |
| 20561 | } | 20676 | } |
| 20562 | | 20677 | |
| 20563 | fn load(ptr: *Temp, val_ty: Type, self: *Self) !Temp { | 20678 | fn toBase(temp: *Temp, cg: *CodeGen) !bool { |
| 20564 | const val_abi_size: u32 = @intCast(val_ty.abiSize(self.pt.zcu)); | 20679 | const temp_tracking = temp.tracking(cg); |
| 20565 | const val = try self.tempAlloc(val_ty); | 20680 | switch (temp_tracking.short) { |
| 20566 | switch (val.tracking(self).short) { | 20681 | else => {}, |
| | 20682 | .indirect, .load_frame => return false, |
| | 20683 | } |
| | 20684 | const new_temp_index = cg.next_temp_index; |
| | 20685 | cg.temp_type[@intFromEnum(new_temp_index)] = temp.typeOf(cg); |
| | 20686 | const new_reg = |
| | 20687 | try cg.register_manager.allocReg(new_temp_index.toIndex(), abi.RegisterClass.gp); |
| | 20688 | try cg.genSetReg(new_reg, Type.usize, temp_tracking.short.address(), .{}); |
| | 20689 | new_temp_index.tracking(cg).* = .init(.{ .indirect = .{ .reg = new_reg } }); |
| | 20690 | try temp.die(cg); |
| | 20691 | cg.next_temp_index = @enumFromInt(@intFromEnum(new_temp_index) + 1); |
| | 20692 | temp.* = .{ .index = new_temp_index.toIndex() }; |
| | 20693 | return true; |
| | 20694 | } |
| | 20695 | |
| | 20696 | fn load(ptr: *Temp, val_ty: Type, cg: *CodeGen) !Temp { |
| | 20697 | const val_abi_size: u32 = @intCast(val_ty.abiSize(cg.pt.zcu)); |
| | 20698 | const val = try cg.tempAlloc(val_ty); |
| | 20699 | switch (val.tracking(cg).short) { |
| 20567 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20700 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| 20568 | .register => |val_reg| { | 20701 | .register => |val_reg| { |
| 20569 | while (try ptr.toLea(self)) {} | 20702 | while (try ptr.toLea(cg)) {} |
| 20570 | switch (val_reg.class()) { | 20703 | switch (val_reg.class()) { |
| 20571 | .general_purpose => try self.asmRegisterMemory( | 20704 | .general_purpose => try cg.asmRegisterMemory( |
| 20572 | .{ ._, .mov }, | 20705 | .{ ._, .mov }, |
| 20573 | registerAlias(val_reg, val_abi_size), | 20706 | registerAlias(val_reg, val_abi_size), |
| 20574 | try ptr.tracking(self).short.deref().mem(self, self.memSize(val_ty)), | 20707 | try ptr.tracking(cg).short.deref().mem(cg, .{ .size = cg.memSize(val_ty) }), |
| 20575 | ), | 20708 | ), |
| 20576 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20709 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| 20577 | } | 20710 | } |
| 20578 | }, | 20711 | }, |
| 20579 | .load_frame => |val_frame_addr| { | 20712 | .load_frame => |val_frame_addr| { |
| 20580 | var val_ptr = try self.tempFromValue(Type.usize, .{ .lea_frame = val_frame_addr }); | 20713 | var val_ptr = try cg.tempFromValue(Type.usize, .{ .lea_frame = val_frame_addr }); |
| 20581 | var len = try self.tempFromValue(Type.usize, .{ .immediate = val_abi_size }); | 20714 | var len = try cg.tempFromValue(Type.usize, .{ .immediate = val_abi_size }); |
| 20582 | try val_ptr.memcpy(ptr, &len, self); | 20715 | try val_ptr.memcpy(ptr, &len, cg); |
| 20583 | try val_ptr.die(self); | 20716 | try val_ptr.die(cg); |
| 20584 | try len.die(self); | 20717 | try len.die(cg); |
| 20585 | }, | 20718 | }, |
| 20586 | } | 20719 | } |
| 20587 | return val; | 20720 | return val; |
| 20588 | } | 20721 | } |
| 20589 | | 20722 | |
| 20590 | fn store(ptr: *Temp, val: *Temp, self: *Self) !void { | 20723 | fn store(ptr: *Temp, val: *Temp, cg: *CodeGen) !void { |
| 20591 | const val_ty = val.typeOf(self); | 20724 | const val_ty = val.typeOf(cg); |
| 20592 | const val_abi_size: u32 = @intCast(val_ty.abiSize(self.pt.zcu)); | 20725 | const val_abi_size: u32 = @intCast(val_ty.abiSize(cg.pt.zcu)); |
| 20593 | val: switch (val.tracking(self).short) { | 20726 | val: switch (val.tracking(cg).short) { |
| 20594 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20727 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| 20595 | .immediate => |imm| if (std.math.cast(i32, imm)) |s| { | 20728 | .immediate => |imm| if (std.math.cast(i32, imm)) |s| { |
| 20596 | while (try ptr.toLea(self)) {} | 20729 | while (try ptr.toLea(cg)) {} |
| 20597 | try self.asmMemoryImmediate( | 20730 | try cg.asmMemoryImmediate( |
| 20598 | .{ ._, .mov }, | 20731 | .{ ._, .mov }, |
| 20599 | try ptr.tracking(self).short.deref().mem(self, self.memSize(val_ty)), | 20732 | try ptr.tracking(cg).short.deref().mem(cg, .{ .size = cg.memSize(val_ty) }), |
| 20600 | .s(s), | 20733 | .s(s), |
| 20601 | ); | 20734 | ); |
| 20602 | } else continue :val .{ .register = undefined }, | 20735 | } else continue :val .{ .register = undefined }, |
| 20603 | .register => { | 20736 | .register => { |
| 20604 | while (try ptr.toLea(self) or try val.toAnyReg(self)) {} | 20737 | while (try ptr.toLea(cg) or try val.toAnyReg(cg)) {} |
| 20605 | const val_reg = val.tracking(self).short.register; | 20738 | const val_reg = val.tracking(cg).short.register; |
| 20606 | switch (val_reg.class()) { | 20739 | switch (val_reg.class()) { |
| 20607 | .general_purpose => try self.asmMemoryRegister( | 20740 | .general_purpose => try cg.asmMemoryRegister( |
| 20608 | .{ ._, .mov }, | 20741 | .{ ._, .mov }, |
| 20609 | try ptr.tracking(self).short.deref().mem(self, self.memSize(val_ty)), | 20742 | try ptr.tracking(cg).short.deref().mem(cg, .{ .size = cg.memSize(val_ty) }), |
| 20610 | registerAlias(val_reg, val_abi_size), | 20743 | registerAlias(val_reg, val_abi_size), |
| 20611 | ), | 20744 | ), |
| 20612 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), | 20745 | else => |tag| std.debug.panic("{s}: {any}\n", .{ @src().fn_name, tag }), |
| ... | @@ -20615,64 +20748,64 @@ const Temp = struct { | ... | @@ -20615,64 +20748,64 @@ const Temp = struct { |
| 20615 | } | 20748 | } |
| 20616 | } | 20749 | } |
| 20617 | | 20750 | |
| 20618 | fn memcpy(dst: *Temp, src: *Temp, len: *Temp, self: *Self) !void { | 20751 | fn memcpy(dst: *Temp, src: *Temp, len: *Temp, cg: *CodeGen) !void { |
| 20619 | while (true) for ([_]*Temp{ dst, src, len }, [_]Register{ .rdi, .rsi, .rcx }) |temp, reg| { | 20752 | while (true) for ([_]*Temp{ dst, src, len }, [_]Register{ .rdi, .rsi, .rcx }) |temp, reg| { |
| 20620 | if (try temp.toReg(reg, self)) break; | 20753 | if (try temp.toReg(reg, cg)) break; |
| 20621 | } else break; | 20754 | } else break; |
| 20622 | try self.asmOpOnly(.{ .@"rep _sb", .mov }); | 20755 | try cg.asmOpOnly(.{ .@"rep _sb", .mov }); |
| 20623 | } | 20756 | } |
| 20624 | | 20757 | |
| 20625 | // i, m, r | 20758 | // i, m, r |
| 20626 | fn add(lhs: *Temp, rhs: *Temp, self: *Self) !Temp { | 20759 | fn add(lhs: *Temp, rhs: *Temp, cg: *CodeGen) !Temp { |
| 20627 | const res_index = self.next_temp_index; | 20760 | const res_index = cg.next_temp_index; |
| 20628 | var res: Temp = .{ .index = res_index.toIndex() }; | 20761 | var res: Temp = .{ .index = res_index.toIndex() }; |
| 20629 | try self.select(&.{ &res, lhs, rhs }, .{ ._, .add }, &.{ | 20762 | try cg.select(&.{ &res, lhs, rhs }, .{ ._, .add }, &.{ |
| 20630 | .{ .ops = &.{ .{ .match = 1 }, .r, .i } }, | 20763 | .{ .ops = &.{ .{ .match = 1 }, .r, .i } }, |
| 20631 | .{ .ops = &.{ .{ .match = 1 }, .m, .i } }, | 20764 | .{ .ops = &.{ .{ .match = 1 }, .m, .i } }, |
| 20632 | .{ .ops = &.{ .{ .match = 1 }, .r, .m } }, | 20765 | .{ .ops = &.{ .{ .match = 1 }, .r, .m } }, |
| 20633 | .{ .ops = &.{ .{ .match = 1 }, .m, .r } }, | 20766 | .{ .ops = &.{ .{ .match = 1 }, .m, .r } }, |
| 20634 | .{ .ops = &.{ .{ .match = 1 }, .r, .r } }, | 20767 | .{ .ops = &.{ .{ .match = 1 }, .r, .r } }, |
| 20635 | }); | 20768 | }); |
| 20636 | self.next_temp_index = @enumFromInt(@intFromEnum(res_index) + 1); | 20769 | cg.next_temp_index = @enumFromInt(@intFromEnum(res_index) + 1); |
| 20637 | self.temp_type[@intFromEnum(res_index)] = lhs.typeOf(self); | 20770 | cg.temp_type[@intFromEnum(res_index)] = lhs.typeOf(cg); |
| 20638 | return res; | 20771 | return res; |
| 20639 | } | 20772 | } |
| 20640 | | 20773 | |
| 20641 | fn mul(lhs: *Temp, rhs: *Temp, self: *Self) !Temp { | 20774 | fn mul(lhs: *Temp, rhs: *Temp, cg: *CodeGen) !Temp { |
| 20642 | const res_index = self.next_temp_index; | 20775 | const res_index = cg.next_temp_index; |
| 20643 | var res: Temp = .{ .index = self.next_temp_index.toIndex() }; | 20776 | var res: Temp = .{ .index = cg.next_temp_index.toIndex() }; |
| 20644 | try self.select(&.{ &res, lhs, rhs }, .{ .i_, .mul }, &.{ | 20777 | try cg.select(&.{ &res, lhs, rhs }, .{ .i_, .mul }, &.{ |
| 20645 | .{ .ops = &.{ .r, .m, .i } }, | 20778 | .{ .ops = &.{ .r, .m, .i } }, |
| 20646 | .{ .ops = &.{ .r, .r, .i } }, | 20779 | .{ .ops = &.{ .r, .r, .i } }, |
| 20647 | .{ .ops = &.{ .{ .match = 1 }, .r, .m } }, | 20780 | .{ .ops = &.{ .{ .match = 1 }, .r, .m } }, |
| 20648 | .{ .ops = &.{ .{ .match = 1 }, .r, .r } }, | 20781 | .{ .ops = &.{ .{ .match = 1 }, .r, .r } }, |
| 20649 | }); | 20782 | }); |
| 20650 | self.next_temp_index = @enumFromInt(@intFromEnum(res_index) + 1); | 20783 | cg.next_temp_index = @enumFromInt(@intFromEnum(res_index) + 1); |
| 20651 | self.temp_type[@intFromEnum(res_index)] = lhs.typeOf(self); | 20784 | cg.temp_type[@intFromEnum(res_index)] = lhs.typeOf(cg); |
| 20652 | return res; | 20785 | return res; |
| 20653 | } | 20786 | } |
| 20654 | | 20787 | |
| 20655 | fn moveTo(temp: Temp, inst: Air.Inst.Index, self: *Self) !void { | 20788 | fn moveTo(temp: Temp, inst: Air.Inst.Index, cg: *CodeGen) !void { |
| 20656 | if (self.liveness.isUnused(inst)) try temp.die(self) else switch (temp.unwrap(self)) { | 20789 | if (cg.liveness.isUnused(inst)) try temp.die(cg) else switch (temp.unwrap(cg)) { |
| 20657 | .ref => { | 20790 | .ref => { |
| 20658 | const result = try self.allocRegOrMem(inst, true); | 20791 | const result = try cg.allocRegOrMem(inst, true); |
| 20659 | try self.genCopy(self.typeOfIndex(inst), result, temp.tracking(self).short, .{}); | 20792 | try cg.genCopy(cg.typeOfIndex(inst), result, temp.tracking(cg).short, .{}); |
| 20660 | tracking_log.debug("{} => {} (birth)", .{ inst, result }); | 20793 | tracking_log.debug("{} => {} (birth)", .{ inst, result }); |
| 20661 | self.inst_tracking.putAssumeCapacityNoClobber(inst, .init(result)); | 20794 | cg.inst_tracking.putAssumeCapacityNoClobber(inst, .init(result)); |
| 20662 | }, | 20795 | }, |
| 20663 | .temp => |temp_index| { | 20796 | .temp => |temp_index| { |
| 20664 | const temp_tracking = temp_index.tracking(self); | 20797 | const temp_tracking = temp_index.tracking(cg); |
| 20665 | tracking_log.debug("{} => {} (birth)", .{ inst, temp_tracking.short }); | 20798 | tracking_log.debug("{} => {} (birth)", .{ inst, temp_tracking.short }); |
| 20666 | self.inst_tracking.putAssumeCapacityNoClobber(inst, temp_tracking.*); | 20799 | cg.inst_tracking.putAssumeCapacityNoClobber(inst, temp_tracking.*); |
| 20667 | assert(self.reuseTemp(inst, temp_index.toIndex(), temp_tracking)); | 20800 | assert(cg.reuseTemp(inst, temp_index.toIndex(), temp_tracking)); |
| 20668 | }, | 20801 | }, |
| 20669 | } | 20802 | } |
| 20670 | } | 20803 | } |
| 20671 | | 20804 | |
| 20672 | fn die(temp: Temp, self: *Self) !void { | 20805 | fn die(temp: Temp, cg: *CodeGen) !void { |
| 20673 | switch (temp.unwrap(self)) { | 20806 | switch (temp.unwrap(cg)) { |
| 20674 | .ref => {}, | 20807 | .ref => {}, |
| 20675 | .temp => |temp_index| try temp_index.tracking(self).die(self, temp_index.toIndex()), | 20808 | .temp => |temp_index| try temp_index.tracking(cg).die(cg, temp_index.toIndex()), |
| 20676 | } | 20809 | } |
| 20677 | } | 20810 | } |
| 20678 | | 20811 | |
| ... | @@ -20687,17 +20820,17 @@ const Temp = struct { | ... | @@ -20687,17 +20820,17 @@ const Temp = struct { |
| 20687 | return @enumFromInt(index.toTargetIndex()); | 20820 | return @enumFromInt(index.toTargetIndex()); |
| 20688 | } | 20821 | } |
| 20689 | | 20822 | |
| 20690 | fn tracking(index: Index, self: *Self) *InstTracking { | 20823 | fn tracking(index: Index, cg: *CodeGen) *InstTracking { |
| 20691 | return &self.inst_tracking.values()[@intFromEnum(index)]; | 20824 | return &cg.inst_tracking.values()[@intFromEnum(index)]; |
| 20692 | } | 20825 | } |
| 20693 | | 20826 | |
| 20694 | fn isValid(index: Index, self: *Self) bool { | 20827 | fn isValid(index: Index, cg: *CodeGen) bool { |
| 20695 | return index.tracking(self).short != .dead; | 20828 | return index.tracking(cg).short != .dead; |
| 20696 | } | 20829 | } |
| 20697 | | 20830 | |
| 20698 | fn typeOf(index: Index, self: *Self) Type { | 20831 | fn typeOf(index: Index, cg: *CodeGen) Type { |
| 20699 | assert(index.isValid(self)); | 20832 | assert(index.isValid(cg)); |
| 20700 | return self.temp_type[@intFromEnum(index)]; | 20833 | return cg.temp_type[@intFromEnum(index)]; |
| 20701 | } | 20834 | } |
| 20702 | | 20835 | |
| 20703 | const max = std.math.maxInt(@typeInfo(Index).@"enum".tag_type); | 20836 | const max = std.math.maxInt(@typeInfo(Index).@"enum".tag_type); |
| ... | @@ -20723,17 +20856,17 @@ const Temp = struct { | ... | @@ -20723,17 +20856,17 @@ const Temp = struct { |
| 20723 | }; | 20856 | }; |
| 20724 | }; | 20857 | }; |
| 20725 | | 20858 | |
| 20726 | fn resetTemps(self: *Self) void { | 20859 | fn resetTemps(cg: *CodeGen) void { |
| 20727 | for (0..@intFromEnum(self.next_temp_index)) |temp_index| { | 20860 | for (0..@intFromEnum(cg.next_temp_index)) |temp_index| { |
| 20728 | const temp: Temp.Index = @enumFromInt(temp_index); | 20861 | const temp: Temp.Index = @enumFromInt(temp_index); |
| 20729 | assert(!temp.isValid(self)); | 20862 | assert(!temp.isValid(cg)); |
| 20730 | self.temp_type[temp_index] = undefined; | 20863 | cg.temp_type[temp_index] = undefined; |
| 20731 | } | 20864 | } |
| 20732 | self.next_temp_index = @enumFromInt(0); | 20865 | cg.next_temp_index = @enumFromInt(0); |
| 20733 | } | 20866 | } |
| 20734 | | 20867 | |
| 20735 | fn reuseTemp( | 20868 | fn reuseTemp( |
| 20736 | self: *Self, | 20869 | cg: *CodeGen, |
| 20737 | new_inst: Air.Inst.Index, | 20870 | new_inst: Air.Inst.Index, |
| 20738 | old_inst: Air.Inst.Index, | 20871 | old_inst: Air.Inst.Index, |
| 20739 | tracking: *InstTracking, | 20872 | tracking: *InstTracking, |
| ... | @@ -20743,79 +20876,80 @@ fn reuseTemp( | ... | @@ -20743,79 +20876,80 @@ fn reuseTemp( |
| 20743 | .register_pair, | 20876 | .register_pair, |
| 20744 | .register_offset, | 20877 | .register_offset, |
| 20745 | .register_overflow, | 20878 | .register_overflow, |
| | 20879 | .indirect, |
| 20746 | => for (tracking.short.getRegs()) |tracked_reg| { | 20880 | => for (tracking.short.getRegs()) |tracked_reg| { |
| 20747 | if (RegisterManager.indexOfRegIntoTracked(tracked_reg)) |tracked_index| { | 20881 | if (RegisterManager.indexOfRegIntoTracked(tracked_reg)) |tracked_index| { |
| 20748 | self.register_manager.registers[tracked_index] = new_inst; | 20882 | cg.register_manager.registers[tracked_index] = new_inst; |
| 20749 | } | 20883 | } |
| 20750 | }, | 20884 | }, |
| 20751 | .load_frame => |frame_addr| if (frame_addr.index.isNamed()) return false, | 20885 | .load_frame => |frame_addr| if (frame_addr.index.isNamed()) return false, |
| 20752 | else => {}, | 20886 | else => {}, |
| 20753 | } | 20887 | } |
| 20754 | switch (tracking.short) { | 20888 | switch (tracking.short) { |
| 20755 | .eflags, .register_overflow => self.eflags_inst = new_inst, | 20889 | .eflags, .register_overflow => cg.eflags_inst = new_inst, |
| 20756 | else => {}, | 20890 | else => {}, |
| 20757 | } | 20891 | } |
| 20758 | tracking.reuse(self, new_inst, old_inst); | 20892 | tracking.reuse(cg, new_inst, old_inst); |
| 20759 | return true; | 20893 | return true; |
| 20760 | } | 20894 | } |
| 20761 | | 20895 | |
| 20762 | fn tempAlloc(self: *Self, ty: Type) !Temp { | 20896 | fn tempAlloc(cg: *CodeGen, ty: Type) !Temp { |
| 20763 | const temp_index = self.next_temp_index; | 20897 | const temp_index = cg.next_temp_index; |
| 20764 | temp_index.tracking(self).* = .init( | 20898 | temp_index.tracking(cg).* = .init( |
| 20765 | try self.allocRegOrMemAdvanced(ty, temp_index.toIndex(), true), | 20899 | try cg.allocRegOrMemAdvanced(ty, temp_index.toIndex(), true), |
| 20766 | ); | 20900 | ); |
| 20767 | self.temp_type[@intFromEnum(temp_index)] = ty; | 20901 | cg.temp_type[@intFromEnum(temp_index)] = ty; |
| 20768 | self.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); | 20902 | cg.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); |
| 20769 | return .{ .index = temp_index.toIndex() }; | 20903 | return .{ .index = temp_index.toIndex() }; |
| 20770 | } | 20904 | } |
| 20771 | | 20905 | |
| 20772 | fn tempAllocReg(self: *Self, ty: Type, rc: RegisterManager.RegisterBitSet) !Temp { | 20906 | fn tempAllocReg(cg: *CodeGen, ty: Type, rc: RegisterManager.RegisterBitSet) !Temp { |
| 20773 | const temp_index = self.next_temp_index; | 20907 | const temp_index = cg.next_temp_index; |
| 20774 | temp_index.tracking(self).* = .init( | 20908 | temp_index.tracking(cg).* = .init( |
| 20775 | .{ .register = try self.register_manager.allocReg(temp_index.toIndex(), rc) }, | 20909 | .{ .register = try cg.register_manager.allocReg(temp_index.toIndex(), rc) }, |
| 20776 | ); | 20910 | ); |
| 20777 | self.temp_type[@intFromEnum(temp_index)] = ty; | 20911 | cg.temp_type[@intFromEnum(temp_index)] = ty; |
| 20778 | self.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); | 20912 | cg.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); |
| 20779 | return .{ .index = temp_index.toIndex() }; | 20913 | return .{ .index = temp_index.toIndex() }; |
| 20780 | } | 20914 | } |
| 20781 | | 20915 | |
| 20782 | fn tempFromValue(self: *Self, ty: Type, value: MCValue) !Temp { | 20916 | fn tempFromValue(cg: *CodeGen, ty: Type, value: MCValue) !Temp { |
| 20783 | const temp_index = self.next_temp_index; | 20917 | const temp_index = cg.next_temp_index; |
| 20784 | temp_index.tracking(self).* = .init(value); | 20918 | temp_index.tracking(cg).* = .init(value); |
| 20785 | self.temp_type[@intFromEnum(temp_index)] = ty; | 20919 | cg.temp_type[@intFromEnum(temp_index)] = ty; |
| 20786 | try self.getValue(value, temp_index.toIndex()); | 20920 | try cg.getValue(value, temp_index.toIndex()); |
| 20787 | self.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); | 20921 | cg.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); |
| 20788 | return .{ .index = temp_index.toIndex() }; | 20922 | return .{ .index = temp_index.toIndex() }; |
| 20789 | } | 20923 | } |
| 20790 | | 20924 | |
| 20791 | fn tempFromOperand( | 20925 | fn tempFromOperand( |
| 20792 | self: *Self, | 20926 | cg: *CodeGen, |
| 20793 | inst: Air.Inst.Index, | 20927 | inst: Air.Inst.Index, |
| 20794 | op_index: Liveness.OperandInt, | 20928 | op_index: Liveness.OperandInt, |
| 20795 | op_ref: Air.Inst.Ref, | 20929 | op_ref: Air.Inst.Ref, |
| 20796 | ) !Temp { | 20930 | ) !Temp { |
| 20797 | const zcu = self.pt.zcu; | 20931 | const zcu = cg.pt.zcu; |
| 20798 | const ip = &zcu.intern_pool; | 20932 | const ip = &zcu.intern_pool; |
| 20799 | | 20933 | |
| 20800 | if (!self.liveness.operandDies(inst, op_index)) { | 20934 | if (!cg.liveness.operandDies(inst, op_index)) { |
| 20801 | if (op_ref.toIndex()) |op_inst| return .{ .index = op_inst }; | 20935 | if (op_ref.toIndex()) |op_inst| return .{ .index = op_inst }; |
| 20802 | const val = op_ref.toInterned().?; | 20936 | const val = op_ref.toInterned().?; |
| 20803 | const gop = try self.const_tracking.getOrPut(self.gpa, val); | 20937 | const gop = try cg.const_tracking.getOrPut(cg.gpa, val); |
| 20804 | if (!gop.found_existing) gop.value_ptr.* = .init(init: { | 20938 | if (!gop.found_existing) gop.value_ptr.* = .init(init: { |
| 20805 | const const_mcv = try self.genTypedValue(.fromInterned(val)); | 20939 | const const_mcv = try cg.genTypedValue(.fromInterned(val)); |
| 20806 | switch (const_mcv) { | 20940 | switch (const_mcv) { |
| 20807 | .lea_tlv => |tlv_sym| switch (self.bin_file.tag) { | 20941 | .lea_tlv => |tlv_sym| switch (cg.bin_file.tag) { |
| 20808 | .elf, .macho => { | 20942 | .elf, .macho => { |
| 20809 | if (self.mod.pic) { | 20943 | if (cg.mod.pic) { |
| 20810 | try self.spillRegisters(&.{ .rdi, .rax }); | 20944 | try cg.spillRegisters(&.{ .rdi, .rax }); |
| 20811 | } else { | 20945 | } else { |
| 20812 | try self.spillRegisters(&.{.rax}); | 20946 | try cg.spillRegisters(&.{.rax}); |
| 20813 | } | 20947 | } |
| 20814 | const frame_index = try self.allocFrameIndex(.init(.{ | 20948 | const frame_index = try cg.allocFrameIndex(.init(.{ |
| 20815 | .size = 8, | 20949 | .size = 8, |
| 20816 | .alignment = .@"8", | 20950 | .alignment = .@"8", |
| 20817 | })); | 20951 | })); |
| 20818 | try self.genSetMem( | 20952 | try cg.genSetMem( |
| 20819 | .{ .frame = frame_index }, | 20953 | .{ .frame = frame_index }, |
| 20820 | 0, | 20954 | 0, |
| 20821 | Type.usize, | 20955 | Type.usize, |
| ... | @@ -20829,24 +20963,24 @@ fn tempFromOperand( | ... | @@ -20829,24 +20963,24 @@ fn tempFromOperand( |
| 20829 | else => break :init const_mcv, | 20963 | else => break :init const_mcv, |
| 20830 | } | 20964 | } |
| 20831 | }); | 20965 | }); |
| 20832 | return self.tempFromValue(.fromInterned(ip.typeOf(val)), gop.value_ptr.short); | 20966 | return cg.tempFromValue(.fromInterned(ip.typeOf(val)), gop.value_ptr.short); |
| 20833 | } | 20967 | } |
| 20834 | | 20968 | |
| 20835 | const temp_index = self.next_temp_index; | 20969 | const temp_index = cg.next_temp_index; |
| 20836 | const temp: Temp = .{ .index = temp_index.toIndex() }; | 20970 | const temp: Temp = .{ .index = temp_index.toIndex() }; |
| 20837 | const op_inst = op_ref.toIndex().?; | 20971 | const op_inst = op_ref.toIndex().?; |
| 20838 | const tracking = self.getResolvedInstValue(op_inst); | 20972 | const tracking = cg.getResolvedInstValue(op_inst); |
| 20839 | temp_index.tracking(self).* = tracking.*; | 20973 | temp_index.tracking(cg).* = tracking.*; |
| 20840 | if (!self.reuseTemp(temp.index, op_inst, tracking)) return .{ .index = op_ref.toIndex().? }; | 20974 | if (!cg.reuseTemp(temp.index, op_inst, tracking)) return .{ .index = op_ref.toIndex().? }; |
| 20841 | self.temp_type[@intFromEnum(temp_index)] = self.typeOf(op_ref); | 20975 | cg.temp_type[@intFromEnum(temp_index)] = cg.typeOf(op_ref); |
| 20842 | self.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); | 20976 | cg.next_temp_index = @enumFromInt(@intFromEnum(temp_index) + 1); |
| 20843 | return temp; | 20977 | return temp; |
| 20844 | } | 20978 | } |
| 20845 | | 20979 | |
| 20846 | inline fn tempsFromOperands(self: *Self, inst: Air.Inst.Index, op_refs: anytype) ![op_refs.len]Temp { | 20980 | inline fn tempsFromOperands(cg: *CodeGen, inst: Air.Inst.Index, op_refs: anytype) ![op_refs.len]Temp { |
| 20847 | var temps: [op_refs.len]Temp = undefined; | 20981 | var temps: [op_refs.len]Temp = undefined; |
| 20848 | inline for (&temps, 0.., op_refs) |*temp, op_index, op_ref| { | 20982 | inline for (&temps, 0.., op_refs) |*temp, op_index, op_ref| { |
| 20849 | temp.* = try self.tempFromOperand(inst, op_index, op_ref); | 20983 | temp.* = try cg.tempFromOperand(inst, op_index, op_ref); |
| 20850 | } | 20984 | } |
| 20851 | return temps; | 20985 | return temps; |
| 20852 | } | 20986 | } |
| ... | @@ -20859,15 +20993,55 @@ const Operand = union(enum) { | ... | @@ -20859,15 +20993,55 @@ const Operand = union(enum) { |
| 20859 | inst: Mir.Inst.Index, | 20993 | inst: Mir.Inst.Index, |
| 20860 | }; | 20994 | }; |
| 20861 | | 20995 | |
| | 20996 | const SelectLoop = struct { |
| | 20997 | element_reloc: Mir.Inst.Index, |
| | 20998 | element_offset: union(enum) { |
| | 20999 | unused, |
| | 21000 | known: u31, |
| | 21001 | temp: Temp, |
| | 21002 | }, |
| | 21003 | element_size: ?u13, |
| | 21004 | limb_reloc: Mir.Inst.Index, |
| | 21005 | limb_offset: union(enum) { |
| | 21006 | unused, |
| | 21007 | known: u31, |
| | 21008 | temp: Temp, |
| | 21009 | }, |
| | 21010 | limb_size: ?u8, |
| | 21011 | remaining_size: ?u64, |
| | 21012 | }; |
| | 21013 | |
| 20862 | const Pattern = struct { | 21014 | const Pattern = struct { |
| 20863 | tag: Mir.Inst.FixedTag, | | |
| 20864 | ops: []const Op, | 21015 | ops: []const Op, |
| 20865 | commute: struct { u8, u8 } = .{ 0, 0 }, | 21016 | commute: struct { u8, u8 } = .{ 0, 0 }, |
| 20866 | features: []const std.Target.x86.Feature = &.{}, | 21017 | |
| | 21018 | const Set = struct { |
| | 21019 | required_features: []const std.Target.x86.Feature = &.{}, |
| | 21020 | loop: enum { |
| | 21021 | /// only execute the instruction once |
| | 21022 | once, |
| | 21023 | /// execute the instruction on all groups of non-overlapping bits in the entire value |
| | 21024 | bitwise, |
| | 21025 | /// for each element, execute the instruction on each limb, propogating the carry flag |
| | 21026 | limbwise_carry, |
| | 21027 | /// for each element, execute the instruction on pairs of limbs, starting from the |
| | 21028 | /// least significant, propogating a limb |
| | 21029 | limbwise_pairs_forward, |
| | 21030 | /// for each element, execute the instruction on pairs of limbs, starting from the |
| | 21031 | /// most significant, propogating a limb |
| | 21032 | limbwise_pairs_reverse, |
| | 21033 | /// for each element, execute the instruction |
| | 21034 | elementwise, |
| | 21035 | } = .once, |
| | 21036 | mir_tag: Mir.Inst.FixedTag, |
| | 21037 | patterns: []const Pattern, |
| | 21038 | }; |
| 20867 | | 21039 | |
| 20868 | const Op = union(enum) { | 21040 | const Op = union(enum) { |
| 20869 | /// match another operand | 21041 | /// reuse another operand |
| 20870 | match: u8, | 21042 | implicit: u8, |
| | 21043 | /// repeat another operand |
| | 21044 | explicit: u8, |
| 20871 | /// any general purpose register | 21045 | /// any general purpose register |
| 20872 | gpr, | 21046 | gpr, |
| 20873 | /// any 64-bit mmx register | 21047 | /// any 64-bit mmx register |
| ... | @@ -20878,165 +21052,449 @@ const Pattern = struct { | ... | @@ -20878,165 +21052,449 @@ const Pattern = struct { |
| 20878 | ymm, | 21052 | ymm, |
| 20879 | /// any memory | 21053 | /// any memory |
| 20880 | mem, | 21054 | mem, |
| | 21055 | /// a limb stored in a gpr |
| | 21056 | gpr_limb, |
| | 21057 | /// a limb stored in a 64-bit mmx register |
| | 21058 | mm_limb, |
| | 21059 | /// a limb stored in a 128-bit sse register |
| | 21060 | xmm_limb, |
| | 21061 | /// a limb stored in a 256-bit sse register |
| | 21062 | ymm_limb, |
| | 21063 | /// a limb stored in memory |
| | 21064 | mem_limb, |
| 20881 | /// specific immediate | 21065 | /// specific immediate |
| 20882 | imm: i8, | 21066 | imm: i8, |
| 20883 | /// any immediate signed extended from 32 bits | 21067 | /// any immediate signed extended from 32 bits |
| 20884 | simm32, | 21068 | simm32, |
| 20885 | | 21069 | |
| 20886 | fn matches(op: Op, is_mut: bool, temp: Temp, self: *Self) bool { | 21070 | fn matches(op: Op, is_mut: bool, temp: Temp, cg: *CodeGen) bool { |
| | 21071 | const abi_size = temp.typeOf(cg).abiSize(cg.pt.zcu); |
| 20887 | return switch (op) { | 21072 | return switch (op) { |
| 20888 | .match => unreachable, | 21073 | .implicit, .explicit => unreachable, |
| 20889 | .gpr => switch (temp.tracking(self).short) { | 21074 | .gpr => abi_size <= 8 and switch (temp.tracking(cg).short) { |
| 20890 | .register => |reg| reg.class() == .general_purpose, | 21075 | .register => |reg| reg.class() == .general_purpose, |
| 20891 | .register_offset => |reg_off| reg_off.reg.class() == .general_purpose and | 21076 | .register_offset => |reg_off| reg_off.reg.class() == .general_purpose and |
| 20892 | reg_off.off == 0, | 21077 | reg_off.off == 0, |
| 20893 | else => self.regClassForType(temp.typeOf(self)) == .general_purpose, | 21078 | else => cg.regClassForType(temp.typeOf(cg)) == .general_purpose, |
| 20894 | }, | 21079 | }, |
| 20895 | .mm => switch (temp.tracking(self).short) { | 21080 | .mm => abi_size <= 8 and switch (temp.tracking(cg).short) { |
| 20896 | .register => |reg| reg.class() == .mmx, | 21081 | .register => |reg| reg.class() == .mmx, |
| 20897 | .register_offset => |reg_off| reg_off.reg.class() == .mmx and reg_off.off == 0, | 21082 | .register_offset => |reg_off| reg_off.reg.class() == .mmx and reg_off.off == 0, |
| 20898 | else => self.regClassForType(temp.typeOf(self)) == .mmx, | 21083 | else => cg.regClassForType(temp.typeOf(cg)) == .mmx, |
| 20899 | }, | 21084 | }, |
| 20900 | .xmm => switch (temp.tracking(self).short) { | 21085 | .xmm => abi_size > 8 and abi_size <= 16 and switch (temp.tracking(cg).short) { |
| 20901 | .register => |reg| reg.class() == .sse, | 21086 | .register => |reg| reg.class() == .sse, |
| 20902 | .register_offset => |reg_off| reg_off.reg.class() == .sse and reg_off.off == 0, | 21087 | .register_offset => |reg_off| reg_off.reg.class() == .sse and reg_off.off == 0, |
| 20903 | else => self.regClassForType(temp.typeOf(self)) == .sse, | 21088 | else => cg.regClassForType(temp.typeOf(cg)) == .sse, |
| 20904 | }, | 21089 | }, |
| 20905 | .ymm => switch (temp.tracking(self).short) { | 21090 | .ymm => abi_size > 16 and abi_size <= 32 and switch (temp.tracking(cg).short) { |
| 20906 | .register => |reg| reg.class() == .sse, | 21091 | .register => |reg| reg.class() == .sse, |
| 20907 | .register_offset => |reg_off| reg_off.reg.class() == .sse and reg_off.off == 0, | 21092 | .register_offset => |reg_off| reg_off.reg.class() == .sse and reg_off.off == 0, |
| 20908 | else => self.regClassForType(temp.typeOf(self)) == .sse, | 21093 | else => cg.regClassForType(temp.typeOf(cg)) == .sse, |
| 20909 | } and temp.typeOf(self).abiSize(self.pt.zcu) > 16, | 21094 | }, |
| 20910 | .mem => (!is_mut or temp.isMut(self)) and temp.tracking(self).short.isMemory(), | 21095 | .mem, .mem_limb => (!is_mut or temp.isMut(cg)) and temp.tracking(cg).short.isMemory(), |
| 20911 | .imm => |specific_imm| if (is_mut) unreachable else switch (temp.tracking(self).short) { | 21096 | .gpr_limb => abi_size > 8, |
| | 21097 | .mm_limb => abi_size > 8 and (!is_mut or temp.isMut(cg)) and temp.tracking(cg).short.isMemory() and cg.regClassForType(temp.typeOf(cg)) == .mmx, |
| | 21098 | .xmm_limb => abi_size > 16 and (!is_mut or temp.isMut(cg)) and temp.tracking(cg).short.isMemory(), |
| | 21099 | .ymm_limb => abi_size > 32 and (!is_mut or temp.isMut(cg)) and temp.tracking(cg).short.isMemory(), |
| | 21100 | .imm => |specific_imm| if (is_mut) unreachable else switch (temp.tracking(cg).short) { |
| 20912 | .immediate => |imm| @as(i64, @bitCast(imm)) == specific_imm, | 21101 | .immediate => |imm| @as(i64, @bitCast(imm)) == specific_imm, |
| 20913 | else => false, | 21102 | else => false, |
| 20914 | }, | 21103 | }, |
| 20915 | .simm32 => if (is_mut) unreachable else switch (temp.tracking(self).short) { | 21104 | .simm32 => if (is_mut) unreachable else switch (temp.tracking(cg).short) { |
| 20916 | .immediate => |imm| temp.typeOf(self).abiSize(self.pt.zcu) <= 4 or | 21105 | .immediate => |imm| abi_size <= 4 or std.math.cast(i32, @as(i64, @bitCast(imm))) != null, |
| 20917 | std.math.cast(i32, @as(i64, @bitCast(imm))) != null, | | |
| 20918 | else => false, | 21106 | else => false, |
| 20919 | }, | 21107 | }, |
| 20920 | }; | 21108 | }; |
| 20921 | } | 21109 | } |
| 20922 | }; | 21110 | }; |
| 20923 | }; | 21111 | }; |
| 20924 | fn select(self: *Self, dst_temps: []Temp, src_temps: []const *Temp, patterns: []const Pattern) !void { | 21112 | fn select(cg: *CodeGen, dst_temps: []Temp, src_temps: []const *Temp, pattern_sets: []const Pattern.Set) !void { |
| 20925 | patterns: for (patterns) |pattern| { | 21113 | var loop: SelectLoop = .{ |
| 20926 | for (pattern.features) |feature| if (!self.hasFeature(feature)) continue :patterns; | 21114 | .element_reloc = undefined, |
| 20927 | for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| if (!switch (src_op) { | 21115 | .element_offset = .unused, |
| 20928 | .match => |match_index| pattern.ops[match_index], | 21116 | .element_size = null, |
| 20929 | else => src_op, | 21117 | .limb_reloc = undefined, |
| 20930 | }.matches(src_op == .match, src_temp.*, self)) continue :patterns; | 21118 | .limb_offset = .unused, |
| 20931 | while (true) for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { | 21119 | .limb_size = null, |
| 20932 | if (switch (switch (src_op) { | 21120 | .remaining_size = null, |
| 20933 | .match => |match_index| pattern.ops[match_index], | 21121 | }; |
| 20934 | else => src_op, | 21122 | var extra_temps: [4]?Temp = @splat(null); |
| 20935 | }) { | 21123 | pattern_sets: for (pattern_sets) |pattern_set| { |
| 20936 | .match => unreachable, | 21124 | for (pattern_set.required_features) |required_feature| if (!cg.hasFeature(required_feature)) continue :pattern_sets; |
| 20937 | .gpr => try src_temp.toRegClass(.general_purpose, self), | 21125 | patterns: for (pattern_set.patterns) |pattern| { |
| 20938 | .mm => try src_temp.toRegClass(.mmx, self), | 21126 | for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { |
| 20939 | .xmm, .ymm => try src_temp.toRegClass(.sse, self), | 21127 | const ref_src_op, const is_mut = switch (src_op) { |
| 20940 | .mem, .imm, .simm32 => false, | 21128 | .implicit, .explicit => |op_index| .{ pattern.ops[op_index], true }, |
| 20941 | }) break; | 21129 | else => .{ src_op, false }, |
| 20942 | } else break; | 21130 | }; |
| 20943 | var mir_ops: [4]Operand = @splat(.none); | 21131 | if (!ref_src_op.matches(is_mut, src_temp.*, cg)) continue :patterns; |
| 20944 | var mir_ops_len = dst_temps.len; | 21132 | } |
| 20945 | for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { | 21133 | while (true) for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { |
| 20946 | const mir_op, const matched_src_op = op: switch (src_op) { | 21134 | if (switch (switch (src_op) { |
| 20947 | .match => |match_index| { | 21135 | .implicit, .explicit => |op_index| pattern.ops[op_index], |
| 20948 | dst_temps[match_index] = src_temp.*; | 21136 | else => src_op, |
| 20949 | break :op .{ &mir_ops[match_index], pattern.ops[match_index] }; | 21137 | }) { |
| 20950 | }, | 21138 | .implicit, .explicit => unreachable, |
| 20951 | else => { | 21139 | .gpr => try src_temp.toRegClass(.general_purpose, cg), |
| 20952 | defer mir_ops_len += 1; | 21140 | .mm => try src_temp.toRegClass(.mmx, cg), |
| 20953 | break :op .{ &mir_ops[mir_ops_len], src_op }; | 21141 | .xmm, .ymm => try src_temp.toRegClass(.sse, cg), |
| 20954 | }, | 21142 | .mem, .imm, .simm32 => false, |
| 20955 | }; | 21143 | .gpr_limb, .mm_limb, .xmm_limb, .ymm_limb, .mem_limb => switch (src_temp.tracking(cg).short) { |
| 20956 | const src_mcv = src_temp.tracking(self).short; | 21144 | .register_pair => false, |
| 20957 | mir_op.* = switch (matched_src_op) { | 21145 | else => try src_temp.toBase(cg), |
| 20958 | .match => unreachable, | 21146 | }, |
| 20959 | .gpr => .{ .reg = registerAlias( | 21147 | }) break; |
| 20960 | src_mcv.register, | 21148 | } else break; |
| 20961 | @intCast(src_temp.typeOf(self).abiSize(self.pt.zcu)), | 21149 | var mir_ops_len = dst_temps.len; |
| 20962 | ) }, | 21150 | for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { |
| 20963 | .mm => .{ .reg = src_mcv.register }, | 21151 | const ref_src_op, const extra_temp = op: switch (src_op) { |
| 20964 | .xmm => .{ .reg = src_mcv.register.to128() }, | 21152 | .implicit => |op_index| { |
| 20965 | .ymm => .{ .reg = src_mcv.register.to256() }, | 21153 | dst_temps[op_index] = if (src_temp.isMut(cg)) |
| 20966 | .mem => .{ .mem = try src_mcv.mem(self, self.memSize(src_temp.typeOf(self))) }, | 21154 | src_temp.* |
| 20967 | .imm => |imm| .{ .imm = .s(imm) }, | 21155 | else |
| 20968 | .simm32 => switch (src_temp.typeOf(self).abiSize(self.pt.zcu)) { | 21156 | try cg.tempAlloc(src_temp.typeOf(cg)); |
| 20969 | else => unreachable, | 21157 | break :op .{ pattern.ops[op_index], &extra_temps[op_index] }; |
| 20970 | 1 => .{ .imm = if (std.math.cast(i8, @as(i64, @bitCast(src_mcv.immediate)))) |small| | 21158 | }, |
| 20971 | .s(small) | 21159 | .explicit => |op_index| { |
| 20972 | else | 21160 | dst_temps[op_index] = if (src_temp.isMut(cg)) |
| 20973 | .u(@as(u8, @intCast(src_mcv.immediate))) }, | 21161 | src_temp.* |
| 20974 | 2 => .{ .imm = if (std.math.cast(i16, @as(i64, @bitCast(src_mcv.immediate)))) |small| | 21162 | else |
| 20975 | .s(small) | 21163 | try cg.tempAlloc(src_temp.typeOf(cg)); |
| 20976 | else | 21164 | defer mir_ops_len += 1; |
| 20977 | .u(@as(u16, @intCast(src_mcv.immediate))) }, | 21165 | break :op .{ pattern.ops[op_index], &extra_temps[mir_ops_len] }; |
| 20978 | 3...8 => .{ .imm = if (std.math.cast(i32, @as(i64, @bitCast(src_mcv.immediate)))) |small| | 21166 | }, |
| 20979 | .s(small) | 21167 | else => { |
| 20980 | else | 21168 | defer mir_ops_len += 1; |
| 20981 | .u(@as(u32, @intCast(src_mcv.immediate))) }, | 21169 | break :op .{ src_op, &extra_temps[mir_ops_len] }; |
| 20982 | }, | 21170 | }, |
| 20983 | }; | 21171 | }; |
| 20984 | } | 21172 | const limb_size: u8, const rc = switch (ref_src_op) { |
| 20985 | for ( | 21173 | else => continue, |
| 20986 | pattern.ops[0..dst_temps.len], | 21174 | .gpr_limb => .{ 8, abi.RegisterClass.gp }, |
| 20987 | dst_temps, | 21175 | .mm_limb => .{ 8, @panic("TODO") }, |
| 20988 | mir_ops[0..dst_temps.len], | 21176 | .xmm_limb => .{ 16, abi.RegisterClass.sse }, |
| 20989 | ) |dst_op, *dst_temp, *mir_op| { | 21177 | .ymm_limb => .{ 32, abi.RegisterClass.sse }, |
| 20990 | if (mir_op.* != .none) continue; | 21178 | }; |
| 20991 | const ty = src_temps[0].typeOf(self); | 21179 | assert(loop.limb_size == null or loop.limb_size == limb_size); |
| 20992 | switch (dst_op) { | 21180 | loop.limb_size = limb_size; |
| 20993 | .match => |match_index| { | 21181 | loop.remaining_size = loop.remaining_size orelse src_temp.typeOf(cg).abiSize(cg.pt.zcu); |
| 20994 | dst_temp.* = dst_temps[match_index]; | 21182 | switch (src_temp.tracking(cg).short) { |
| 20995 | mir_op.* = mir_ops[match_index]; | 21183 | .register_pair => switch (loop.limb_offset) { |
| 20996 | }, | 21184 | .unused, .temp => loop.limb_offset = .{ .known = 0 }, |
| 20997 | .gpr => { | 21185 | .known => {}, |
| 20998 | dst_temp.* = try self.tempAllocReg(ty, abi.RegisterClass.gp); | 21186 | }, |
| 20999 | mir_op.* = .{ .reg = registerAlias( | 21187 | else => { |
| 21000 | dst_temp.tracking(self).short.register, | 21188 | switch (loop.limb_offset) { |
| 21001 | @intCast(ty.abiSize(self.pt.zcu)), | 21189 | .unused => loop.limb_offset = .{ .temp = undefined }, |
| 21002 | ) }; | 21190 | .known, .temp => {}, |
| 21003 | }, | 21191 | } |
| 21004 | .mm => @panic("TODO"), | 21192 | extra_temp.* = try cg.tempAllocReg(Type.usize, rc); |
| 21005 | .xmm => { | 21193 | }, |
| 21006 | dst_temp.* = try self.tempAllocReg(ty, abi.RegisterClass.sse); | 21194 | } |
| 21007 | mir_op.* = .{ .reg = dst_temp.tracking(self).short.register.to128() }; | 21195 | } |
| 21008 | }, | 21196 | switch (loop.element_offset) { |
| 21009 | .ymm => { | 21197 | .unused, .known => {}, |
| 21010 | dst_temp.* = try self.tempAllocReg(ty, abi.RegisterClass.sse); | 21198 | .temp => |*element_offset| { |
| 21011 | mir_op.* = .{ .reg = dst_temp.tracking(self).short.register.to256() }; | 21199 | element_offset.* = try cg.tempAllocReg(Type.usize, abi.RegisterClass.gp); |
| | 21200 | const element_offset_reg = element_offset.tracking(cg).short.register; |
| | 21201 | try cg.asmRegisterRegister(.{ ._, .xor }, element_offset_reg.to32(), element_offset_reg.to32()); |
| | 21202 | loop.element_reloc = @intCast(cg.mir_instructions.len); |
| 21012 | }, | 21203 | }, |
| 21013 | .mem => @panic("TODO"), | | |
| 21014 | .imm, .simm32 => unreachable, // unmodifiable destination | | |
| 21015 | } | 21204 | } |
| 21016 | } | 21205 | while (true) { |
| 21017 | std.mem.swap(Operand, &mir_ops[pattern.commute[0]], &mir_ops[pattern.commute[1]]); | 21206 | switch (loop.limb_offset) { |
| 21018 | self.asmOps(pattern.tag, mir_ops) catch |err| switch (err) { | 21207 | .unused, .known => {}, |
| 21019 | error.InvalidInstruction => { | 21208 | .temp => |*limb_offset| { |
| 21020 | const fixes = @tagName(pattern.tag[0]); | 21209 | limb_offset.* = try cg.tempAllocReg(Type.usize, abi.RegisterClass.gp); |
| 21021 | const fixes_replace = std.mem.indexOfScalar(u8, fixes, '_').?; | 21210 | const limb_offset_reg = limb_offset.tracking(cg).short.register; |
| 21022 | return self.fail( | 21211 | try cg.asmRegisterRegister(.{ ._, .xor }, limb_offset_reg.to32(), limb_offset_reg.to32()); |
| 21023 | "invalid instruction: '{s}{s}{s} {s} {s} {s} {s}'", | 21212 | loop.limb_reloc = @intCast(cg.mir_instructions.len); |
| 21024 | .{ | | |
| 21025 | fixes[0..fixes_replace], | | |
| 21026 | @tagName(pattern.tag[1]), | | |
| 21027 | fixes[fixes_replace + 1 ..], | | |
| 21028 | @tagName(mir_ops[0]), | | |
| 21029 | @tagName(mir_ops[1]), | | |
| 21030 | @tagName(mir_ops[2]), | | |
| 21031 | @tagName(mir_ops[3]), | | |
| 21032 | }, | 21213 | }, |
| 21033 | ); | 21214 | } |
| 21034 | }, | 21215 | while (true) { |
| 21035 | else => |e| return e, | 21216 | var mir_ops: [4]Operand = @splat(.none); |
| 21036 | }; | 21217 | mir_ops_len = dst_temps.len; |
| 21037 | return; | 21218 | for (src_temps, pattern.ops[dst_temps.len..]) |src_temp, src_op| { |
| | 21219 | const mir_op, const ref_src_op, const extra_temp = op: switch (src_op) { |
| | 21220 | .implicit => |op_index| .{ &mir_ops[op_index], pattern.ops[op_index], &extra_temps[op_index] }, |
| | 21221 | .explicit => |op_index| { |
| | 21222 | defer mir_ops_len += 1; |
| | 21223 | break :op .{ &mir_ops[mir_ops_len], pattern.ops[op_index], &extra_temps[mir_ops_len] }; |
| | 21224 | }, |
| | 21225 | else => { |
| | 21226 | defer mir_ops_len += 1; |
| | 21227 | break :op .{ &mir_ops[mir_ops_len], src_op, &extra_temps[mir_ops_len] }; |
| | 21228 | }, |
| | 21229 | }; |
| | 21230 | const src_mcv = src_temp.tracking(cg).short; |
| | 21231 | switch (ref_src_op) { |
| | 21232 | else => {}, |
| | 21233 | .gpr_limb, .mm_limb, .xmm_limb, .ymm_limb => switch (src_mcv) { |
| | 21234 | .register_pair => {}, |
| | 21235 | else => try cg.asmRegisterMemory( |
| | 21236 | switch (ref_src_op) { |
| | 21237 | else => unreachable, |
| | 21238 | .gpr_limb => .{ ._, .mov }, |
| | 21239 | .mm_limb => .{ ._q, .mov }, |
| | 21240 | .xmm_limb, .ymm_limb => .{ if (cg.hasFeature(.avx)) .v_ else ._, .movdqu }, |
| | 21241 | }, |
| | 21242 | registerAlias(extra_temp.*.?.tracking(cg).short.register, loop.limb_size.?), |
| | 21243 | try src_mcv.mem(cg, switch (loop.limb_offset) { |
| | 21244 | .unused => unreachable, |
| | 21245 | .known => |limb_offset| .{ |
| | 21246 | .size = .fromSize(loop.limb_size.?), |
| | 21247 | .disp = limb_offset, |
| | 21248 | }, |
| | 21249 | .temp => |limb_offset| .{ |
| | 21250 | .size = .fromSize(loop.limb_size.?), |
| | 21251 | .index = limb_offset.tracking(cg).short.register.to64(), |
| | 21252 | }, |
| | 21253 | }), |
| | 21254 | ), |
| | 21255 | }, |
| | 21256 | } |
| | 21257 | mir_op.* = switch (ref_src_op) { |
| | 21258 | .implicit, .explicit => unreachable, |
| | 21259 | .gpr => .{ .reg = registerAlias( |
| | 21260 | src_mcv.register, |
| | 21261 | @intCast(src_temp.typeOf(cg).abiSize(cg.pt.zcu)), |
| | 21262 | ) }, |
| | 21263 | .mm => .{ .reg = src_mcv.register }, |
| | 21264 | .xmm => .{ .reg = src_mcv.register.to128() }, |
| | 21265 | .ymm => .{ .reg = src_mcv.register.to256() }, |
| | 21266 | .mem => .{ .mem = try src_mcv.mem(cg, .{ .size = cg.memSize(src_temp.typeOf(cg)) }) }, |
| | 21267 | .gpr_limb, .mm_limb, .xmm_limb, .ymm_limb => switch (src_mcv) { |
| | 21268 | .register_pair => |src_regs| switch (loop.limb_offset) { |
| | 21269 | .unused => unreachable, |
| | 21270 | .known => |limb_offset| .{ .reg = registerAlias( |
| | 21271 | src_regs[@divExact(limb_offset, loop.limb_size.?)], |
| | 21272 | loop.limb_size.?, |
| | 21273 | ) }, |
| | 21274 | .temp => unreachable, |
| | 21275 | }, |
| | 21276 | else => .{ .reg = registerAlias( |
| | 21277 | extra_temp.*.?.tracking(cg).short.register, |
| | 21278 | loop.limb_size.?, |
| | 21279 | ) }, |
| | 21280 | }, |
| | 21281 | .mem_limb => .{ .mem = switch (src_mcv) { |
| | 21282 | .register_pair => unreachable, |
| | 21283 | else => switch (loop.limb_offset) { |
| | 21284 | .unused => unreachable, |
| | 21285 | .known => |limb_offset| try src_mcv.mem(cg, .{ |
| | 21286 | .size = .fromSize(loop.limb_size.?), |
| | 21287 | .disp = limb_offset, |
| | 21288 | }), |
| | 21289 | .temp => |limb_offset| try src_mcv.mem(cg, .{ |
| | 21290 | .size = .fromSize(loop.limb_size.?), |
| | 21291 | .index = limb_offset.tracking(cg).short.register.to64(), |
| | 21292 | }), |
| | 21293 | }, |
| | 21294 | } }, |
| | 21295 | .imm => |imm| .{ .imm = .s(imm) }, |
| | 21296 | .simm32 => switch (src_temp.typeOf(cg).abiSize(cg.pt.zcu)) { |
| | 21297 | else => unreachable, |
| | 21298 | 1 => .{ .imm = if (std.math.cast(i8, @as(i64, @bitCast(src_mcv.immediate)))) |small| |
| | 21299 | .s(small) |
| | 21300 | else |
| | 21301 | .u(@as(u8, @intCast(src_mcv.immediate))) }, |
| | 21302 | 2 => .{ .imm = if (std.math.cast(i16, @as(i64, @bitCast(src_mcv.immediate)))) |small| |
| | 21303 | .s(small) |
| | 21304 | else |
| | 21305 | .u(@as(u16, @intCast(src_mcv.immediate))) }, |
| | 21306 | 3...8 => .{ .imm = if (std.math.cast(i32, @as(i64, @bitCast(src_mcv.immediate)))) |small| |
| | 21307 | .s(small) |
| | 21308 | else |
| | 21309 | .u(@as(u32, @intCast(src_mcv.immediate))) }, |
| | 21310 | }, |
| | 21311 | }; |
| | 21312 | } |
| | 21313 | for ( |
| | 21314 | pattern.ops[0..dst_temps.len], |
| | 21315 | dst_temps, |
| | 21316 | mir_ops[0..dst_temps.len], |
| | 21317 | extra_temps[0..dst_temps.len], |
| | 21318 | ) |dst_op, *dst_temp, *mir_op, *extra_temp| { |
| | 21319 | if (mir_op.* != .none) continue; |
| | 21320 | const ty = src_temps[0].typeOf(cg); |
| | 21321 | switch (dst_op) { |
| | 21322 | .implicit => unreachable, |
| | 21323 | .explicit => |op_index| { |
| | 21324 | dst_temp.* = dst_temps[op_index]; |
| | 21325 | mir_op.* = mir_ops[op_index]; |
| | 21326 | }, |
| | 21327 | .gpr => { |
| | 21328 | dst_temp.* = try cg.tempAllocReg(ty, abi.RegisterClass.gp); |
| | 21329 | mir_op.* = .{ .reg = registerAlias( |
| | 21330 | dst_temp.tracking(cg).short.register, |
| | 21331 | @intCast(ty.abiSize(cg.pt.zcu)), |
| | 21332 | ) }; |
| | 21333 | }, |
| | 21334 | .mm => @panic("TODO"), |
| | 21335 | .xmm => { |
| | 21336 | dst_temp.* = try cg.tempAllocReg(ty, abi.RegisterClass.sse); |
| | 21337 | mir_op.* = .{ .reg = dst_temp.tracking(cg).short.register.to128() }; |
| | 21338 | }, |
| | 21339 | .ymm => { |
| | 21340 | dst_temp.* = try cg.tempAllocReg(ty, abi.RegisterClass.sse); |
| | 21341 | mir_op.* = .{ .reg = dst_temp.tracking(cg).short.register.to256() }; |
| | 21342 | }, |
| | 21343 | .mem => @panic("TODO"), |
| | 21344 | .gpr_limb => { |
| | 21345 | dst_temp.* = try cg.tempAlloc(ty); |
| | 21346 | extra_temp.* = try cg.tempAllocReg(Type.usize, abi.RegisterClass.gp); |
| | 21347 | mir_op.* = .{ .reg = extra_temp.*.?.tracking(cg).short.register.to64() }; |
| | 21348 | }, |
| | 21349 | .mm_limb => { |
| | 21350 | dst_temp.* = try cg.tempAlloc(ty); |
| | 21351 | extra_temp.* = try cg.tempAllocReg(Type.usize, @panic("TODO")); |
| | 21352 | mir_op.* = .{ .reg = extra_temp.*.?.tracking(cg).short.register }; |
| | 21353 | }, |
| | 21354 | .xmm_limb => { |
| | 21355 | dst_temp.* = try cg.tempAlloc(ty); |
| | 21356 | extra_temp.* = try cg.tempAllocReg(Type.usize, abi.RegisterClass.sse); |
| | 21357 | mir_op.* = .{ .reg = extra_temp.*.?.tracking(cg).short.register.to128() }; |
| | 21358 | }, |
| | 21359 | .ymm_limb => { |
| | 21360 | dst_temp.* = try cg.tempAlloc(ty); |
| | 21361 | extra_temp.* = try cg.tempAllocReg(Type.usize, abi.RegisterClass.sse); |
| | 21362 | mir_op.* = .{ .reg = extra_temp.*.?.tracking(cg).short.register.to256() }; |
| | 21363 | }, |
| | 21364 | .mem_limb => { |
| | 21365 | dst_temp.* = try cg.tempAlloc(ty); |
| | 21366 | mir_op.* = .{ .mem = try dst_temp.tracking(cg).short.mem(cg, switch (loop.limb_offset) { |
| | 21367 | .unused => unreachable, |
| | 21368 | .known => |limb_offset| .{ |
| | 21369 | .size = .fromSize(loop.limb_size.?), |
| | 21370 | .disp = limb_offset, |
| | 21371 | }, |
| | 21372 | .temp => |limb_offset| .{ |
| | 21373 | .size = .fromSize(loop.limb_size.?), |
| | 21374 | .index = limb_offset.tracking(cg).short.register.to64(), |
| | 21375 | }, |
| | 21376 | }) }; |
| | 21377 | }, |
| | 21378 | .imm, .simm32 => unreachable, // unmodifiable destination |
| | 21379 | } |
| | 21380 | } |
| | 21381 | std.mem.swap(Operand, &mir_ops[pattern.commute[0]], &mir_ops[pattern.commute[1]]); |
| | 21382 | cg.asmOps(pattern_set.mir_tag, mir_ops) catch |err| switch (err) { |
| | 21383 | error.InvalidInstruction => { |
| | 21384 | const fixes = @tagName(pattern_set.mir_tag[0]); |
| | 21385 | const fixes_blank = std.mem.indexOfScalar(u8, fixes, '_').?; |
| | 21386 | return cg.fail( |
| | 21387 | "invalid instruction: '{s}{s}{s} {s} {s} {s} {s}'", |
| | 21388 | .{ |
| | 21389 | fixes[0..fixes_blank], |
| | 21390 | @tagName(pattern_set.mir_tag[1]), |
| | 21391 | fixes[fixes_blank + 1 ..], |
| | 21392 | @tagName(mir_ops[0]), |
| | 21393 | @tagName(mir_ops[1]), |
| | 21394 | @tagName(mir_ops[2]), |
| | 21395 | @tagName(mir_ops[3]), |
| | 21396 | }, |
| | 21397 | ); |
| | 21398 | }, |
| | 21399 | else => |e| return e, |
| | 21400 | }; |
| | 21401 | for ( |
| | 21402 | extra_temps[0..dst_temps.len], |
| | 21403 | pattern.ops[0..dst_temps.len], |
| | 21404 | dst_temps, |
| | 21405 | ) |maybe_extra_temp, dst_op, dst_temp| if (maybe_extra_temp) |extra_temp| switch (dst_op) { |
| | 21406 | else => {}, |
| | 21407 | .gpr_limb, .mm_limb, .xmm_limb, .ymm_limb => switch (dst_temp.tracking(cg).short) { |
| | 21408 | .register_pair => |dst_regs| switch (loop.limb_offset) { |
| | 21409 | .unused => unreachable, |
| | 21410 | .known => |limb_offset| try cg.asmRegisterRegister( |
| | 21411 | .{ ._, .mov }, |
| | 21412 | dst_regs[@divExact(limb_offset, loop.limb_size.?)].to64(), |
| | 21413 | extra_temp.tracking(cg).short.register.to64(), |
| | 21414 | ), |
| | 21415 | .temp => unreachable, |
| | 21416 | }, |
| | 21417 | else => |dst_mcv| try cg.asmMemoryRegister( |
| | 21418 | switch (dst_op) { |
| | 21419 | else => unreachable, |
| | 21420 | .gpr_limb => .{ ._, .mov }, |
| | 21421 | .mm_limb => .{ ._q, .mov }, |
| | 21422 | .xmm_limb, .ymm_limb => .{ if (cg.hasFeature(.avx)) .v_ else ._, .movdqu }, |
| | 21423 | }, |
| | 21424 | try dst_mcv.mem(cg, switch (loop.limb_offset) { |
| | 21425 | .unused => unreachable, |
| | 21426 | .known => |limb_offset| .{ |
| | 21427 | .size = .fromSize(loop.limb_size.?), |
| | 21428 | .disp = limb_offset, |
| | 21429 | }, |
| | 21430 | .temp => |limb_offset| .{ |
| | 21431 | .size = .fromSize(loop.limb_size.?), |
| | 21432 | .index = limb_offset.tracking(cg).short.register.to64(), |
| | 21433 | }, |
| | 21434 | }), |
| | 21435 | registerAlias(extra_temp.tracking(cg).short.register, loop.limb_size.?), |
| | 21436 | ), |
| | 21437 | }, |
| | 21438 | }; |
| | 21439 | switch (pattern_set.loop) { |
| | 21440 | .once => break :pattern_sets, |
| | 21441 | .bitwise => {}, |
| | 21442 | .limbwise_carry => @panic("TODO"), |
| | 21443 | .limbwise_pairs_forward => @panic("TODO"), |
| | 21444 | .limbwise_pairs_reverse => @panic("TODO"), |
| | 21445 | .elementwise => @panic("TODO"), |
| | 21446 | } |
| | 21447 | switch (loop.limb_offset) { |
| | 21448 | .unused => break, |
| | 21449 | .known => |*limb_offset| { |
| | 21450 | limb_offset.* += loop.limb_size.?; |
| | 21451 | loop.remaining_size.? -= loop.limb_size.?; |
| | 21452 | if (loop.remaining_size.? < loop.limb_size.? or |
| | 21453 | (loop.element_size != null and limb_offset.* >= loop.element_size.?)) |
| | 21454 | { |
| | 21455 | limb_offset.* = 0; |
| | 21456 | break; |
| | 21457 | } |
| | 21458 | }, |
| | 21459 | .temp => |limb_offset| { |
| | 21460 | const limb_offset_reg = limb_offset.tracking(cg).short.register; |
| | 21461 | try cg.asmRegisterMemory(.{ ._, .lea }, limb_offset_reg.to32(), .{ |
| | 21462 | .base = .{ .reg = limb_offset_reg.to64() }, |
| | 21463 | .mod = .{ .rm = .{ |
| | 21464 | .size = .qword, |
| | 21465 | .disp = loop.limb_size.?, |
| | 21466 | } }, |
| | 21467 | }); |
| | 21468 | try cg.asmRegisterImmediate( |
| | 21469 | .{ ._, .cmp }, |
| | 21470 | limb_offset_reg.to32(), |
| | 21471 | .u(loop.element_size orelse loop.remaining_size.?), |
| | 21472 | ); |
| | 21473 | _ = try cg.asmJccReloc(.b, loop.limb_reloc); |
| | 21474 | try limb_offset.die(cg); |
| | 21475 | break; |
| | 21476 | }, |
| | 21477 | } |
| | 21478 | } |
| | 21479 | switch (loop.element_offset) { |
| | 21480 | .unused => break :pattern_sets, |
| | 21481 | .known => |*element_offset| { |
| | 21482 | if (loop.remaining_size.? == 0) break :pattern_sets; |
| | 21483 | element_offset.* += loop.element_size.?; |
| | 21484 | }, |
| | 21485 | .temp => |element_offset| { |
| | 21486 | if (true) @panic("TODO"); |
| | 21487 | try element_offset.die(cg); |
| | 21488 | if (loop.remaining_size.? == 0) break :pattern_sets; |
| | 21489 | break; |
| | 21490 | }, |
| | 21491 | } |
| | 21492 | } |
| | 21493 | } |
| | 21494 | } else { |
| | 21495 | log.err("failed to select:", .{}); |
| | 21496 | for (src_temps) |src_temp| log.err("{}", .{src_temp.tracking(cg)}); |
| | 21497 | return cg.fail("failed to select", .{}); |
| 21038 | } | 21498 | } |
| 21039 | log.err("failed to select:", .{}); | 21499 | for (extra_temps) |extra_temp| if (extra_temp) |temp| try temp.die(cg); |
| 21040 | for (src_temps) |src_temp| log.err("{}", .{src_temp.tracking(self)}); | | |
| 21041 | return self.fail("failed to select", .{}); | | |
| 21042 | } | 21500 | } |