authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2024-04-15 21:50:45+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2024-04-20 23:36:41+02:00
logd5fdb7315f2f5742c58af547909437401651ffd5
treebd9f8e9f3947e83b0c20230d00f79000c2f8fb19
parent700644d35dd674c7381c4794d566e0e64f45c174

link/elf: port macho symbol extras handling


6 files changed, 42 insertions(+), 65 deletions(-)

src/link/Elf/LinkerDefined.zig+2-2
...@@ -60,10 +60,10 @@ pub fn updateSymtabSize(self: *LinkerDefined, elf_file: *Elf) !void {...@@ -60,10 +60,10 @@ pub fn updateSymtabSize(self: *LinkerDefined, elf_file: *Elf) !void {
60 if (file_ptr.index() != self.index) continue;60 if (file_ptr.index() != self.index) continue;
61 global.flags.output_symtab = true;61 global.flags.output_symtab = true;
62 if (global.isLocal(elf_file)) {62 if (global.isLocal(elf_file)) {
63 try global.setOutputSymtabIndex(self.output_symtab_ctx.nlocals, elf_file);63 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nlocals }, elf_file);
64 self.output_symtab_ctx.nlocals += 1;64 self.output_symtab_ctx.nlocals += 1;
65 } else {65 } else {
66 try global.setOutputSymtabIndex(self.output_symtab_ctx.nglobals, elf_file);66 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nglobals }, elf_file);
67 self.output_symtab_ctx.nglobals += 1;67 self.output_symtab_ctx.nglobals += 1;
68 }68 }
69 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;69 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;
src/link/Elf/Object.zig+3-3
...@@ -853,7 +853,7 @@ pub fn updateSymtabSize(self: *Object, elf_file: *Elf) !void {...@@ -853,7 +853,7 @@ pub fn updateSymtabSize(self: *Object, elf_file: *Elf) !void {
853 else => {},853 else => {},
854 }854 }
855 local.flags.output_symtab = true;855 local.flags.output_symtab = true;
856 try local.setOutputSymtabIndex(self.output_symtab_ctx.nlocals, elf_file);856 try local.addExtra(.{ .symtab = self.output_symtab_ctx.nlocals }, elf_file);
857 self.output_symtab_ctx.nlocals += 1;857 self.output_symtab_ctx.nlocals += 1;
858 self.output_symtab_ctx.strsize += @as(u32, @intCast(local.name(elf_file).len)) + 1;858 self.output_symtab_ctx.strsize += @as(u32, @intCast(local.name(elf_file).len)) + 1;
859 }859 }
...@@ -865,10 +865,10 @@ pub fn updateSymtabSize(self: *Object, elf_file: *Elf) !void {...@@ -865,10 +865,10 @@ pub fn updateSymtabSize(self: *Object, elf_file: *Elf) !void {
865 if (global.atom(elf_file)) |atom| if (!atom.flags.alive) continue;865 if (global.atom(elf_file)) |atom| if (!atom.flags.alive) continue;
866 global.flags.output_symtab = true;866 global.flags.output_symtab = true;
867 if (global.isLocal(elf_file)) {867 if (global.isLocal(elf_file)) {
868 try global.setOutputSymtabIndex(self.output_symtab_ctx.nlocals, elf_file);868 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nlocals }, elf_file);
869 self.output_symtab_ctx.nlocals += 1;869 self.output_symtab_ctx.nlocals += 1;
870 } else {870 } else {
871 try global.setOutputSymtabIndex(self.output_symtab_ctx.nglobals, elf_file);871 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nglobals }, elf_file);
872 self.output_symtab_ctx.nglobals += 1;872 self.output_symtab_ctx.nglobals += 1;
873 }873 }
874 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;874 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;
src/link/Elf/SharedObject.zig+1-1
...@@ -269,7 +269,7 @@ pub fn updateSymtabSize(self: *SharedObject, elf_file: *Elf) !void {...@@ -269,7 +269,7 @@ pub fn updateSymtabSize(self: *SharedObject, elf_file: *Elf) !void {
269 if (file_ptr.index() != self.index) continue;269 if (file_ptr.index() != self.index) continue;
270 if (global.isLocal(elf_file)) continue;270 if (global.isLocal(elf_file)) continue;
271 global.flags.output_symtab = true;271 global.flags.output_symtab = true;
272 try global.setOutputSymtabIndex(self.output_symtab_ctx.nglobals, elf_file);272 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nglobals }, elf_file);
273 self.output_symtab_ctx.nglobals += 1;273 self.output_symtab_ctx.nglobals += 1;
274 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;274 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;
275 }275 }
src/link/Elf/Symbol.zig+24-10
...@@ -143,14 +143,6 @@ pub fn outputSymtabIndex(symbol: Symbol, elf_file: *Elf) ?u32 {...@@ -143,14 +143,6 @@ pub fn outputSymtabIndex(symbol: Symbol, elf_file: *Elf) ?u32 {
143 return if (symbol.isLocal(elf_file)) idx + symtab_ctx.ilocal else idx + symtab_ctx.iglobal;143 return if (symbol.isLocal(elf_file)) idx + symtab_ctx.ilocal else idx + symtab_ctx.iglobal;
144}144}
145145
146pub fn setOutputSymtabIndex(symbol: *Symbol, index: u32, elf_file: *Elf) !void {
147 if (symbol.extra(elf_file)) |extras| {
148 var new_extras = extras;
149 new_extras.symtab = index;
150 symbol.setExtra(new_extras, elf_file);
151 } else try symbol.addExtra(.{ .symtab = index }, elf_file);
152}
153
154pub fn gotAddress(symbol: Symbol, elf_file: *Elf) u64 {146pub fn gotAddress(symbol: Symbol, elf_file: *Elf) u64 {
155 if (!symbol.flags.has_got) return 0;147 if (!symbol.flags.has_got) return 0;
156 const extras = symbol.extra(elf_file).?;148 const extras = symbol.extra(elf_file).?;
...@@ -240,8 +232,30 @@ pub fn dsoAlignment(symbol: Symbol, elf_file: *Elf) !u64 {...@@ -240,8 +232,30 @@ pub fn dsoAlignment(symbol: Symbol, elf_file: *Elf) !u64 {
240 @min(alignment, try std.math.powi(u64, 2, @ctz(esym.st_value)));232 @min(alignment, try std.math.powi(u64, 2, @ctz(esym.st_value)));
241}233}
242234
243pub fn addExtra(symbol: *Symbol, extras: Extra, elf_file: *Elf) !void {235const AddExtraOpts = struct {
244 symbol.extra_index = try elf_file.addSymbolExtra(extras);236 got: ?u32 = null,
237 plt: ?u32 = null,
238 plt_got: ?u32 = null,
239 dynamic: ?u32 = null,
240 symtab: ?u32 = null,
241 copy_rel: ?u32 = null,
242 tlsgd: ?u32 = null,
243 gottp: ?u32 = null,
244 tlsdesc: ?u32 = null,
245 zig_got: ?u32 = null,
246};
247
248pub fn addExtra(symbol: *Symbol, opts: AddExtraOpts, elf_file: *Elf) !void {
249 if (symbol.extra(elf_file) == null) {
250 symbol.extra_index = try elf_file.addSymbolExtra(.{});
251 }
252 var extras = symbol.extra(elf_file).?;
253 inline for (@typeInfo(@TypeOf(opts)).Struct.fields) |field| {
254 if (@field(opts, field.name)) |x| {
255 @field(extras, field.name) = x;
256 }
257 }
258 symbol.setExtra(extras, elf_file);
245}259}
246260
247pub fn extra(symbol: Symbol, elf_file: *Elf) ?Extra {261pub fn extra(symbol: Symbol, elf_file: *Elf) ?Extra {
src/link/Elf/ZigObject.zig+3-3
...@@ -566,7 +566,7 @@ pub fn updateSymtabSize(self: *ZigObject, elf_file: *Elf) !void {...@@ -566,7 +566,7 @@ pub fn updateSymtabSize(self: *ZigObject, elf_file: *Elf) !void {
566 else => {},566 else => {},
567 }567 }
568 local.flags.output_symtab = true;568 local.flags.output_symtab = true;
569 try local.setOutputSymtabIndex(self.output_symtab_ctx.nlocals, elf_file);569 try local.addExtra(.{ .symtab = self.output_symtab_ctx.nlocals }, elf_file);
570 self.output_symtab_ctx.nlocals += 1;570 self.output_symtab_ctx.nlocals += 1;
571 self.output_symtab_ctx.strsize += @as(u32, @intCast(local.name(elf_file).len)) + 1;571 self.output_symtab_ctx.strsize += @as(u32, @intCast(local.name(elf_file).len)) + 1;
572 }572 }
...@@ -578,10 +578,10 @@ pub fn updateSymtabSize(self: *ZigObject, elf_file: *Elf) !void {...@@ -578,10 +578,10 @@ pub fn updateSymtabSize(self: *ZigObject, elf_file: *Elf) !void {
578 if (global.atom(elf_file)) |atom| if (!atom.flags.alive) continue;578 if (global.atom(elf_file)) |atom| if (!atom.flags.alive) continue;
579 global.flags.output_symtab = true;579 global.flags.output_symtab = true;
580 if (global.isLocal(elf_file)) {580 if (global.isLocal(elf_file)) {
581 try global.setOutputSymtabIndex(self.output_symtab_ctx.nlocals, elf_file);581 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nlocals }, elf_file);
582 self.output_symtab_ctx.nlocals += 1;582 self.output_symtab_ctx.nlocals += 1;
583 } else {583 } else {
584 try global.setOutputSymtabIndex(self.output_symtab_ctx.nglobals, elf_file);584 try global.addExtra(.{ .symtab = self.output_symtab_ctx.nglobals }, elf_file);
585 self.output_symtab_ctx.nglobals += 1;585 self.output_symtab_ctx.nglobals += 1;
586 }586 }
587 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;587 self.output_symtab_ctx.strsize += @as(u32, @intCast(global.name(elf_file).len)) + 1;
src/link/Elf/synthetic_sections.zig+9-46
...@@ -259,11 +259,7 @@ pub const ZigGotSection = struct {...@@ -259,11 +259,7 @@ pub const ZigGotSection = struct {
259 if (elf_file.isEffectivelyDynLib() or (elf_file.base.isExe() and comp.config.pie)) {259 if (elf_file.isEffectivelyDynLib() or (elf_file.base.isExe() and comp.config.pie)) {
260 zig_got.flags.needs_rela = true;260 zig_got.flags.needs_rela = true;
261 }261 }
262 if (symbol.extra(elf_file)) |extra| {262 try symbol.addExtra(.{ .zig_got = index }, elf_file);
263 var new_extra = extra;
264 new_extra.zig_got = index;
265 symbol.setExtra(new_extra, elf_file);
266 } else try symbol.addExtra(.{ .zig_got = index }, elf_file);
267 return index;263 return index;
268 }264 }
269265
...@@ -499,11 +495,7 @@ pub const GotSection = struct {...@@ -499,11 +495,7 @@ pub const GotSection = struct {
499 {495 {
500 got.flags.needs_rela = true;496 got.flags.needs_rela = true;
501 }497 }
502 if (symbol.extra(elf_file)) |extra| {498 try symbol.addExtra(.{ .got = index }, elf_file);
503 var new_extra = extra;
504 new_extra.got = index;
505 symbol.setExtra(new_extra, elf_file);
506 } else try symbol.addExtra(.{ .got = index }, elf_file);
507 return index;499 return index;
508 }500 }
509501
...@@ -529,11 +521,7 @@ pub const GotSection = struct {...@@ -529,11 +521,7 @@ pub const GotSection = struct {
529 const symbol = elf_file.symbol(sym_index);521 const symbol = elf_file.symbol(sym_index);
530 symbol.flags.has_tlsgd = true;522 symbol.flags.has_tlsgd = true;
531 if (symbol.flags.import or elf_file.isEffectivelyDynLib()) got.flags.needs_rela = true;523 if (symbol.flags.import or elf_file.isEffectivelyDynLib()) got.flags.needs_rela = true;
532 if (symbol.extra(elf_file)) |extra| {524 try symbol.addExtra(.{ .tlsgd = index }, elf_file);
533 var new_extra = extra;
534 new_extra.tlsgd = index;
535 symbol.setExtra(new_extra, elf_file);
536 } else try symbol.addExtra(.{ .tlsgd = index }, elf_file);
537 }525 }
538526
539 pub fn addGotTpSymbol(got: *GotSection, sym_index: Symbol.Index, elf_file: *Elf) !void {527 pub fn addGotTpSymbol(got: *GotSection, sym_index: Symbol.Index, elf_file: *Elf) !void {
...@@ -546,11 +534,7 @@ pub const GotSection = struct {...@@ -546,11 +534,7 @@ pub const GotSection = struct {
546 const symbol = elf_file.symbol(sym_index);534 const symbol = elf_file.symbol(sym_index);
547 symbol.flags.has_gottp = true;535 symbol.flags.has_gottp = true;
548 if (symbol.flags.import or elf_file.isEffectivelyDynLib()) got.flags.needs_rela = true;536 if (symbol.flags.import or elf_file.isEffectivelyDynLib()) got.flags.needs_rela = true;
549 if (symbol.extra(elf_file)) |extra| {537 try symbol.addExtra(.{ .gottp = index }, elf_file);
550 var new_extra = extra;
551 new_extra.gottp = index;
552 symbol.setExtra(new_extra, elf_file);
553 } else try symbol.addExtra(.{ .gottp = index }, elf_file);
554 }538 }
555539
556 pub fn addTlsDescSymbol(got: *GotSection, sym_index: Symbol.Index, elf_file: *Elf) !void {540 pub fn addTlsDescSymbol(got: *GotSection, sym_index: Symbol.Index, elf_file: *Elf) !void {
...@@ -563,11 +547,7 @@ pub const GotSection = struct {...@@ -563,11 +547,7 @@ pub const GotSection = struct {
563 const symbol = elf_file.symbol(sym_index);547 const symbol = elf_file.symbol(sym_index);
564 symbol.flags.has_tlsdesc = true;548 symbol.flags.has_tlsdesc = true;
565 got.flags.needs_rela = true;549 got.flags.needs_rela = true;
566 if (symbol.extra(elf_file)) |extra| {550 try symbol.addExtra(.{ .tlsdesc = index }, elf_file);
567 var new_extra = extra;
568 new_extra.tlsdesc = index;
569 symbol.setExtra(new_extra, elf_file);
570 } else try symbol.addExtra(.{ .tlsdesc = index }, elf_file);
571 }551 }
572552
573 pub fn size(got: GotSection, elf_file: *Elf) usize {553 pub fn size(got: GotSection, elf_file: *Elf) usize {
...@@ -877,11 +857,7 @@ pub const PltSection = struct {...@@ -877,11 +857,7 @@ pub const PltSection = struct {
877 const index = @as(u32, @intCast(plt.symbols.items.len));857 const index = @as(u32, @intCast(plt.symbols.items.len));
878 const symbol = elf_file.symbol(sym_index);858 const symbol = elf_file.symbol(sym_index);
879 symbol.flags.has_plt = true;859 symbol.flags.has_plt = true;
880 if (symbol.extra(elf_file)) |extra| {860 try symbol.addExtra(.{ .plt = index }, elf_file);
881 var new_extra = extra;
882 new_extra.plt = index;
883 symbol.setExtra(new_extra, elf_file);
884 } else try symbol.addExtra(.{ .plt = index }, elf_file);
885 try plt.symbols.append(gpa, sym_index);861 try plt.symbols.append(gpa, sym_index);
886 }862 }
887863
...@@ -1132,11 +1108,7 @@ pub const PltGotSection = struct {...@@ -1132,11 +1108,7 @@ pub const PltGotSection = struct {
1132 const symbol = elf_file.symbol(sym_index);1108 const symbol = elf_file.symbol(sym_index);
1133 symbol.flags.has_plt = true;1109 symbol.flags.has_plt = true;
1134 symbol.flags.has_got = true;1110 symbol.flags.has_got = true;
1135 if (symbol.extra(elf_file)) |extra| {1111 try symbol.addExtra(.{ .plt_got = index }, elf_file);
1136 var new_extra = extra;
1137 new_extra.plt_got = index;
1138 symbol.setExtra(new_extra, elf_file);
1139 } else try symbol.addExtra(.{ .plt_got = index }, elf_file);
1140 try plt_got.symbols.append(gpa, sym_index);1112 try plt_got.symbols.append(gpa, sym_index);
1141 }1113 }
11421114
...@@ -1248,12 +1220,7 @@ pub const CopyRelSection = struct {...@@ -1248,12 +1220,7 @@ pub const CopyRelSection = struct {
1248 symbol.flags.@"export" = true;1220 symbol.flags.@"export" = true;
1249 symbol.flags.has_copy_rel = true;1221 symbol.flags.has_copy_rel = true;
1250 symbol.flags.weak = false;1222 symbol.flags.weak = false;
12511223 try symbol.addExtra(.{ .copy_rel = index }, elf_file);
1252 if (symbol.extra(elf_file)) |extra| {
1253 var new_extra = extra;
1254 new_extra.copy_rel = index;
1255 symbol.setExtra(new_extra, elf_file);
1256 } else try symbol.addExtra(.{ .copy_rel = index }, elf_file);
1257 try copy_rel.symbols.append(gpa, sym_index);1224 try copy_rel.symbols.append(gpa, sym_index);
12581225
1259 const shared_object = symbol.file(elf_file).?.shared_object;1226 const shared_object = symbol.file(elf_file).?.shared_object;
...@@ -1335,11 +1302,7 @@ pub const DynsymSection = struct {...@@ -1335,11 +1302,7 @@ pub const DynsymSection = struct {
1335 const index = @as(u32, @intCast(dynsym.entries.items.len + 1));1302 const index = @as(u32, @intCast(dynsym.entries.items.len + 1));
1336 const sym = elf_file.symbol(sym_index);1303 const sym = elf_file.symbol(sym_index);
1337 sym.flags.has_dynamic = true;1304 sym.flags.has_dynamic = true;
1338 if (sym.extra(elf_file)) |extra| {1305 try sym.addExtra(.{ .dynamic = index }, elf_file);
1339 var new_extra = extra;
1340 new_extra.dynamic = index;
1341 sym.setExtra(new_extra, elf_file);
1342 } else try sym.addExtra(.{ .dynamic = index }, elf_file);
1343 const off = try elf_file.insertDynString(sym.name(elf_file));1306 const off = try elf_file.insertDynString(sym.name(elf_file));
1344 try dynsym.entries.append(gpa, .{ .symbol_index = sym_index, .off = off });1307 try dynsym.entries.append(gpa, .{ .symbol_index = sym_index, .off = off });
1345 }1308 }