authorgravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2024-08-22 16:30:17-04:00
committergravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2024-08-22 20:08:05-04:00
log0a5291435513727a9f19570008388364f391b0d2
tree5dd347b79f82eb2faf01624f74bb0992de488b5c
parent17171cdb073b940d01eafbc07e989f5c1adf843f

Elf: all dwarf relocs need to become linker relocs


1 files changed, 61 insertions(+), 5 deletions(-)

src/link/Elf/ZigObject.zig+61-5
...@@ -169,7 +169,6 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi...@@ -169,7 +169,6 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi
169 if (self.dwarf) |*dwarf| {169 if (self.dwarf) |*dwarf| {
170 const pt: Zcu.PerThread = .{ .zcu = elf_file.base.comp.module.?, .tid = tid };170 const pt: Zcu.PerThread = .{ .zcu = elf_file.base.comp.module.?, .tid = tid };
171 try dwarf.flushModule(pt);171 try dwarf.flushModule(pt);
172 try dwarf.resolveRelocs();
173172
174 const gpa = elf_file.base.comp.gpa;173 const gpa = elf_file.base.comp.gpa;
175 const cpu_arch = elf_file.getTarget().cpu.arch;174 const cpu_arch = elf_file.getTarget().cpu.arch;
...@@ -209,7 +208,28 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi...@@ -209,7 +208,28 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi
209208
210 const relocs = &self.relocs.items[atom_ptr.relocsShndx().?];209 const relocs = &self.relocs.items[atom_ptr.relocsShndx().?];
211 for (sect.units.items) |*unit| {210 for (sect.units.items) |*unit| {
212 try relocs.ensureUnusedCapacity(gpa, unit.cross_section_relocs.items.len);211 try relocs.ensureUnusedCapacity(gpa, unit.cross_unit_relocs.items.len +
212 unit.cross_section_relocs.items.len);
213 for (unit.cross_unit_relocs.items) |reloc| {
214 const target_unit = sect.getUnit(reloc.target_unit);
215 const r_offset = unit.off + reloc.source_off;
216 const r_addend: i64 = @intCast(target_unit.off + reloc.target_off + (if (reloc.target_entry.unwrap()) |target_entry|
217 target_unit.header_len + target_unit.getEntry(target_entry).assertNonEmpty(unit, sect, dwarf).off
218 else
219 0));
220 const r_type = relocation.dwarf.crossSectionRelocType(dwarf.format, cpu_arch);
221 log.debug(" {s} <- r_off={x}, r_add={x}, r_type={}", .{
222 self.symbol(sym_index).name(elf_file),
223 r_offset,
224 r_addend,
225 relocation.fmtRelocType(r_type, cpu_arch),
226 });
227 atom_ptr.addRelocAssumeCapacity(.{
228 .r_offset = r_offset,
229 .r_addend = r_addend,
230 .r_info = (@as(u64, @intCast(sym_index)) << 32) | r_type,
231 }, self);
232 }
213 for (unit.cross_section_relocs.items) |reloc| {233 for (unit.cross_section_relocs.items) |reloc| {
214 const target_sym_index = switch (reloc.target_sec) {234 const target_sym_index = switch (reloc.target_sec) {
215 .debug_abbrev => self.debug_abbrev_index.?,235 .debug_abbrev => self.debug_abbrev_index.?,
...@@ -246,7 +266,45 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi...@@ -246,7 +266,45 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi
246 for (unit.entries.items) |*entry| {266 for (unit.entries.items) |*entry| {
247 const entry_off = unit.off + unit.header_len + entry.off;267 const entry_off = unit.off + unit.header_len + entry.off;
248268
249 try relocs.ensureUnusedCapacity(gpa, entry.cross_section_relocs.items.len);269 try relocs.ensureUnusedCapacity(gpa, entry.cross_entry_relocs.items.len +
270 entry.cross_unit_relocs.items.len + entry.cross_section_relocs.items.len +
271 entry.external_relocs.items.len);
272 for (entry.cross_entry_relocs.items) |reloc| {
273 const r_offset = entry_off + reloc.source_off;
274 const r_addend: i64 = @intCast(unit.off + reloc.target_off + unit.header_len + unit.getEntry(reloc.target_entry).assertNonEmpty(unit, sect, dwarf).off);
275 const r_type = relocation.dwarf.crossSectionRelocType(dwarf.format, cpu_arch);
276 log.debug(" {s} <- r_off={x}, r_add={x}, r_type={}", .{
277 self.symbol(sym_index).name(elf_file),
278 r_offset,
279 r_addend,
280 relocation.fmtRelocType(r_type, cpu_arch),
281 });
282 atom_ptr.addRelocAssumeCapacity(.{
283 .r_offset = r_offset,
284 .r_addend = r_addend,
285 .r_info = (@as(u64, @intCast(sym_index)) << 32) | r_type,
286 }, self);
287 }
288 for (entry.cross_unit_relocs.items) |reloc| {
289 const target_unit = sect.getUnit(reloc.target_unit);
290 const r_offset = entry_off + reloc.source_off;
291 const r_addend: i64 = @intCast(target_unit.off + reloc.target_off + (if (reloc.target_entry.unwrap()) |target_entry|
292 target_unit.header_len + target_unit.getEntry(target_entry).assertNonEmpty(unit, sect, dwarf).off
293 else
294 0));
295 const r_type = relocation.dwarf.crossSectionRelocType(dwarf.format, cpu_arch);
296 log.debug(" {s} <- r_off={x}, r_add={x}, r_type={}", .{
297 self.symbol(sym_index).name(elf_file),
298 r_offset,
299 r_addend,
300 relocation.fmtRelocType(r_type, cpu_arch),
301 });
302 atom_ptr.addRelocAssumeCapacity(.{
303 .r_offset = r_offset,
304 .r_addend = r_addend,
305 .r_info = (@as(u64, @intCast(sym_index)) << 32) | r_type,
306 }, self);
307 }
250 for (entry.cross_section_relocs.items) |reloc| {308 for (entry.cross_section_relocs.items) |reloc| {
251 const target_sym_index = switch (reloc.target_sec) {309 const target_sym_index = switch (reloc.target_sec) {
252 .debug_abbrev => self.debug_abbrev_index.?,310 .debug_abbrev => self.debug_abbrev_index.?,
...@@ -279,8 +337,6 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi...@@ -279,8 +337,6 @@ pub fn flushModule(self: *ZigObject, elf_file: *Elf, tid: Zcu.PerThread.Id) !voi
279 .r_info = (@as(u64, @intCast(target_sym_index)) << 32) | r_type,337 .r_info = (@as(u64, @intCast(target_sym_index)) << 32) | r_type,
280 }, self);338 }, self);
281 }339 }
282
283 try relocs.ensureUnusedCapacity(gpa, entry.external_relocs.items.len);
284 for (entry.external_relocs.items) |reloc| {340 for (entry.external_relocs.items) |reloc| {
285 const target_sym = self.symbol(reloc.target_sym);341 const target_sym = self.symbol(reloc.target_sym);
286 const r_offset = entry_off + reloc.source_off;342 const r_offset = entry_off + reloc.source_off;