authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2023-03-31 22:39:41+02:00
committergravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2023-04-01 14:22:44+02:00
log6f83a741d8f3847c65aa8b791a865f339b77531d
tree01c99cb5ef60f2d9db71abf6c51dc7a58377a4ca
parentf2587de4e915423d0224b8b6ef0cb3d9cb7e60e2

macho: handle weird case of entrypoint being a stub


2 files changed, 22 insertions(+), 2 deletions(-)

src/link/MachO/ZldAtom.zig+1-1
...@@ -389,7 +389,7 @@ pub fn addGotEntry(zld: *Zld, target: SymbolWithLoc) !void {...@@ -389,7 +389,7 @@ pub fn addGotEntry(zld: *Zld, target: SymbolWithLoc) !void {
389 try zld.got_table.putNoClobber(gpa, target, got_index);389 try zld.got_table.putNoClobber(gpa, target, got_index);
390}390}
391391
392fn addStub(zld: *Zld, target: SymbolWithLoc) !void {392pub fn addStub(zld: *Zld, target: SymbolWithLoc) !void {
393 const target_sym = zld.getSymbol(target);393 const target_sym = zld.getSymbol(target);
394 if (!target_sym.undf()) return;394 if (!target_sym.undf()) return;
395 if (zld.stubs_table.contains(target)) return;395 if (zld.stubs_table.contains(target)) return;
src/link/MachO/zld.zig+21-1
...@@ -4042,6 +4042,16 @@ pub fn linkWithZld(macho_file: *MachO, comp: *Compilation, prog_node: *std.Progr...@@ -4042,6 +4042,16 @@ pub fn linkWithZld(macho_file: *MachO, comp: *Compilation, prog_node: *std.Progr
4042 try zld.createTentativeDefAtoms();4042 try zld.createTentativeDefAtoms();
4043 try zld.createStubHelperPreambleAtom();4043 try zld.createStubHelperPreambleAtom();
40444044
4045 if (zld.options.output_mode == .Exe) {
4046 const global = zld.getEntryPoint();
4047 if (zld.getSymbol(global).undf()) {
4048 // We do one additional check here in case the entry point was found in one of the dylibs.
4049 // (I actually have no idea what this would imply but it is a possible outcome and so we
4050 // support it.)
4051 try Atom.addStub(&zld, global);
4052 }
4053 }
4054
4045 for (zld.objects.items) |object| {4055 for (zld.objects.items) |object| {
4046 for (object.atoms.items) |atom_index| {4056 for (object.atoms.items) |atom_index| {
4047 const atom = zld.getAtom(atom_index);4057 const atom = zld.getAtom(atom_index);
...@@ -4153,8 +4163,18 @@ pub fn linkWithZld(macho_file: *MachO, comp: *Compilation, prog_node: *std.Progr...@@ -4153,8 +4163,18 @@ pub fn linkWithZld(macho_file: *MachO, comp: *Compilation, prog_node: *std.Progr
4153 const seg = zld.segments.items[seg_id];4163 const seg = zld.segments.items[seg_id];
4154 const global = zld.getEntryPoint();4164 const global = zld.getEntryPoint();
4155 const sym = zld.getSymbol(global);4165 const sym = zld.getSymbol(global);
4166
4167 const addr: u64 = if (sym.undf()) blk: {
4168 // In this case, the symbol has been resolved in one of dylibs and so we point
4169 // to the stub as its vmaddr value.
4170 const stub_atom_index = zld.getStubsAtomIndexForSymbol(global).?;
4171 const stub_atom = zld.getAtom(stub_atom_index);
4172 const stub_sym = zld.getSymbol(stub_atom.getSymbolWithLoc());
4173 break :blk stub_sym.n_value;
4174 } else sym.n_value;
4175
4156 try lc_writer.writeStruct(macho.entry_point_command{4176 try lc_writer.writeStruct(macho.entry_point_command{
4157 .entryoff = @intCast(u32, sym.n_value - seg.vmaddr),4177 .entryoff = @intCast(u32, addr - seg.vmaddr),
4158 .stacksize = options.stack_size_override orelse 0,4178 .stacksize = options.stack_size_override orelse 0,
4159 });4179 });
4160 } else {4180 } else {