| ... | ... | @@ -133,8 +133,8 @@ objc_selrefs_section_index: ?u16 = null, |
| 133 | 133 | objc_classrefs_section_index: ?u16 = null, |
| 134 | 134 | objc_data_section_index: ?u16 = null, |
| 135 | 135 | |
| 136 | | bss_file_offset: ?u32 = null, |
| 137 | | tlv_bss_file_offset: ?u32 = null, |
| 136 | bss_file_offset: u32 = 0, |
| 137 | tlv_bss_file_offset: u32 = 0, |
| 138 | 138 | |
| 139 | 139 | locals: std.ArrayListUnmanaged(macho.nlist_64) = .{}, |
| 140 | 140 | globals: std.ArrayListUnmanaged(macho.nlist_64) = .{}, |
| ... | ... | @@ -749,6 +749,17 @@ pub fn flush(self: *MachO, comp: *Compilation) !void { |
| 749 | 749 | try self.parseInputFiles(positionals.items, self.base.options.sysroot); |
| 750 | 750 | try self.parseLibs(libs.items, self.base.options.sysroot); |
| 751 | 751 | |
| 752 | if (self.bss_section_index) |idx| { |
| 753 | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 754 | const sect = &seg.sections.items[idx]; |
| 755 | sect.offset = self.bss_file_offset; |
| 756 | } |
| 757 | if (self.tlv_bss_section_index) |idx| { |
| 758 | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 759 | const sect = &seg.sections.items[idx]; |
| 760 | sect.offset = self.tlv_bss_file_offset; |
| 761 | } |
| 762 | |
| 752 | 763 | try self.resolveSymbols(); |
| 753 | 764 | try self.addRpathLCs(rpath_table.keys()); |
| 754 | 765 | try self.addLoadDylibLCs(); |
| ... | ... | @@ -781,6 +792,20 @@ pub fn flush(self: *MachO, comp: *Compilation) !void { |
| 781 | 792 | } |
| 782 | 793 | } |
| 783 | 794 | try self.writeAtoms(); |
| 795 | |
| 796 | if (self.bss_section_index) |idx| { |
| 797 | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 798 | const sect = &seg.sections.items[idx]; |
| 799 | self.bss_file_offset = sect.offset; |
| 800 | sect.offset = 0; |
| 801 | } |
| 802 | if (self.tlv_bss_section_index) |idx| { |
| 803 | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 804 | const sect = &seg.sections.items[idx]; |
| 805 | self.tlv_bss_file_offset = sect.offset; |
| 806 | sect.offset = 0; |
| 807 | } |
| 808 | |
| 784 | 809 | try self.flushModule(comp); |
| 785 | 810 | } |
| 786 | 811 | |
| ... | ... | @@ -1687,8 +1712,7 @@ pub fn writeAtom(self: *MachO, atom: *TextBlock, match: MatchingSection) !void { |
| 1687 | 1712 | const seg = self.load_commands.items[match.seg].Segment; |
| 1688 | 1713 | const sect = seg.sections.items[match.sect]; |
| 1689 | 1714 | const sym = self.locals.items[atom.local_sym_index]; |
| 1690 | | const sect_offset = self.getPtrToSectionOffset(match).*; |
| 1691 | | const file_offset = sect_offset + sym.n_value - sect.addr; |
| 1715 | const file_offset = sect.offset + sym.n_value - sect.addr; |
| 1692 | 1716 | try atom.resolveRelocs(self); |
| 1693 | 1717 | log.debug("writing atom for symbol {s} at file offset 0x{x}", .{ self.getString(sym.n_strx), file_offset }); |
| 1694 | 1718 | try self.base.file.?.pwriteAll(atom.code.items, file_offset); |
| ... | ... | @@ -3469,13 +3493,9 @@ pub fn populateMissingMetadata(self: *MachO) !void { |
| 3469 | 3493 | .flags = macho.S_THREAD_LOCAL_ZEROFILL, |
| 3470 | 3494 | }, |
| 3471 | 3495 | ); |
| 3472 | | |
| 3473 | | // We keep offset to the section in a separate variable as the actual section is usually pointing at the |
| 3474 | | // beginning of the file. |
| 3475 | | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 3476 | | const out_sect = &seg.sections.items[self.tlv_bss_section_index.?]; |
| 3477 | | self.tlv_bss_file_offset = out_sect.offset; |
| 3478 | | out_sect.offset = 0; |
| 3496 | const seg = self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 3497 | const sect = seg.sections.items[self.tlv_bss_section_index.?]; |
| 3498 | self.tlv_bss_file_offset = sect.offset; |
| 3479 | 3499 | } |
| 3480 | 3500 | |
| 3481 | 3501 | if (self.bss_section_index == null) { |
| ... | ... | @@ -3490,13 +3510,9 @@ pub fn populateMissingMetadata(self: *MachO) !void { |
| 3490 | 3510 | .flags = macho.S_ZEROFILL, |
| 3491 | 3511 | }, |
| 3492 | 3512 | ); |
| 3493 | | |
| 3494 | | // We keep offset to the section in a separate variable as the actual section is usually pointing at the |
| 3495 | | // beginning of the file. |
| 3496 | | const seg = &self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 3497 | | const out_sect = &seg.sections.items[self.bss_section_index.?]; |
| 3498 | | self.bss_file_offset = out_sect.offset; |
| 3499 | | out_sect.offset = 0; |
| 3513 | const seg = self.load_commands.items[self.data_segment_cmd_index.?].Segment; |
| 3514 | const sect = seg.sections.items[self.bss_section_index.?]; |
| 3515 | self.bss_file_offset = sect.offset; |
| 3500 | 3516 | } |
| 3501 | 3517 | |
| 3502 | 3518 | if (self.linkedit_segment_cmd_index == null) { |
| ... | ... | @@ -3767,8 +3783,7 @@ fn growSection(self: *MachO, match: MatchingSection, new_size: u32) !void { |
| 3767 | 3783 | const sect = &seg.sections.items[match.sect]; |
| 3768 | 3784 | |
| 3769 | 3785 | const alignment = try math.powi(u32, 2, sect.@"align"); |
| 3770 | | const sect_offset = self.getPtrToSectionOffset(match); |
| 3771 | | const max_size = self.allocatedSize(match.seg, sect_offset.*); |
| 3786 | const max_size = self.allocatedSize(match.seg, sect.offset); |
| 3772 | 3787 | const ideal_size = padToIdeal(new_size); |
| 3773 | 3788 | const needed_size = mem.alignForwardGeneric(u32, ideal_size, alignment); |
| 3774 | 3789 | |
| ... | ... | @@ -3830,24 +3845,22 @@ fn growSection(self: *MachO, match: MatchingSection, new_size: u32) !void { |
| 3830 | 3845 | }); |
| 3831 | 3846 | |
| 3832 | 3847 | for (next_seg.sections.items) |*moved_sect, moved_sect_id| { |
| 3833 | | const moved_match = MatchingSection{ |
| 3834 | | .seg = @intCast(u16, next), |
| 3835 | | .sect = @intCast(u16, moved_sect_id), |
| 3836 | | }; |
| 3837 | | const ptr_sect_offset = self.getPtrToSectionOffset(moved_match); |
| 3838 | | ptr_sect_offset.* += @intCast(u32, seg_offset_amt); |
| 3848 | moved_sect.offset += @intCast(u32, seg_offset_amt); |
| 3839 | 3849 | moved_sect.addr += seg_offset_amt; |
| 3840 | 3850 | |
| 3841 | 3851 | log.warn(" (new {s},{s} file offsets from 0x{x} to 0x{x} (in memory 0x{x} to 0x{x}))", .{ |
| 3842 | 3852 | commands.segmentName(moved_sect.*), |
| 3843 | 3853 | commands.sectionName(moved_sect.*), |
| 3844 | | ptr_sect_offset.*, |
| 3845 | | ptr_sect_offset.* + moved_sect.size, |
| 3854 | moved_sect.offset, |
| 3855 | moved_sect.offset + moved_sect.size, |
| 3846 | 3856 | moved_sect.addr, |
| 3847 | 3857 | moved_sect.addr + moved_sect.size, |
| 3848 | 3858 | }); |
| 3849 | 3859 | |
| 3850 | | try self.allocateLocalSymbols(moved_match, @intCast(i64, seg_offset_amt)); |
| 3860 | try self.allocateLocalSymbols(.{ |
| 3861 | .seg = @intCast(u16, next), |
| 3862 | .sect = @intCast(u16, moved_sect_id), |
| 3863 | }, @intCast(i64, seg_offset_amt)); |
| 3851 | 3864 | } |
| 3852 | 3865 | } |
| 3853 | 3866 | } |
| ... | ... | @@ -3867,25 +3880,23 @@ fn growSection(self: *MachO, match: MatchingSection, new_size: u32) !void { |
| 3867 | 3880 | |
| 3868 | 3881 | var next = match.sect + 1; |
| 3869 | 3882 | while (next < seg.sections.items.len) : (next += 1) { |
| 3870 | | const moved_match = MatchingSection{ |
| 3871 | | .seg = match.seg, |
| 3872 | | .sect = next, |
| 3873 | | }; |
| 3874 | 3883 | const moved_sect = &seg.sections.items[next]; |
| 3875 | | const ptr_sect_offset = self.getPtrToSectionOffset(moved_match); |
| 3876 | | ptr_sect_offset.* += @intCast(u32, offset_amt); |
| 3884 | moved_sect.offset += @intCast(u32, offset_amt); |
| 3877 | 3885 | moved_sect.addr += offset_amt; |
| 3878 | 3886 | |
| 3879 | 3887 | log.warn(" (new {s},{s} file offsets from 0x{x} to 0x{x} (in memory 0x{x} to 0x{x}))", .{ |
| 3880 | 3888 | commands.segmentName(moved_sect.*), |
| 3881 | 3889 | commands.sectionName(moved_sect.*), |
| 3882 | | ptr_sect_offset.*, |
| 3883 | | ptr_sect_offset.* + moved_sect.size, |
| 3890 | moved_sect.offset, |
| 3891 | moved_sect.offset + moved_sect.size, |
| 3884 | 3892 | moved_sect.addr, |
| 3885 | 3893 | moved_sect.addr + moved_sect.size, |
| 3886 | 3894 | }); |
| 3887 | 3895 | |
| 3888 | | try self.allocateLocalSymbols(moved_match, @intCast(i64, offset_amt)); |
| 3896 | try self.allocateLocalSymbols(.{ |
| 3897 | .seg = match.seg, |
| 3898 | .sect = next, |
| 3899 | }, @intCast(i64, offset_amt)); |
| 3889 | 3900 | } |
| 3890 | 3901 | } |
| 3891 | 3902 | |
| ... | ... | @@ -3916,25 +3927,6 @@ fn getSectionMaxAlignment(self: *MachO, segment_id: u16, start_sect_id: u16) !u3 |
| 3916 | 3927 | return max_alignment; |
| 3917 | 3928 | } |
| 3918 | 3929 | |
| 3919 | | fn getPtrToSectionOffset(self: *MachO, match: MatchingSection) *u32 { |
| 3920 | | if (self.data_segment_cmd_index.? == match.seg) { |
| 3921 | | if (self.bss_section_index) |idx| { |
| 3922 | | if (idx == match.sect) { |
| 3923 | | return &self.bss_file_offset.?; |
| 3924 | | } |
| 3925 | | } |
| 3926 | | if (self.tlv_bss_section_index) |idx| { |
| 3927 | | if (idx == match.sect) { |
| 3928 | | return &self.tlv_bss_file_offset.?; |
| 3929 | | } |
| 3930 | | } |
| 3931 | | } |
| 3932 | | |
| 3933 | | const seg = &self.load_commands.items[match.seg].Segment; |
| 3934 | | const sect = &seg.sections.items[match.sect]; |
| 3935 | | return &sect.offset; |
| 3936 | | } |
| 3937 | | |
| 3938 | 3930 | fn allocateTextBlock(self: *MachO, text_block: *TextBlock, new_block_size: u64, alignment: u64) !u64 { |
| 3939 | 3931 | const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment; |
| 3940 | 3932 | const text_section = &text_segment.sections.items[self.text_section_index.?]; |