authorgravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2026-07-06 17:21:00+02:00
committergravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2026-07-09 10:49:18+02:00
logf7c11ea389faa3184355af75ebc4f261359f2ab9
treec7beb097e87f0a869d7c4871774ab2329e484065
parent001d7ed757cf67ed955bfdb15d46cc57949c6ecb
signaturebadge-check Signed by SSH key SHA256:7B/LJ7bpR1eX8aCXSr4mtd5M45VMPKcx9zY8e95b5QM

Elf2: implement some sparc-specific GOT relocations


1 files changed, 62 insertions(+), 2 deletions(-)

src/link/Elf2.zig+62-2
......@@ -779,10 +779,10 @@ const GotReloc = struct {
779779 };
780780
781781 const Type = enum(u8) {
782 offset64,
783782 offset32,
784 rel64,
783 offset64,
785784 rel32,
785 rel64,
786786
787787 larch_rel32_hi20,
788788 larch_rel64_lo20,
......@@ -791,6 +791,12 @@ const GotReloc = struct {
791791 larch_abs32_hi20,
792792 larch_abs64_lo20,
793793 larch_abs64_hi12,
794
795 sparc_10,
796 sparc_13,
797 sparc_22,
798 sparc_op_hix22,
799 sparc_op_lox10,
794800 };
795801
796802 const Index = enum(u32) {
......@@ -895,6 +901,37 @@ const GotReloc = struct {
895901 const target_value = got_vaddr +% got_offset +% addend;
896902 link.loongarch.writeK12(dest_slice[0..4], @truncate(target_value >> 52));
897903 },
904
905 .sparc_10 => {
906 const dest_ptr: *link.sparc.reloc.Simm13 = @ptrCast(@alignCast(dest_slice));
907 var result = elf.targetLoad(dest_ptr);
908 result.simm13 = @as(u10, @truncate(got_offset));
909 elf.targetStore(dest_ptr, result);
910 },
911 .sparc_13 => {
912 const dest_ptr: *link.sparc.reloc.Simm13 = @ptrCast(@alignCast(dest_slice));
913 var result = elf.targetLoad(dest_ptr);
914 result.simm13 = @truncate(got_offset);
915 elf.targetStore(dest_ptr, result);
916 },
917 .sparc_22 => {
918 const dest_ptr: *link.sparc.reloc.Simm22 = @ptrCast(@alignCast(dest_slice));
919 var result = elf.targetLoad(dest_ptr);
920 result.simm22 = @truncate(got_offset >> 10);
921 elf.targetStore(dest_ptr, result);
922 },
923 .sparc_op_hix22 => {
924 const dest_ptr: *link.sparc.reloc.Imm22 = @ptrCast(@alignCast(dest_slice));
925 var result = elf.targetLoad(dest_ptr);
926 result.imm22 = @truncate(got_offset >> 10);
927 elf.targetStore(dest_ptr, result);
928 },
929 .sparc_op_lox10 => {
930 const dest_ptr: *link.sparc.reloc.Imm13 = @ptrCast(@alignCast(dest_slice));
931 var result = elf.targetLoad(dest_ptr);
932 result.imm13 = @as(u10, @truncate(got_offset));
933 elf.targetStore(dest_ptr, result);
934 },
898935 }
899936 }
900937};
......@@ -6067,6 +6104,29 @@ fn addRelocAssumeCapacity(
60676104 .GOT64_LO20 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .larch_abs64_lo20),
60686105 .GOT64_HI12 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .larch_abs64_hi12),
60696106 },
6107 .SPARCV9 => switch (@"type".SPARC) {
6108 else => std.debug.panic("TODO: unsupported input relocation, {t}", .{@"type".SPARC}),
6109
6110 _,
6111 .NONE,
6112 .COPY,
6113 .JMP_SLOT,
6114 .RELATIVE,
6115 .IRELATIVE,
6116 => std.debug.panic("TODO: error for illegal or unsupported input relocation, {t}", .{@"type".SPARC}),
6117
6118 // Relocations targeting a GOT entry
6119 .GOT10 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .sparc_10),
6120 .GOT13 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .sparc_13),
6121 .GOT22 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .sparc_22),
6122 // These need similar handling to `R_X86_64_GOTOFF64`. No compiler seems to emit them though.
6123 .GOTDATA_HIX22 => @panic("TODO: R_SPARC_GOTDATA_HIX22"),
6124 .GOTDATA_LOX10 => @panic("TODO: R_SPARC_GOTDATA_LOX10"),
6125 .GOTDATA_OP_HIX22 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .sparc_op_hix22),
6126 .GOTDATA_OP_LOX10 => elf.addGotRelocAssumeCapacity(node, offset, .{ .symbol = target }, addend, .sparc_op_lox10),
6127 // We currently do no relaxation, so nothing to do for this one.
6128 .GOTDATA_OP => {},
6129 },
60706130 },
60716131 }
60726132}