authorgravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2022-12-30 14:28:04+02:00
committergravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2022-12-30 17:00:50+02:00
log4e64373fc07a1e24735bcbdfd463e11839c8c273
treee59da20f467d336240c12cdc832834f22f361b30
parent4b5fc5239c37fa3f49965188256a781c7b1277a3

fix generic function arg debug info referencing wrong parameter

Closes #14123

12 files changed, 48 insertions(+), 38 deletions(-)

src/Air.zig+7-2
...@@ -31,7 +31,7 @@ pub const Inst = struct {...@@ -31,7 +31,7 @@ pub const Inst = struct {
31 /// The first N instructions in the main block must be one arg instruction per31 /// The first N instructions in the main block must be one arg instruction per
32 /// function parameter. This makes function parameters participate in32 /// function parameter. This makes function parameters participate in
33 /// liveness analysis without any special handling.33 /// liveness analysis without any special handling.
34 /// Uses the `ty` field.34 /// Uses the `arg` field.
35 arg,35 arg,
36 /// Float or integer addition. For integers, wrapping is undefined behavior.36 /// Float or integer addition. For integers, wrapping is undefined behavior.
37 /// Both operands are guaranteed to be the same type, and the result type37 /// Both operands are guaranteed to be the same type, and the result type
...@@ -795,6 +795,10 @@ pub const Inst = struct {...@@ -795,6 +795,10 @@ pub const Inst = struct {
795 rhs: Ref,795 rhs: Ref,
796 },796 },
797 ty: Type,797 ty: Type,
798 arg: struct {
799 ty: Ref,
800 src_index: u32,
801 },
798 ty_op: struct {802 ty_op: struct {
799 ty: Ref,803 ty: Ref,
800 operand: Ref,804 operand: Ref,
...@@ -1103,11 +1107,12 @@ pub fn typeOfIndex(air: Air, inst: Air.Inst.Index) Type {...@@ -1103,11 +1107,12 @@ pub fn typeOfIndex(air: Air, inst: Air.Inst.Index) Type {
11031107
1104 .alloc,1108 .alloc,
1105 .ret_ptr,1109 .ret_ptr,
1106 .arg,
1107 .err_return_trace,1110 .err_return_trace,
1108 .c_va_start,1111 .c_va_start,
1109 => return datas[inst].ty,1112 => return datas[inst].ty,
11101113
1114 .arg => return air.getRefType(datas[inst].arg.ty),
1115
1111 .assembly,1116 .assembly,
1112 .block,1117 .block,
1113 .constant,1118 .constant,
src/Module.zig+5-1
...@@ -5672,11 +5672,15 @@ pub fn analyzeFnBody(mod: *Module, func: *Fn, arena: Allocator) SemaError!Air {...@@ -5672,11 +5672,15 @@ pub fn analyzeFnBody(mod: *Module, func: *Fn, arena: Allocator) SemaError!Air {
5672 runtime_param_index += 1;5672 runtime_param_index += 1;
5673 continue;5673 continue;
5674 }5674 }
5675 const air_ty = try sema.addType(param_ty);
5675 const arg_index = @intCast(u32, sema.air_instructions.len);5676 const arg_index = @intCast(u32, sema.air_instructions.len);
5676 inner_block.instructions.appendAssumeCapacity(arg_index);5677 inner_block.instructions.appendAssumeCapacity(arg_index);
5677 sema.air_instructions.appendAssumeCapacity(.{5678 sema.air_instructions.appendAssumeCapacity(.{
5678 .tag = .arg,5679 .tag = .arg,
5679 .data = .{ .ty = param_ty },5680 .data = .{ .arg = .{
5681 .ty = air_ty,
5682 .src_index = @intCast(u32, total_param_index),
5683 } },
5680 });5684 });
5681 sema.inst_map.putAssumeCapacityNoClobber(inst, Air.indexToRef(arg_index));5685 sema.inst_map.putAssumeCapacityNoClobber(inst, Air.indexToRef(arg_index));
5682 total_param_index += 1;5686 total_param_index += 1;
src/Sema.zig+7-8
...@@ -476,13 +476,6 @@ pub const Block = struct {...@@ -476,13 +476,6 @@ pub const Block = struct {
476 });476 });
477 }477 }
478478
479 fn addArg(block: *Block, ty: Type) error{OutOfMemory}!Air.Inst.Ref {
480 return block.addInst(.{
481 .tag = .arg,
482 .data = .{ .ty = ty },
483 });
484 }
485
486 fn addStructFieldPtr(479 fn addStructFieldPtr(
487 block: *Block,480 block: *Block,
488 struct_ptr: Air.Inst.Ref,481 struct_ptr: Air.Inst.Ref,
...@@ -7258,7 +7251,13 @@ fn instantiateGenericCall(...@@ -7258,7 +7251,13 @@ fn instantiateGenericCall(
7258 } else {7251 } else {
7259 // We insert into the map an instruction which is runtime-known7252 // We insert into the map an instruction which is runtime-known
7260 // but has the type of the argument.7253 // but has the type of the argument.
7261 const child_arg = try child_block.addArg(arg_ty);7254 const child_arg = try child_block.addInst(.{
7255 .tag = .arg,
7256 .data = .{ .arg = .{
7257 .ty = try child_sema.addType(arg_ty),
7258 .src_index = @intCast(u32, arg_i),
7259 } },
7260 });
7262 child_sema.inst_map.putAssumeCapacityNoClobber(inst, child_arg);7261 child_sema.inst_map.putAssumeCapacityNoClobber(inst, child_arg);
7263 }7262 }
7264 }7263 }
src/arch/aarch64/CodeGen.zig+2-1
...@@ -4158,7 +4158,8 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {...@@ -4158,7 +4158,8 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {
41584158
4159 const ty = self.air.typeOfIndex(inst);4159 const ty = self.air.typeOfIndex(inst);
4160 const result = self.args[arg_index];4160 const result = self.args[arg_index];
4161 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg_index);4161 const src_index = self.air.instructions.items(.data)[inst].arg.src_index;
4162 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, src_index);
41624163
4163 const mcv = switch (result) {4164 const mcv = switch (result) {
4164 // Copy registers to the stack4165 // Copy registers to the stack
src/arch/arm/CodeGen.zig+3-2
...@@ -4037,8 +4037,9 @@ fn genInlineMemsetCode(...@@ -4037,8 +4037,9 @@ fn genInlineMemsetCode(
40374037
4038fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, arg_index: u32) error{OutOfMemory}!void {4038fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, arg_index: u32) error{OutOfMemory}!void {
4039 const mcv = self.args[arg_index];4039 const mcv = self.args[arg_index];
4040 const ty = self.air.instructions.items(.data)[inst].ty;4040 const arg = self.air.instructions.items(.data)[inst].arg;
4041 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg_index);4041 const ty = self.air.getRefType(arg.ty);
4042 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg.src_index);
40424043
4043 switch (self.debug_output) {4044 switch (self.debug_output) {
4044 .dwarf => |dw| {4045 .dwarf => |dw| {
src/arch/riscv64/CodeGen.zig+5-4
...@@ -1608,9 +1608,10 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void {...@@ -1608,9 +1608,10 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void {
1608 return self.fail("TODO implement codegen airFieldParentPtr", .{});1608 return self.fail("TODO implement codegen airFieldParentPtr", .{});
1609}1609}
16101610
1611fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, mcv: MCValue, arg_index: u32) !void {1611fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, mcv: MCValue) !void {
1612 const ty = self.air.instructions.items(.data)[inst].ty;1612 const arg = self.air.instructions.items(.data)[inst].arg;
1613 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg_index);1613 const ty = self.air.getRefType(arg.ty);
1614 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg.src_index);
16141615
1615 switch (self.debug_output) {1616 switch (self.debug_output) {
1616 .dwarf => |dw| switch (mcv) {1617 .dwarf => |dw| switch (mcv) {
...@@ -1640,7 +1641,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {...@@ -1640,7 +1641,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {
1640 // TODO support stack-only arguments1641 // TODO support stack-only arguments
1641 // TODO Copy registers to the stack1642 // TODO Copy registers to the stack
1642 const mcv = result;1643 const mcv = result;
1643 try self.genArgDbgInfo(inst, mcv, @intCast(u32, arg_index));1644 try self.genArgDbgInfo(inst, mcv);
16441645
1645 if (self.liveness.isUnused(inst))1646 if (self.liveness.isUnused(inst))
1646 return self.finishAirBookkeeping();1647 return self.finishAirBookkeeping();
src/arch/sparc64/CodeGen.zig+5-4
...@@ -1016,7 +1016,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {...@@ -1016,7 +1016,7 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {
1016 }1016 }
1017 };1017 };
10181018
1019 try self.genArgDbgInfo(inst, mcv, @intCast(u32, arg_index));1019 try self.genArgDbgInfo(inst, mcv);
10201020
1021 if (self.liveness.isUnused(inst))1021 if (self.liveness.isUnused(inst))
1022 return self.finishAirBookkeeping();1022 return self.finishAirBookkeeping();
...@@ -3407,9 +3407,10 @@ fn finishAir(self: *Self, inst: Air.Inst.Index, result: MCValue, operands: [Live...@@ -3407,9 +3407,10 @@ fn finishAir(self: *Self, inst: Air.Inst.Index, result: MCValue, operands: [Live
3407 self.finishAirBookkeeping();3407 self.finishAirBookkeeping();
3408}3408}
34093409
3410fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, mcv: MCValue, arg_index: u32) !void {3410fn genArgDbgInfo(self: Self, inst: Air.Inst.Index, mcv: MCValue) !void {
3411 const ty = self.air.instructions.items(.data)[inst].ty;3411 const arg = self.air.instructions.items(.data)[inst].arg;
3412 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg_index);3412 const ty = self.air.getRefType(arg.ty);
3413 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg.src_index);
34133414
3414 switch (self.debug_output) {3415 switch (self.debug_output) {
3415 .dwarf => |dw| switch (mcv) {3416 .dwarf => |dw| switch (mcv) {
src/arch/wasm/CodeGen.zig+2-2
...@@ -2474,8 +2474,8 @@ fn airArg(func: *CodeGen, inst: Air.Inst.Index) InnerError!void {...@@ -2474,8 +2474,8 @@ fn airArg(func: *CodeGen, inst: Air.Inst.Index) InnerError!void {
24742474
2475 switch (func.debug_output) {2475 switch (func.debug_output) {
2476 .dwarf => |dwarf| {2476 .dwarf => |dwarf| {
2477 // TODO: Get the original arg index rather than wasm arg index2477 const src_index = func.air.instructions.items(.data)[inst].arg.src_index;
2478 const name = func.mod_fn.getParamName(func.bin_file.base.options.module.?, arg_index);2478 const name = func.mod_fn.getParamName(func.bin_file.base.options.module.?, src_index);
2479 try dwarf.genArgDbgInfo(name, arg_ty, .wasm, func.mod_fn.owner_decl, .{2479 try dwarf.genArgDbgInfo(name, arg_ty, .wasm, func.mod_fn.owner_decl, .{
2480 .wasm_local = arg.local.value,2480 .wasm_local = arg.local.value,
2481 });2481 });
src/arch/x86_64/CodeGen.zig+2-1
...@@ -3799,7 +3799,8 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {...@@ -3799,7 +3799,8 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void {
37993799
3800 const ty = self.air.typeOfIndex(inst);3800 const ty = self.air.typeOfIndex(inst);
3801 const mcv = self.args[arg_index];3801 const mcv = self.args[arg_index];
3802 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, arg_index);3802 const src_index = self.air.instructions.items(.data)[inst].arg.src_index;
3803 const name = self.mod_fn.getParamName(self.bin_file.options.module.?, src_index);
38033804
3804 if (self.liveness.isUnused(inst))3805 if (self.liveness.isUnused(inst))
3805 return self.finishAirBookkeeping();3806 return self.finishAirBookkeeping();
src/codegen/llvm.zig+1-11
...@@ -8062,7 +8062,7 @@ pub const FuncGen = struct {...@@ -8062,7 +8062,7 @@ pub const FuncGen = struct {
8062 return arg_val;8062 return arg_val;
8063 }8063 }
80648064
8065 const src_index = self.getSrcArgIndex(self.arg_index - 1);8065 const src_index = self.air.instructions.items(.data)[inst].arg.src_index;
8066 const func = self.dg.decl.getFunction().?;8066 const func = self.dg.decl.getFunction().?;
8067 const lbrace_line = self.dg.module.declPtr(func.owner_decl).src_line + func.lbrace_line + 1;8067 const lbrace_line = self.dg.module.declPtr(func.owner_decl).src_line + func.lbrace_line + 1;
8068 const lbrace_col = func.lbrace_column + 1;8068 const lbrace_col = func.lbrace_column + 1;
...@@ -8095,16 +8095,6 @@ pub const FuncGen = struct {...@@ -8095,16 +8095,6 @@ pub const FuncGen = struct {
8095 return arg_val;8095 return arg_val;
8096 }8096 }
80978097
8098 fn getSrcArgIndex(self: *FuncGen, runtime_index: u32) u32 {
8099 const fn_info = self.dg.decl.ty.fnInfo();
8100 var i: u32 = 0;
8101 for (fn_info.param_types) |param_ty, src_index| {
8102 if (!param_ty.hasRuntimeBitsIgnoreComptime()) continue;
8103 if (i == runtime_index) return @intCast(u32, src_index);
8104 i += 1;
8105 } else unreachable;
8106 }
8107
8108 fn airAlloc(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value {8098 fn airAlloc(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value {
8109 if (self.liveness.isUnused(inst)) return null;8099 if (self.liveness.isUnused(inst)) return null;
8110 const ptr_ty = self.air.typeOfIndex(inst);8100 const ptr_ty = self.air.typeOfIndex(inst);
src/link/SpirV.zig+1-1
...@@ -314,7 +314,7 @@ fn cloneAir(air: Air, gpa: Allocator, air_arena: Allocator) !Air {...@@ -314,7 +314,7 @@ fn cloneAir(air: Air, gpa: Allocator, air_arena: Allocator) !Air {
314314
315 for (air_tags) |tag, i| {315 for (air_tags) |tag, i| {
316 switch (tag) {316 switch (tag) {
317 .arg, .alloc, .ret_ptr, .const_ty => air_datas[i].ty = try air_datas[i].ty.copy(air_arena),317 .alloc, .ret_ptr, .const_ty => air_datas[i].ty = try air_datas[i].ty.copy(air_arena),
318 else => {},318 else => {},
319 }319 }
320 }320 }
src/print_air.zig+8-1
...@@ -204,11 +204,12 @@ const Writer = struct {...@@ -204,11 +204,12 @@ const Writer = struct {
204 .const_ty,204 .const_ty,
205 .alloc,205 .alloc,
206 .ret_ptr,206 .ret_ptr,
207 .arg,
208 .err_return_trace,207 .err_return_trace,
209 .c_va_start,208 .c_va_start,
210 => try w.writeTy(s, inst),209 => try w.writeTy(s, inst),
211210
211 .arg => try w.writeArg(s, inst),
212
212 .not,213 .not,
213 .bitcast,214 .bitcast,
214 .load,215 .load,
...@@ -351,6 +352,12 @@ const Writer = struct {...@@ -351,6 +352,12 @@ const Writer = struct {
351 try w.writeType(s, ty);352 try w.writeType(s, ty);
352 }353 }
353354
355 fn writeArg(w: *Writer, s: anytype, inst: Air.Inst.Index) @TypeOf(s).Error!void {
356 const arg = w.air.instructions.items(.data)[inst].arg;
357 try w.writeType(s, w.air.getRefType(arg.ty));
358 try s.print(", {d}", .{arg.src_index});
359 }
360
354 fn writeTyOp(w: *Writer, s: anytype, inst: Air.Inst.Index) @TypeOf(s).Error!void {361 fn writeTyOp(w: *Writer, s: anytype, inst: Air.Inst.Index) @TypeOf(s).Error!void {
355 const ty_op = w.air.instructions.items(.data)[inst].ty_op;362 const ty_op = w.air.instructions.items(.data)[inst].ty_op;
356 try w.writeType(s, w.air.getRefType(ty_op.ty));363 try w.writeType(s, w.air.getRefType(ty_op.ty));