From 7be983ac9217a596b7f35e7ef4c49fda0270e10b Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Fri, 13 Oct 2023 14:54:52 +0200 Subject: elf: create new synthetic section ZigGotSection --- src/codegen.zig | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'src/codegen.zig') diff --git a/src/codegen.zig b/src/codegen.zig index 2c5fd7b630..e2ebcecee2 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -889,9 +889,8 @@ fn genDeclRef( if (bin_file.cast(link.File.Elf)) |elf_file| { const sym_index = try elf_file.getOrCreateMetadataForDecl(decl_index); const sym = elf_file.symbol(sym_index); - sym.flags.needs_got = true; - _ = try sym.getOrCreateGotEntry(sym_index, elf_file); - return GenResult.mcv(.{ .memory = sym.gotAddress(elf_file) }); + _ = try sym.getOrCreateZigGotEntry(sym_index, elf_file); + return GenResult.mcv(.{ .memory = sym.zigGotAddress(elf_file) }); } else if (bin_file.cast(link.File.MachO)) |macho_file| { const atom_index = try macho_file.getOrCreateAtomForDecl(decl_index); const sym_index = macho_file.getAtom(atom_index).getSymbolIndex().?; -- cgit v1.2.3 From 17635e4f2ae78e358a7a997b161e64de71a01191 Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Sat, 14 Oct 2023 09:04:08 +0200 Subject: x86_64: add -fPIC support targeting ELF --- src/arch/x86_64/CodeGen.zig | 91 +++++++++++++++++++++++++++------------------ src/arch/x86_64/Emit.zig | 11 +++++- src/codegen.zig | 13 ++++++- src/link/Elf.zig | 3 ++ src/link/Elf/Atom.zig | 31 +++++++-------- 5 files changed, 92 insertions(+), 57 deletions(-) (limited to 'src/codegen.zig') diff --git a/src/arch/x86_64/CodeGen.zig b/src/arch/x86_64/CodeGen.zig index 4e568e294f..c488209366 100644 --- a/src/arch/x86_64/CodeGen.zig +++ b/src/arch/x86_64/CodeGen.zig @@ -9190,14 +9190,19 @@ fn genCall(self: *Self, info: union(enum) { const sym_index = try elf_file.getOrCreateMetadataForDecl(owner_decl); const sym = elf_file.symbol(sym_index); _ = try sym.getOrCreateZigGotEntry(sym_index, elf_file); - _ = try self.addInst(.{ - .tag = .call, - .ops = .direct_got_reloc, - .data = .{ .reloc = .{ - .atom_index = try self.owner.getSymbolIndex(self), - .sym_index = sym.esym_index, - } }, - }); + if (self.bin_file.options.pic) { + try self.genSetReg(.rax, Type.usize, .{ .lea_got = sym.esym_index }); + try self.asmRegister(.{ ._, .call }, .rax); + } else { + _ = try self.addInst(.{ + .tag = .call, + .ops = .direct_got_reloc, + .data = .{ .reloc = .{ + .atom_index = try self.owner.getSymbolIndex(self), + .sym_index = sym.esym_index, + } }, + }); + } } else if (self.bin_file.cast(link.File.Coff)) |coff_file| { const atom = try coff_file.getOrCreateAtomForDecl(owner_decl); const sym_index = coff_file.getAtom(atom).getSymbolIndex().?; @@ -11637,34 +11642,48 @@ fn genLazySymbolRef( return self.fail("{s} creating lazy symbol", .{@errorName(err)}); const sym = elf_file.symbol(sym_index); _ = try sym.getOrCreateZigGotEntry(sym_index, elf_file); - const reloc = Mir.Reloc{ - .atom_index = try self.owner.getSymbolIndex(self), - .sym_index = sym.esym_index, - }; - switch (tag) { - .lea, .mov => _ = try self.addInst(.{ - .tag = .mov, - .ops = .direct_got_reloc, - .data = .{ .rx = .{ - .r1 = reg.to64(), - .payload = try self.addExtra(reloc), - } }, - }), - .call => _ = try self.addInst(.{ - .tag = .call, - .ops = .direct_got_reloc, - .data = .{ .reloc = reloc }, - }), - else => unreachable, - } - switch (tag) { - .lea, .call => {}, - .mov => try self.asmRegisterMemory( - .{ ._, tag }, - reg.to64(), - Memory.sib(.qword, .{ .base = .{ .reg = reg.to64() } }), - ), - else => unreachable, + + if (self.bin_file.options.pic) { + switch (tag) { + .lea, .call => try self.genSetReg(reg, Type.usize, .{ .lea_got = sym.esym_index }), + .mov => try self.genSetReg(reg, Type.usize, .{ .load_got = sym.esym_index }), + else => unreachable, + } + switch (tag) { + .lea, .mov => {}, + .call => try self.asmRegister(.{ ._, .call }, reg), + else => unreachable, + } + } else { + const reloc = Mir.Reloc{ + .atom_index = try self.owner.getSymbolIndex(self), + .sym_index = sym.esym_index, + }; + switch (tag) { + .lea, .mov => _ = try self.addInst(.{ + .tag = .mov, + .ops = .direct_got_reloc, + .data = .{ .rx = .{ + .r1 = reg.to64(), + .payload = try self.addExtra(reloc), + } }, + }), + .call => _ = try self.addInst(.{ + .tag = .call, + .ops = .direct_got_reloc, + .data = .{ .reloc = reloc }, + }), + else => unreachable, + } + switch (tag) { + .lea, .call => {}, + .mov => try self.asmRegisterMemory( + .{ ._, tag }, + reg.to64(), + Memory.sib(.qword, .{ .base = .{ .reg = reg.to64() } }), + ), + else => unreachable, + } } } else if (self.bin_file.cast(link.File.Plan9)) |p9_file| { const atom_index = p9_file.getOrCreateAtomForLazySymbol(lazy_sym) catch |err| diff --git a/src/arch/x86_64/Emit.zig b/src/arch/x86_64/Emit.zig index d2a199da42..3347460eb8 100644 --- a/src/arch/x86_64/Emit.zig +++ b/src/arch/x86_64/Emit.zig @@ -85,14 +85,21 @@ pub fn emitMir(emit: *Emit) Error!void { .linker_tlv, => |symbol| if (emit.bin_file.cast(link.File.Elf)) |elf_file| { const r_type: u32 = switch (lowered_relocs[0].target) { - .linker_direct_got => std.elf.R_X86_64_GOT32, + .linker_direct_got => link.File.Elf.R_X86_64_ZIG_GOT32, + .linker_got => link.File.Elf.R_X86_64_ZIG_GOTPCREL, + .linker_direct => std.elf.R_X86_64_PC32, + else => unreachable, + }; + const r_addend: i64 = switch (lowered_relocs[0].target) { + .linker_direct_got => 0, + .linker_got, .linker_direct => -4, else => unreachable, }; const atom_ptr = elf_file.symbol(symbol.atom_index).atom(elf_file).?; try atom_ptr.addReloc(elf_file, .{ .r_offset = end_offset - 4, .r_info = (@as(u64, @intCast(symbol.sym_index)) << 32) | r_type, - .r_addend = 0, + .r_addend = r_addend, }); } else if (emit.bin_file.cast(link.File.MachO)) |macho_file| { const atom_index = macho_file.getAtomIndexForSymbol(.{ .sym_index = symbol.atom_index }).?; diff --git a/src/codegen.zig b/src/codegen.zig index e2ebcecee2..b5f7f3885e 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -890,7 +890,11 @@ fn genDeclRef( const sym_index = try elf_file.getOrCreateMetadataForDecl(decl_index); const sym = elf_file.symbol(sym_index); _ = try sym.getOrCreateZigGotEntry(sym_index, elf_file); - return GenResult.mcv(.{ .memory = sym.zigGotAddress(elf_file) }); + if (bin_file.options.pic) { + return GenResult.mcv(.{ .load_got = sym.esym_index }); + } else { + return GenResult.mcv(.{ .memory = sym.zigGotAddress(elf_file) }); + } } else if (bin_file.cast(link.File.MachO)) |macho_file| { const atom_index = try macho_file.getOrCreateAtomForDecl(decl_index); const sym_index = macho_file.getAtom(atom_index).getSymbolIndex().?; @@ -925,7 +929,12 @@ fn genUnnamedConst( return GenResult.fail(bin_file.allocator, src_loc, "lowering unnamed constant failed: {s}", .{@errorName(err)}); }; if (bin_file.cast(link.File.Elf)) |elf_file| { - return GenResult.mcv(.{ .memory = elf_file.symbol(local_sym_index).value }); + const local = elf_file.symbol(local_sym_index); + if (bin_file.options.pic) { + return GenResult.mcv(.{ .load_direct = local.esym_index }); + } else { + return GenResult.mcv(.{ .memory = local.value }); + } } else if (bin_file.cast(link.File.MachO)) |_| { return GenResult.mcv(.{ .load_direct = local_sym_index }); } else if (bin_file.cast(link.File.Coff)) |_| { diff --git a/src/link/Elf.zig b/src/link/Elf.zig index f89f303c6a..5659bfc858 100644 --- a/src/link/Elf.zig +++ b/src/link/Elf.zig @@ -6074,6 +6074,9 @@ const SystemLib = struct { path: []const u8, }; +pub const R_X86_64_ZIG_GOT32 = elf.R_X86_64_NUM + 1; +pub const R_X86_64_ZIG_GOTPCREL = elf.R_X86_64_NUM + 2; + const std = @import("std"); const build_options = @import("build_options"); const builtin = @import("builtin"); diff --git a/src/link/Elf/Atom.zig b/src/link/Elf/Atom.zig index fae96dec5e..b0d780c0c3 100644 --- a/src/link/Elf/Atom.zig +++ b/src/link/Elf/Atom.zig @@ -370,16 +370,6 @@ pub fn scanRelocs(self: Atom, elf_file: *Elf, code: ?[]const u8, undefs: anytype try self.scanReloc(symbol, rel, dynAbsRelocAction(symbol, elf_file), elf_file); }, - // TODO I have temporarily repurposed those for handling .zig.got indirection - // but we should probably claim unused custom values for incremental linking - // that get rewritten to standard relocs when lowering to a relocatable object - // file. - elf.R_X86_64_GOT32, - elf.R_X86_64_GOT64, - => { - assert(symbol.flags.has_zig_got); - }, - elf.R_X86_64_GOTPC32, elf.R_X86_64_GOTPC64, elf.R_X86_64_GOTPCREL, @@ -461,6 +451,13 @@ pub fn scanRelocs(self: Atom, elf_file: *Elf, code: ?[]const u8, undefs: anytype elf.R_X86_64_TLSDESC_CALL, => {}, + // Zig custom relocations + Elf.R_X86_64_ZIG_GOT32, + Elf.R_X86_64_ZIG_GOTPCREL, + => { + assert(symbol.flags.has_zig_got); + }, + else => try self.reportUnhandledRelocError(rel, elf_file), } } @@ -813,13 +810,6 @@ pub fn resolveRelocsAlloc(self: Atom, elf_file: *Elf, code: []u8) !void { elf.R_X86_64_32 => try cwriter.writeIntLittle(u32, @as(u32, @truncate(@as(u64, @intCast(S + A))))), elf.R_X86_64_32S => try cwriter.writeIntLittle(i32, @as(i32, @truncate(S + A))), - // TODO I have temporarily repurposed those for handling .zig.got indirection - // but we should probably claim unused custom values for incremental linking - // that get rewritten to standard relocs when lowering to a relocatable object - // file. - elf.R_X86_64_GOT32 => try cwriter.writeIntLittle(u32, @as(u32, @intCast(ZIG_GOT + A))), - elf.R_X86_64_GOT64 => try cwriter.writeIntLittle(u64, @as(u64, @intCast(ZIG_GOT + A))), - elf.R_X86_64_TPOFF32 => try cwriter.writeIntLittle(i32, @as(i32, @truncate(S + A - TP))), elf.R_X86_64_TPOFF64 => try cwriter.writeIntLittle(i64, S + A - TP), @@ -888,6 +878,10 @@ pub fn resolveRelocsAlloc(self: Atom, elf_file: *Elf, code: []u8) !void { } }, + // Zig custom relocations + Elf.R_X86_64_ZIG_GOT32 => try cwriter.writeIntLittle(u32, @as(u32, @intCast(ZIG_GOT + A))), + Elf.R_X86_64_ZIG_GOTPCREL => try cwriter.writeIntLittle(i32, @as(i32, @intCast(ZIG_GOT + A - P))), + else => {}, } } @@ -1136,6 +1130,9 @@ fn formatRelocType( elf.R_X86_64_GOTPCRELX => "R_X86_64_GOTPCRELX", elf.R_X86_64_REX_GOTPCRELX => "R_X86_64_REX_GOTPCRELX", elf.R_X86_64_NUM => "R_X86_64_NUM", + // Zig custom relocations + Elf.R_X86_64_ZIG_GOT32 => "R_X86_64_ZIG_GOT32", + Elf.R_X86_64_ZIG_GOTPCREL => "R_X86_64_ZIG_GOTPCREL", else => "R_X86_64_UNKNOWN", }; try writer.print("{s}", .{str}); -- cgit v1.2.3 From 45197ea7adfa34806b549263c06b988b5e35d48c Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Sun, 15 Oct 2023 09:10:46 +0200 Subject: codegen+elf: lower imported data refs --- src/arch/aarch64/CodeGen.zig | 6 ++- src/arch/arm/CodeGen.zig | 2 +- src/arch/riscv64/CodeGen.zig | 2 +- src/arch/sparc64/CodeGen.zig | 2 +- src/arch/x86_64/CodeGen.zig | 87 +++++++++++++++++++++++++++++++++++--------- src/arch/x86_64/Emit.zig | 4 +- src/arch/x86_64/Lower.zig | 6 ++- src/arch/x86_64/Mir.zig | 2 + src/codegen.zig | 10 +++++ src/link/Dwarf.zig | 1 + src/link/Elf.zig | 14 ++++--- 11 files changed, 107 insertions(+), 29 deletions(-) (limited to 'src/codegen.zig') diff --git a/src/arch/aarch64/CodeGen.zig b/src/arch/aarch64/CodeGen.zig index 5a114459d8..154e2ea129 100644 --- a/src/arch/aarch64/CodeGen.zig +++ b/src/arch/aarch64/CodeGen.zig @@ -4012,6 +4012,7 @@ fn store(self: *Self, ptr: MCValue, value: MCValue, ptr_ty: Type, value_ty: Type .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, + .actual_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5531,6 +5532,7 @@ fn genSetStack(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) InnerErro .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, + .actual_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5652,6 +5654,7 @@ fn genSetReg(self: *Self, ty: Type, reg: Register, mcv: MCValue) InnerError!void .got => .load_memory_got, .direct => .load_memory_direct, .import => .load_memory_import, + .actual_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5849,6 +5852,7 @@ fn genSetStackArgument(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) I .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, + .actual_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -6176,7 +6180,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .memory => |addr| .{ .memory = addr }, .load_got => |sym_index| .{ .linker_load = .{ .type = .got, .sym_index = sym_index } }, .load_direct => |sym_index| .{ .linker_load = .{ .type = .direct, .sym_index = sym_index } }, - .load_tlv => unreachable, // TODO + .load_actual_got, .load_tlv => unreachable, // TODO }, .fail => |msg| { self.err_msg = msg; diff --git a/src/arch/arm/CodeGen.zig b/src/arch/arm/CodeGen.zig index aefac7bdd4..7a505de659 100644 --- a/src/arch/arm/CodeGen.zig +++ b/src/arch/arm/CodeGen.zig @@ -6135,7 +6135,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = @as(u32, @truncate(imm)) }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/riscv64/CodeGen.zig b/src/arch/riscv64/CodeGen.zig index eb7d7187eb..0191e8a302 100644 --- a/src/arch/riscv64/CodeGen.zig +++ b/src/arch/riscv64/CodeGen.zig @@ -2591,7 +2591,7 @@ fn genTypedValue(self: *Self, typed_value: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = imm }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/sparc64/CodeGen.zig b/src/arch/sparc64/CodeGen.zig index b5fd40ed95..504f9b4c43 100644 --- a/src/arch/sparc64/CodeGen.zig +++ b/src/arch/sparc64/CodeGen.zig @@ -4137,7 +4137,7 @@ fn genTypedValue(self: *Self, typed_value: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = imm }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/x86_64/CodeGen.zig b/src/arch/x86_64/CodeGen.zig index c488209366..0d50f03d95 100644 --- a/src/arch/x86_64/CodeGen.zig +++ b/src/arch/x86_64/CodeGen.zig @@ -207,6 +207,10 @@ pub const MCValue = union(enum) { /// The value is a pointer to a value referenced indirectly via GOT. /// Payload is a symbol index. lea_got: u32, + /// TODO indirection via actual .got table + /// LOL Jakub, the king of naming... + load_actual_got: u32, + lea_actual_got: u32, /// The value is a threadlocal variable. /// Payload is a symbol index. load_tlv: u32, @@ -295,6 +299,7 @@ pub const MCValue = union(enum) { .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -308,6 +313,7 @@ pub const MCValue = union(enum) { .load_direct => |sym_index| .{ .lea_direct = sym_index }, .load_got => |sym_index| .{ .lea_got = sym_index }, .load_tlv => |sym_index| .{ .lea_tlv = sym_index }, + .load_actual_got => |sym_index| .{ .lea_actual_got = sym_index }, .load_frame => |frame_addr| .{ .lea_frame = frame_addr }, }; } @@ -325,6 +331,7 @@ pub const MCValue = union(enum) { .indirect, .load_direct, .load_got, + .load_actual_got, .load_tlv, .load_frame, .reserved_frame, @@ -335,6 +342,7 @@ pub const MCValue = union(enum) { .register_offset => |reg_off| .{ .indirect = reg_off }, .lea_direct => |sym_index| .{ .load_direct = sym_index }, .lea_got => |sym_index| .{ .load_got = sym_index }, + .lea_actual_got => |sym_index| .{ .load_actual_got = sym_index }, .lea_tlv => |sym_index| .{ .load_tlv = sym_index }, .lea_frame => |frame_addr| .{ .load_frame = frame_addr }, }; @@ -358,6 +366,8 @@ pub const MCValue = union(enum) { .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -392,6 +402,8 @@ pub const MCValue = union(enum) { .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .lea_frame, @@ -434,6 +446,8 @@ pub const MCValue = union(enum) { .lea_direct => |pl| try writer.print("direct:{d}", .{pl}), .load_got => |pl| try writer.print("[got:{d}]", .{pl}), .lea_got => |pl| try writer.print("got:{d}", .{pl}), + .load_actual_got => |pl| try writer.print("[actual_got:{d}]", .{pl}), + .lea_actual_got => |pl| try writer.print("actual_got:{d}", .{pl}), .load_tlv => |pl| try writer.print("[tlv:{d}]", .{pl}), .lea_tlv => |pl| try writer.print("tlv:{d}", .{pl}), .load_frame => |pl| try writer.print("[{} + 0x{x}]", .{ pl.index, pl.off }), @@ -461,6 +475,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -520,6 +536,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -555,6 +573,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .lea_frame, @@ -4371,6 +4391,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { .memory, .load_direct, .load_got, + .load_actual_got, .load_tlv, => try self.genSetReg(addr_reg, Type.usize, array.address()), .lea_direct, .lea_tlv => unreachable, @@ -5851,6 +5872,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro .register_offset, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, => try self.genCopy(dst_ty, dst_mcv, ptr_mcv.deref()), @@ -5858,6 +5880,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro .indirect, .load_direct, .load_got, + .load_actual_got, .load_tlv, .load_frame, => { @@ -5996,6 +6019,7 @@ fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerErr .register_offset, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, => try self.genCopy(src_ty, ptr_mcv.deref(), src_mcv), @@ -6003,6 +6027,7 @@ fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerErr .indirect, .load_direct, .load_got, + .load_actual_got, .load_tlv, .load_frame, => { @@ -6424,6 +6449,7 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -6431,7 +6457,7 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC => unreachable, // unmodifiable destination .register => |dst_reg| try self.asmRegister(mir_tag, registerAlias(dst_reg, abi_size)), .register_pair => unreachable, // unimplemented - .memory, .load_got, .load_direct, .load_tlv => { + .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => { const addr_reg = try self.register_manager.allocReg(null, abi.RegisterClass.gp); const addr_reg_lock = self.register_manager.lockRegAssumeUnused(addr_reg); defer self.register_manager.unlockReg(addr_reg_lock); @@ -7389,6 +7415,8 @@ fn genBinOp( .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .lea_frame, @@ -7445,6 +7473,8 @@ fn genBinOp( .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .lea_frame, @@ -8397,6 +8427,7 @@ fn genBinOpMir( .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -8485,6 +8516,8 @@ fn genBinOpMir( .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -8517,6 +8550,7 @@ fn genBinOpMir( .register_offset, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, => { @@ -8532,6 +8566,7 @@ fn genBinOpMir( .memory, .load_direct, .load_got, + .load_actual_got, .load_tlv, => { const ptr_ty = try mod.singleConstPtrType(ty); @@ -8552,13 +8587,13 @@ fn genBinOpMir( } } }, - .memory, .indirect, .load_got, .load_direct, .load_tlv, .load_frame => { + .memory, .indirect, .load_got, .load_actual_got, .load_direct, .load_tlv, .load_frame => { const OpInfo = ?struct { addr_reg: Register, addr_lock: RegisterLock }; const limb_abi_size: u32 = @min(abi_size, 8); const dst_info: OpInfo = switch (dst_mcv) { else => unreachable, - .memory, .load_got, .load_direct, .load_tlv => dst: { + .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => dst: { const dst_addr_reg = (try self.register_manager.allocReg(null, abi.RegisterClass.gp)).to64(); const dst_addr_lock = self.register_manager.lockRegAssumeUnused(dst_addr_reg); @@ -8592,16 +8627,17 @@ fn genBinOpMir( .indirect, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .load_frame, .lea_frame, => null, - .memory, .load_got, .load_direct, .load_tlv => src: { + .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => src: { switch (resolved_src_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr))) != null and math.cast(i32, @as(i64, @bitCast(addr)) + abi_size - limb_abi_size) != null) break :src null, - .load_got, .load_direct, .load_tlv => {}, + .load_got, .load_actual_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -8644,6 +8680,7 @@ fn genBinOpMir( switch (dst_mcv) { .memory, .load_got, + .load_actual_got, .load_direct, .load_tlv, => .{ .base = .{ .reg = dst_info.?.addr_reg }, .disp = off }, @@ -8728,6 +8765,8 @@ fn genBinOpMir( .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -8743,6 +8782,7 @@ fn genBinOpMir( .register_offset, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, => switch (limb_i) { @@ -8792,6 +8832,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -8840,6 +8881,8 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .lea_frame, @@ -8878,7 +8921,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M } }, .register_pair => unreachable, // unimplemented - .memory, .indirect, .load_direct, .load_got, .load_tlv, .load_frame => { + .memory, .indirect, .load_direct, .load_got, .load_actual_got, .load_tlv, .load_frame => { const tmp_reg = try self.copyToTmpRegister(dst_ty, dst_mcv); const tmp_mcv = MCValue{ .register = tmp_reg }; const tmp_lock = self.register_manager.lockRegAssumeUnused(tmp_reg); @@ -8971,6 +9014,7 @@ fn genVarDbgInfo( //} }, .memory => |address| .{ .memory = address }, .load_got => |sym_index| .{ .linker_load = .{ .type = .got, .sym_index = sym_index } }, + .load_actual_got => |sym_index| .{ .linker_load = .{ .type = .actual_got, .sym_index = sym_index } }, .load_direct => |sym_index| .{ .linker_load = .{ .type = .direct, .sym_index = sym_index } }, .immediate => |x| .{ .immediate = x }, .undef => .undef, @@ -9410,13 +9454,14 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { .indirect, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, .air_ref, => unreachable, .register_pair, .load_frame => null, - .memory, .load_got, .load_direct, .load_tlv => dst: { + .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => dst: { switch (resolved_dst_mcv) { .memory => |addr| if (math.cast( i32, @@ -9425,7 +9470,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { i32, @as(i64, @bitCast(addr)) + abi_size - 8, ) != null) break :dst null, - .load_got, .load_direct, .load_tlv => {}, + .load_got, .load_actual_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -9468,13 +9513,14 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { .indirect, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, .air_ref, => unreachable, .register_pair, .load_frame => null, - .memory, .load_got, .load_direct, .load_tlv => src: { + .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => src: { switch (resolved_src_mcv) { .memory => |addr| if (math.cast( i32, @@ -9483,7 +9529,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { i32, @as(i64, @bitCast(addr)) + abi_size - 8, ) != null) break :src null, - .load_got, .load_direct, .load_tlv => {}, + .load_got, .load_actual_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -9902,6 +9948,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -9928,6 +9975,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC .memory, .load_got, + .load_actual_got, .load_direct, .load_tlv, => { @@ -10485,7 +10533,7 @@ fn airAsm(self: *Self, inst: Air.Inst.Index) !void { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |_| break :arg input_mcv, .indirect, .load_frame => break :arg input_mcv, - .load_direct, .load_got, .load_tlv => {}, + .load_direct, .load_got, .load_actual_got, .load_tlv => {}, else => { const temp_mcv = try self.allocTempRegOrMem(ty, false); try self.genCopy(ty, temp_mcv, input_mcv); @@ -11146,6 +11194,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError .register_overflow, .lea_direct, .lea_got, + .lea_actual_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -11197,11 +11246,11 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError } }, .indirect => |reg_off| try self.genSetMem(.{ .reg = reg_off.reg }, reg_off.off, ty, src_mcv), - .memory, .load_direct, .load_got, .load_tlv => { + .memory, .load_direct, .load_got, .load_actual_got, .load_tlv => { switch (dst_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| return self.genSetMem(.{ .reg = .ds }, small_addr, ty, src_mcv), - .load_direct, .load_got, .load_tlv => {}, + .load_direct, .load_got, .load_actual_got, .load_tlv => {}, else => unreachable, } @@ -11363,7 +11412,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr else => unreachable, }, )), - .memory, .load_direct, .load_got, .load_tlv => { + .memory, .load_direct, .load_got, .load_actual_got, .load_tlv => { switch (src_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| return (try self.moveStrategy( @@ -11391,7 +11440,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr }, .Float, .Vector => {}, }, - .load_got, .load_tlv => {}, + .load_got, .load_actual_got, .load_tlv => {}, else => unreachable, } @@ -11405,17 +11454,18 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr Memory.sib(Memory.PtrSize.fromSize(abi_size), .{ .base = .{ .reg = addr_reg } }), ); }, - .lea_direct, .lea_got => |sym_index| { + .lea_direct, .lea_got, .lea_actual_got => |sym_index| { const atom_index = try self.owner.getSymbolIndex(self); _ = try self.addInst(.{ .tag = switch (src_mcv) { .lea_direct => .lea, - .lea_got => .mov, + .lea_got, .lea_actual_got => .mov, else => unreachable, }, .ops = switch (src_mcv) { .lea_direct => .direct_reloc, .lea_got => .got_reloc, + .lea_actual_got => .actual_got_reloc, else => unreachable, }, .data = .{ .rx = .{ @@ -11551,6 +11601,8 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal .lea_direct, .load_got, .lea_got, + .load_actual_got, + .lea_actual_got, .load_tlv, .lea_tlv, .load_frame, @@ -13556,6 +13608,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .memory => |addr| .{ .memory = addr }, .load_direct => |sym_index| .{ .load_direct = sym_index }, .load_got => |sym_index| .{ .lea_got = sym_index }, + .load_actual_got => |sym_index| .{ .lea_actual_got = sym_index }, .load_tlv => |sym_index| .{ .lea_tlv = sym_index }, }, .fail => |msg| { diff --git a/src/arch/x86_64/Emit.zig b/src/arch/x86_64/Emit.zig index 3347460eb8..9c0c48121f 100644 --- a/src/arch/x86_64/Emit.zig +++ b/src/arch/x86_64/Emit.zig @@ -79,6 +79,7 @@ pub fn emitMir(emit: *Emit) Error!void { @tagName(emit.bin_file.tag), }), .linker_got, + .linker_actual_got, .linker_direct, .linker_direct_got, .linker_import, @@ -87,12 +88,13 @@ pub fn emitMir(emit: *Emit) Error!void { const r_type: u32 = switch (lowered_relocs[0].target) { .linker_direct_got => link.File.Elf.R_X86_64_ZIG_GOT32, .linker_got => link.File.Elf.R_X86_64_ZIG_GOTPCREL, + .linker_actual_got => std.elf.R_X86_64_GOTPCREL, .linker_direct => std.elf.R_X86_64_PC32, else => unreachable, }; const r_addend: i64 = switch (lowered_relocs[0].target) { .linker_direct_got => 0, - .linker_got, .linker_direct => -4, + .linker_got, .linker_actual_got, .linker_direct => -4, else => unreachable, }; const atom_ptr = elf_file.symbol(symbol.atom_index).atom(elf_file).?; diff --git a/src/arch/x86_64/Lower.zig b/src/arch/x86_64/Lower.zig index 71f411bdaf..f8091e5476 100644 --- a/src/arch/x86_64/Lower.zig +++ b/src/arch/x86_64/Lower.zig @@ -51,6 +51,7 @@ pub const Reloc = struct { inst: Mir.Inst.Index, linker_extern_fn: Mir.Reloc, linker_got: Mir.Reloc, + linker_actual_got: Mir.Reloc, linker_direct: Mir.Reloc, linker_direct_got: Mir.Reloc, linker_import: Mir.Reloc, @@ -388,7 +389,7 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void { .rrmi_sib, .rrmi_rip => inst.data.rrix.fixes, .mi_sib_u, .mi_rip_u, .mi_sib_s, .mi_rip_s => inst.data.x.fixes, .m_sib, .m_rip, .rax_moffs, .moffs_rax => inst.data.x.fixes, - .extern_fn_reloc, .got_reloc, .direct_reloc, .direct_got_reloc, .import_reloc, .tlv_reloc => ._, + .extern_fn_reloc, .got_reloc, .actual_got_reloc, .direct_reloc, .direct_got_reloc, .import_reloc, .tlv_reloc => ._, else => return lower.fail("TODO lower .{s}", .{@tagName(inst.ops)}), }; try lower.emit(switch (fixes) { @@ -532,11 +533,12 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void { else => unreachable, } }, - .got_reloc, .direct_reloc, .import_reloc, .tlv_reloc => ops: { + .got_reloc, .actual_got_reloc, .direct_reloc, .import_reloc, .tlv_reloc => ops: { const reg = inst.data.rx.r1; const extra = lower.mir.extraData(Mir.Reloc, inst.data.rx.payload).data; _ = lower.reloc(switch (inst.ops) { .got_reloc => .{ .linker_got = extra }, + .actual_got_reloc => .{ .linker_actual_got = extra }, .direct_reloc => .{ .linker_direct = extra }, .import_reloc => .{ .linker_import = extra }, .tlv_reloc => .{ .linker_tlv = extra }, diff --git a/src/arch/x86_64/Mir.zig b/src/arch/x86_64/Mir.zig index b17da20862..1e159d5a16 100644 --- a/src/arch/x86_64/Mir.zig +++ b/src/arch/x86_64/Mir.zig @@ -783,6 +783,8 @@ pub const Inst = struct { /// Linker relocation - GOT indirection. /// Uses `rx` payload with extra data of type `Reloc`. got_reloc, + /// TODO + actual_got_reloc, /// Linker relocation - direct reference. /// Uses `rx` payload with extra data of type `Reloc`. direct_reloc, diff --git a/src/codegen.zig b/src/codegen.zig index b5f7f3885e..de5ff9651a 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -798,6 +798,7 @@ fn lowerDeclRef( pub const LinkerLoad = struct { type: enum { got, + actual_got, direct, import, }, @@ -827,6 +828,8 @@ pub const GenResult = union(enum) { load_got: u32, /// Direct by-address reference to memory location. memory: u64, + /// TODO LOL Jakub, the king of naming... + load_actual_got: u32, }; fn mcv(val: MCValue) GenResult { @@ -885,8 +888,15 @@ fn genDeclRef( try mod.markDeclAlive(decl); const is_threadlocal = tv.val.isPtrToThreadLocal(mod) and !bin_file.options.single_threaded; + const is_extern = decl.isExtern(mod); if (bin_file.cast(link.File.Elf)) |elf_file| { + if (is_extern) { + const variable = decl.getOwnedVariable(mod).?; + const name = mod.intern_pool.stringToSlice(decl.name); + const lib_name = mod.intern_pool.stringToSliceUnwrap(variable.lib_name); + return GenResult.mcv(.{ .load_actual_got = try elf_file.getGlobalSymbol(name, lib_name) }); + } const sym_index = try elf_file.getOrCreateMetadataForDecl(decl_index); const sym = elf_file.symbol(sym_index); _ = try sym.getOrCreateZigGotEntry(sym_index, elf_file); diff --git a/src/link/Dwarf.zig b/src/link/Dwarf.zig index e271a7d399..ffe078f831 100644 --- a/src/link/Dwarf.zig +++ b/src/link/Dwarf.zig @@ -1389,6 +1389,7 @@ pub fn commitDeclState( .prev_vaddr = 0, }); }, + .elf => {}, // TODO else => unreachable, } } diff --git a/src/link/Elf.zig b/src/link/Elf.zig index 9fe2f6b7ed..d27e3c7f3b 100644 --- a/src/link/Elf.zig +++ b/src/link/Elf.zig @@ -3196,12 +3196,16 @@ pub fn updateDecl( const decl = mod.declPtr(decl_index); if (decl.val.getExternFunc(mod)) |_| { - return; // TODO Should we do more when front-end analyzed extern decl? + return; } - if (decl.val.getVariable(mod)) |variable| { - if (variable.is_extern) { - return; // TODO Should we do more when front-end analyzed extern decl? - } + + if (decl.isExtern(mod)) { + // Extern variable gets a .got entry only. + const variable = decl.getOwnedVariable(mod).?; + const name = mod.intern_pool.stringToSlice(decl.name); + const lib_name = mod.intern_pool.stringToSliceUnwrap(variable.lib_name); + _ = try self.getGlobalSymbol(name, lib_name); + return; } const sym_index = try self.getOrCreateMetadataForDecl(decl_index); -- cgit v1.2.3 From 7b2cbcf0fe6dcaea7ee108c13422f6d00ed4bc8e Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Sun, 15 Oct 2023 15:38:16 +0200 Subject: codegen+elf: check if extern is a variable ref --- src/codegen.zig | 7 +++++-- src/link/Elf.zig | 1 - src/link/Elf/Object.zig | 2 -- 3 files changed, 5 insertions(+), 5 deletions(-) (limited to 'src/codegen.zig') diff --git a/src/codegen.zig b/src/codegen.zig index de5ff9651a..54ed9c0cf5 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -892,9 +892,12 @@ fn genDeclRef( if (bin_file.cast(link.File.Elf)) |elf_file| { if (is_extern) { - const variable = decl.getOwnedVariable(mod).?; const name = mod.intern_pool.stringToSlice(decl.name); - const lib_name = mod.intern_pool.stringToSliceUnwrap(variable.lib_name); + // TODO audit this + const lib_name = if (decl.getOwnedVariable(mod)) |ov| + mod.intern_pool.stringToSliceUnwrap(ov.lib_name) + else + null; return GenResult.mcv(.{ .load_actual_got = try elf_file.getGlobalSymbol(name, lib_name) }); } const sym_index = try elf_file.getOrCreateMetadataForDecl(decl_index); diff --git a/src/link/Elf.zig b/src/link/Elf.zig index d27e3c7f3b..589a13d0ad 100644 --- a/src/link/Elf.zig +++ b/src/link/Elf.zig @@ -4597,7 +4597,6 @@ fn allocateAllocSections(self: *Elf) error{OutOfMemory}!void { for (slice, 0..) |*shdr, ii| { if (shdr.sh_type == elf.SHT_NOBITS) continue; off = alignment.@"align"(cover.start + ii, shdr.sh_addralign, off); - // off = mem.alignForward(u64, off, shdr.sh_addralign); shdr.sh_offset = off; off += shdr.sh_size; try self.phdr_to_shdr_table.putNoClobber(gpa, @intCast(ii + cover.start), phndx); diff --git a/src/link/Elf/Object.zig b/src/link/Elf/Object.zig index 3c42a0e349..173934db86 100644 --- a/src/link/Elf/Object.zig +++ b/src/link/Elf/Object.zig @@ -214,8 +214,6 @@ fn initOutputSection(self: Object, elf_file: *Elf, shdr: ElfShdr) error{OutOfMem break :blk prefix; } } - if (std.mem.eql(u8, name, ".tcommon")) break :blk ".tbss"; - if (std.mem.eql(u8, name, ".common")) break :blk ".bss"; break :blk name; }; const @"type" = switch (shdr.sh_type) { -- cgit v1.2.3 From 6993b3e23e3b8f45f66902ebe23980aa155b343c Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Sun, 15 Oct 2023 22:06:18 +0200 Subject: codegen: refactor .actual_got into .extern_got --- src/arch/aarch64/CodeGen.zig | 10 +-- src/arch/arm/CodeGen.zig | 2 +- src/arch/riscv64/CodeGen.zig | 2 +- src/arch/sparc64/CodeGen.zig | 2 +- src/arch/x86_64/CodeGen.zig | 142 ++++++++++++++++++++++--------------------- src/arch/x86_64/Emit.zig | 6 +- src/arch/x86_64/Lower.zig | 8 +-- src/arch/x86_64/Mir.zig | 5 +- src/codegen.zig | 9 +-- 9 files changed, 95 insertions(+), 91 deletions(-) (limited to 'src/codegen.zig') diff --git a/src/arch/aarch64/CodeGen.zig b/src/arch/aarch64/CodeGen.zig index 154e2ea129..d0e068da73 100644 --- a/src/arch/aarch64/CodeGen.zig +++ b/src/arch/aarch64/CodeGen.zig @@ -4012,7 +4012,7 @@ fn store(self: *Self, ptr: MCValue, value: MCValue, ptr_ty: Type, value_ty: Type .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, - .actual_got => unreachable, + .extern_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5532,7 +5532,7 @@ fn genSetStack(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) InnerErro .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, - .actual_got => unreachable, + .extern_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5654,7 +5654,7 @@ fn genSetReg(self: *Self, ty: Type, reg: Register, mcv: MCValue) InnerError!void .got => .load_memory_got, .direct => .load_memory_direct, .import => .load_memory_import, - .actual_got => unreachable, + .extern_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -5852,7 +5852,7 @@ fn genSetStackArgument(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) I .got => .load_memory_ptr_got, .direct => .load_memory_ptr_direct, .import => unreachable, - .actual_got => unreachable, + .extern_got => unreachable, }; const atom_index = switch (self.bin_file.tag) { .macho => blk: { @@ -6180,7 +6180,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .memory => |addr| .{ .memory = addr }, .load_got => |sym_index| .{ .linker_load = .{ .type = .got, .sym_index = sym_index } }, .load_direct => |sym_index| .{ .linker_load = .{ .type = .direct, .sym_index = sym_index } }, - .load_actual_got, .load_tlv => unreachable, // TODO + .load_extern_got, .load_tlv => unreachable, // TODO }, .fail => |msg| { self.err_msg = msg; diff --git a/src/arch/arm/CodeGen.zig b/src/arch/arm/CodeGen.zig index 7a505de659..a7c437bb59 100644 --- a/src/arch/arm/CodeGen.zig +++ b/src/arch/arm/CodeGen.zig @@ -6135,7 +6135,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_extern_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = @as(u32, @truncate(imm)) }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/riscv64/CodeGen.zig b/src/arch/riscv64/CodeGen.zig index 0191e8a302..e4c4266531 100644 --- a/src/arch/riscv64/CodeGen.zig +++ b/src/arch/riscv64/CodeGen.zig @@ -2591,7 +2591,7 @@ fn genTypedValue(self: *Self, typed_value: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_extern_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = imm }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/sparc64/CodeGen.zig b/src/arch/sparc64/CodeGen.zig index 504f9b4c43..ae4fc29e8a 100644 --- a/src/arch/sparc64/CodeGen.zig +++ b/src/arch/sparc64/CodeGen.zig @@ -4137,7 +4137,7 @@ fn genTypedValue(self: *Self, typed_value: TypedValue) InnerError!MCValue { .mcv => |mcv| switch (mcv) { .none => .none, .undef => .undef, - .load_got, .load_actual_got, .load_direct, .load_tlv => unreachable, // TODO + .load_got, .load_extern_got, .load_direct, .load_tlv => unreachable, // TODO .immediate => |imm| .{ .immediate = imm }, .memory => |addr| .{ .memory = addr }, }, diff --git a/src/arch/x86_64/CodeGen.zig b/src/arch/x86_64/CodeGen.zig index 0d50f03d95..980b96c0ed 100644 --- a/src/arch/x86_64/CodeGen.zig +++ b/src/arch/x86_64/CodeGen.zig @@ -207,10 +207,12 @@ pub const MCValue = union(enum) { /// The value is a pointer to a value referenced indirectly via GOT. /// Payload is a symbol index. lea_got: u32, - /// TODO indirection via actual .got table - /// LOL Jakub, the king of naming... - load_actual_got: u32, - lea_actual_got: u32, + /// The value is an extern variable referenced via GOT. + /// Payload is a symbol index. + load_extern_got: u32, + /// The value is a pointer to an extern variable referenced via GOT. + /// Payload is a symbol index. + lea_extern_got: u32, /// The value is a threadlocal variable. /// Payload is a symbol index. load_tlv: u32, @@ -299,7 +301,7 @@ pub const MCValue = union(enum) { .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -313,7 +315,7 @@ pub const MCValue = union(enum) { .load_direct => |sym_index| .{ .lea_direct = sym_index }, .load_got => |sym_index| .{ .lea_got = sym_index }, .load_tlv => |sym_index| .{ .lea_tlv = sym_index }, - .load_actual_got => |sym_index| .{ .lea_actual_got = sym_index }, + .load_extern_got => |sym_index| .{ .lea_extern_got = sym_index }, .load_frame => |frame_addr| .{ .lea_frame = frame_addr }, }; } @@ -331,7 +333,7 @@ pub const MCValue = union(enum) { .indirect, .load_direct, .load_got, - .load_actual_got, + .load_extern_got, .load_tlv, .load_frame, .reserved_frame, @@ -342,7 +344,7 @@ pub const MCValue = union(enum) { .register_offset => |reg_off| .{ .indirect = reg_off }, .lea_direct => |sym_index| .{ .load_direct = sym_index }, .lea_got => |sym_index| .{ .load_got = sym_index }, - .lea_actual_got => |sym_index| .{ .load_actual_got = sym_index }, + .lea_extern_got => |sym_index| .{ .load_extern_got = sym_index }, .lea_tlv => |sym_index| .{ .load_tlv = sym_index }, .lea_frame => |frame_addr| .{ .load_frame = frame_addr }, }; @@ -366,8 +368,8 @@ pub const MCValue = union(enum) { .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -402,8 +404,8 @@ pub const MCValue = union(enum) { .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .lea_frame, @@ -446,8 +448,8 @@ pub const MCValue = union(enum) { .lea_direct => |pl| try writer.print("direct:{d}", .{pl}), .load_got => |pl| try writer.print("[got:{d}]", .{pl}), .lea_got => |pl| try writer.print("got:{d}", .{pl}), - .load_actual_got => |pl| try writer.print("[actual_got:{d}]", .{pl}), - .lea_actual_got => |pl| try writer.print("actual_got:{d}", .{pl}), + .load_extern_got => |pl| try writer.print("[extern_got:{d}]", .{pl}), + .lea_extern_got => |pl| try writer.print("extern_got:{d}", .{pl}), .load_tlv => |pl| try writer.print("[tlv:{d}]", .{pl}), .lea_tlv => |pl| try writer.print("tlv:{d}", .{pl}), .load_frame => |pl| try writer.print("[{} + 0x{x}]", .{ pl.index, pl.off }), @@ -475,8 +477,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -536,8 +538,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -573,8 +575,8 @@ const InstTracking = struct { .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .lea_frame, @@ -4391,7 +4393,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { .memory, .load_direct, .load_got, - .load_actual_got, + .load_extern_got, .load_tlv, => try self.genSetReg(addr_reg, Type.usize, array.address()), .lea_direct, .lea_tlv => unreachable, @@ -5872,7 +5874,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro .register_offset, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, => try self.genCopy(dst_ty, dst_mcv, ptr_mcv.deref()), @@ -5880,7 +5882,7 @@ fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerErro .indirect, .load_direct, .load_got, - .load_actual_got, + .load_extern_got, .load_tlv, .load_frame, => { @@ -6019,7 +6021,7 @@ fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerErr .register_offset, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, => try self.genCopy(src_ty, ptr_mcv.deref(), src_mcv), @@ -6027,7 +6029,7 @@ fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerErr .indirect, .load_direct, .load_got, - .load_actual_got, + .load_extern_got, .load_tlv, .load_frame, => { @@ -6449,7 +6451,7 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -6457,7 +6459,7 @@ fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MC => unreachable, // unmodifiable destination .register => |dst_reg| try self.asmRegister(mir_tag, registerAlias(dst_reg, abi_size)), .register_pair => unreachable, // unimplemented - .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => { + .memory, .load_got, .load_extern_got, .load_direct, .load_tlv => { const addr_reg = try self.register_manager.allocReg(null, abi.RegisterClass.gp); const addr_reg_lock = self.register_manager.lockRegAssumeUnused(addr_reg); defer self.register_manager.unlockReg(addr_reg_lock); @@ -7415,8 +7417,8 @@ fn genBinOp( .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .lea_frame, @@ -7473,8 +7475,8 @@ fn genBinOp( .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .lea_frame, @@ -8427,7 +8429,7 @@ fn genBinOpMir( .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -8516,8 +8518,8 @@ fn genBinOpMir( .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -8550,7 +8552,7 @@ fn genBinOpMir( .register_offset, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, => { @@ -8566,7 +8568,7 @@ fn genBinOpMir( .memory, .load_direct, .load_got, - .load_actual_got, + .load_extern_got, .load_tlv, => { const ptr_ty = try mod.singleConstPtrType(ty); @@ -8587,13 +8589,13 @@ fn genBinOpMir( } } }, - .memory, .indirect, .load_got, .load_actual_got, .load_direct, .load_tlv, .load_frame => { + .memory, .indirect, .load_got, .load_extern_got, .load_direct, .load_tlv, .load_frame => { const OpInfo = ?struct { addr_reg: Register, addr_lock: RegisterLock }; const limb_abi_size: u32 = @min(abi_size, 8); const dst_info: OpInfo = switch (dst_mcv) { else => unreachable, - .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => dst: { + .memory, .load_got, .load_extern_got, .load_direct, .load_tlv => dst: { const dst_addr_reg = (try self.register_manager.allocReg(null, abi.RegisterClass.gp)).to64(); const dst_addr_lock = self.register_manager.lockRegAssumeUnused(dst_addr_reg); @@ -8627,17 +8629,17 @@ fn genBinOpMir( .indirect, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .load_frame, .lea_frame, => null, - .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => src: { + .memory, .load_got, .load_extern_got, .load_direct, .load_tlv => src: { switch (resolved_src_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr))) != null and math.cast(i32, @as(i64, @bitCast(addr)) + abi_size - limb_abi_size) != null) break :src null, - .load_got, .load_actual_got, .load_direct, .load_tlv => {}, + .load_got, .load_extern_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -8680,7 +8682,7 @@ fn genBinOpMir( switch (dst_mcv) { .memory, .load_got, - .load_actual_got, + .load_extern_got, .load_direct, .load_tlv, => .{ .base = .{ .reg = dst_info.?.addr_reg }, .disp = off }, @@ -8765,8 +8767,8 @@ fn genBinOpMir( .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -8782,7 +8784,7 @@ fn genBinOpMir( .register_offset, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, => switch (limb_i) { @@ -8832,7 +8834,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -8881,8 +8883,8 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .lea_frame, @@ -8921,7 +8923,7 @@ fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: M } }, .register_pair => unreachable, // unimplemented - .memory, .indirect, .load_direct, .load_got, .load_actual_got, .load_tlv, .load_frame => { + .memory, .indirect, .load_direct, .load_got, .load_extern_got, .load_tlv, .load_frame => { const tmp_reg = try self.copyToTmpRegister(dst_ty, dst_mcv); const tmp_mcv = MCValue{ .register = tmp_reg }; const tmp_lock = self.register_manager.lockRegAssumeUnused(tmp_reg); @@ -9014,7 +9016,7 @@ fn genVarDbgInfo( //} }, .memory => |address| .{ .memory = address }, .load_got => |sym_index| .{ .linker_load = .{ .type = .got, .sym_index = sym_index } }, - .load_actual_got => |sym_index| .{ .linker_load = .{ .type = .actual_got, .sym_index = sym_index } }, + .load_extern_got => |sym_index| .{ .linker_load = .{ .type = .extern_got, .sym_index = sym_index } }, .load_direct => |sym_index| .{ .linker_load = .{ .type = .direct, .sym_index = sym_index } }, .immediate => |x| .{ .immediate = x }, .undef => .undef, @@ -9454,14 +9456,14 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { .indirect, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, .air_ref, => unreachable, .register_pair, .load_frame => null, - .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => dst: { + .memory, .load_got, .load_extern_got, .load_direct, .load_tlv => dst: { switch (resolved_dst_mcv) { .memory => |addr| if (math.cast( i32, @@ -9470,7 +9472,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { i32, @as(i64, @bitCast(addr)) + abi_size - 8, ) != null) break :dst null, - .load_got, .load_actual_got, .load_direct, .load_tlv => {}, + .load_got, .load_extern_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -9513,14 +9515,14 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { .indirect, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, .air_ref, => unreachable, .register_pair, .load_frame => null, - .memory, .load_got, .load_actual_got, .load_direct, .load_tlv => src: { + .memory, .load_got, .load_extern_got, .load_direct, .load_tlv => src: { switch (resolved_src_mcv) { .memory => |addr| if (math.cast( i32, @@ -9529,7 +9531,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { i32, @as(i64, @bitCast(addr)) + abi_size - 8, ) != null) break :src null, - .load_got, .load_actual_got, .load_direct, .load_tlv => {}, + .load_got, .load_extern_got, .load_direct, .load_tlv => {}, else => unreachable, } @@ -9948,7 +9950,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -9975,7 +9977,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC .memory, .load_got, - .load_actual_got, + .load_extern_got, .load_direct, .load_tlv, => { @@ -10533,7 +10535,7 @@ fn airAsm(self: *Self, inst: Air.Inst.Index) !void { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |_| break :arg input_mcv, .indirect, .load_frame => break :arg input_mcv, - .load_direct, .load_got, .load_actual_got, .load_tlv => {}, + .load_direct, .load_got, .load_extern_got, .load_tlv => {}, else => { const temp_mcv = try self.allocTempRegOrMem(ty, false); try self.genCopy(ty, temp_mcv, input_mcv); @@ -11194,7 +11196,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError .register_overflow, .lea_direct, .lea_got, - .lea_actual_got, + .lea_extern_got, .lea_tlv, .lea_frame, .reserved_frame, @@ -11246,11 +11248,11 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError } }, .indirect => |reg_off| try self.genSetMem(.{ .reg = reg_off.reg }, reg_off.off, ty, src_mcv), - .memory, .load_direct, .load_got, .load_actual_got, .load_tlv => { + .memory, .load_direct, .load_got, .load_extern_got, .load_tlv => { switch (dst_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| return self.genSetMem(.{ .reg = .ds }, small_addr, ty, src_mcv), - .load_direct, .load_got, .load_actual_got, .load_tlv => {}, + .load_direct, .load_got, .load_extern_got, .load_tlv => {}, else => unreachable, } @@ -11412,7 +11414,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr else => unreachable, }, )), - .memory, .load_direct, .load_got, .load_actual_got, .load_tlv => { + .memory, .load_direct, .load_got, .load_extern_got, .load_tlv => { switch (src_mcv) { .memory => |addr| if (math.cast(i32, @as(i64, @bitCast(addr)))) |small_addr| return (try self.moveStrategy( @@ -11440,7 +11442,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr }, .Float, .Vector => {}, }, - .load_got, .load_actual_got, .load_tlv => {}, + .load_got, .load_extern_got, .load_tlv => {}, else => unreachable, } @@ -11454,18 +11456,18 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr Memory.sib(Memory.PtrSize.fromSize(abi_size), .{ .base = .{ .reg = addr_reg } }), ); }, - .lea_direct, .lea_got, .lea_actual_got => |sym_index| { + .lea_direct, .lea_got, .lea_extern_got => |sym_index| { const atom_index = try self.owner.getSymbolIndex(self); _ = try self.addInst(.{ .tag = switch (src_mcv) { .lea_direct => .lea, - .lea_got, .lea_actual_got => .mov, + .lea_got, .lea_extern_got => .mov, else => unreachable, }, .ops = switch (src_mcv) { .lea_direct => .direct_reloc, .lea_got => .got_reloc, - .lea_actual_got => .actual_got_reloc, + .lea_extern_got => .extern_got_reloc, else => unreachable, }, .data = .{ .rx = .{ @@ -11601,8 +11603,8 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal .lea_direct, .load_got, .lea_got, - .load_actual_got, - .lea_actual_got, + .load_extern_got, + .lea_extern_got, .load_tlv, .lea_tlv, .load_frame, @@ -13608,7 +13610,7 @@ fn genTypedValue(self: *Self, arg_tv: TypedValue) InnerError!MCValue { .memory => |addr| .{ .memory = addr }, .load_direct => |sym_index| .{ .load_direct = sym_index }, .load_got => |sym_index| .{ .lea_got = sym_index }, - .load_actual_got => |sym_index| .{ .lea_actual_got = sym_index }, + .load_extern_got => |sym_index| .{ .lea_extern_got = sym_index }, .load_tlv => |sym_index| .{ .lea_tlv = sym_index }, }, .fail => |msg| { diff --git a/src/arch/x86_64/Emit.zig b/src/arch/x86_64/Emit.zig index 9c0c48121f..e03b0f01b5 100644 --- a/src/arch/x86_64/Emit.zig +++ b/src/arch/x86_64/Emit.zig @@ -79,7 +79,7 @@ pub fn emitMir(emit: *Emit) Error!void { @tagName(emit.bin_file.tag), }), .linker_got, - .linker_actual_got, + .linker_extern_got, .linker_direct, .linker_direct_got, .linker_import, @@ -88,13 +88,13 @@ pub fn emitMir(emit: *Emit) Error!void { const r_type: u32 = switch (lowered_relocs[0].target) { .linker_direct_got => link.File.Elf.R_X86_64_ZIG_GOT32, .linker_got => link.File.Elf.R_X86_64_ZIG_GOTPCREL, - .linker_actual_got => std.elf.R_X86_64_GOTPCREL, + .linker_extern_got => std.elf.R_X86_64_GOTPCREL, .linker_direct => std.elf.R_X86_64_PC32, else => unreachable, }; const r_addend: i64 = switch (lowered_relocs[0].target) { .linker_direct_got => 0, - .linker_got, .linker_actual_got, .linker_direct => -4, + .linker_got, .linker_extern_got, .linker_direct => -4, else => unreachable, }; const atom_ptr = elf_file.symbol(symbol.atom_index).atom(elf_file).?; diff --git a/src/arch/x86_64/Lower.zig b/src/arch/x86_64/Lower.zig index f8091e5476..ae5f86d6b0 100644 --- a/src/arch/x86_64/Lower.zig +++ b/src/arch/x86_64/Lower.zig @@ -51,7 +51,7 @@ pub const Reloc = struct { inst: Mir.Inst.Index, linker_extern_fn: Mir.Reloc, linker_got: Mir.Reloc, - linker_actual_got: Mir.Reloc, + linker_extern_got: Mir.Reloc, linker_direct: Mir.Reloc, linker_direct_got: Mir.Reloc, linker_import: Mir.Reloc, @@ -389,7 +389,7 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void { .rrmi_sib, .rrmi_rip => inst.data.rrix.fixes, .mi_sib_u, .mi_rip_u, .mi_sib_s, .mi_rip_s => inst.data.x.fixes, .m_sib, .m_rip, .rax_moffs, .moffs_rax => inst.data.x.fixes, - .extern_fn_reloc, .got_reloc, .actual_got_reloc, .direct_reloc, .direct_got_reloc, .import_reloc, .tlv_reloc => ._, + .extern_fn_reloc, .got_reloc, .extern_got_reloc, .direct_reloc, .direct_got_reloc, .import_reloc, .tlv_reloc => ._, else => return lower.fail("TODO lower .{s}", .{@tagName(inst.ops)}), }; try lower.emit(switch (fixes) { @@ -533,12 +533,12 @@ fn generic(lower: *Lower, inst: Mir.Inst) Error!void { else => unreachable, } }, - .got_reloc, .actual_got_reloc, .direct_reloc, .import_reloc, .tlv_reloc => ops: { + .got_reloc, .extern_got_reloc, .direct_reloc, .import_reloc, .tlv_reloc => ops: { const reg = inst.data.rx.r1; const extra = lower.mir.extraData(Mir.Reloc, inst.data.rx.payload).data; _ = lower.reloc(switch (inst.ops) { .got_reloc => .{ .linker_got = extra }, - .actual_got_reloc => .{ .linker_actual_got = extra }, + .extern_got_reloc => .{ .linker_extern_got = extra }, .direct_reloc => .{ .linker_direct = extra }, .import_reloc => .{ .linker_import = extra }, .tlv_reloc => .{ .linker_tlv = extra }, diff --git a/src/arch/x86_64/Mir.zig b/src/arch/x86_64/Mir.zig index 1e159d5a16..0e2a4cca6d 100644 --- a/src/arch/x86_64/Mir.zig +++ b/src/arch/x86_64/Mir.zig @@ -783,8 +783,9 @@ pub const Inst = struct { /// Linker relocation - GOT indirection. /// Uses `rx` payload with extra data of type `Reloc`. got_reloc, - /// TODO - actual_got_reloc, + /// Linker relocation - reference to an extern variable via GOT. + /// Uses `rx` payload with extra data of type `Reloc`. + extern_got_reloc, /// Linker relocation - direct reference. /// Uses `rx` payload with extra data of type `Reloc`. direct_reloc, diff --git a/src/codegen.zig b/src/codegen.zig index 54ed9c0cf5..24269f38ba 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -793,12 +793,13 @@ fn lowerDeclRef( /// Helper struct to denote that the value is in memory but requires a linker relocation fixup: /// * got - the value is referenced indirectly via GOT entry index (the linker emits a got-type reloc) +/// * extern_got - pointer to extern variable referenced via GOT /// * direct - the value is referenced directly via symbol index index (the linker emits a displacement reloc) /// * import - the value is referenced indirectly via import entry index (the linker emits an import-type reloc) pub const LinkerLoad = struct { type: enum { got, - actual_got, + extern_got, direct, import, }, @@ -828,8 +829,8 @@ pub const GenResult = union(enum) { load_got: u32, /// Direct by-address reference to memory location. memory: u64, - /// TODO LOL Jakub, the king of naming... - load_actual_got: u32, + /// Pointer to extern variable via GOT. + load_extern_got: u32, }; fn mcv(val: MCValue) GenResult { @@ -898,7 +899,7 @@ fn genDeclRef( mod.intern_pool.stringToSliceUnwrap(ov.lib_name) else null; - return GenResult.mcv(.{ .load_actual_got = try elf_file.getGlobalSymbol(name, lib_name) }); + return GenResult.mcv(.{ .load_extern_got = try elf_file.getGlobalSymbol(name, lib_name) }); } const sym_index = try elf_file.getOrCreateMetadataForDecl(decl_index); const sym = elf_file.symbol(sym_index); -- cgit v1.2.3