authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2023-08-21 22:17:34+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2023-08-29 11:39:34+02:00
loge1e0ccb0c7ac32024aeb079a6cb57e237f941473
tree1c64dcaf809555250eda5e606257935935b70053
parent05c9d6c00babc4ccc7949b3eb0224f70719d12a5

macho: unify Section concept across drivers


5 files changed, 27 insertions(+), 46 deletions(-)

src/link/MachO.zig+2-4
......@@ -69,12 +69,10 @@ pub const Mode = enum {
6969 zld,
7070};
7171
72const Section = struct {
72pub const Section = struct {
7373 header: macho.section_64,
7474 segment_index: u8,
75
76 // TODO is null here necessary, or can we do away with tracking via section
77 // size in incremental context?
75 first_atom_index: ?Atom.Index = null,
7876 last_atom_index: ?Atom.Index = null,
7977
8078 /// A list of atoms that have surplus capacity. This list can have false
src/link/MachO/Object.zig+4-6
......@@ -55,7 +55,7 @@ source_section_index_lookup: []Entry = undefined,
5555/// Can be undefined as set together with in_symtab.
5656strtab_lookup: []u32 = undefined,
5757/// Can be undefined as set together with in_symtab.
58atom_by_index_table: []AtomIndex = undefined,
58atom_by_index_table: []?AtomIndex = undefined,
5959/// Can be undefined as set together with in_symtab.
6060globals_lookup: []i64 = undefined,
6161/// Can be undefined as set together with in_symtab.
......@@ -156,7 +156,7 @@ pub fn parse(self: *Object, allocator: Allocator) !void {
156156 self.reverse_symtab_lookup = try allocator.alloc(u32, self.in_symtab.?.len);
157157 self.strtab_lookup = try allocator.alloc(u32, self.in_symtab.?.len);
158158 self.globals_lookup = try allocator.alloc(i64, self.in_symtab.?.len);
159 self.atom_by_index_table = try allocator.alloc(AtomIndex, self.in_symtab.?.len + nsects);
159 self.atom_by_index_table = try allocator.alloc(?AtomIndex, self.in_symtab.?.len + nsects);
160160 self.relocs_lookup = try allocator.alloc(Entry, self.in_symtab.?.len + nsects);
161161 // This is wasteful but we need to be able to lookup source symbol address after stripping and
162162 // allocating of sections.
......@@ -174,7 +174,7 @@ pub fn parse(self: *Object, allocator: Allocator) !void {
174174 }
175175
176176 @memset(self.globals_lookup, -1);
177 @memset(self.atom_by_index_table, 0);
177 @memset(self.atom_by_index_table, null);
178178 @memset(self.source_section_index_lookup, .{});
179179 @memset(self.relocs_lookup, .{});
180180
......@@ -1060,9 +1060,7 @@ pub fn getGlobal(self: Object, sym_index: u32) ?u32 {
10601060}
10611061
10621062pub fn getAtomIndexForSymbol(self: Object, sym_index: u32) ?AtomIndex {
1063 const atom_index = self.atom_by_index_table[sym_index];
1064 if (atom_index == 0) return null;
1065 return atom_index;
1063 return self.atom_by_index_table[sym_index];
10661064}
10671065
10681066pub fn hasUnwindRecords(self: Object) bool {
src/link/MachO/dead_strip.zig+2-2
......@@ -466,8 +466,8 @@ fn prune(zld: *Zld, alive: AtomTable) void {
466466 section.last_atom_index = prev_index;
467467 } else {
468468 assert(section.header.size == 0);
469 section.first_atom_index = 0;
470 section.last_atom_index = 0;
469 section.first_atom_index = null;
470 section.last_atom_index = null;
471471 }
472472 }
473473
src/link/MachO/thunks.zig+1-1
......@@ -75,7 +75,7 @@ pub fn createThunks(zld: *Zld, sect_id: u8) !void {
7575 if (header.size == 0) return;
7676
7777 const gpa = zld.gpa;
78 const first_atom_index = zld.sections.items(.first_atom_index)[sect_id];
78 const first_atom_index = zld.sections.items(.first_atom_index)[sect_id].?;
7979
8080 header.size = 0;
8181 header.@"align" = 0;
src/link/MachO/zld.zig+18-33
......@@ -31,6 +31,7 @@ const MachO = @import("../MachO.zig");
3131const Md5 = std.crypto.hash.Md5;
3232const LibStub = @import("../tapi.zig").LibStub;
3333const Object = @import("Object.zig");
34const Section = MachO.Section;
3435const StringTable = @import("../strtab.zig").StringTable;
3536const SymbolWithLoc = MachO.SymbolWithLoc;
3637const SymbolResolver = MachO.SymbolResolver;
......@@ -231,7 +232,7 @@ pub const Zld = struct {
231232 const sym = self.getSymbol(atom.getSymbolWithLoc());
232233 var section = self.sections.get(sym.n_sect - 1);
233234 if (section.header.size > 0) {
234 const last_atom = self.getAtomPtr(section.last_atom_index);
235 const last_atom = self.getAtomPtr(section.last_atom_index.?);
235236 last_atom.next_index = atom_index;
236237 atom.prev_index = section.last_atom_index;
237238 } else {
......@@ -445,7 +446,7 @@ pub const Zld = struct {
445446 fn writeLazyPointer(self: *Zld, stub_helper_index: u32, writer: anytype) !void {
446447 const target_addr = blk: {
447448 const sect_id = self.getSectionByName("__TEXT", "__stub_helper").?;
448 var atom_index = self.sections.items(.first_atom_index)[sect_id];
449 var atom_index = self.sections.items(.first_atom_index)[sect_id].?;
449450 var count: u32 = 0;
450451 while (count < stub_helper_index + 1) : (count += 1) {
451452 const atom = self.getAtom(atom_index);
......@@ -497,7 +498,7 @@ pub const Zld = struct {
497498 const target_addr = blk: {
498499 // TODO: cache this at stub atom creation; they always go in pairs anyhow
499500 const la_sect_id = self.getSectionByName("__DATA", "__la_symbol_ptr").?;
500 var la_atom_index = self.sections.items(.first_atom_index)[la_sect_id];
501 var la_atom_index = self.sections.items(.first_atom_index)[la_sect_id].?;
501502 var count: u32 = 0;
502503 while (count < stub_index) : (count += 1) {
503504 const la_atom = self.getAtom(la_atom_index);
......@@ -1012,11 +1013,10 @@ pub const Zld = struct {
10121013
10131014 for (slice.items(.first_atom_index), 0..) |first_atom_index, sect_id| {
10141015 const header = slice.items(.header)[sect_id];
1015 var atom_index = first_atom_index;
1016
1017 if (atom_index == 0) continue;
10181016 if (header.isZerofill()) continue;
10191017
1018 var atom_index = first_atom_index orelse continue;
1019
10201020 var buffer = std.ArrayList(u8).init(gpa);
10211021 defer buffer.deinit();
10221022 try buffer.ensureTotalCapacity(math.cast(usize, header.size) orelse return error.Overflow);
......@@ -1129,7 +1129,7 @@ pub const Zld = struct {
11291129 while (i < slice.len) : (i += 1) {
11301130 const section = self.sections.get(i);
11311131 if (section.header.size == 0) {
1132 log.debug("pruning section {s},{s} {d}", .{
1132 log.debug("pruning section {s},{s} {?d}", .{
11331133 section.header.segName(),
11341134 section.header.sectName(),
11351135 section.first_atom_index,
......@@ -1156,8 +1156,7 @@ pub const Zld = struct {
11561156 if (header.isCode() and !(header.type() == macho.S_SYMBOL_STUBS) and !mem.eql(u8, header.sectName(), "__stub_helper")) continue;
11571157 }
11581158
1159 var atom_index = slice.items(.first_atom_index)[sect_id];
1160 if (atom_index == 0) continue;
1159 var atom_index = slice.items(.first_atom_index)[sect_id] orelse continue;
11611160
11621161 header.size = 0;
11631162 header.@"align" = 0;
......@@ -1195,8 +1194,7 @@ pub const Zld = struct {
11951194 // We need to do this since our unwind info synthesiser relies on
11961195 // traversing the symbols when synthesising unwind info and DWARF CFI records.
11971196 for (slice.items(.first_atom_index)) |first_atom_index| {
1198 if (first_atom_index == 0) continue;
1199 var atom_index = first_atom_index;
1197 var atom_index = first_atom_index orelse continue;
12001198
12011199 while (true) {
12021200 const atom = self.getAtom(atom_index);
......@@ -1278,8 +1276,9 @@ pub const Zld = struct {
12781276 @as(u32, @intCast(segment.fileoff + start_aligned));
12791277 header.addr = segment.vmaddr + start_aligned;
12801278
1281 var atom_index = slice.items(.first_atom_index)[indexes.start + sect_id];
1282 if (atom_index > 0) {
1279 if (slice.items(.first_atom_index)[indexes.start + sect_id]) |first_atom_index| {
1280 var atom_index = first_atom_index;
1281
12831282 log.debug("allocating local symbols in sect({d}, '{s},{s}')", .{
12841283 n_sect,
12851284 header.segName(),
......@@ -1362,8 +1361,6 @@ pub const Zld = struct {
13621361 .reserved1 = opts.reserved1,
13631362 .reserved2 = opts.reserved2,
13641363 },
1365 .first_atom_index = 0,
1366 .last_atom_index = 0,
13671364 });
13681365 return index;
13691366 }
......@@ -1491,7 +1488,7 @@ pub const Zld = struct {
14911488 if (self.getSectionByName("__DATA", "__la_symbol_ptr")) |sect_id| {
14921489 const segment_index = slice.items(.segment_index)[sect_id];
14931490 const seg = self.getSegment(sect_id);
1494 var atom_index = slice.items(.first_atom_index)[sect_id];
1491 var atom_index = slice.items(.first_atom_index)[sect_id].?;
14951492
14961493 try rebase.entries.ensureUnusedCapacity(self.gpa, self.stubs.items.len);
14971494
......@@ -1531,8 +1528,7 @@ pub const Zld = struct {
15311528 log.debug("{s},{s}", .{ header.segName(), header.sectName() });
15321529
15331530 const cpu_arch = self.options.target.cpu.arch;
1534 var atom_index = slice.items(.first_atom_index)[sect_id];
1535 if (atom_index == 0) continue;
1531 var atom_index = slice.items(.first_atom_index)[sect_id] orelse continue;
15361532
15371533 while (true) {
15381534 const atom = self.getAtom(atom_index);
......@@ -1668,8 +1664,7 @@ pub const Zld = struct {
16681664 if (segment.maxprot & macho.PROT.WRITE == 0) continue;
16691665
16701666 const cpu_arch = self.options.target.cpu.arch;
1671 var atom_index = slice.items(.first_atom_index)[sect_id];
1672 if (atom_index == 0) continue;
1667 var atom_index = slice.items(.first_atom_index)[sect_id] orelse continue;
16731668
16741669 log.debug("{s},{s}", .{ header.segName(), header.sectName() });
16751670
......@@ -1757,7 +1752,7 @@ pub const Zld = struct {
17571752 const slice = self.sections.slice();
17581753 const segment_index = slice.items(.segment_index)[sect_id];
17591754 const seg = self.getSegment(sect_id);
1760 var atom_index = slice.items(.first_atom_index)[sect_id];
1755 var atom_index = slice.items(.first_atom_index)[sect_id].?;
17611756
17621757 // TODO: we actually don't need to store lazy pointer atoms as they are synthetically generated by the linker
17631758 try lazy_bind.entries.ensureUnusedCapacity(self.gpa, self.stubs.items.len);
......@@ -1920,7 +1915,7 @@ pub const Zld = struct {
19201915 const section = self.sections.get(stub_helper_section_index);
19211916 const stub_offset = stub_helpers.calcStubOffsetInStubHelper(self.options.target.cpu.arch);
19221917 const header = section.header;
1923 var atom_index = section.first_atom_index;
1918 var atom_index = section.first_atom_index.?;
19241919 atom_index = self.getAtom(atom_index).next_index.?; // skip preamble
19251920
19261921 var index: usize = 0;
......@@ -2923,9 +2918,7 @@ pub const Zld = struct {
29232918 log.debug("atoms:", .{});
29242919 const slice = self.sections.slice();
29252920 for (slice.items(.first_atom_index), 0..) |first_atom_index, sect_id| {
2926 var atom_index = first_atom_index;
2927 if (atom_index == 0) continue;
2928
2921 var atom_index = first_atom_index orelse continue;
29292922 const header = slice.items(.header)[sect_id];
29302923
29312924 log.debug("{s},{s}", .{ header.segName(), header.sectName() });
......@@ -2990,13 +2983,6 @@ pub const Zld = struct {
29902983
29912984pub const N_DEAD: u16 = @as(u16, @bitCast(@as(i16, -1)));
29922985
2993const Section = struct {
2994 header: macho.section_64,
2995 segment_index: u8,
2996 first_atom_index: AtomIndex,
2997 last_atom_index: AtomIndex,
2998};
2999
30002986pub const AtomIndex = u32;
30012987
30022988const IndirectPointer = struct {
......@@ -3183,7 +3169,6 @@ pub fn linkWithZld(macho_file: *MachO, comp: *Compilation, prog_node: *std.Progr
31833169 };
31843170 defer zld.deinit();
31853171
3186 try zld.atoms.append(gpa, Atom.empty); // AtomIndex at 0 is reserved as null atom
31873172 try zld.strtab.buffer.append(gpa, 0);
31883173
31893174 // Positional arguments to the linker such as object files and static archives.