diff options
| author | Jakub Konka <kubkon@jakubkonka.com> | 2024-08-15 10:21:20 +0200 |
|---|---|---|
| committer | Jakub Konka <kubkon@jakubkonka.com> | 2024-08-15 10:21:20 +0200 |
| commit | 0fd0b11bc43a6053c68f649e1e1a1e23b995a266 (patch) | |
| tree | 2826a6066d838f456b3cc537aa199e9f11e9a8fe /src | |
| parent | 8a0cb7002e6b8f7b50fdf7ee40311ce93fbef009 (diff) | |
| download | zig-0fd0b11bc43a6053c68f649e1e1a1e23b995a266.tar.gz zig-0fd0b11bc43a6053c68f649e1e1a1e23b995a266.zip | |
riscv: do not emit GOT relocations for special linker symbols
Diffstat (limited to 'src')
| -rw-r--r-- | src/arch/riscv64/Emit.zig | 15 | ||||
| -rw-r--r-- | src/codegen.zig | 2 | ||||
| -rw-r--r-- | src/link/Elf.zig | 27 | ||||
| -rw-r--r-- | src/link/Elf/Atom.zig | 25 | ||||
| -rw-r--r-- | src/link/Elf/relocation.zig | 14 |
5 files changed, 17 insertions, 66 deletions
diff --git a/src/arch/riscv64/Emit.zig b/src/arch/riscv64/Emit.zig index c1e7565c0b..8b32f1e580 100644 --- a/src/arch/riscv64/Emit.zig +++ b/src/arch/riscv64/Emit.zig @@ -49,14 +49,17 @@ pub fn emitMir(emit: *Emit) Error!void { const atom_ptr = zo.symbol(symbol.atom_index).atom(elf_file).?; const sym = zo.symbol(symbol.sym_index); - var hi_r_type: u32 = @intFromEnum(std.elf.R_RISCV.HI20); - var lo_r_type: u32 = @intFromEnum(std.elf.R_RISCV.LO12_I); - - if (sym.flags.needs_got) { - hi_r_type = Elf.R_GOT_HI20_STATIC; // TODO: rework this #20887 - lo_r_type = Elf.R_GOT_LO12_I_STATIC; // TODO: rework this #20887 + if (sym.flags.is_extern_ptr) blk: { + const name = sym.name(elf_file); + if (mem.eql(u8, "__init_array_start", name) or mem.eql(u8, "__init_array_end", name) or + mem.eql(u8, "__fini_array_start", name) or mem.eql(u8, "__fini_array_end", name)) + break :blk; + return emit.fail("emit GOT relocation for symbol '{s}'", .{name}); } + const hi_r_type: u32 = @intFromEnum(std.elf.R_RISCV.HI20); + const lo_r_type: u32 = @intFromEnum(std.elf.R_RISCV.LO12_I); + try atom_ptr.addReloc(elf_file, .{ .r_offset = start_offset, .r_info = (@as(u64, @intCast(symbol.sym_index)) << 32) | hi_r_type, diff --git a/src/codegen.zig b/src/codegen.zig index 3df7ce37ab..89b4a8a291 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -900,7 +900,7 @@ fn genNavRef( if (is_extern) { const sym_index = try elf_file.getGlobalSymbol(name.toSlice(ip), lib_name.toSlice(ip)); zo.symbol(sym_index).flags.is_extern_ptr = true; - return GenResult.mcv(.{ .load_symbol = sym_index }); + return GenResult.mcv(.{ .lea_symbol = sym_index }); } const sym_index = try zo.getOrCreateMetadataForNav(elf_file, nav_index); if (!single_threaded and is_threadlocal) { diff --git a/src/link/Elf.zig b/src/link/Elf.zig index 3dcfb0bc6a..0ef1e9862d 100644 --- a/src/link/Elf.zig +++ b/src/link/Elf.zig @@ -5934,33 +5934,6 @@ const RelaSection = struct { }; const RelaSectionTable = std.AutoArrayHashMapUnmanaged(u32, RelaSection); -pub const R_GOT_HI20_STATIC: u32 = 0xff04; -pub const R_GOT_LO12_I_STATIC: u32 = 0xff05; - -// Comptime asserts that no Zig relocs overlap with another ISA's reloc number -comptime { - const zig_relocs = .{ - R_GOT_HI20_STATIC, - R_GOT_LO12_I_STATIC, - }; - - const other_relocs = .{ - elf.R_X86_64, - elf.R_AARCH64, - elf.R_RISCV, - elf.R_PPC64, - }; - - @setEvalBranchQuota(@min(other_relocs.len * zig_relocs.len * 256, 6200)); - for (other_relocs) |relocs| { - for (@typeInfo(relocs).Enum.fields) |reloc| { - for (zig_relocs) |zig_reloc| { - assert(reloc.value != zig_reloc); - } - } - } -} - fn defaultEntrySymbolName(cpu_arch: std.Target.Cpu.Arch) []const u8 { return switch (cpu_arch) { .mips, .mipsel, .mips64, .mips64el => "__start", diff --git a/src/link/Elf/Atom.zig b/src/link/Elf/Atom.zig index 47bb216080..c214b07914 100644 --- a/src/link/Elf/Atom.zig +++ b/src/link/Elf/Atom.zig @@ -1978,13 +1978,7 @@ const riscv = struct { .SUB32, => {}, - else => |x| switch (@intFromEnum(x)) { - Elf.R_GOT_HI20_STATIC, - Elf.R_GOT_LO12_I_STATIC, - => symbol.flags.needs_got = true, - - else => try atom.reportUnhandledRelocError(rel, elf_file), - }, + else => try atom.reportUnhandledRelocError(rel, elf_file), } } @@ -2121,22 +2115,7 @@ const riscv = struct { // TODO: annotates an ADD instruction that can be removed when TPREL is relaxed }, - else => |x| switch (@intFromEnum(x)) { - // Zig custom relocations - Elf.R_GOT_HI20_STATIC => { - assert(target.flags.has_got); - const disp: u32 = @bitCast(math.cast(i32, G + GOT + A) orelse return error.Overflow); - riscv_util.writeInstU(code[r_offset..][0..4], disp); - }, - - Elf.R_GOT_LO12_I_STATIC => { - assert(target.flags.has_got); - const disp: u32 = @bitCast(math.cast(i32, G + GOT + A) orelse return error.Overflow); - riscv_util.writeInstI(code[r_offset..][0..4], disp); - }, - - else => try atom.reportUnhandledRelocError(rel, elf_file), - }, + else => try atom.reportUnhandledRelocError(rel, elf_file), } } diff --git a/src/link/Elf/relocation.zig b/src/link/Elf/relocation.zig index 887aece8bc..e1a317f67d 100644 --- a/src/link/Elf/relocation.zig +++ b/src/link/Elf/relocation.zig @@ -112,15 +112,11 @@ fn formatRelocType( _ = unused_fmt_string; _ = options; const r_type = ctx.r_type; - switch (r_type) { - Elf.R_GOT_HI20_STATIC => try writer.writeAll("R_GOT_HI20_STATIC"), - Elf.R_GOT_LO12_I_STATIC => try writer.writeAll("R_GOT_LO12_I_STATIC"), - else => switch (ctx.cpu_arch) { - .x86_64 => try writer.print("R_X86_64_{s}", .{@tagName(@as(elf.R_X86_64, @enumFromInt(r_type)))}), - .aarch64 => try writer.print("R_AARCH64_{s}", .{@tagName(@as(elf.R_AARCH64, @enumFromInt(r_type)))}), - .riscv64 => try writer.print("R_RISCV_{s}", .{@tagName(@as(elf.R_RISCV, @enumFromInt(r_type)))}), - else => unreachable, - }, + switch (ctx.cpu_arch) { + .x86_64 => try writer.print("R_X86_64_{s}", .{@tagName(@as(elf.R_X86_64, @enumFromInt(r_type)))}), + .aarch64 => try writer.print("R_AARCH64_{s}", .{@tagName(@as(elf.R_AARCH64, @enumFromInt(r_type)))}), + .riscv64 => try writer.print("R_RISCV_{s}", .{@tagName(@as(elf.R_RISCV, @enumFromInt(r_type)))}), + else => unreachable, } } |
