| ... | ... | @@ -18,15 +18,15 @@ pub const ZigGotSection = struct { |
| 18 | 18 | } |
| 19 | 19 | |
| 20 | 20 | pub fn addSymbol(zig_got: *ZigGotSection, sym_index: Symbol.Index, macho_file: *MachO) !Index { |
| 21 | | const comp = macho_file.base.comp; |
| 22 | | const gpa = comp.gpa; |
| 21 | const gpa = macho_file.base.comp.gpa; |
| 22 | const zo = macho_file.getZigObject().?; |
| 23 | 23 | const index = try zig_got.allocateEntry(gpa); |
| 24 | 24 | const entry = &zig_got.entries.items[index]; |
| 25 | 25 | entry.* = sym_index; |
| 26 | | const symbol = macho_file.getSymbol(sym_index); |
| 26 | const symbol = zo.getSymbol(sym_index); |
| 27 | 27 | assert(symbol.flags.needs_zig_got); |
| 28 | 28 | symbol.flags.has_zig_got = true; |
| 29 | | try symbol.addExtra(.{ .zig_got = index }, macho_file); |
| 29 | symbol.addExtra(.{ .zig_got = index }, macho_file); |
| 30 | 30 | return index; |
| 31 | 31 | } |
| 32 | 32 | |
| ... | ... | @@ -53,9 +53,10 @@ pub const ZigGotSection = struct { |
| 53 | 53 | try macho_file.growSection(macho_file.zig_got_sect_index.?, needed_size); |
| 54 | 54 | zig_got.dirty = false; |
| 55 | 55 | } |
| 56 | const zo = macho_file.getZigObject().?; |
| 56 | 57 | const off = zig_got.entryOffset(index, macho_file); |
| 57 | 58 | const entry = zig_got.entries.items[index]; |
| 58 | | const value = macho_file.getSymbol(entry).getAddress(.{ .stubs = false }, macho_file); |
| 59 | const value = zo.getSymbol(entry).getAddress(.{ .stubs = false }, macho_file); |
| 59 | 60 | |
| 60 | 61 | var buf: [8]u8 = undefined; |
| 61 | 62 | std.mem.writeInt(u64, &buf, value, .little); |
| ... | ... | @@ -63,8 +64,9 @@ pub const ZigGotSection = struct { |
| 63 | 64 | } |
| 64 | 65 | |
| 65 | 66 | pub fn writeAll(zig_got: ZigGotSection, macho_file: *MachO, writer: anytype) !void { |
| 67 | const zo = macho_file.getZigObject().?; |
| 66 | 68 | for (zig_got.entries.items) |entry| { |
| 67 | | const symbol = macho_file.getSymbol(entry); |
| 69 | const symbol = zo.getSymbol(entry); |
| 68 | 70 | const value = symbol.address(.{ .stubs = false }, macho_file); |
| 69 | 71 | try writer.writeInt(u64, value, .little); |
| 70 | 72 | } |
| ... | ... | @@ -87,22 +89,25 @@ pub const ZigGotSection = struct { |
| 87 | 89 | ) !void { |
| 88 | 90 | _ = options; |
| 89 | 91 | _ = unused_fmt_string; |
| 92 | const zig_got = ctx.zig_got; |
| 93 | const macho_file = ctx.macho_file; |
| 94 | const zo = macho_file.getZigObject().?; |
| 90 | 95 | try writer.writeAll("__zig_got\n"); |
| 91 | | for (ctx.zig_got.entries.items, 0..) |entry, index| { |
| 92 | | const symbol = ctx.macho_file.getSymbol(entry); |
| 96 | for (zig_got.entries.items, 0..) |entry, index| { |
| 97 | const symbol = zo.getSymbol(entry); |
| 93 | 98 | try writer.print(" {d}@0x{x} => {d}@0x{x} ({s})\n", .{ |
| 94 | 99 | index, |
| 95 | | ctx.zig_got.entryAddress(@intCast(index), ctx.macho_file), |
| 100 | zig_got.entryAddress(@intCast(index), macho_file), |
| 96 | 101 | entry, |
| 97 | | symbol.getAddress(.{}, ctx.macho_file), |
| 98 | | symbol.getName(ctx.macho_file), |
| 102 | symbol.getAddress(.{}, macho_file), |
| 103 | symbol.getName(macho_file), |
| 99 | 104 | }); |
| 100 | 105 | } |
| 101 | 106 | } |
| 102 | 107 | }; |
| 103 | 108 | |
| 104 | 109 | pub const GotSection = struct { |
| 105 | | symbols: std.ArrayListUnmanaged(Symbol.Index) = .{}, |
| 110 | symbols: std.ArrayListUnmanaged(MachO.Ref) = .{}, |
| 106 | 111 | |
| 107 | 112 | pub const Index = u32; |
| 108 | 113 | |
| ... | ... | @@ -110,14 +115,14 @@ pub const GotSection = struct { |
| 110 | 115 | got.symbols.deinit(allocator); |
| 111 | 116 | } |
| 112 | 117 | |
| 113 | | pub fn addSymbol(got: *GotSection, sym_index: Symbol.Index, macho_file: *MachO) !void { |
| 118 | pub fn addSymbol(got: *GotSection, ref: MachO.Ref, macho_file: *MachO) !void { |
| 114 | 119 | const gpa = macho_file.base.comp.gpa; |
| 115 | 120 | const index = @as(Index, @intCast(got.symbols.items.len)); |
| 116 | 121 | const entry = try got.symbols.addOne(gpa); |
| 117 | | entry.* = sym_index; |
| 118 | | const symbol = macho_file.getSymbol(sym_index); |
| 122 | entry.* = ref; |
| 123 | const symbol = ref.getSymbol(macho_file).?; |
| 119 | 124 | symbol.flags.has_got = true; |
| 120 | | try symbol.addExtra(.{ .got = index }, macho_file); |
| 125 | symbol.addExtra(.{ .got = index }, macho_file); |
| 121 | 126 | } |
| 122 | 127 | |
| 123 | 128 | pub fn getAddress(got: GotSection, index: Index, macho_file: *MachO) u64 { |
| ... | ... | @@ -133,8 +138,8 @@ pub const GotSection = struct { |
| 133 | 138 | pub fn write(got: GotSection, macho_file: *MachO, writer: anytype) !void { |
| 134 | 139 | const tracy = trace(@src()); |
| 135 | 140 | defer tracy.end(); |
| 136 | | for (got.symbols.items) |sym_index| { |
| 137 | | const sym = macho_file.getSymbol(sym_index); |
| 141 | for (got.symbols.items) |ref| { |
| 142 | const sym = ref.getSymbol(macho_file).?; |
| 138 | 143 | const value = if (sym.flags.import) @as(u64, 0) else sym.getAddress(.{}, macho_file); |
| 139 | 144 | try writer.writeInt(u64, value, .little); |
| 140 | 145 | } |
| ... | ... | @@ -157,12 +162,12 @@ pub const GotSection = struct { |
| 157 | 162 | ) !void { |
| 158 | 163 | _ = options; |
| 159 | 164 | _ = unused_fmt_string; |
| 160 | | for (ctx.got.symbols.items, 0..) |entry, i| { |
| 161 | | const symbol = ctx.macho_file.getSymbol(entry); |
| 165 | for (ctx.got.symbols.items, 0..) |ref, i| { |
| 166 | const symbol = ref.getSymbol(ctx.macho_file).?; |
| 162 | 167 | try writer.print(" {d}@0x{x} => {d}@0x{x} ({s})\n", .{ |
| 163 | 168 | i, |
| 164 | 169 | symbol.getGotAddress(ctx.macho_file), |
| 165 | | entry, |
| 170 | ref, |
| 166 | 171 | symbol.getAddress(.{}, ctx.macho_file), |
| 167 | 172 | symbol.getName(ctx.macho_file), |
| 168 | 173 | }); |
| ... | ... | @@ -171,7 +176,7 @@ pub const GotSection = struct { |
| 171 | 176 | }; |
| 172 | 177 | |
| 173 | 178 | pub const StubsSection = struct { |
| 174 | | symbols: std.ArrayListUnmanaged(Symbol.Index) = .{}, |
| 179 | symbols: std.ArrayListUnmanaged(MachO.Ref) = .{}, |
| 175 | 180 | |
| 176 | 181 | pub const Index = u32; |
| 177 | 182 | |
| ... | ... | @@ -179,13 +184,13 @@ pub const StubsSection = struct { |
| 179 | 184 | stubs.symbols.deinit(allocator); |
| 180 | 185 | } |
| 181 | 186 | |
| 182 | | pub fn addSymbol(stubs: *StubsSection, sym_index: Symbol.Index, macho_file: *MachO) !void { |
| 187 | pub fn addSymbol(stubs: *StubsSection, ref: MachO.Ref, macho_file: *MachO) !void { |
| 183 | 188 | const gpa = macho_file.base.comp.gpa; |
| 184 | 189 | const index = @as(Index, @intCast(stubs.symbols.items.len)); |
| 185 | 190 | const entry = try stubs.symbols.addOne(gpa); |
| 186 | | entry.* = sym_index; |
| 187 | | const symbol = macho_file.getSymbol(sym_index); |
| 188 | | try symbol.addExtra(.{ .stubs = index }, macho_file); |
| 191 | entry.* = ref; |
| 192 | const symbol = ref.getSymbol(macho_file).?; |
| 193 | symbol.addExtra(.{ .stubs = index }, macho_file); |
| 189 | 194 | } |
| 190 | 195 | |
| 191 | 196 | pub fn getAddress(stubs: StubsSection, index: Index, macho_file: *MachO) u64 { |
| ... | ... | @@ -205,8 +210,8 @@ pub const StubsSection = struct { |
| 205 | 210 | const cpu_arch = macho_file.getTarget().cpu.arch; |
| 206 | 211 | const laptr_sect = macho_file.sections.items(.header)[macho_file.la_symbol_ptr_sect_index.?]; |
| 207 | 212 | |
| 208 | | for (stubs.symbols.items, 0..) |sym_index, idx| { |
| 209 | | const sym = macho_file.getSymbol(sym_index); |
| 213 | for (stubs.symbols.items, 0..) |ref, idx| { |
| 214 | const sym = ref.getSymbol(macho_file).?; |
| 210 | 215 | const source = sym.getAddress(.{ .stubs = true }, macho_file); |
| 211 | 216 | const target = laptr_sect.addr + idx * @sizeOf(u64); |
| 212 | 217 | switch (cpu_arch) { |
| ... | ... | @@ -248,12 +253,12 @@ pub const StubsSection = struct { |
| 248 | 253 | ) !void { |
| 249 | 254 | _ = options; |
| 250 | 255 | _ = unused_fmt_string; |
| 251 | | for (ctx.stubs.symbols.items, 0..) |entry, i| { |
| 252 | | const symbol = ctx.macho_file.getSymbol(entry); |
| 256 | for (ctx.stubs.symbols.items, 0..) |ref, i| { |
| 257 | const symbol = ref.getSymbol(ctx.macho_file).?; |
| 253 | 258 | try writer.print(" {d}@0x{x} => {d}@0x{x} ({s})\n", .{ |
| 254 | 259 | i, |
| 255 | 260 | symbol.getStubsAddress(ctx.macho_file), |
| 256 | | entry, |
| 261 | ref, |
| 257 | 262 | symbol.getAddress(.{}, ctx.macho_file), |
| 258 | 263 | symbol.getName(ctx.macho_file), |
| 259 | 264 | }); |
| ... | ... | @@ -284,8 +289,8 @@ pub const StubsHelperSection = struct { |
| 284 | 289 | _ = stubs_helper; |
| 285 | 290 | const cpu_arch = macho_file.getTarget().cpu.arch; |
| 286 | 291 | var s: usize = preambleSize(cpu_arch); |
| 287 | | for (macho_file.stubs.symbols.items) |sym_index| { |
| 288 | | const sym = macho_file.getSymbol(sym_index); |
| 292 | for (macho_file.stubs.symbols.items) |ref| { |
| 293 | const sym = ref.getSymbol(macho_file).?; |
| 289 | 294 | if (sym.flags.weak) continue; |
| 290 | 295 | s += entrySize(cpu_arch); |
| 291 | 296 | } |
| ... | ... | @@ -304,8 +309,8 @@ pub const StubsHelperSection = struct { |
| 304 | 309 | const entry_size = entrySize(cpu_arch); |
| 305 | 310 | |
| 306 | 311 | var idx: usize = 0; |
| 307 | | for (macho_file.stubs.symbols.items) |sym_index| { |
| 308 | | const sym = macho_file.getSymbol(sym_index); |
| 312 | for (macho_file.stubs.symbols.items) |ref| { |
| 313 | const sym = ref.getSymbol(macho_file).?; |
| 309 | 314 | if (sym.flags.weak) continue; |
| 310 | 315 | const offset = macho_file.lazy_bind.offsets.items[idx]; |
| 311 | 316 | const source: i64 = @intCast(sect.addr + preamble_size + entry_size * idx); |
| ... | ... | @@ -339,14 +344,15 @@ pub const StubsHelperSection = struct { |
| 339 | 344 | |
| 340 | 345 | fn writePreamble(stubs_helper: StubsHelperSection, macho_file: *MachO, writer: anytype) !void { |
| 341 | 346 | _ = stubs_helper; |
| 347 | const obj = macho_file.getInternalObject().?; |
| 342 | 348 | const cpu_arch = macho_file.getTarget().cpu.arch; |
| 343 | 349 | const sect = macho_file.sections.items(.header)[macho_file.stubs_helper_sect_index.?]; |
| 344 | 350 | const dyld_private_addr = target: { |
| 345 | | const sym = macho_file.getSymbol(macho_file.dyld_private_index.?); |
| 351 | const sym = obj.getDyldPrivateRef(macho_file).?.getSymbol(macho_file).?; |
| 346 | 352 | break :target sym.getAddress(.{}, macho_file); |
| 347 | 353 | }; |
| 348 | 354 | const dyld_stub_binder_addr = target: { |
| 349 | | const sym = macho_file.getSymbol(macho_file.dyld_stub_binder_index.?); |
| 355 | const sym = obj.getDyldStubBinderRef(macho_file).?.getSymbol(macho_file).?; |
| 350 | 356 | break :target sym.getGotAddress(macho_file); |
| 351 | 357 | }; |
| 352 | 358 | switch (cpu_arch) { |
| ... | ... | @@ -402,8 +408,8 @@ pub const LaSymbolPtrSection = struct { |
| 402 | 408 | const cpu_arch = macho_file.getTarget().cpu.arch; |
| 403 | 409 | const sect = macho_file.sections.items(.header)[macho_file.stubs_helper_sect_index.?]; |
| 404 | 410 | var stub_helper_idx: u32 = 0; |
| 405 | | for (macho_file.stubs.symbols.items) |sym_index| { |
| 406 | | const sym = macho_file.getSymbol(sym_index); |
| 411 | for (macho_file.stubs.symbols.items) |ref| { |
| 412 | const sym = ref.getSymbol(macho_file).?; |
| 407 | 413 | if (sym.flags.weak) { |
| 408 | 414 | const value = sym.getAddress(.{ .stubs = false }, macho_file); |
| 409 | 415 | try writer.writeInt(u64, @intCast(value), .little); |
| ... | ... | @@ -418,7 +424,7 @@ pub const LaSymbolPtrSection = struct { |
| 418 | 424 | }; |
| 419 | 425 | |
| 420 | 426 | pub const TlvPtrSection = struct { |
| 421 | | symbols: std.ArrayListUnmanaged(Symbol.Index) = .{}, |
| 427 | symbols: std.ArrayListUnmanaged(MachO.Ref) = .{}, |
| 422 | 428 | |
| 423 | 429 | pub const Index = u32; |
| 424 | 430 | |
| ... | ... | @@ -426,13 +432,13 @@ pub const TlvPtrSection = struct { |
| 426 | 432 | tlv.symbols.deinit(allocator); |
| 427 | 433 | } |
| 428 | 434 | |
| 429 | | pub fn addSymbol(tlv: *TlvPtrSection, sym_index: Symbol.Index, macho_file: *MachO) !void { |
| 435 | pub fn addSymbol(tlv: *TlvPtrSection, ref: MachO.Ref, macho_file: *MachO) !void { |
| 430 | 436 | const gpa = macho_file.base.comp.gpa; |
| 431 | 437 | const index = @as(Index, @intCast(tlv.symbols.items.len)); |
| 432 | 438 | const entry = try tlv.symbols.addOne(gpa); |
| 433 | | entry.* = sym_index; |
| 434 | | const symbol = macho_file.getSymbol(sym_index); |
| 435 | | try symbol.addExtra(.{ .tlv_ptr = index }, macho_file); |
| 439 | entry.* = ref; |
| 440 | const symbol = ref.getSymbol(macho_file).?; |
| 441 | symbol.addExtra(.{ .tlv_ptr = index }, macho_file); |
| 436 | 442 | } |
| 437 | 443 | |
| 438 | 444 | pub fn getAddress(tlv: TlvPtrSection, index: Index, macho_file: *MachO) u64 { |
| ... | ... | @@ -449,8 +455,8 @@ pub const TlvPtrSection = struct { |
| 449 | 455 | const tracy = trace(@src()); |
| 450 | 456 | defer tracy.end(); |
| 451 | 457 | |
| 452 | | for (tlv.symbols.items) |sym_index| { |
| 453 | | const sym = macho_file.getSymbol(sym_index); |
| 458 | for (tlv.symbols.items) |ref| { |
| 459 | const sym = ref.getSymbol(macho_file).?; |
| 454 | 460 | if (sym.flags.import) { |
| 455 | 461 | try writer.writeInt(u64, 0, .little); |
| 456 | 462 | } else { |
| ... | ... | @@ -476,12 +482,12 @@ pub const TlvPtrSection = struct { |
| 476 | 482 | ) !void { |
| 477 | 483 | _ = options; |
| 478 | 484 | _ = unused_fmt_string; |
| 479 | | for (ctx.tlv.symbols.items, 0..) |entry, i| { |
| 480 | | const symbol = ctx.macho_file.getSymbol(entry); |
| 485 | for (ctx.tlv.symbols.items, 0..) |ref, i| { |
| 486 | const symbol = ref.getSymbol(ctx.macho_file).?; |
| 481 | 487 | try writer.print(" {d}@0x{x} => {d}@0x{x} ({s})\n", .{ |
| 482 | 488 | i, |
| 483 | 489 | symbol.getTlvPtrAddress(ctx.macho_file), |
| 484 | | entry, |
| 490 | ref, |
| 485 | 491 | symbol.getAddress(.{}, ctx.macho_file), |
| 486 | 492 | symbol.getName(ctx.macho_file), |
| 487 | 493 | }); |
| ... | ... | @@ -490,7 +496,7 @@ pub const TlvPtrSection = struct { |
| 490 | 496 | }; |
| 491 | 497 | |
| 492 | 498 | pub const ObjcStubsSection = struct { |
| 493 | | symbols: std.ArrayListUnmanaged(Symbol.Index) = .{}, |
| 499 | symbols: std.ArrayListUnmanaged(MachO.Ref) = .{}, |
| 494 | 500 | |
| 495 | 501 | pub fn deinit(objc: *ObjcStubsSection, allocator: Allocator) void { |
| 496 | 502 | objc.symbols.deinit(allocator); |
| ... | ... | @@ -504,13 +510,13 @@ pub const ObjcStubsSection = struct { |
| 504 | 510 | }; |
| 505 | 511 | } |
| 506 | 512 | |
| 507 | | pub fn addSymbol(objc: *ObjcStubsSection, sym_index: Symbol.Index, macho_file: *MachO) !void { |
| 513 | pub fn addSymbol(objc: *ObjcStubsSection, ref: MachO.Ref, macho_file: *MachO) !void { |
| 508 | 514 | const gpa = macho_file.base.comp.gpa; |
| 509 | 515 | const index = @as(Index, @intCast(objc.symbols.items.len)); |
| 510 | 516 | const entry = try objc.symbols.addOne(gpa); |
| 511 | | entry.* = sym_index; |
| 512 | | const symbol = macho_file.getSymbol(sym_index); |
| 513 | | try symbol.addExtra(.{ .objc_stubs = index }, macho_file); |
| 517 | entry.* = ref; |
| 518 | const symbol = ref.getSymbol(macho_file).?; |
| 519 | symbol.addExtra(.{ .objc_stubs = index }, macho_file); |
| 514 | 520 | } |
| 515 | 521 | |
| 516 | 522 | pub fn getAddress(objc: ObjcStubsSection, index: Index, macho_file: *MachO) u64 { |
| ... | ... | @@ -527,8 +533,10 @@ pub const ObjcStubsSection = struct { |
| 527 | 533 | const tracy = trace(@src()); |
| 528 | 534 | defer tracy.end(); |
| 529 | 535 | |
| 530 | | for (objc.symbols.items, 0..) |sym_index, idx| { |
| 531 | | const sym = macho_file.getSymbol(sym_index); |
| 536 | const obj = macho_file.getInternalObject().?; |
| 537 | |
| 538 | for (objc.symbols.items, 0..) |ref, idx| { |
| 539 | const sym = ref.getSymbol(macho_file).?; |
| 532 | 540 | const addr = objc.getAddress(@intCast(idx), macho_file); |
| 533 | 541 | switch (macho_file.getTarget().cpu.arch) { |
| 534 | 542 | .x86_64 => { |
| ... | ... | @@ -540,7 +548,7 @@ pub const ObjcStubsSection = struct { |
| 540 | 548 | } |
| 541 | 549 | try writer.writeAll(&.{ 0xff, 0x25 }); |
| 542 | 550 | { |
| 543 | | const target_sym = macho_file.getSymbol(macho_file.objc_msg_send_index.?); |
| 551 | const target_sym = obj.getObjcMsgSendRef(macho_file).?.getSymbol(macho_file).?; |
| 544 | 552 | const target = target_sym.getGotAddress(macho_file); |
| 545 | 553 | const source = addr + 7; |
| 546 | 554 | try writer.writeInt(i32, @intCast(target - source - 2 - 4), .little); |
| ... | ... | @@ -560,7 +568,7 @@ pub const ObjcStubsSection = struct { |
| 560 | 568 | ); |
| 561 | 569 | } |
| 562 | 570 | { |
| 563 | | const target_sym = macho_file.getSymbol(macho_file.objc_msg_send_index.?); |
| 571 | const target_sym = obj.getObjcMsgSendRef(macho_file).?.getSymbol(macho_file).?; |
| 564 | 572 | const target = target_sym.getGotAddress(macho_file); |
| 565 | 573 | const source = addr + 2 * @sizeOf(u32); |
| 566 | 574 | const pages = try aarch64.calcNumberOfPages(@intCast(source), @intCast(target)); |
| ... | ... | @@ -599,12 +607,12 @@ pub const ObjcStubsSection = struct { |
| 599 | 607 | ) !void { |
| 600 | 608 | _ = options; |
| 601 | 609 | _ = unused_fmt_string; |
| 602 | | for (ctx.objc.symbols.items, 0..) |entry, i| { |
| 603 | | const symbol = ctx.macho_file.getSymbol(entry); |
| 610 | for (ctx.objc.symbols.items, 0..) |ref, i| { |
| 611 | const symbol = ref.getSymbol(ctx.macho_file).?; |
| 604 | 612 | try writer.print(" {d}@0x{x} => {d}@0x{x} ({s})\n", .{ |
| 605 | 613 | i, |
| 606 | 614 | symbol.getObjcStubsAddress(ctx.macho_file), |
| 607 | | entry, |
| 615 | ref, |
| 608 | 616 | symbol.getAddress(.{}, ctx.macho_file), |
| 609 | 617 | symbol.getName(ctx.macho_file), |
| 610 | 618 | }); |
| ... | ... | @@ -620,31 +628,89 @@ pub const Indsymtab = struct { |
| 620 | 628 | return @intCast(macho_file.stubs.symbols.items.len * 2 + macho_file.got.symbols.items.len); |
| 621 | 629 | } |
| 622 | 630 | |
| 631 | pub fn updateSize(ind: *Indsymtab, macho_file: *MachO) !void { |
| 632 | macho_file.dysymtab_cmd.nindirectsyms = ind.nsyms(macho_file); |
| 633 | } |
| 634 | |
| 623 | 635 | pub fn write(ind: Indsymtab, macho_file: *MachO, writer: anytype) !void { |
| 624 | 636 | const tracy = trace(@src()); |
| 625 | 637 | defer tracy.end(); |
| 626 | 638 | |
| 627 | 639 | _ = ind; |
| 628 | 640 | |
| 629 | | for (macho_file.stubs.symbols.items) |sym_index| { |
| 630 | | const sym = macho_file.getSymbol(sym_index); |
| 641 | for (macho_file.stubs.symbols.items) |ref| { |
| 642 | const sym = ref.getSymbol(macho_file).?; |
| 631 | 643 | try writer.writeInt(u32, sym.getOutputSymtabIndex(macho_file).?, .little); |
| 632 | 644 | } |
| 633 | 645 | |
| 634 | | for (macho_file.got.symbols.items) |sym_index| { |
| 635 | | const sym = macho_file.getSymbol(sym_index); |
| 646 | for (macho_file.got.symbols.items) |ref| { |
| 647 | const sym = ref.getSymbol(macho_file).?; |
| 636 | 648 | try writer.writeInt(u32, sym.getOutputSymtabIndex(macho_file).?, .little); |
| 637 | 649 | } |
| 638 | 650 | |
| 639 | | for (macho_file.stubs.symbols.items) |sym_index| { |
| 640 | | const sym = macho_file.getSymbol(sym_index); |
| 651 | for (macho_file.stubs.symbols.items) |ref| { |
| 652 | const sym = ref.getSymbol(macho_file).?; |
| 641 | 653 | try writer.writeInt(u32, sym.getOutputSymtabIndex(macho_file).?, .little); |
| 642 | 654 | } |
| 643 | 655 | } |
| 644 | 656 | }; |
| 645 | 657 | |
| 658 | pub const DataInCode = struct { |
| 659 | entries: std.ArrayListUnmanaged(macho.data_in_code_entry) = .{}, |
| 660 | |
| 661 | pub fn deinit(dice: *DataInCode, allocator: Allocator) void { |
| 662 | dice.entries.deinit(allocator); |
| 663 | } |
| 664 | |
| 665 | pub fn size(dice: DataInCode) usize { |
| 666 | return dice.entries.items.len * @sizeOf(macho.data_in_code_entry); |
| 667 | } |
| 668 | |
| 669 | pub fn updateSize(dice: *DataInCode, macho_file: *MachO) !void { |
| 670 | const gpa = macho_file.base.comp.gpa; |
| 671 | const base_address = if (!macho_file.base.isRelocatable()) |
| 672 | macho_file.getTextSegment().vmaddr |
| 673 | else |
| 674 | 0; |
| 675 | |
| 676 | for (macho_file.objects.items) |index| { |
| 677 | const object = macho_file.getFile(index).?.object; |
| 678 | const dices = object.getDataInCode(); |
| 679 | |
| 680 | try dice.entries.ensureUnusedCapacity(gpa, dices.len); |
| 681 | |
| 682 | var next_dice: usize = 0; |
| 683 | for (object.getAtoms()) |atom_index| { |
| 684 | if (next_dice >= dices.len) break; |
| 685 | const atom = object.getAtom(atom_index) orelse continue; |
| 686 | if (!atom.flags.alive) continue; |
| 687 | const start_off = atom.getInputAddress(macho_file); |
| 688 | const end_off = start_off + atom.size; |
| 689 | const start_dice = next_dice; |
| 690 | |
| 691 | if (end_off < dices[next_dice].offset) continue; |
| 692 | |
| 693 | while (next_dice < dices.len and |
| 694 | dices[next_dice].offset < end_off) : (next_dice += 1) |
| 695 | {} |
| 696 | |
| 697 | if (atom.alive.load(.seq_cst)) for (dices[start_dice..next_dice]) |d| { |
| 698 | dice.entries.appendAssumeCapacity(.{ |
| 699 | .offset = @intCast(atom.getAddress(macho_file) + d.offset - start_off - base_address), |
| 700 | .length = d.length, |
| 701 | .kind = d.kind, |
| 702 | }); |
| 703 | }; |
| 704 | } |
| 705 | } |
| 706 | |
| 707 | macho_file.data_in_code_cmd.datasize = math.cast(u32, dice.size()) orelse return error.Overflow; |
| 708 | } |
| 709 | }; |
| 710 | |
| 646 | 711 | const aarch64 = @import("../aarch64.zig"); |
| 647 | 712 | const assert = std.debug.assert; |
| 713 | const macho = std.macho; |
| 648 | 714 | const math = std.math; |
| 649 | 715 | const std = @import("std"); |
| 650 | 716 | const trace = @import("../../tracy.zig").trace; |