From 8ba31ed39a84ba00e85c456e74d0ea4d682d86c0 Mon Sep 17 00:00:00 2001 From: Jakub Konka Date: Wed, 21 Feb 2024 22:47:52 +0100 Subject: [PATCH] elf: sort input relocs if targeting riscv64 --- src/link/Elf/Object.zig | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/src/link/Elf/Object.zig b/src/link/Elf/Object.zig index 92485ae20b..31b31f0578 100644 --- a/src/link/Elf/Object.zig +++ b/src/link/Elf/Object.zig @@ -245,6 +245,9 @@ fn initAtoms(self: *Object, allocator: Allocator, handle: std.fs.File, elf_file: atom.rel_index = @intCast(self.relocs.items.len); atom.rel_num = @intCast(relocs.len); try self.relocs.appendUnalignedSlice(allocator, relocs); + if (elf_file.getTarget().cpu.arch == .riscv64) { + sortRelocs(self.relocs.items[atom.rel_index..][0..atom.rel_num]); + } } }, else => {}, @@ -381,12 +384,15 @@ fn parseEhFrame(self: *Object, allocator: Allocator, handle: std.fs.File, shndx: defer allocator.free(relocs); const rel_start = @as(u32, @intCast(self.relocs.items.len)); try self.relocs.appendUnalignedSlice(allocator, relocs); + if (elf_file.getTarget().cpu.arch == .riscv64) { + sortRelocs(self.relocs.items[rel_start..][0..relocs.len]); + } const fdes_start = self.fdes.items.len; const cies_start = self.cies.items.len; var it = eh_frame.Iterator{ .data = raw }; while (try it.next()) |rec| { - const rel_range = filterRelocs(relocs, rec.offset, rec.size + 4); + const rel_range = filterRelocs(self.relocs.items[rel_start..][0..relocs.len], rec.offset, rec.size + 4); switch (rec.tag) { .cie => try self.cies.append(allocator, .{ .offset = data_start + rec.offset, @@ -449,8 +455,18 @@ fn parseEhFrame(self: *Object, allocator: Allocator, handle: std.fs.File, shndx: } } +fn sortRelocs(relocs: []elf.Elf64_Rela) void { + const sortFn = struct { + fn lessThan(c: void, lhs: elf.Elf64_Rela, rhs: elf.Elf64_Rela) bool { + _ = c; + return lhs.r_offset < rhs.r_offset; + } + }.lessThan; + mem.sort(elf.Elf64_Rela, relocs, {}, sortFn); +} + fn filterRelocs( - relocs: []align(1) const elf.Elf64_Rela, + relocs: []const elf.Elf64_Rela, start: u64, len: u64, ) struct { start: u64, len: u64 } {