| ... | @@ -104,9 +104,7 @@ dyld_stub_binder_index: ?u16 = null, | ... | @@ -104,9 +104,7 @@ dyld_stub_binder_index: ?u16 = null, |
| 104 | /// Table of symbol names aka the string table. | 104 | /// Table of symbol names aka the string table. |
| 105 | string_table: std.ArrayListUnmanaged(u8) = .{}, | 105 | string_table: std.ArrayListUnmanaged(u8) = .{}, |
| 106 | | 106 | |
| 107 | /// Table of symbol vaddr values. The values is the absolute vaddr value. | 107 | /// Table of trampolines to the actual symbols in __text section. |
| 108 | /// If the vaddr of the executable __TEXT segment vaddr changes, the entire offset | | |
| 109 | /// table needs to be rewritten. | | |
| 110 | offset_table: std.ArrayListUnmanaged(u64) = .{}, | 108 | offset_table: std.ArrayListUnmanaged(u64) = .{}, |
| 111 | | 109 | |
| 112 | /// Table of binding info entries. | 110 | /// Table of binding info entries. |
| ... | @@ -1307,35 +1305,35 @@ pub fn populateMissingMetadata(self: *MachO) !void { | ... | @@ -1307,35 +1305,35 @@ pub fn populateMissingMetadata(self: *MachO) !void { |
| 1307 | | 1305 | |
| 1308 | log.debug("found __TEXT segment free space 0x{x} to 0x{x}\n", .{ 0, needed_size }); | 1306 | log.debug("found __TEXT segment free space 0x{x} to 0x{x}\n", .{ 0, needed_size }); |
| 1309 | | 1307 | |
| 1310 | try self.load_commands.append(self.base.allocator, .{ | 1308 | var segment = SegmentCommand.empty(.{ |
| 1311 | .Segment = SegmentCommand.empty(.{ | 1309 | .cmd = macho.LC_SEGMENT_64, |
| 1312 | .cmd = macho.LC_SEGMENT_64, | 1310 | .cmdsize = @sizeOf(macho.segment_command_64), |
| 1313 | .cmdsize = @sizeOf(macho.segment_command_64), | 1311 | .segname = makeStaticString("__TEXT"), |
| 1314 | .segname = makeStaticString("__TEXT"), | 1312 | .vmaddr = 0x100000000, // always starts at 4GB |
| 1315 | .vmaddr = 0x100000000, // always starts at 4GB | 1313 | .vmsize = needed_size, |
| 1316 | .vmsize = needed_size, | 1314 | .fileoff = 0, |
| 1317 | .fileoff = 0, | 1315 | .filesize = needed_size, |
| 1318 | .filesize = needed_size, | 1316 | .maxprot = maxprot, |
| 1319 | .maxprot = maxprot, | 1317 | .initprot = initprot, |
| 1320 | .initprot = initprot, | 1318 | .nsects = 0, |
| 1321 | .nsects = 0, | 1319 | .flags = 0, |
| 1322 | .flags = 0, | | |
| 1323 | }), | | |
| 1324 | }); | 1320 | }); |
| | 1321 | segment.header_pad = self.header_pad; |
| | 1322 | try self.load_commands.append(self.base.allocator, .{ .Segment = segment }); |
| 1325 | self.cmd_table_dirty = true; | 1323 | self.cmd_table_dirty = true; |
| 1326 | } | 1324 | } |
| 1327 | if (self.text_section_index == null) { | 1325 | if (self.text_section_index == null) { |
| 1328 | const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment; | 1326 | const text_segment = &self.load_commands.items[self.text_segment_cmd_index.?].Segment; |
| 1329 | self.text_section_index = @intCast(u16, text_segment.sections.items.len); | 1327 | self.text_section_index = @intCast(u16, text_segment.sections.items.len); |
| 1330 | | 1328 | |
| 1331 | const alignment: u32 = switch (self.base.options.target.cpu.arch) { | 1329 | const alignment: u2 = switch (self.base.options.target.cpu.arch) { |
| 1332 | .x86_64 => 0, | 1330 | .x86_64 => 0, |
| 1333 | .aarch64 => 2, | 1331 | .aarch64 => 2, |
| 1334 | else => unreachable, // unhandled architecture type | 1332 | else => unreachable, // unhandled architecture type |
| 1335 | }; | 1333 | }; |
| 1336 | const flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS; | 1334 | const flags = macho.S_REGULAR | macho.S_ATTR_PURE_INSTRUCTIONS | macho.S_ATTR_SOME_INSTRUCTIONS; |
| 1337 | const needed_size = self.base.options.program_code_size_hint; | 1335 | const needed_size = self.base.options.program_code_size_hint; |
| 1338 | const off = self.header_pad; | 1336 | const off = text_segment.findFreeSpace(needed_size, @as(u16, 1) << alignment); |
| 1339 | | 1337 | |
| 1340 | log.debug("found __text section free space 0x{x} to 0x{x}\n", .{ off, off + needed_size }); | 1338 | log.debug("found __text section free space 0x{x} to 0x{x}\n", .{ off, off + needed_size }); |
| 1341 | | 1339 | |
| ... | @@ -2086,7 +2084,7 @@ fn parseFromFile(self: *MachO, file: fs.File) !void { | ... | @@ -2086,7 +2084,7 @@ fn parseFromFile(self: *MachO, file: fs.File) !void { |
| 2086 | self.header = header; | 2084 | self.header = header; |
| 2087 | } | 2085 | } |
| 2088 | | 2086 | |
| 2089 | pub fn parseAndCmpName(name: []const u8, needle: []const u8) bool { | 2087 | fn parseAndCmpName(name: []const u8, needle: []const u8) bool { |
| 2090 | const len = mem.indexOfScalar(u8, name[0..], @as(u8, 0)) orelse name.len; | 2088 | const len = mem.indexOfScalar(u8, name[0..], @as(u8, 0)) orelse name.len; |
| 2091 | return mem.eql(u8, name[0..len], needle); | 2089 | return mem.eql(u8, name[0..len], needle); |
| 2092 | } | 2090 | } |