| ... | @@ -2660,17 +2660,40 @@ fn writeExportInfo(self: *Zld) !void { | ... | @@ -2660,17 +2660,40 @@ fn writeExportInfo(self: *Zld) !void { |
| 2660 | defer trie.deinit(); | 2660 | defer trie.deinit(); |
| 2661 | | 2661 | |
| 2662 | const text_segment = self.load_commands.items[self.text_segment_cmd_index.?].Segment; | 2662 | const text_segment = self.load_commands.items[self.text_segment_cmd_index.?].Segment; |
| | 2663 | const base_address = text_segment.inner.vmaddr; |
| 2663 | | 2664 | |
| 2664 | // TODO export items for dylibs | 2665 | // TODO handle macho.EXPORT_SYMBOL_FLAGS_REEXPORT and macho.EXPORT_SYMBOL_FLAGS_STUB_AND_RESOLVER. |
| 2665 | const sym = self.globals.get("_main") orelse return error.MissingMainEntrypoint; | 2666 | log.debug("writing export trie", .{}); |
| 2666 | const reg = sym.cast(Symbol.Regular) orelse unreachable; | | |
| 2667 | assert(reg.address >= text_segment.inner.vmaddr); | | |
| 2668 | | 2667 | |
| 2669 | try trie.put(.{ | 2668 | const Sorter = struct { |
| 2670 | .name = sym.name, | 2669 | fn lessThan(_: void, a: []const u8, b: []const u8) bool { |
| 2671 | .vmaddr_offset = reg.address - text_segment.inner.vmaddr, | 2670 | return mem.lessThan(u8, a, b); |
| 2672 | .export_flags = macho.EXPORT_SYMBOL_FLAGS_KIND_REGULAR, | 2671 | } |
| 2673 | }); | 2672 | }; |
| | 2673 | |
| | 2674 | var sorted_globals = std.ArrayList([]const u8).init(self.allocator); |
| | 2675 | defer sorted_globals.deinit(); |
| | 2676 | |
| | 2677 | for (self.globals.values()) |sym| { |
| | 2678 | const reg = sym.cast(Symbol.Regular) orelse continue; |
| | 2679 | if (reg.linkage != .global) continue; |
| | 2680 | try sorted_globals.append(sym.name); |
| | 2681 | } |
| | 2682 | |
| | 2683 | std.sort.sort([]const u8, sorted_globals.items, {}, Sorter.lessThan); |
| | 2684 | |
| | 2685 | for (sorted_globals.items) |sym_name| { |
| | 2686 | const sym = self.globals.get(sym_name) orelse unreachable; |
| | 2687 | const reg = sym.cast(Symbol.Regular) orelse unreachable; |
| | 2688 | |
| | 2689 | log.debug(" | putting '{s}' defined at 0x{x}", .{ reg.base.name, reg.address }); |
| | 2690 | |
| | 2691 | try trie.put(.{ |
| | 2692 | .name = sym.name, |
| | 2693 | .vmaddr_offset = reg.address - base_address, |
| | 2694 | .export_flags = macho.EXPORT_SYMBOL_FLAGS_KIND_REGULAR, |
| | 2695 | }); |
| | 2696 | } |
| 2674 | | 2697 | |
| 2675 | try trie.finalize(); | 2698 | try trie.finalize(); |
| 2676 | | 2699 | |