authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2024-08-23 10:20:53+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2024-08-25 10:20:15+02:00
log7173ea1a152e0b546f158cbfec017d81b3665047
tree8f50eefa54b4ffb7ad9838d4299c469a68c09dce
parent95c30fb4864ddde2f8d8da7fc64f6f90baa42325

elf: simplify output section symbol tracking


4 files changed, 27 insertions(+), 52 deletions(-)

src/link/Elf.zig+24-45
...@@ -4013,7 +4013,7 @@ pub fn updateSymtabSize(self: *Elf) !void {...@@ -4013,7 +4013,7 @@ pub fn updateSymtabSize(self: *Elf) !void {
4013 nlocals += @intCast(self.sections.slice().len);4013 nlocals += @intCast(self.sections.slice().len);
40144014
4015 if (self.requiresThunks()) for (self.thunks.items) |*th| {4015 if (self.requiresThunks()) for (self.thunks.items) |*th| {
4016 th.output_symtab_ctx.ilocal = nlocals + 1;4016 th.output_symtab_ctx.ilocal = nlocals;
4017 th.calcSymtabSize(self);4017 th.calcSymtabSize(self);
4018 nlocals += th.output_symtab_ctx.nlocals;4018 nlocals += th.output_symtab_ctx.nlocals;
4019 strsize += th.output_symtab_ctx.strsize;4019 strsize += th.output_symtab_ctx.strsize;
...@@ -4024,8 +4024,8 @@ pub fn updateSymtabSize(self: *Elf) !void {...@@ -4024,8 +4024,8 @@ pub fn updateSymtabSize(self: *Elf) !void {
4024 const ctx = switch (file_ptr) {4024 const ctx = switch (file_ptr) {
4025 inline else => |x| &x.output_symtab_ctx,4025 inline else => |x| &x.output_symtab_ctx,
4026 };4026 };
4027 ctx.ilocal = nlocals + 1;4027 ctx.ilocal = nlocals;
4028 ctx.iglobal = nglobals + 1;4028 ctx.iglobal = nglobals;
4029 try file_ptr.updateSymtabSize(self);4029 try file_ptr.updateSymtabSize(self);
4030 nlocals += ctx.nlocals;4030 nlocals += ctx.nlocals;
4031 nglobals += ctx.nglobals;4031 nglobals += ctx.nglobals;
...@@ -4033,21 +4033,21 @@ pub fn updateSymtabSize(self: *Elf) !void {...@@ -4033,21 +4033,21 @@ pub fn updateSymtabSize(self: *Elf) !void {
4033 }4033 }
40344034
4035 if (self.got_section_index) |_| {4035 if (self.got_section_index) |_| {
4036 self.got.output_symtab_ctx.ilocal = nlocals + 1;4036 self.got.output_symtab_ctx.ilocal = nlocals;
4037 self.got.updateSymtabSize(self);4037 self.got.updateSymtabSize(self);
4038 nlocals += self.got.output_symtab_ctx.nlocals;4038 nlocals += self.got.output_symtab_ctx.nlocals;
4039 strsize += self.got.output_symtab_ctx.strsize;4039 strsize += self.got.output_symtab_ctx.strsize;
4040 }4040 }
40414041
4042 if (self.plt_section_index) |_| {4042 if (self.plt_section_index) |_| {
4043 self.plt.output_symtab_ctx.ilocal = nlocals + 1;4043 self.plt.output_symtab_ctx.ilocal = nlocals;
4044 self.plt.updateSymtabSize(self);4044 self.plt.updateSymtabSize(self);
4045 nlocals += self.plt.output_symtab_ctx.nlocals;4045 nlocals += self.plt.output_symtab_ctx.nlocals;
4046 strsize += self.plt.output_symtab_ctx.strsize;4046 strsize += self.plt.output_symtab_ctx.strsize;
4047 }4047 }
40484048
4049 if (self.plt_got_section_index) |_| {4049 if (self.plt_got_section_index) |_| {
4050 self.plt_got.output_symtab_ctx.ilocal = nlocals + 1;4050 self.plt_got.output_symtab_ctx.ilocal = nlocals;
4051 self.plt_got.updateSymtabSize(self);4051 self.plt_got.updateSymtabSize(self);
4052 nlocals += self.plt_got.output_symtab_ctx.nlocals;4052 nlocals += self.plt_got.output_symtab_ctx.nlocals;
4053 strsize += self.plt_got.output_symtab_ctx.strsize;4053 strsize += self.plt_got.output_symtab_ctx.strsize;
...@@ -4063,14 +4063,14 @@ pub fn updateSymtabSize(self: *Elf) !void {...@@ -4063,14 +4063,14 @@ pub fn updateSymtabSize(self: *Elf) !void {
40634063
4064 const slice = self.sections.slice();4064 const slice = self.sections.slice();
4065 const symtab_shdr = &slice.items(.shdr)[self.symtab_section_index.?];4065 const symtab_shdr = &slice.items(.shdr)[self.symtab_section_index.?];
4066 symtab_shdr.sh_info = nlocals + 1;4066 symtab_shdr.sh_info = nlocals;
4067 symtab_shdr.sh_link = self.strtab_section_index.?;4067 symtab_shdr.sh_link = self.strtab_section_index.?;
40684068
4069 const sym_size: u64 = switch (self.ptr_width) {4069 const sym_size: u64 = switch (self.ptr_width) {
4070 .p32 => @sizeOf(elf.Elf32_Sym),4070 .p32 => @sizeOf(elf.Elf32_Sym),
4071 .p64 => @sizeOf(elf.Elf64_Sym),4071 .p64 => @sizeOf(elf.Elf64_Sym),
4072 };4072 };
4073 const needed_size = (nlocals + nglobals + 1) * sym_size;4073 const needed_size = (nlocals + nglobals) * sym_size;
4074 symtab_shdr.sh_size = needed_size;4074 symtab_shdr.sh_size = needed_size;
40754075
4076 const strtab = &slice.items(.shdr)[self.strtab_section_index.?];4076 const strtab = &slice.items(.shdr)[self.strtab_section_index.?];
...@@ -4243,7 +4243,17 @@ pub fn writeSymtab(self: *Elf) !void {...@@ -4243,7 +4243,17 @@ pub fn writeSymtab(self: *Elf) !void {
4243 const needed_strtab_size = math.cast(usize, strtab_shdr.sh_size - 1) orelse return error.Overflow;4243 const needed_strtab_size = math.cast(usize, strtab_shdr.sh_size - 1) orelse return error.Overflow;
4244 try self.strtab.ensureUnusedCapacity(gpa, needed_strtab_size);4244 try self.strtab.ensureUnusedCapacity(gpa, needed_strtab_size);
42454245
4246 self.writeSectionSymbols();4246 for (slice.items(.shdr), 0..) |shdr, shndx| {
4247 const out_sym = &self.symtab.items[shndx];
4248 out_sym.* = .{
4249 .st_name = 0,
4250 .st_value = shdr.sh_addr,
4251 .st_info = if (shdr.sh_type == elf.SHT_NULL) elf.STT_NOTYPE else elf.STT_SECTION,
4252 .st_shndx = @intCast(shndx),
4253 .st_size = 0,
4254 .st_other = 0,
4255 };
4256 }
42474257
4248 if (self.requiresThunks()) for (self.thunks.items) |th| {4258 if (self.requiresThunks()) for (self.thunks.items) |th| {
4249 th.writeSymtab(self);4259 th.writeSymtab(self);
...@@ -4309,42 +4319,6 @@ pub fn writeSymtab(self: *Elf) !void {...@@ -4309,42 +4319,6 @@ pub fn writeSymtab(self: *Elf) !void {
4309 try self.base.file.?.pwriteAll(self.strtab.items, strtab_shdr.sh_offset);4319 try self.base.file.?.pwriteAll(self.strtab.items, strtab_shdr.sh_offset);
4310}4320}
43114321
4312fn writeSectionSymbols(self: *Elf) void {
4313 const slice = self.sections.slice();
4314 var ilocal: u32 = 1;
4315 for (slice.items(.shdr), 0..) |shdr, shndx| {
4316 const out_sym = &self.symtab.items[ilocal];
4317 out_sym.* = .{
4318 .st_name = 0,
4319 .st_value = shdr.sh_addr,
4320 .st_info = elf.STT_SECTION,
4321 .st_shndx = @intCast(shndx),
4322 .st_size = 0,
4323 .st_other = 0,
4324 };
4325 ilocal += 1;
4326 }
4327
4328 if (self.eh_frame_section_index) |shndx| {
4329 const shdr = slice.items(.shdr)[shndx];
4330 const out_sym = &self.symtab.items[ilocal];
4331 out_sym.* = .{
4332 .st_name = 0,
4333 .st_value = shdr.sh_addr,
4334 .st_info = elf.STT_SECTION,
4335 .st_shndx = @intCast(shndx),
4336 .st_size = 0,
4337 .st_other = 0,
4338 };
4339 ilocal += 1;
4340 }
4341}
4342
4343pub fn sectionSymbolOutputSymtabIndex(self: Elf, shndx: u32) u32 {
4344 _ = self;
4345 return shndx + 1;
4346}
4347
4348/// Always 4 or 8 depending on whether this is 32-bit ELF or 64-bit ELF.4322/// Always 4 or 8 depending on whether this is 32-bit ELF or 64-bit ELF.
4349pub fn ptrWidthBytes(self: Elf) u8 {4323pub fn ptrWidthBytes(self: Elf) u8 {
4350 return switch (self.ptr_width) {4324 return switch (self.ptr_width) {
...@@ -5535,8 +5509,13 @@ pub const SymbolResolver = struct {...@@ -5535,8 +5509,13 @@ pub const SymbolResolver = struct {
5535};5509};
55365510
5537const Section = struct {5511const Section = struct {
5512 /// Section header.
5538 shdr: elf.Elf64_Shdr,5513 shdr: elf.Elf64_Shdr,
5514
5515 /// Assigned program header index if any.
5539 phndx: ?u32 = null,5516 phndx: ?u32 = null,
5517
5518 /// List of atoms contributing to this section.
5540 atom_list: std.ArrayListUnmanaged(Ref) = .{},5519 atom_list: std.ArrayListUnmanaged(Ref) = .{},
55415520
5542 /// Index of the last allocated atom in this section.5521 /// Index of the last allocated atom in this section.
src/link/Elf/Atom.zig+1-4
...@@ -336,10 +336,7 @@ pub fn writeRelocs(self: Atom, elf_file: *Elf, out_relocs: *std.ArrayList(elf.El...@@ -336,10 +336,7 @@ pub fn writeRelocs(self: Atom, elf_file: *Elf, out_relocs: *std.ArrayList(elf.El
336 switch (target.type(elf_file)) {336 switch (target.type(elf_file)) {
337 elf.STT_SECTION => {337 elf.STT_SECTION => {
338 r_addend += @intCast(target.address(.{}, elf_file));338 r_addend += @intCast(target.address(.{}, elf_file));
339 r_sym = if (target.outputShndx(elf_file)) |osec|339 r_sym = target.outputShndx(elf_file) orelse 0;
340 elf_file.sectionSymbolOutputSymtabIndex(osec)
341 else
342 0;
343 },340 },
344 else => {341 else => {
345 r_sym = target.outputSymtabIndex(elf_file) orelse 0;342 r_sym = target.outputSymtabIndex(elf_file) orelse 0;
src/link/Elf/eh_frame.zig+1-1
...@@ -425,7 +425,7 @@ fn emitReloc(elf_file: *Elf, rec: anytype, sym: *const Symbol, rel: elf.Elf64_Re...@@ -425,7 +425,7 @@ fn emitReloc(elf_file: *Elf, rec: anytype, sym: *const Symbol, rel: elf.Elf64_Re
425 switch (sym.type(elf_file)) {425 switch (sym.type(elf_file)) {
426 elf.STT_SECTION => {426 elf.STT_SECTION => {
427 r_addend += @intCast(sym.address(.{}, elf_file));427 r_addend += @intCast(sym.address(.{}, elf_file));
428 r_sym = elf_file.sectionSymbolOutputSymtabIndex(sym.outputShndx(elf_file).?);428 r_sym = sym.outputShndx(elf_file).?;
429 },429 },
430 else => {430 else => {
431 r_sym = sym.outputSymtabIndex(elf_file) orelse 0;431 r_sym = sym.outputSymtabIndex(elf_file) orelse 0;
src/link/Elf/relocatable.zig+1-2
...@@ -393,8 +393,7 @@ fn updateComdatGroupsSizes(elf_file: *Elf) void {...@@ -393,8 +393,7 @@ fn updateComdatGroupsSizes(elf_file: *Elf) void {
393 shdr.sh_link = elf_file.symtab_section_index.?;393 shdr.sh_link = elf_file.symtab_section_index.?;
394394
395 const sym = cg.symbol(elf_file);395 const sym = cg.symbol(elf_file);
396 shdr.sh_info = sym.outputSymtabIndex(elf_file) orelse396 shdr.sh_info = sym.outputSymtabIndex(elf_file) orelse sym.outputShndx(elf_file).?;
397 elf_file.sectionSymbolOutputSymtabIndex(sym.outputShndx(elf_file).?);
398 }397 }
399}398}
400399