| ... | ... | @@ -243,8 +243,6 @@ unnamed_const_atoms: UnnamedConstTable = .{}, |
| 243 | 243 | /// TODO consolidate this. |
| 244 | 244 | decls: std.AutoArrayHashMapUnmanaged(Module.Decl.Index, ?MatchingSection) = .{}, |
| 245 | 245 | |
| 246 | | gc_roots: std.AutoHashMapUnmanaged(*Atom, void) = .{}, |
| 247 | | |
| 248 | 246 | const Entry = struct { |
| 249 | 247 | target: SymbolWithLoc, |
| 250 | 248 | atom: *Atom, |
| ... | ... | @@ -631,7 +629,8 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 631 | 629 | const tracy = trace(@src()); |
| 632 | 630 | defer tracy.end(); |
| 633 | 631 | |
| 634 | | var arena_allocator = std.heap.ArenaAllocator.init(self.base.allocator); |
| 632 | const gpa = self.base.allocator; |
| 633 | var arena_allocator = std.heap.ArenaAllocator.init(gpa); |
| 635 | 634 | defer arena_allocator.deinit(); |
| 636 | 635 | const arena = arena_allocator.allocator(); |
| 637 | 636 | |
| ... | ... | @@ -676,6 +675,7 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 676 | 675 | const is_dyn_lib = self.base.options.link_mode == .Dynamic and is_lib; |
| 677 | 676 | const is_exe_or_dyn_lib = is_dyn_lib or self.base.options.output_mode == .Exe; |
| 678 | 677 | const stack_size = self.base.options.stack_size_override orelse 0; |
| 678 | const dead_strip = self.base.options.gc_sections orelse false; |
| 679 | 679 | |
| 680 | 680 | const id_symlink_basename = "zld.id"; |
| 681 | 681 | |
| ... | ... | @@ -707,7 +707,7 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 707 | 707 | man.hash.addOptional(self.base.options.search_strategy); |
| 708 | 708 | man.hash.addOptional(self.base.options.headerpad_size); |
| 709 | 709 | man.hash.add(self.base.options.headerpad_max_install_names); |
| 710 | | man.hash.add(self.base.options.gc_sections orelse false); |
| 710 | man.hash.add(dead_strip); |
| 711 | 711 | man.hash.add(self.base.options.dead_strip_dylibs); |
| 712 | 712 | man.hash.addListOfBytes(self.base.options.lib_dirs); |
| 713 | 713 | man.hash.addListOfBytes(self.base.options.framework_dirs); |
| ... | ... | @@ -790,14 +790,14 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 790 | 790 | .mode = link.determineMode(self.base.options), |
| 791 | 791 | }); |
| 792 | 792 | // Index 0 is always a null symbol. |
| 793 | | try self.locals.append(self.base.allocator, .{ |
| 793 | try self.locals.append(gpa, .{ |
| 794 | 794 | .n_strx = 0, |
| 795 | 795 | .n_type = 0, |
| 796 | 796 | .n_sect = 0, |
| 797 | 797 | .n_desc = 0, |
| 798 | 798 | .n_value = 0, |
| 799 | 799 | }); |
| 800 | | try self.strtab.buffer.append(self.base.allocator, 0); |
| 800 | try self.strtab.buffer.append(gpa, 0); |
| 801 | 801 | try self.populateMissingMetadata(); |
| 802 | 802 | |
| 803 | 803 | var lib_not_found = false; |
| ... | ... | @@ -964,10 +964,10 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 964 | 964 | .cmdsize = cmdsize, |
| 965 | 965 | .path = @sizeOf(macho.rpath_command), |
| 966 | 966 | }); |
| 967 | | rpath_cmd.data = try self.base.allocator.alloc(u8, cmdsize - rpath_cmd.inner.path); |
| 967 | rpath_cmd.data = try gpa.alloc(u8, cmdsize - rpath_cmd.inner.path); |
| 968 | 968 | mem.set(u8, rpath_cmd.data, 0); |
| 969 | 969 | mem.copy(u8, rpath_cmd.data, rpath); |
| 970 | | try self.load_commands.append(self.base.allocator, .{ .rpath = rpath_cmd }); |
| 970 | try self.load_commands.append(gpa, .{ .rpath = rpath_cmd }); |
| 971 | 971 | try rpath_table.putNoClobber(rpath, {}); |
| 972 | 972 | self.load_commands_dirty = true; |
| 973 | 973 | } |
| ... | ... | @@ -975,11 +975,11 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 975 | 975 | // code signature and entitlements |
| 976 | 976 | if (self.base.options.entitlements) |path| { |
| 977 | 977 | if (self.code_signature) |*csig| { |
| 978 | | try csig.addEntitlements(self.base.allocator, path); |
| 978 | try csig.addEntitlements(gpa, path); |
| 979 | 979 | csig.code_directory.ident = self.base.options.emit.?.sub_path; |
| 980 | 980 | } else { |
| 981 | 981 | var csig = CodeSignature.init(self.page_size); |
| 982 | | try csig.addEntitlements(self.base.allocator, path); |
| 982 | try csig.addEntitlements(gpa, path); |
| 983 | 983 | csig.code_directory.ident = self.base.options.emit.?.sub_path; |
| 984 | 984 | self.code_signature = csig; |
| 985 | 985 | } |
| ... | ... | @@ -1033,10 +1033,8 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 1033 | 1033 | try argv.append("-headerpad_max_install_names"); |
| 1034 | 1034 | } |
| 1035 | 1035 | |
| 1036 | | if (self.base.options.gc_sections) |is_set| { |
| 1037 | | if (is_set) { |
| 1038 | | try argv.append("-dead_strip"); |
| 1039 | | } |
| 1036 | if (dead_strip) { |
| 1037 | try argv.append("-dead_strip"); |
| 1040 | 1038 | } |
| 1041 | 1039 | |
| 1042 | 1040 | if (self.base.options.dead_strip_dylibs) { |
| ... | ... | @@ -1120,7 +1118,7 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 1120 | 1118 | var dependent_libs = std.fifo.LinearFifo(struct { |
| 1121 | 1119 | id: Dylib.Id, |
| 1122 | 1120 | parent: u16, |
| 1123 | | }, .Dynamic).init(self.base.allocator); |
| 1121 | }, .Dynamic).init(gpa); |
| 1124 | 1122 | defer dependent_libs.deinit(); |
| 1125 | 1123 | try self.parseInputFiles(positionals.items, self.base.options.sysroot, &dependent_libs); |
| 1126 | 1124 | try self.parseAndForceLoadStaticArchives(must_link_archives.keys()); |
| ... | ... | @@ -1153,11 +1151,21 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 1153 | 1151 | |
| 1154 | 1152 | try self.createTentativeDefAtoms(); |
| 1155 | 1153 | |
| 1156 | | for (self.objects.items) |*object, object_id| { |
| 1157 | | try object.splitIntoAtomsOneShot(self, @intCast(u32, object_id)); |
| 1154 | if (dead_strip) { |
| 1155 | var gc_roots = std.AutoHashMap(*Atom, void).init(gpa); |
| 1156 | defer gc_roots.deinit(); |
| 1157 | |
| 1158 | for (self.objects.items) |*object, object_id| { |
| 1159 | try object.splitIntoAtomsOneShot(self, @intCast(u32, object_id), &gc_roots); |
| 1160 | } |
| 1161 | |
| 1162 | try self.gcAtoms(&gc_roots); |
| 1163 | } else { |
| 1164 | for (self.objects.items) |*object, object_id| { |
| 1165 | try object.splitIntoAtomsOneShot(self, @intCast(u32, object_id), null); |
| 1166 | } |
| 1158 | 1167 | } |
| 1159 | 1168 | |
| 1160 | | try self.gcAtoms(); |
| 1161 | 1169 | try self.pruneAndSortSections(); |
| 1162 | 1170 | try self.allocateSegments(); |
| 1163 | 1171 | try self.allocateSymbols(); |
| ... | ... | @@ -1184,7 +1192,7 @@ fn linkOneShot(self: *MachO, comp: *Compilation, prog_node: *std.Progress.Node) |
| 1184 | 1192 | try self.writeLinkeditSegment(); |
| 1185 | 1193 | |
| 1186 | 1194 | if (self.code_signature) |*csig| { |
| 1187 | | csig.clear(self.base.allocator); |
| 1195 | csig.clear(gpa); |
| 1188 | 1196 | csig.code_directory.ident = self.base.options.emit.?.sub_path; |
| 1189 | 1197 | // Preallocate space for the code signature. |
| 1190 | 1198 | // We need to do this at this stage so that we have the load commands with proper values |
| ... | ... | @@ -3294,7 +3302,6 @@ pub fn deinit(self: *MachO) void { |
| 3294 | 3302 | self.locals.deinit(self.base.allocator); |
| 3295 | 3303 | self.locals_free_list.deinit(self.base.allocator); |
| 3296 | 3304 | self.unresolved.deinit(self.base.allocator); |
| 3297 | | self.gc_roots.deinit(self.base.allocator); |
| 3298 | 3305 | |
| 3299 | 3306 | for (self.objects.items) |*object| { |
| 3300 | 3307 | object.deinit(self.base.allocator); |
| ... | ... | @@ -5447,9 +5454,8 @@ fn pruneAndSortSections(self: *MachO) !void { |
| 5447 | 5454 | self.sections_order_dirty = false; |
| 5448 | 5455 | } |
| 5449 | 5456 | |
| 5450 | | fn gcAtoms(self: *MachO) !void { |
| 5451 | | const dead_strip = self.base.options.gc_sections orelse return; |
| 5452 | | if (!dead_strip) return; |
| 5457 | fn gcAtoms(self: *MachO, gc_roots: *std.AutoHashMap(*Atom, void)) !void { |
| 5458 | assert(self.base.options.gc_sections.?); |
| 5453 | 5459 | |
| 5454 | 5460 | const gpa = self.base.allocator; |
| 5455 | 5461 | |
| ... | ... | @@ -5461,7 +5467,7 @@ fn gcAtoms(self: *MachO) !void { |
| 5461 | 5467 | log.debug("skipping {s}", .{self.getSymbolName(global)}); |
| 5462 | 5468 | continue; |
| 5463 | 5469 | }; |
| 5464 | | _ = try self.gc_roots.getOrPut(gpa, gc_root); |
| 5470 | _ = try gc_roots.getOrPut(gc_root); |
| 5465 | 5471 | } |
| 5466 | 5472 | |
| 5467 | 5473 | // Add any atom targeting an import as GC root |
| ... | ... | @@ -5474,7 +5480,7 @@ fn gcAtoms(self: *MachO) !void { |
| 5474 | 5480 | if ((try rel.getTargetAtom(self)) == null) { |
| 5475 | 5481 | const target_sym = self.getSymbol(rel.target); |
| 5476 | 5482 | if (target_sym.undf()) { |
| 5477 | | _ = try self.gc_roots.getOrPut(gpa, atom); |
| 5483 | _ = try gc_roots.getOrPut(atom); |
| 5478 | 5484 | break; |
| 5479 | 5485 | } |
| 5480 | 5486 | } |
| ... | ... | @@ -5488,14 +5494,14 @@ fn gcAtoms(self: *MachO) !void { |
| 5488 | 5494 | |
| 5489 | 5495 | var stack = std.ArrayList(*Atom).init(gpa); |
| 5490 | 5496 | defer stack.deinit(); |
| 5491 | | try stack.ensureUnusedCapacity(self.gc_roots.count()); |
| 5497 | try stack.ensureUnusedCapacity(gc_roots.count()); |
| 5492 | 5498 | |
| 5493 | 5499 | var retained = std.AutoHashMap(*Atom, void).init(gpa); |
| 5494 | 5500 | defer retained.deinit(); |
| 5495 | | try retained.ensureUnusedCapacity(self.gc_roots.count()); |
| 5501 | try retained.ensureUnusedCapacity(gc_roots.count()); |
| 5496 | 5502 | |
| 5497 | 5503 | log.debug("GC roots:", .{}); |
| 5498 | | var gc_roots_it = self.gc_roots.keyIterator(); |
| 5504 | var gc_roots_it = gc_roots.keyIterator(); |
| 5499 | 5505 | while (gc_roots_it.next()) |gc_root| { |
| 5500 | 5506 | self.logAtom(gc_root.*); |
| 5501 | 5507 | |