authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2021-08-16 19:15:04+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2021-08-16 19:15:04+02:00
loga51edc978f90fa3b96e4b1d4886030848f97a7b0
treed41aefb6f0a64379ed263394ce45cf96986a9917
parent4c90c1ff63883c2bb8d2baa40e952674daba6814

macho: converge populateMetadata with populateMissingMetadata


1 files changed, 127 insertions(+), 420 deletions(-)

src/link/MachO.zig+127-420
...@@ -386,6 +386,36 @@ pub fn openPath(allocator: *Allocator, sub_path: []const u8, options: link.Optio...@@ -386,6 +386,36 @@ pub fn openPath(allocator: *Allocator, sub_path: []const u8, options: link.Optio
386 try self.populateMissingMetadata();386 try self.populateMissingMetadata();
387 try self.writeLocalSymbol(0);387 try self.writeLocalSymbol(0);
388388
389 if (!self.strtab_dir.containsAdapted(@as([]const u8, "dyld_stub_binder"), StringSliceAdapter{
390 .strtab = &self.strtab,
391 })) {
392 const import_sym_index = @intCast(u32, self.undefs.items.len);
393 const n_strx = try self.makeString("dyld_stub_binder");
394 try self.undefs.append(self.base.allocator, .{
395 .n_strx = n_strx,
396 .n_type = macho.N_UNDF | macho.N_EXT,
397 .n_sect = 0,
398 .n_desc = @intCast(u8, 1) * macho.N_SYMBOL_RESOLVER,
399 .n_value = 0,
400 });
401 try self.symbol_resolver.putNoClobber(self.base.allocator, n_strx, .{
402 .where = .undef,
403 .where_index = import_sym_index,
404 });
405 const got_key = GotIndirectionKey{
406 .where = .undef,
407 .where_index = import_sym_index,
408 };
409 const got_index = @intCast(u32, self.got_entries.items.len);
410 try self.got_entries.append(self.base.allocator, got_key);
411 try self.got_entries_map.putNoClobber(self.base.allocator, got_key, got_index);
412 try self.writeGotEntry(got_index);
413 self.binding_info_dirty = true;
414 }
415 if (self.stub_helper_stubs_start_off == null) {
416 try self.writeStubHelperPreamble();
417 }
418
389 if (self.d_sym) |*ds| {419 if (self.d_sym) |*ds| {
390 try ds.populateMissingMetadata(allocator);420 try ds.populateMissingMetadata(allocator);
391 try ds.writeLocalSymbol(0);421 try ds.writeLocalSymbol(0);
...@@ -556,7 +586,7 @@ pub fn flush(self: *MachO, comp: *Compilation) !void {...@@ -556,7 +586,7 @@ pub fn flush(self: *MachO, comp: *Compilation) !void {
556 .read = true,586 .read = true,
557 .mode = link.determineMode(self.base.options),587 .mode = link.determineMode(self.base.options),
558 });588 });
559 try self.populateMetadata();589 try self.populateMissingMetadata();
560590
561 // TODO mimicking insertion of null symbol from incremental linker.591 // TODO mimicking insertion of null symbol from incremental linker.
562 // This will need to moved.592 // This will need to moved.
...@@ -798,6 +828,17 @@ pub fn flush(self: *MachO, comp: *Compilation) !void {...@@ -798,6 +828,17 @@ pub fn flush(self: *MachO, comp: *Compilation) !void {
798 try self.allocateTextBlocks();828 try self.allocateTextBlocks();
799 try self.flushZld();829 try self.flushZld();
800 } else {830 } else {
831 // TODO this is just a temp; libsystem load command will be autoresolved when parsing libSystem from
832 // the linker line and actually referencing symbols.
833 if (self.libsystem_cmd_index == null) {
834 self.libsystem_cmd_index = @intCast(u16, self.load_commands.items.len);
835 var dylib_cmd = try commands.createLoadDylibCommand(self.base.allocator, mem.spanZ(LIB_SYSTEM_PATH), 2, 0, 0);
836 errdefer dylib_cmd.deinit(self.base.allocator);
837 try self.load_commands.append(self.base.allocator, .{ .Dylib = dylib_cmd });
838 self.load_commands_dirty = true;
839 }
840 try self.addDataInCodeLC();
841 try self.addCodeSignatureLC();
801 try self.flushModule(comp);842 try self.flushModule(comp);
802 }843 }
803 }844 }
...@@ -2503,328 +2544,6 @@ fn parseTextBlocks(self: *MachO) !void {...@@ -2503,328 +2544,6 @@ fn parseTextBlocks(self: *MachO) !void {
2503 }2544 }
2504}2545}
25052546
2506fn populateMetadata(self: *MachO) !void {
2507 if (self.pagezero_segment_cmd_index == null) {
2508 self.pagezero_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
2509 try self.load_commands.append(self.base.allocator, .{
2510 .Segment = SegmentCommand.empty("__PAGEZERO", .{
2511 .vmsize = 0x100000000, // size always set to 4GB
2512 }),
2513 });
2514 }
2515
2516 if (self.text_segment_cmd_index == null) {
2517 self.text_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
2518 try self.load_commands.append(self.base.allocator, .{
2519 .Segment = SegmentCommand.empty("__TEXT", .{
2520 .vmaddr = 0x100000000, // always starts at 4GB
2521 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_EXECUTE,
2522 .initprot = macho.VM_PROT_READ | macho.VM_PROT_EXECUTE,
2523 }),
2524 });
2525 }
2526
2527 if (self.text_section_index == null) {
2528 const text_seg = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
2529 self.text_section_index = @intCast(u16, text_seg.sections.items.len);
2530 const alignment: u2 = switch (self.base.options.target.cpu.arch) {
2531 .x86_64 => 0,
2532 .aarch64 => 2,
2533 else => unreachable, // unhandled architecture type
2534 };
2535 try text_seg.addSection(self.base.allocator, "__text", .{
2536 .@"align" = alignment,
2537 .flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
2538 });
2539 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2540 .seg = self.text_segment_cmd_index.?,
2541 .sect = self.text_section_index.?,
2542 });
2543 }
2544
2545 if (self.stubs_section_index == null) {
2546 const text_seg = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
2547 self.stubs_section_index = @intCast(u16, text_seg.sections.items.len);
2548 const alignment: u2 = switch (self.base.options.target.cpu.arch) {
2549 .x86_64 => 0,
2550 .aarch64 => 2,
2551 else => unreachable, // unhandled architecture type
2552 };
2553 const stub_size: u4 = switch (self.base.options.target.cpu.arch) {
2554 .x86_64 => 6,
2555 .aarch64 => 3 * @sizeOf(u32),
2556 else => unreachable, // unhandled architecture type
2557 };
2558 try text_seg.addSection(self.base.allocator, "__stubs", .{
2559 .@"align" = alignment,
2560 .flags = macho.S_SYMBOL_STUBS | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
2561 .reserved2 = stub_size,
2562 });
2563 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2564 .seg = self.text_segment_cmd_index.?,
2565 .sect = self.stubs_section_index.?,
2566 });
2567 }
2568
2569 if (self.stub_helper_section_index == null) {
2570 const text_seg = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
2571 self.stub_helper_section_index = @intCast(u16, text_seg.sections.items.len);
2572 const alignment: u2 = switch (self.base.options.target.cpu.arch) {
2573 .x86_64 => 0,
2574 .aarch64 => 2,
2575 else => unreachable, // unhandled architecture type
2576 };
2577 const stub_helper_size: u6 = switch (self.base.options.target.cpu.arch) {
2578 .x86_64 => 15,
2579 .aarch64 => 6 * @sizeOf(u32),
2580 else => unreachable,
2581 };
2582 try text_seg.addSection(self.base.allocator, "__stub_helper", .{
2583 .size = stub_helper_size,
2584 .@"align" = alignment,
2585 .flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
2586 });
2587 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2588 .seg = self.text_segment_cmd_index.?,
2589 .sect = self.stub_helper_section_index.?,
2590 });
2591 }
2592
2593 if (self.data_const_segment_cmd_index == null) {
2594 self.data_const_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
2595 try self.load_commands.append(self.base.allocator, .{
2596 .Segment = SegmentCommand.empty("__DATA_CONST", .{
2597 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
2598 .initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
2599 }),
2600 });
2601 }
2602
2603 if (self.got_section_index == null) {
2604 const data_const_seg = &self.load_commands.items[self.data_const_segment_cmd_index.?].Segment;
2605 self.got_section_index = @intCast(u16, data_const_seg.sections.items.len);
2606 try data_const_seg.addSection(self.base.allocator, "__got", .{
2607 .@"align" = 3, // 2^3 = @sizeOf(u64)
2608 .flags = macho.S_NON_LAZY_SYMBOL_POINTERS,
2609 });
2610 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2611 .seg = self.data_const_segment_cmd_index.?,
2612 .sect = self.got_section_index.?,
2613 });
2614 }
2615
2616 if (self.data_segment_cmd_index == null) {
2617 self.data_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
2618 try self.load_commands.append(self.base.allocator, .{
2619 .Segment = SegmentCommand.empty("__DATA", .{
2620 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
2621 .initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
2622 }),
2623 });
2624 }
2625
2626 if (self.la_symbol_ptr_section_index == null) {
2627 const data_seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;
2628 self.la_symbol_ptr_section_index = @intCast(u16, data_seg.sections.items.len);
2629 try data_seg.addSection(self.base.allocator, "__la_symbol_ptr", .{
2630 .@"align" = 3, // 2^3 = @sizeOf(u64)
2631 .flags = macho.S_LAZY_SYMBOL_POINTERS,
2632 });
2633 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2634 .seg = self.data_segment_cmd_index.?,
2635 .sect = self.la_symbol_ptr_section_index.?,
2636 });
2637 }
2638
2639 if (self.data_section_index == null) {
2640 const data_seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;
2641 self.data_section_index = @intCast(u16, data_seg.sections.items.len);
2642 try data_seg.addSection(self.base.allocator, "__data", .{
2643 .@"align" = 3, // 2^3 = @sizeOf(u64)
2644 });
2645 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
2646 .seg = self.data_segment_cmd_index.?,
2647 .sect = self.data_section_index.?,
2648 });
2649 }
2650
2651 if (self.linkedit_segment_cmd_index == null) {
2652 self.linkedit_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
2653 try self.load_commands.append(self.base.allocator, .{
2654 .Segment = SegmentCommand.empty("__LINKEDIT", .{
2655 .maxprot = macho.VM_PROT_READ,
2656 .initprot = macho.VM_PROT_READ,
2657 }),
2658 });
2659 }
2660
2661 if (self.dyld_info_cmd_index == null) {
2662 self.dyld_info_cmd_index = @intCast(u16, self.load_commands.items.len);
2663 try self.load_commands.append(self.base.allocator, .{
2664 .DyldInfoOnly = .{
2665 .cmd = macho.LC_DYLD_INFO_ONLY,
2666 .cmdsize = @sizeOf(macho.dyld_info_command),
2667 .rebase_off = 0,
2668 .rebase_size = 0,
2669 .bind_off = 0,
2670 .bind_size = 0,
2671 .weak_bind_off = 0,
2672 .weak_bind_size = 0,
2673 .lazy_bind_off = 0,
2674 .lazy_bind_size = 0,
2675 .export_off = 0,
2676 .export_size = 0,
2677 },
2678 });
2679 }
2680
2681 if (self.symtab_cmd_index == null) {
2682 self.symtab_cmd_index = @intCast(u16, self.load_commands.items.len);
2683 try self.load_commands.append(self.base.allocator, .{
2684 .Symtab = .{
2685 .cmd = macho.LC_SYMTAB,
2686 .cmdsize = @sizeOf(macho.symtab_command),
2687 .symoff = 0,
2688 .nsyms = 0,
2689 .stroff = 0,
2690 .strsize = 0,
2691 },
2692 });
2693 }
2694
2695 if (self.dysymtab_cmd_index == null) {
2696 self.dysymtab_cmd_index = @intCast(u16, self.load_commands.items.len);
2697 try self.load_commands.append(self.base.allocator, .{
2698 .Dysymtab = .{
2699 .cmd = macho.LC_DYSYMTAB,
2700 .cmdsize = @sizeOf(macho.dysymtab_command),
2701 .ilocalsym = 0,
2702 .nlocalsym = 0,
2703 .iextdefsym = 0,
2704 .nextdefsym = 0,
2705 .iundefsym = 0,
2706 .nundefsym = 0,
2707 .tocoff = 0,
2708 .ntoc = 0,
2709 .modtaboff = 0,
2710 .nmodtab = 0,
2711 .extrefsymoff = 0,
2712 .nextrefsyms = 0,
2713 .indirectsymoff = 0,
2714 .nindirectsyms = 0,
2715 .extreloff = 0,
2716 .nextrel = 0,
2717 .locreloff = 0,
2718 .nlocrel = 0,
2719 },
2720 });
2721 }
2722
2723 if (self.dylinker_cmd_index == null) {
2724 self.dylinker_cmd_index = @intCast(u16, self.load_commands.items.len);
2725 const cmdsize = @intCast(u32, mem.alignForwardGeneric(
2726 u64,
2727 @sizeOf(macho.dylinker_command) + mem.lenZ(DEFAULT_DYLD_PATH),
2728 @sizeOf(u64),
2729 ));
2730 var dylinker_cmd = commands.emptyGenericCommandWithData(macho.dylinker_command{
2731 .cmd = macho.LC_LOAD_DYLINKER,
2732 .cmdsize = cmdsize,
2733 .name = @sizeOf(macho.dylinker_command),
2734 });
2735 dylinker_cmd.data = try self.base.allocator.alloc(u8, cmdsize - dylinker_cmd.inner.name);
2736 mem.set(u8, dylinker_cmd.data, 0);
2737 mem.copy(u8, dylinker_cmd.data, mem.spanZ(DEFAULT_DYLD_PATH));
2738 try self.load_commands.append(self.base.allocator, .{ .Dylinker = dylinker_cmd });
2739 }
2740
2741 if (self.main_cmd_index == null and self.base.options.output_mode == .Exe) {
2742 self.main_cmd_index = @intCast(u16, self.load_commands.items.len);
2743 try self.load_commands.append(self.base.allocator, .{
2744 .Main = .{
2745 .cmd = macho.LC_MAIN,
2746 .cmdsize = @sizeOf(macho.entry_point_command),
2747 .entryoff = 0x0,
2748 .stacksize = 0,
2749 },
2750 });
2751 }
2752
2753 if (self.dylib_id_cmd_index == null and self.base.options.output_mode == .Lib) {
2754 self.dylib_id_cmd_index = @intCast(u16, self.load_commands.items.len);
2755 const install_name = try std.fmt.allocPrint(self.base.allocator, "@rpath/{s}", .{
2756 self.base.options.emit.?.sub_path,
2757 });
2758 defer self.base.allocator.free(install_name);
2759 var dylib_cmd = try commands.createLoadDylibCommand(
2760 self.base.allocator,
2761 install_name,
2762 2,
2763 0x10000, // TODO forward user-provided versions
2764 0x10000,
2765 );
2766 errdefer dylib_cmd.deinit(self.base.allocator);
2767 dylib_cmd.inner.cmd = macho.LC_ID_DYLIB;
2768 try self.load_commands.append(self.base.allocator, .{ .Dylib = dylib_cmd });
2769 }
2770
2771 if (self.source_version_cmd_index == null) {
2772 self.source_version_cmd_index = @intCast(u16, self.load_commands.items.len);
2773 try self.load_commands.append(self.base.allocator, .{
2774 .SourceVersion = .{
2775 .cmd = macho.LC_SOURCE_VERSION,
2776 .cmdsize = @sizeOf(macho.source_version_command),
2777 .version = 0x0,
2778 },
2779 });
2780 }
2781
2782 if (self.build_version_cmd_index == null) {
2783 self.build_version_cmd_index = @intCast(u16, self.load_commands.items.len);
2784 const cmdsize = @intCast(u32, mem.alignForwardGeneric(
2785 u64,
2786 @sizeOf(macho.build_version_command) + @sizeOf(macho.build_tool_version),
2787 @sizeOf(u64),
2788 ));
2789 const ver = self.base.options.target.os.version_range.semver.min;
2790 const version = ver.major << 16 | ver.minor << 8 | ver.patch;
2791 const is_simulator_abi = self.base.options.target.abi == .simulator;
2792 var cmd = commands.emptyGenericCommandWithData(macho.build_version_command{
2793 .cmd = macho.LC_BUILD_VERSION,
2794 .cmdsize = cmdsize,
2795 .platform = switch (self.base.options.target.os.tag) {
2796 .macos => macho.PLATFORM_MACOS,
2797 .ios => if (is_simulator_abi) macho.PLATFORM_IOSSIMULATOR else macho.PLATFORM_IOS,
2798 .watchos => if (is_simulator_abi) macho.PLATFORM_WATCHOSSIMULATOR else macho.PLATFORM_WATCHOS,
2799 .tvos => if (is_simulator_abi) macho.PLATFORM_TVOSSIMULATOR else macho.PLATFORM_TVOS,
2800 else => unreachable,
2801 },
2802 .minos = version,
2803 .sdk = version,
2804 .ntools = 1,
2805 });
2806 const ld_ver = macho.build_tool_version{
2807 .tool = macho.TOOL_LD,
2808 .version = 0x0,
2809 };
2810 cmd.data = try self.base.allocator.alloc(u8, cmdsize - @sizeOf(macho.build_version_command));
2811 mem.set(u8, cmd.data, 0);
2812 mem.copy(u8, cmd.data, mem.asBytes(&ld_ver));
2813 try self.load_commands.append(self.base.allocator, .{ .BuildVersion = cmd });
2814 }
2815
2816 if (self.uuid_cmd_index == null) {
2817 self.uuid_cmd_index = @intCast(u16, self.load_commands.items.len);
2818 var uuid_cmd: macho.uuid_command = .{
2819 .cmd = macho.LC_UUID,
2820 .cmdsize = @sizeOf(macho.uuid_command),
2821 .uuid = undefined,
2822 };
2823 std.crypto.random.bytes(&uuid_cmd.uuid);
2824 try self.load_commands.append(self.base.allocator, .{ .Uuid = uuid_cmd });
2825 }
2826}
2827
2828fn addDataInCodeLC(self: *MachO) !void {2547fn addDataInCodeLC(self: *MachO) !void {
2829 if (self.data_in_code_cmd_index == null) {2548 if (self.data_in_code_cmd_index == null) {
2830 self.data_in_code_cmd_index = @intCast(u16, self.load_commands.items.len);2549 self.data_in_code_cmd_index = @intCast(u16, self.load_commands.items.len);
...@@ -4004,12 +3723,6 @@ pub fn getDeclVAddr(self: *MachO, decl: *const Module.Decl) u64 {...@@ -4004,12 +3723,6 @@ pub fn getDeclVAddr(self: *MachO, decl: *const Module.Decl) u64 {
4004}3723}
40053724
4006pub fn populateMissingMetadata(self: *MachO) !void {3725pub fn populateMissingMetadata(self: *MachO) !void {
4007 switch (self.base.options.output_mode) {
4008 .Exe => {},
4009 .Obj => return error.TODOImplementWritingObjFiles,
4010 .Lib => return error.TODOImplementWritingLibFiles,
4011 }
4012
4013 if (self.pagezero_segment_cmd_index == null) {3726 if (self.pagezero_segment_cmd_index == null) {
4014 self.pagezero_segment_cmd_index = @intCast(u16, self.load_commands.items.len);3727 self.pagezero_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
4015 try self.load_commands.append(self.base.allocator, .{3728 try self.load_commands.append(self.base.allocator, .{
...@@ -4019,11 +3732,9 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4019,11 +3732,9 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4019 });3732 });
4020 self.load_commands_dirty = true;3733 self.load_commands_dirty = true;
4021 }3734 }
3735
4022 if (self.text_segment_cmd_index == null) {3736 if (self.text_segment_cmd_index == null) {
4023 self.text_segment_cmd_index = @intCast(u16, self.load_commands.items.len);3737 self.text_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
4024 const maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE | macho.VM_PROT_EXECUTE;
4025 const initprot = macho.VM_PROT_READ | macho.VM_PROT_EXECUTE;
4026
4027 const program_code_size_hint = self.base.options.program_code_size_hint;3738 const program_code_size_hint = self.base.options.program_code_size_hint;
4028 const got_size_hint = @sizeOf(u64) * self.base.options.symbol_count_hint;3739 const got_size_hint = @sizeOf(u64) * self.base.options.symbol_count_hint;
4029 const ideal_size = self.header_pad + program_code_size_hint + 3 * got_size_hint;3740 const ideal_size = self.header_pad + program_code_size_hint + 3 * got_size_hint;
...@@ -4036,12 +3747,13 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4036,12 +3747,13 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4036 .vmaddr = 0x100000000, // always starts at 4GB3747 .vmaddr = 0x100000000, // always starts at 4GB
4037 .vmsize = needed_size,3748 .vmsize = needed_size,
4038 .filesize = needed_size,3749 .filesize = needed_size,
4039 .maxprot = maxprot,3750 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_EXECUTE,
4040 .initprot = initprot,3751 .initprot = macho.VM_PROT_READ | macho.VM_PROT_EXECUTE,
4041 }),3752 }),
4042 });3753 });
4043 self.load_commands_dirty = true;3754 self.load_commands_dirty = true;
4044 }3755 }
3756
4045 if (self.text_section_index == null) {3757 if (self.text_section_index == null) {
4046 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;3758 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
4047 self.text_section_index = @intCast(u16, text_segment.sections.items.len);3759 self.text_section_index = @intCast(u16, text_segment.sections.items.len);
...@@ -4051,7 +3763,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4051,7 +3763,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4051 .aarch64 => 2,3763 .aarch64 => 2,
4052 else => unreachable, // unhandled architecture type3764 else => unreachable, // unhandled architecture type
4053 };3765 };
4054 const flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS;
4055 const needed_size = self.base.options.program_code_size_hint;3766 const needed_size = self.base.options.program_code_size_hint;
4056 const off = text_segment.findFreeSpace(needed_size, @as(u16, 1) << alignment, self.header_pad);3767 const off = text_segment.findFreeSpace(needed_size, @as(u16, 1) << alignment, self.header_pad);
40573768
...@@ -4062,10 +3773,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4062,10 +3773,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4062 .size = @intCast(u32, needed_size),3773 .size = @intCast(u32, needed_size),
4063 .offset = @intCast(u32, off),3774 .offset = @intCast(u32, off),
4064 .@"align" = alignment,3775 .@"align" = alignment,
4065 .flags = flags,3776 .flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
3777 });
3778 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3779 .seg = self.text_segment_cmd_index.?,
3780 .sect = self.text_section_index.?,
4066 });3781 });
4067 self.load_commands_dirty = true;3782 self.load_commands_dirty = true;
4068 }3783 }
3784
4069 if (self.stubs_section_index == null) {3785 if (self.stubs_section_index == null) {
4070 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;3786 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
4071 self.stubs_section_index = @intCast(u16, text_segment.sections.items.len);3787 self.stubs_section_index = @intCast(u16, text_segment.sections.items.len);
...@@ -4080,7 +3796,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4080,7 +3796,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4080 .aarch64 => 3 * @sizeOf(u32),3796 .aarch64 => 3 * @sizeOf(u32),
4081 else => unreachable, // unhandled architecture type3797 else => unreachable, // unhandled architecture type
4082 };3798 };
4083 const flags = macho.S_SYMBOL_STUBS | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS;
4084 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;3799 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;
4085 const off = text_segment.findFreeSpace(needed_size, @alignOf(u64), self.header_pad);3800 const off = text_segment.findFreeSpace(needed_size, @alignOf(u64), self.header_pad);
4086 assert(off + needed_size <= text_segment.inner.fileoff + text_segment.inner.filesize); // TODO Must expand __TEXT segment.3801 assert(off + needed_size <= text_segment.inner.fileoff + text_segment.inner.filesize); // TODO Must expand __TEXT segment.
...@@ -4092,11 +3807,16 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4092,11 +3807,16 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4092 .size = needed_size,3807 .size = needed_size,
4093 .offset = @intCast(u32, off),3808 .offset = @intCast(u32, off),
4094 .@"align" = alignment,3809 .@"align" = alignment,
4095 .flags = flags,3810 .flags = macho.S_SYMBOL_STUBS | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
4096 .reserved2 = stub_size,3811 .reserved2 = stub_size,
4097 });3812 });
3813 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3814 .seg = self.text_segment_cmd_index.?,
3815 .sect = self.stubs_section_index.?,
3816 });
4098 self.load_commands_dirty = true;3817 self.load_commands_dirty = true;
4099 }3818 }
3819
4100 if (self.stub_helper_section_index == null) {3820 if (self.stub_helper_section_index == null) {
4101 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;3821 const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment;
4102 self.stub_helper_section_index = @intCast(u16, text_segment.sections.items.len);3822 self.stub_helper_section_index = @intCast(u16, text_segment.sections.items.len);
...@@ -4106,7 +3826,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4106,7 +3826,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4106 .aarch64 => 2,3826 .aarch64 => 2,
4107 else => unreachable, // unhandled architecture type3827 else => unreachable, // unhandled architecture type
4108 };3828 };
4109 const flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS;
4110 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;3829 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;
4111 const off = text_segment.findFreeSpace(needed_size, @alignOf(u64), self.header_pad);3830 const off = text_segment.findFreeSpace(needed_size, @alignOf(u64), self.header_pad);
4112 assert(off + needed_size <= text_segment.inner.fileoff + text_segment.inner.filesize); // TODO Must expand __TEXT segment.3831 assert(off + needed_size <= text_segment.inner.fileoff + text_segment.inner.filesize); // TODO Must expand __TEXT segment.
...@@ -4118,16 +3837,18 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4118,16 +3837,18 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4118 .size = needed_size,3837 .size = needed_size,
4119 .offset = @intCast(u32, off),3838 .offset = @intCast(u32, off),
4120 .@"align" = alignment,3839 .@"align" = alignment,
4121 .flags = flags,3840 .flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS,
3841 });
3842 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3843 .seg = self.text_segment_cmd_index.?,
3844 .sect = self.stub_helper_section_index.?,
4122 });3845 });
4123 self.load_commands_dirty = true;3846 self.load_commands_dirty = true;
4124 }3847 }
3848
4125 if (self.data_const_segment_cmd_index == null) {3849 if (self.data_const_segment_cmd_index == null) {
4126 self.data_const_segment_cmd_index = @intCast(u16, self.load_commands.items.len);3850 self.data_const_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
4127 const maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE | macho.VM_PROT_EXECUTE;
4128 const initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE;
4129 const address_and_offset = self.nextSegmentAddressAndOffset();3851 const address_and_offset = self.nextSegmentAddressAndOffset();
4130
4131 const ideal_size = @sizeOf(u64) * self.base.options.symbol_count_hint;3852 const ideal_size = @sizeOf(u64) * self.base.options.symbol_count_hint;
4132 const needed_size = mem.alignForwardGeneric(u64, padToIdeal(ideal_size), self.page_size);3853 const needed_size = mem.alignForwardGeneric(u64, padToIdeal(ideal_size), self.page_size);
41333854
...@@ -4139,17 +3860,17 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4139,17 +3860,17 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4139 .vmsize = needed_size,3860 .vmsize = needed_size,
4140 .fileoff = address_and_offset.offset,3861 .fileoff = address_and_offset.offset,
4141 .filesize = needed_size,3862 .filesize = needed_size,
4142 .maxprot = maxprot,3863 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
4143 .initprot = initprot,3864 .initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
4144 }),3865 }),
4145 });3866 });
4146 self.load_commands_dirty = true;3867 self.load_commands_dirty = true;
4147 }3868 }
3869
4148 if (self.got_section_index == null) {3870 if (self.got_section_index == null) {
4149 const dc_segment = &self.load_commands.items[self.data_const_segment_cmd_index.?].Segment;3871 const dc_segment = &self.load_commands.items[self.data_const_segment_cmd_index.?].Segment;
4150 self.got_section_index = @intCast(u16, dc_segment.sections.items.len);3872 self.got_section_index = @intCast(u16, dc_segment.sections.items.len);
41513873
4152 const flags = macho.S_NON_LAZY_SYMBOL_POINTERS;
4153 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;3874 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;
4154 const off = dc_segment.findFreeSpace(needed_size, @alignOf(u64), null);3875 const off = dc_segment.findFreeSpace(needed_size, @alignOf(u64), null);
4155 assert(off + needed_size <= dc_segment.inner.fileoff + dc_segment.inner.filesize); // TODO Must expand __DATA_CONST segment.3876 assert(off + needed_size <= dc_segment.inner.fileoff + dc_segment.inner.filesize); // TODO Must expand __DATA_CONST segment.
...@@ -4161,16 +3882,18 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4161,16 +3882,18 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4161 .size = needed_size,3882 .size = needed_size,
4162 .offset = @intCast(u32, off),3883 .offset = @intCast(u32, off),
4163 .@"align" = 3, // 2^3 = @sizeOf(u64)3884 .@"align" = 3, // 2^3 = @sizeOf(u64)
4164 .flags = flags,3885 .flags = macho.S_NON_LAZY_SYMBOL_POINTERS,
3886 });
3887 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3888 .seg = self.data_const_segment_cmd_index.?,
3889 .sect = self.got_section_index.?,
4165 });3890 });
4166 self.load_commands_dirty = true;3891 self.load_commands_dirty = true;
4167 }3892 }
3893
4168 if (self.data_segment_cmd_index == null) {3894 if (self.data_segment_cmd_index == null) {
4169 self.data_segment_cmd_index = @intCast(u16, self.load_commands.items.len);3895 self.data_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
4170 const maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE | macho.VM_PROT_EXECUTE;
4171 const initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE;
4172 const address_and_offset = self.nextSegmentAddressAndOffset();3896 const address_and_offset = self.nextSegmentAddressAndOffset();
4173
4174 const ideal_size = 2 * @sizeOf(u64) * self.base.options.symbol_count_hint;3897 const ideal_size = 2 * @sizeOf(u64) * self.base.options.symbol_count_hint;
4175 const needed_size = mem.alignForwardGeneric(u64, padToIdeal(ideal_size), self.page_size);3898 const needed_size = mem.alignForwardGeneric(u64, padToIdeal(ideal_size), self.page_size);
41763899
...@@ -4182,17 +3905,17 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4182,17 +3905,17 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4182 .vmsize = needed_size,3905 .vmsize = needed_size,
4183 .fileoff = address_and_offset.offset,3906 .fileoff = address_and_offset.offset,
4184 .filesize = needed_size,3907 .filesize = needed_size,
4185 .maxprot = maxprot,3908 .maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
4186 .initprot = initprot,3909 .initprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE,
4187 }),3910 }),
4188 });3911 });
4189 self.load_commands_dirty = true;3912 self.load_commands_dirty = true;
4190 }3913 }
3914
4191 if (self.la_symbol_ptr_section_index == null) {3915 if (self.la_symbol_ptr_section_index == null) {
4192 const data_segment = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;3916 const data_segment = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;
4193 self.la_symbol_ptr_section_index = @intCast(u16, data_segment.sections.items.len);3917 self.la_symbol_ptr_section_index = @intCast(u16, data_segment.sections.items.len);
41943918
4195 const flags = macho.S_LAZY_SYMBOL_POINTERS;
4196 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;3919 const needed_size = @sizeOf(u64) * self.base.options.symbol_count_hint;
4197 const off = data_segment.findFreeSpace(needed_size, @alignOf(u64), null);3920 const off = data_segment.findFreeSpace(needed_size, @alignOf(u64), null);
4198 assert(off + needed_size <= data_segment.inner.fileoff + data_segment.inner.filesize); // TODO Must expand __DATA segment.3921 assert(off + needed_size <= data_segment.inner.fileoff + data_segment.inner.filesize); // TODO Must expand __DATA segment.
...@@ -4204,10 +3927,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4204,10 +3927,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4204 .size = needed_size,3927 .size = needed_size,
4205 .offset = @intCast(u32, off),3928 .offset = @intCast(u32, off),
4206 .@"align" = 3, // 2^3 = @sizeOf(u64)3929 .@"align" = 3, // 2^3 = @sizeOf(u64)
4207 .flags = flags,3930 .flags = macho.S_LAZY_SYMBOL_POINTERS,
3931 });
3932 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3933 .seg = self.data_segment_cmd_index.?,
3934 .sect = self.la_symbol_ptr_section_index.?,
4208 });3935 });
4209 self.load_commands_dirty = true;3936 self.load_commands_dirty = true;
4210 }3937 }
3938
4211 if (self.data_section_index == null) {3939 if (self.data_section_index == null) {
4212 const data_segment = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;3940 const data_segment = &self.load_commands.items[self.data_segment_cmd_index.?].Segment;
4213 self.data_section_index = @intCast(u16, data_segment.sections.items.len);3941 self.data_section_index = @intCast(u16, data_segment.sections.items.len);
...@@ -4224,13 +3952,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4224,13 +3952,15 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4224 .offset = @intCast(u32, off),3952 .offset = @intCast(u32, off),
4225 .@"align" = 3, // 2^3 = @sizeOf(u64)3953 .@"align" = 3, // 2^3 = @sizeOf(u64)
4226 });3954 });
3955 _ = try self.section_ordinals.getOrPut(self.base.allocator, .{
3956 .seg = self.data_segment_cmd_index.?,
3957 .sect = self.data_section_index.?,
3958 });
4227 self.load_commands_dirty = true;3959 self.load_commands_dirty = true;
4228 }3960 }
3961
4229 if (self.linkedit_segment_cmd_index == null) {3962 if (self.linkedit_segment_cmd_index == null) {
4230 self.linkedit_segment_cmd_index = @intCast(u16, self.load_commands.items.len);3963 self.linkedit_segment_cmd_index = @intCast(u16, self.load_commands.items.len);
4231
4232 const maxprot = macho.VM_PROT_READ | macho.VM_PROT_WRITE | macho.VM_PROT_EXECUTE;
4233 const initprot = macho.VM_PROT_READ;
4234 const address_and_offset = self.nextSegmentAddressAndOffset();3964 const address_and_offset = self.nextSegmentAddressAndOffset();
42353965
4236 log.debug("found __LINKEDIT segment free space at 0x{x}", .{address_and_offset.offset});3966 log.debug("found __LINKEDIT segment free space at 0x{x}", .{address_and_offset.offset});
...@@ -4239,12 +3969,13 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4239,12 +3969,13 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4239 .Segment = SegmentCommand.empty("__LINKEDIT", .{3969 .Segment = SegmentCommand.empty("__LINKEDIT", .{
4240 .vmaddr = address_and_offset.address,3970 .vmaddr = address_and_offset.address,
4241 .fileoff = address_and_offset.offset,3971 .fileoff = address_and_offset.offset,
4242 .maxprot = maxprot,3972 .maxprot = macho.VM_PROT_READ,
4243 .initprot = initprot,3973 .initprot = macho.VM_PROT_READ,
4244 }),3974 }),
4245 });3975 });
4246 self.load_commands_dirty = true;3976 self.load_commands_dirty = true;
4247 }3977 }
3978
4248 if (self.dyld_info_cmd_index == null) {3979 if (self.dyld_info_cmd_index == null) {
4249 self.dyld_info_cmd_index = @intCast(u16, self.load_commands.items.len);3980 self.dyld_info_cmd_index = @intCast(u16, self.load_commands.items.len);
42503981
...@@ -4291,6 +4022,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4291,6 +4022,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {
42914022
4292 self.load_commands_dirty = true;4023 self.load_commands_dirty = true;
4293 }4024 }
4025
4294 if (self.symtab_cmd_index == null) {4026 if (self.symtab_cmd_index == null) {
4295 self.symtab_cmd_index = @intCast(u16, self.load_commands.items.len);4027 self.symtab_cmd_index = @intCast(u16, self.load_commands.items.len);
42964028
...@@ -4323,6 +4055,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4323,6 +4055,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4323 self.load_commands_dirty = true;4055 self.load_commands_dirty = true;
4324 self.strtab_dirty = true;4056 self.strtab_dirty = true;
4325 }4057 }
4058
4326 if (self.dysymtab_cmd_index == null) {4059 if (self.dysymtab_cmd_index == null) {
4327 self.dysymtab_cmd_index = @intCast(u16, self.load_commands.items.len);4060 self.dysymtab_cmd_index = @intCast(u16, self.load_commands.items.len);
43284061
...@@ -4358,6 +4091,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4358,6 +4091,7 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4358 });4091 });
4359 self.load_commands_dirty = true;4092 self.load_commands_dirty = true;
4360 }4093 }
4094
4361 if (self.dylinker_cmd_index == null) {4095 if (self.dylinker_cmd_index == null) {
4362 self.dylinker_cmd_index = @intCast(u16, self.load_commands.items.len);4096 self.dylinker_cmd_index = @intCast(u16, self.load_commands.items.len);
4363 const cmdsize = @intCast(u32, mem.alignForwardGeneric(4097 const cmdsize = @intCast(u32, mem.alignForwardGeneric(
...@@ -4376,17 +4110,8 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4376,17 +4110,8 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4376 try self.load_commands.append(self.base.allocator, .{ .Dylinker = dylinker_cmd });4110 try self.load_commands.append(self.base.allocator, .{ .Dylinker = dylinker_cmd });
4377 self.load_commands_dirty = true;4111 self.load_commands_dirty = true;
4378 }4112 }
4379 if (self.libsystem_cmd_index == null) {
4380 self.libsystem_cmd_index = @intCast(u16, self.load_commands.items.len);
4381
4382 var dylib_cmd = try commands.createLoadDylibCommand(self.base.allocator, mem.spanZ(LIB_SYSTEM_PATH), 2, 0, 0);
4383 errdefer dylib_cmd.deinit(self.base.allocator);
4384
4385 try self.load_commands.append(self.base.allocator, .{ .Dylib = dylib_cmd });
43864113
4387 self.load_commands_dirty = true;4114 if (self.main_cmd_index == null and self.base.options.output_mode == .Exe) {
4388 }
4389 if (self.main_cmd_index == null) {
4390 self.main_cmd_index = @intCast(u16, self.load_commands.items.len);4115 self.main_cmd_index = @intCast(u16, self.load_commands.items.len);
4391 try self.load_commands.append(self.base.allocator, .{4116 try self.load_commands.append(self.base.allocator, .{
4392 .Main = .{4117 .Main = .{
...@@ -4398,6 +4123,38 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4398,6 +4123,38 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4398 });4123 });
4399 self.load_commands_dirty = true;4124 self.load_commands_dirty = true;
4400 }4125 }
4126
4127 if (self.dylib_id_cmd_index == null and self.base.options.output_mode == .Lib) {
4128 self.dylib_id_cmd_index = @intCast(u16, self.load_commands.items.len);
4129 const install_name = try std.fmt.allocPrint(self.base.allocator, "@rpath/{s}", .{
4130 self.base.options.emit.?.sub_path,
4131 });
4132 defer self.base.allocator.free(install_name);
4133 var dylib_cmd = try commands.createLoadDylibCommand(
4134 self.base.allocator,
4135 install_name,
4136 2,
4137 0x10000, // TODO forward user-provided versions
4138 0x10000,
4139 );
4140 errdefer dylib_cmd.deinit(self.base.allocator);
4141 dylib_cmd.inner.cmd = macho.LC_ID_DYLIB;
4142 try self.load_commands.append(self.base.allocator, .{ .Dylib = dylib_cmd });
4143 self.load_commands_dirty = true;
4144 }
4145
4146 if (self.source_version_cmd_index == null) {
4147 self.source_version_cmd_index = @intCast(u16, self.load_commands.items.len);
4148 try self.load_commands.append(self.base.allocator, .{
4149 .SourceVersion = .{
4150 .cmd = macho.LC_SOURCE_VERSION,
4151 .cmdsize = @sizeOf(macho.source_version_command),
4152 .version = 0x0,
4153 },
4154 });
4155 self.load_commands_dirty = true;
4156 }
4157
4401 if (self.build_version_cmd_index == null) {4158 if (self.build_version_cmd_index == null) {
4402 self.build_version_cmd_index = @intCast(u16, self.load_commands.items.len);4159 self.build_version_cmd_index = @intCast(u16, self.load_commands.items.len);
4403 const cmdsize = @intCast(u32, mem.alignForwardGeneric(4160 const cmdsize = @intCast(u32, mem.alignForwardGeneric(
...@@ -4430,18 +4187,9 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4430,18 +4187,9 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4430 mem.set(u8, cmd.data, 0);4187 mem.set(u8, cmd.data, 0);
4431 mem.copy(u8, cmd.data, mem.asBytes(&ld_ver));4188 mem.copy(u8, cmd.data, mem.asBytes(&ld_ver));
4432 try self.load_commands.append(self.base.allocator, .{ .BuildVersion = cmd });4189 try self.load_commands.append(self.base.allocator, .{ .BuildVersion = cmd });
4433 }
4434 if (self.source_version_cmd_index == null) {
4435 self.source_version_cmd_index = @intCast(u16, self.load_commands.items.len);
4436 try self.load_commands.append(self.base.allocator, .{
4437 .SourceVersion = .{
4438 .cmd = macho.LC_SOURCE_VERSION,
4439 .cmdsize = @sizeOf(macho.source_version_command),
4440 .version = 0x0,
4441 },
4442 });
4443 self.load_commands_dirty = true;4190 self.load_commands_dirty = true;
4444 }4191 }
4192
4445 if (self.uuid_cmd_index == null) {4193 if (self.uuid_cmd_index == null) {
4446 self.uuid_cmd_index = @intCast(u16, self.load_commands.items.len);4194 self.uuid_cmd_index = @intCast(u16, self.load_commands.items.len);
4447 var uuid_cmd: macho.uuid_command = .{4195 var uuid_cmd: macho.uuid_command = .{
...@@ -4453,47 +4201,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {...@@ -4453,47 +4201,6 @@ pub fn populateMissingMetadata(self: *MachO) !void {
4453 try self.load_commands.append(self.base.allocator, .{ .Uuid = uuid_cmd });4201 try self.load_commands.append(self.base.allocator, .{ .Uuid = uuid_cmd });
4454 self.load_commands_dirty = true;4202 self.load_commands_dirty = true;
4455 }4203 }
4456 if (self.code_signature_cmd_index == null and self.requires_adhoc_codesig) {
4457 self.code_signature_cmd_index = @intCast(u16, self.load_commands.items.len);
4458 try self.load_commands.append(self.base.allocator, .{
4459 .LinkeditData = .{
4460 .cmd = macho.LC_CODE_SIGNATURE,
4461 .cmdsize = @sizeOf(macho.linkedit_data_command),
4462 .dataoff = 0,
4463 .datasize = 0,
4464 },
4465 });
4466 self.load_commands_dirty = true;
4467 }
4468 if (!self.strtab_dir.containsAdapted(@as([]const u8, "dyld_stub_binder"), StringSliceAdapter{
4469 .strtab = &self.strtab,
4470 })) {
4471 const import_sym_index = @intCast(u32, self.undefs.items.len);
4472 const n_strx = try self.makeString("dyld_stub_binder");
4473 try self.undefs.append(self.base.allocator, .{
4474 .n_strx = n_strx,
4475 .n_type = macho.N_UNDF | macho.N_EXT,
4476 .n_sect = 0,
4477 .n_desc = @intCast(u8, 1) * macho.N_SYMBOL_RESOLVER,
4478 .n_value = 0,
4479 });
4480 try self.symbol_resolver.putNoClobber(self.base.allocator, n_strx, .{
4481 .where = .undef,
4482 .where_index = import_sym_index,
4483 });
4484 const got_key = GotIndirectionKey{
4485 .where = .undef,
4486 .where_index = import_sym_index,
4487 };
4488 const got_index = @intCast(u32, self.got_entries.items.len);
4489 try self.got_entries.append(self.base.allocator, got_key);
4490 try self.got_entries_map.putNoClobber(self.base.allocator, got_key, got_index);
4491 try self.writeGotEntry(got_index);
4492 self.binding_info_dirty = true;
4493 }
4494 if (self.stub_helper_stubs_start_off == null) {
4495 try self.writeStubHelperPreamble();
4496 }
4497}4204}
44984205
4499fn allocateTextBlock(self: *MachO, text_block: *TextBlock, new_block_size: u64, alignment: u64) !u64 {4206fn allocateTextBlock(self: *MachO, text_block: *TextBlock, new_block_size: u64, alignment: u64) !u64 {