authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2021-07-02 11:58:28+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2021-07-15 18:49:46+02:00
log980f2915fa15ab35029e8f3cab21d309811f6e30
tree8e0bafb88c9c250ec7ffda25f5474a4ce92e1a62
parentee6e25bc13b3f23b5f2fd0c8b57f0d115c239fc2

zld: use index to symbol in reloc

instead of pointer to the Symbol struct in the hope that we can overwrite the Symbol in the object's symbol table with the resolved Symbol later down the line.

5 files changed, 29 insertions(+), 34 deletions(-)

src/link/MachO/Object.zig+2-2
......@@ -377,7 +377,6 @@ pub fn parseSections(self: *Object) !void {
377377 self.arch.?,
378378 section.code,
379379 mem.bytesAsSlice(macho.relocation_info, raw_relocs),
380 self.symbols.items,
381380 );
382381 }
383382
......@@ -395,7 +394,8 @@ pub fn parseInitializers(self: *Object) !void {
395394 const relocs = section.relocs orelse unreachable;
396395 try self.initializers.ensureCapacity(self.allocator, relocs.len);
397396 for (relocs) |rel| {
398 self.initializers.appendAssumeCapacity(rel.target.symbol);
397 const sym = self.symbols.items[rel.target.symbol];
398 self.initializers.appendAssumeCapacity(sym);
399399 }
400400
401401 mem.reverse(*Symbol, self.initializers.items);
src/link/MachO/Zld.zig+9-7
......@@ -1172,7 +1172,7 @@ fn allocateProxyBindAddresses(self: *Zld) !void {
11721172 if (rel.@"type" != .unsigned) continue; // GOT is currently special-cased
11731173 if (rel.target != .symbol) continue;
11741174
1175 const sym = rel.target.symbol.getTopmostAlias();
1175 const sym = object.symbols.items[rel.target.symbol].getTopmostAlias();
11761176 if (sym.cast(Symbol.Proxy)) |proxy| {
11771177 const target_map = sect.target_map orelse continue;
11781178 const target_seg = self.load_commands.items[target_map.segment_id].Segment;
......@@ -1670,7 +1670,7 @@ fn resolveStubsAndGotEntries(self: *Zld) !void {
16701670 switch (rel.@"type") {
16711671 .unsigned => continue,
16721672 .got_page, .got_page_off, .got_load, .got, .pointer_to_got => {
1673 const sym = rel.target.symbol.getTopmostAlias();
1673 const sym = object.symbols.items[rel.target.symbol].getTopmostAlias();
16741674 if (sym.got_index != null) continue;
16751675
16761676 const index = @intCast(u32, self.got_entries.items.len);
......@@ -1682,7 +1682,7 @@ fn resolveStubsAndGotEntries(self: *Zld) !void {
16821682 else => {
16831683 if (rel.target != .symbol) continue;
16841684
1685 const sym = rel.target.symbol.getTopmostAlias();
1685 const sym = object.symbols.items[rel.target.symbol].getTopmostAlias();
16861686 assert(sym.@"type" != .unresolved);
16871687
16881688 if (sym.stubs_index != null) continue;
......@@ -1781,7 +1781,7 @@ fn resolveRelocsAndWriteSections(self: *Zld) !void {
17811781 break :rebase false;
17821782 }
17831783 if (rel.target == .symbol) {
1784 const final = rel.target.symbol.getTopmostAlias();
1784 const final = object.symbols.items[rel.target.symbol].getTopmostAlias();
17851785 if (final.cast(Symbol.Proxy)) |_| {
17861786 break :rebase false;
17871787 }
......@@ -1801,7 +1801,7 @@ fn resolveRelocsAndWriteSections(self: *Zld) !void {
18011801 // Calculate the offset to the initializer.
18021802 if (flags == macho.S_THREAD_LOCAL_VARIABLES) tlv: {
18031803 // TODO we don't want to save offset to tlv_bootstrap
1804 if (mem.eql(u8, rel.target.symbol.name, "__tlv_bootstrap")) break :tlv;
1804 if (mem.eql(u8, object.symbols.items[rel.target.symbol].name, "__tlv_bootstrap")) break :tlv;
18051805
18061806 const base_addr = blk: {
18071807 if (self.tlv_data_section_index) |index| {
......@@ -1823,7 +1823,8 @@ fn resolveRelocsAndWriteSections(self: *Zld) !void {
18231823 .got_page, .got_page_off, .got_load, .got, .pointer_to_got => {
18241824 const dc_seg = self.load_commands.items[self.data_const_segment_cmd_index.?].Segment;
18251825 const got = dc_seg.sections.items[self.got_section_index.?];
1826 const final = rel.target.symbol.getTopmostAlias();
1826 const sym = object.symbols.items[rel.target.symbol];
1827 const final = sym.getTopmostAlias();
18271828 const got_index = final.got_index orelse {
18281829 log.err("expected GOT index relocating symbol '{s}'", .{final.name});
18291830 log.err("this is an internal linker error", .{});
......@@ -1879,7 +1880,8 @@ fn resolveRelocsAndWriteSections(self: *Zld) !void {
18791880fn relocTargetAddr(self: *Zld, object: *const Object, target: reloc.Relocation.Target) !u64 {
18801881 const target_addr = blk: {
18811882 switch (target) {
1882 .symbol => |sym| {
1883 .symbol => |sym_id| {
1884 const sym = object.symbols.items[sym_id];
18831885 const final = sym.getTopmostAlias();
18841886 if (final.cast(Symbol.Regular)) |reg| {
18851887 log.debug(" | regular '{s}'", .{sym.name});
src/link/MachO/reloc.zig+3-7
......@@ -10,7 +10,6 @@ const aarch64 = @import("reloc/aarch64.zig");
1010const x86_64 = @import("reloc/x86_64.zig");
1111
1212const Allocator = mem.Allocator;
13const Symbol = @import("Symbol.zig");
1413
1514pub const Relocation = struct {
1615 @"type": Type,
......@@ -81,12 +80,12 @@ pub const Relocation = struct {
8180 };
8281
8382 pub const Target = union(enum) {
84 symbol: *Symbol,
83 symbol: u32,
8584 section: u16,
8685
87 pub fn from_reloc(reloc: macho.relocation_info, symbols: []*Symbol) Target {
86 pub fn fromReloc(reloc: macho.relocation_info) Target {
8887 return if (reloc.r_extern == 1) .{
89 .symbol = symbols[reloc.r_symbolnum],
88 .symbol = reloc.r_symbolnum,
9089 } else .{
9190 .section = @intCast(u16, reloc.r_symbolnum - 1),
9291 };
......@@ -142,7 +141,6 @@ pub fn parse(
142141 arch: std.Target.Cpu.Arch,
143142 code: []u8,
144143 relocs: []const macho.relocation_info,
145 symbols: []*Symbol,
146144) ![]*Relocation {
147145 var it = RelocIterator{
148146 .buffer = relocs,
......@@ -155,7 +153,6 @@ pub fn parse(
155153 .it = &it,
156154 .code = code,
157155 .parsed = std.ArrayList(*Relocation).init(allocator),
158 .symbols = symbols,
159156 };
160157 defer parser.deinit();
161158 try parser.parse();
......@@ -168,7 +165,6 @@ pub fn parse(
168165 .it = &it,
169166 .code = code,
170167 .parsed = std.ArrayList(*Relocation).init(allocator),
171 .symbols = symbols,
172168 };
173169 defer parser.deinit();
174170 try parser.parse();
src/link/MachO/reloc/aarch64.zig+8-9
......@@ -203,7 +203,6 @@ pub const Parser = struct {
203203 it: *reloc.RelocIterator,
204204 code: []u8,
205205 parsed: std.ArrayList(*Relocation),
206 symbols: []*Symbol,
207206 addend: ?u32 = null,
208207 subtractor: ?Relocation.Target = null,
209208
......@@ -287,7 +286,7 @@ pub const Parser = struct {
287286 var branch = try parser.allocator.create(Branch);
288287 errdefer parser.allocator.destroy(branch);
289288
290 const target = Relocation.Target.from_reloc(rel, parser.symbols);
289 const target = Relocation.Target.fromReloc(rel);
291290
292291 branch.* = .{
293292 .base = .{
......@@ -308,7 +307,7 @@ pub const Parser = struct {
308307 assert(rel.r_length == 2);
309308
310309 const rel_type = @intToEnum(macho.reloc_type_arm64, rel.r_type);
311 const target = Relocation.Target.from_reloc(rel, parser.symbols);
310 const target = Relocation.Target.fromReloc(rel);
312311
313312 const offset = @intCast(u32, rel.r_address);
314313 const inst = parser.code[offset..][0..4];
......@@ -414,7 +413,7 @@ pub const Parser = struct {
414413 aarch64.Instruction.load_store_register,
415414 ), inst) };
416415 }
417 const target = Relocation.Target.from_reloc(rel, parser.symbols);
416 const target = Relocation.Target.fromReloc(rel);
418417
419418 var page_off = try parser.allocator.create(PageOff);
420419 errdefer parser.allocator.destroy(page_off);
......@@ -451,7 +450,7 @@ pub const Parser = struct {
451450 ), inst);
452451 assert(parsed_inst.size == 3);
453452
454 const target = Relocation.Target.from_reloc(rel, parser.symbols);
453 const target = Relocation.Target.fromReloc(rel);
455454
456455 var page_off = try parser.allocator.create(GotPageOff);
457456 errdefer parser.allocator.destroy(page_off);
......@@ -510,7 +509,7 @@ pub const Parser = struct {
510509 }
511510 };
512511
513 const target = Relocation.Target.from_reloc(rel, parser.symbols);
512 const target = Relocation.Target.fromReloc(rel);
514513
515514 var page_off = try parser.allocator.create(TlvpPageOff);
516515 errdefer parser.allocator.destroy(page_off);
......@@ -545,7 +544,7 @@ pub const Parser = struct {
545544 assert(rel.r_pcrel == 0);
546545 assert(parser.subtractor == null);
547546
548 parser.subtractor = Relocation.Target.from_reloc(rel, parser.symbols);
547 parser.subtractor = Relocation.Target.fromReloc(rel);
549548
550549 // Verify SUBTRACTOR is followed by UNSIGNED.
551550 const next = @intToEnum(macho.reloc_type_arm64, parser.it.peek().r_type);
......@@ -568,7 +567,7 @@ pub const Parser = struct {
568567 var unsigned = try parser.allocator.create(reloc.Unsigned);
569568 errdefer parser.allocator.destroy(unsigned);
570569
571 const target = Relocation.Target.from_reloc(rel, parser.symbols);
570 const target = Relocation.Target.fromReloc(rel);
572571 const is_64bit: bool = switch (rel.r_length) {
573572 3 => true,
574573 2 => false,
......@@ -605,7 +604,7 @@ pub const Parser = struct {
605604 var ptr_to_got = try parser.allocator.create(PointerToGot);
606605 errdefer parser.allocator.destroy(ptr_to_got);
607606
608 const target = Relocation.Target.from_reloc(rel, parser.symbols);
607 const target = Relocation.Target.fromReloc(rel);
609608 const offset = @intCast(u32, rel.r_address);
610609
611610 ptr_to_got.* = .{
src/link/MachO/reloc/x86_64.zig+7-9
......@@ -9,7 +9,6 @@ const reloc = @import("../reloc.zig");
99
1010const Allocator = mem.Allocator;
1111const Relocation = reloc.Relocation;
12const Symbol = @import("../Symbol.zig");
1312
1413pub const Branch = struct {
1514 base: Relocation,
......@@ -103,7 +102,6 @@ pub const Parser = struct {
103102 it: *reloc.RelocIterator,
104103 code: []u8,
105104 parsed: std.ArrayList(*Relocation),
106 symbols: []*Symbol,
107105 subtractor: ?Relocation.Target = null,
108106
109107 pub fn deinit(parser: *Parser) void {
......@@ -154,7 +152,7 @@ pub const Parser = struct {
154152 var branch = try parser.allocator.create(Branch);
155153 errdefer parser.allocator.destroy(branch);
156154
157 const target = Relocation.Target.from_reloc(rel, parser.symbols);
155 const target = Relocation.Target.fromReloc(rel);
158156
159157 branch.* = .{
160158 .base = .{
......@@ -174,7 +172,7 @@ pub const Parser = struct {
174172 assert(rel.r_length == 2);
175173
176174 const rel_type = @intToEnum(macho.reloc_type_x86_64, rel.r_type);
177 const target = Relocation.Target.from_reloc(rel, parser.symbols);
175 const target = Relocation.Target.fromReloc(rel);
178176
179177 const offset = @intCast(u32, rel.r_address);
180178 const inst = parser.code[offset..][0..4];
......@@ -213,7 +211,7 @@ pub const Parser = struct {
213211
214212 const offset = @intCast(u32, rel.r_address);
215213 const inst = parser.code[offset..][0..4];
216 const target = Relocation.Target.from_reloc(rel, parser.symbols);
214 const target = Relocation.Target.fromReloc(rel);
217215
218216 var got_load = try parser.allocator.create(GotLoad);
219217 errdefer parser.allocator.destroy(got_load);
......@@ -239,7 +237,7 @@ pub const Parser = struct {
239237
240238 const offset = @intCast(u32, rel.r_address);
241239 const inst = parser.code[offset..][0..4];
242 const target = Relocation.Target.from_reloc(rel, parser.symbols);
240 const target = Relocation.Target.fromReloc(rel);
243241 const addend = mem.readIntLittle(i32, inst);
244242
245243 var got = try parser.allocator.create(Got);
......@@ -267,7 +265,7 @@ pub const Parser = struct {
267265
268266 const offset = @intCast(u32, rel.r_address);
269267 const inst = parser.code[offset..][0..4];
270 const target = Relocation.Target.from_reloc(rel, parser.symbols);
268 const target = Relocation.Target.fromReloc(rel);
271269
272270 var tlv = try parser.allocator.create(Tlv);
273271 errdefer parser.allocator.destroy(tlv);
......@@ -292,7 +290,7 @@ pub const Parser = struct {
292290 assert(rel.r_pcrel == 0);
293291 assert(parser.subtractor == null);
294292
295 parser.subtractor = Relocation.Target.from_reloc(rel, parser.symbols);
293 parser.subtractor = Relocation.Target.fromReloc(rel);
296294
297295 // Verify SUBTRACTOR is followed by UNSIGNED.
298296 const next = @intToEnum(macho.reloc_type_x86_64, parser.it.peek().r_type);
......@@ -315,7 +313,7 @@ pub const Parser = struct {
315313 var unsigned = try parser.allocator.create(reloc.Unsigned);
316314 errdefer parser.allocator.destroy(unsigned);
317315
318 const target = Relocation.Target.from_reloc(rel, parser.symbols);
316 const target = Relocation.Target.fromReloc(rel);
319317 const is_64bit: bool = switch (rel.r_length) {
320318 3 => true,
321319 2 => false,