Commit 05e221796a
Changed files (2)
src
link
src/link/MachO/DebugSymbols.zig
@@ -148,6 +148,40 @@ fn allocateSection(self: *DebugSymbols, sectname: []const u8, size: u64, alignme
return index;
}
+pub fn growSection(self: *DebugSymbols, sect_index: u8, needed_size: u32) !void {
+ const sect = self.getSectionPtr(sect_index);
+
+ if (needed_size > self.allocatedSize(sect.offset)) {
+ const new_offset = self.findFreeSpace(needed_size, 1);
+
+ log.debug("moving {s} section: {} bytes from 0x{x} to 0x{x}", .{
+ sect.sectName(),
+ sect.size,
+ sect.offset,
+ new_offset,
+ });
+
+ const amt = try self.file.copyRangeAll(
+ sect.offset,
+ self.file,
+ new_offset,
+ sect.size,
+ );
+ if (amt != sect.size) return error.InputOutput;
+ sect.offset = @intCast(u32, new_offset);
+ }
+ sect.size = needed_size;
+ self.markDirty(sect_index);
+}
+
+pub fn markDirty(self: *DebugSymbols, sect_index: u8) void {
+ if (self.debug_info_section_index.? == sect_index) {
+ self.debug_info_header_dirty = true;
+ } else if (self.debug_line_section_index.? == sect_index) {
+ self.debug_line_header_dirty = true;
+ }
+}
+
fn detectAllocCollision(self: *DebugSymbols, start: u64, size: u64) ?u64 {
const end = start + padToIdeal(size);
for (self.sections.items) |section| {
@@ -556,3 +590,13 @@ fn getLinkeditSegmentPtr(self: *DebugSymbols) *macho.segment_command_64 {
const index = self.linkedit_segment_cmd_index.?;
return &self.segments.items[index];
}
+
+pub fn getSectionPtr(self: *DebugSymbols, sect: u8) *macho.section_64 {
+ assert(sect < self.sections.items.len);
+ return &self.sections.items[sect];
+}
+
+pub fn getSection(self: DebugSymbols, sect: u8) macho.section_64 {
+ assert(sect < self.sections.items.len);
+ return self.sections.items[sect];
+}
src/link/Dwarf.zig
@@ -1106,7 +1106,7 @@ pub fn commitDeclState(
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_line_sect = &d_sym.sections.items[d_sym.debug_line_section_index.?];
+ const debug_line_sect = d_sym.getSectionPtr(d_sym.debug_line_section_index.?);
const file_pos = debug_line_sect.offset + src_fn.off;
try pwriteDbgLineNops(d_sym.file, file_pos, 0, &[0]u8{}, src_fn.len);
},
@@ -1187,7 +1187,7 @@ pub fn commitDeclState(
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_line_sect = &d_sym.sections.items[d_sym.debug_line_section_index.?];
+ const debug_line_sect = d_sym.getSectionPtr(d_sym.debug_line_section_index.?);
if (needed_size != debug_line_sect.size) {
if (needed_size > d_sym.allocatedSize(debug_line_sect.offset)) {
const new_offset = d_sym.findFreeSpace(needed_size, 1);
@@ -1381,7 +1381,7 @@ fn updateDeclDebugInfoAllocation(self: *Dwarf, atom: *Atom, len: u32) !void {
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_info_sect = &d_sym.sections.items[d_sym.debug_info_section_index.?];
+ const debug_info_sect = d_sym.getSectionPtr(d_sym.debug_info_section_index.?);
const file_pos = debug_info_sect.offset + atom.off;
try pwriteDbgInfoNops(d_sym.file, file_pos, 0, &[0]u8{}, atom.len, false);
},
@@ -1477,29 +1477,10 @@ fn writeDeclDebugInfo(self: *Dwarf, atom: *Atom, dbg_info_buf: []const u8) !void
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_info_sect = &d_sym.sections.items[d_sym.debug_info_section_index.?];
- if (needed_size != debug_info_sect.size) {
- if (needed_size > d_sym.allocatedSize(debug_info_sect.offset)) {
- const new_offset = d_sym.findFreeSpace(needed_size, 1);
- const existing_size = last_decl.off;
- std.log.scoped(.dsym).debug("moving __debug_info section: {} bytes from 0x{x} to 0x{x}", .{
- existing_size,
- debug_info_sect.offset,
- new_offset,
- });
- const amt = try d_sym.file.copyRangeAll(
- debug_info_sect.offset,
- d_sym.file,
- new_offset,
- existing_size,
- );
- if (amt != existing_size) return error.InputOutput;
- debug_info_sect.offset = @intCast(u32, new_offset);
- }
- debug_info_sect.size = needed_size;
- d_sym.debug_info_header_dirty = true;
- }
- const file_pos = debug_info_sect.offset + atom.off;
+ const sect_index = d_sym.debug_info_section_index.?;
+ try d_sym.growSection(sect_index, needed_size);
+ const sect = d_sym.getSection(sect_index);
+ const file_pos = sect.offset + atom.off;
try pwriteDbgInfoNops(
d_sym.file,
file_pos,
@@ -1916,7 +1897,7 @@ pub fn writeDbgInfoHeader(self: *Dwarf, module: *Module, low_pc: u64, high_pc: u
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_info_sect = d_sym.sections.items[d_sym.debug_info_section_index.?];
+ const debug_info_sect = d_sym.getSection(d_sym.debug_info_section_index.?);
const file_pos = debug_info_sect.offset;
try pwriteDbgInfoNops(d_sym.file, file_pos, 0, di_buf.items, jmp_amt, false);
},
@@ -2406,7 +2387,7 @@ pub fn writeDbgLineHeader(self: *Dwarf, module: *Module) !void {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_line_sect = &d_sym.sections.items[d_sym.debug_line_section_index.?];
+ const debug_line_sect = d_sym.getSectionPtr(d_sym.debug_line_section_index.?);
const needed_size = debug_line_sect.size + delta;
if (needed_size > d_sym.allocatedSize(debug_line_sect.offset)) {
@@ -2463,7 +2444,7 @@ pub fn writeDbgLineHeader(self: *Dwarf, module: *Module) !void {
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_line_sect = d_sym.sections.items[d_sym.debug_line_section_index.?];
+ const debug_line_sect = d_sym.getSection(d_sym.debug_line_section_index.?);
const file_pos = debug_line_sect.offset;
try pwriteDbgLineNops(d_sym.file, file_pos, 0, di_buf.items, jmp_amt);
},
@@ -2606,7 +2587,7 @@ pub fn flushModule(self: *Dwarf, module: *Module) !void {
.macho => {
const macho_file = self.bin_file.cast(File.MachO).?;
const d_sym = &macho_file.d_sym.?;
- const debug_info_sect = &d_sym.sections.items[d_sym.debug_info_section_index.?];
+ const debug_info_sect = d_sym.getSectionPtr(d_sym.debug_info_section_index.?);
break :blk debug_info_sect.offset;
},
// for wasm, the offset is always 0 as we write to memory first