diff options
| author | Jakub Konka <kubkon@jakubkonka.com> | 2024-02-02 14:05:51 +0100 |
|---|---|---|
| committer | Jakub Konka <kubkon@jakubkonka.com> | 2024-02-02 22:00:16 +0100 |
| commit | 92deebcd668750bd4042c5874bf35b447828cd8a (patch) | |
| tree | 412ac01bd1ee8c20bf4fc55281626e885e8fd0e4 /src | |
| parent | 9eda6ccefce370c76209ea50dd57fe65bfe25536 (diff) | |
| download | zig-92deebcd668750bd4042c5874bf35b447828cd8a.tar.gz zig-92deebcd668750bd4042c5874bf35b447828cd8a.zip | |
cli+build: handle -ObjC flag and route it to MachO linker
Diffstat (limited to 'src')
| -rw-r--r-- | src/Compilation.zig | 8 | ||||
| -rw-r--r-- | src/clang_options_data.zig | 9 | ||||
| -rw-r--r-- | src/link.zig | 26 | ||||
| -rw-r--r-- | src/link/Coff/lld.zig | 2 | ||||
| -rw-r--r-- | src/link/Elf.zig | 2 | ||||
| -rw-r--r-- | src/link/MachO.zig | 9 | ||||
| -rw-r--r-- | src/link/Wasm.zig | 4 | ||||
| -rw-r--r-- | src/main.zig | 11 |
8 files changed, 51 insertions, 20 deletions
diff --git a/src/Compilation.zig b/src/Compilation.zig index 237f22df58..beb2c8cf99 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -1113,6 +1113,8 @@ pub const CreateOptions = struct { headerpad_max_install_names: bool = false, /// (Darwin) remove dylibs that are unreachable by the entry point or exported symbols dead_strip_dylibs: bool = false, + /// (Darwin) Force load all members of static archives that implement an Objective-C class or category + force_load_objc: bool = false, libcxx_abi_version: libcxx.AbiVersion = libcxx.AbiVersion.default, /// (Windows) PDB source path prefix to instruct the linker how to resolve relative /// paths when consolidating CodeView streams into a single PDB file. @@ -1591,6 +1593,7 @@ pub fn create(gpa: Allocator, arena: Allocator, options: CreateOptions) !*Compil .headerpad_size = options.headerpad_size, .headerpad_max_install_names = options.headerpad_max_install_names, .dead_strip_dylibs = options.dead_strip_dylibs, + .force_load_objc = options.force_load_objc, .pdb_source_path = options.pdb_source_path, .pdb_out_path = options.pdb_out_path, .entry_addr = null, // CLI does not expose this option (yet?) @@ -2456,7 +2459,7 @@ fn prepareWholeEmitSubPath(arena: Allocator, opt_emit: ?EmitLoc) error{OutOfMemo /// to remind the programmer to update multiple related pieces of code that /// are in different locations. Bump this number when adding or deleting /// anything from the link cache manifest. -pub const link_hash_implementation_version = 11; +pub const link_hash_implementation_version = 12; fn addNonIncrementalStuffToCacheManifest( comp: *Compilation, @@ -2465,7 +2468,7 @@ fn addNonIncrementalStuffToCacheManifest( ) !void { const gpa = comp.gpa; - comptime assert(link_hash_implementation_version == 11); + comptime assert(link_hash_implementation_version == 12); if (comp.module) |mod| { try addModuleTableToCacheHash(gpa, arena, &man.hash, mod.root_mod, mod.main_mod, .{ .files = man }); @@ -2589,6 +2592,7 @@ fn addNonIncrementalStuffToCacheManifest( man.hash.addOptional(opts.headerpad_size); man.hash.add(opts.headerpad_max_install_names); man.hash.add(opts.dead_strip_dylibs); + man.hash.add(opts.force_load_objc); // COFF specific stuff man.hash.addOptional(opts.subsystem); diff --git a/src/clang_options_data.zig b/src/clang_options_data.zig index a1a7435999..0137d2cbfc 100644 --- a/src/clang_options_data.zig +++ b/src/clang_options_data.zig @@ -115,7 +115,14 @@ flagpd1("Mach"), .pd2 = false, .psl = false, }, -flagpd1("ObjC"), +.{ + .name = "ObjC", + .syntax = .flag, + .zig_equivalent = .force_load_objc, + .pd1 = true, + .pd2 = false, + .psl = false, +}, flagpd1("ObjC++"), flagpd1("P"), flagpd1("Q"), diff --git a/src/link.zig b/src/link.zig index 528ba10d1b..bdd531096e 100644 --- a/src/link.zig +++ b/src/link.zig @@ -136,30 +136,36 @@ pub const File = struct { framework_dirs: []const []const u8, rpath_list: []const []const u8, - /// (Zig compiler development) Enable dumping of linker's state as JSON. + /// Zig compiler development linker flags. + /// Enable dumping of linker's state as JSON. enable_link_snapshots: bool, - /// (Darwin) Install name for the dylib + /// Darwin-specific linker flags: + /// Install name for the dylib install_name: ?[]const u8, - /// (Darwin) Path to entitlements file + /// Path to entitlements file entitlements: ?[]const u8, - /// (Darwin) size of the __PAGEZERO segment + /// size of the __PAGEZERO segment pagezero_size: ?u64, - /// (Darwin) set minimum space for future expansion of the load commands + /// Set minimum space for future expansion of the load commands headerpad_size: ?u32, - /// (Darwin) set enough space as if all paths were MATPATHLEN + /// Set enough space as if all paths were MATPATHLEN headerpad_max_install_names: bool, - /// (Darwin) remove dylibs that are unreachable by the entry point or exported symbols + /// Remove dylibs that are unreachable by the entry point or exported symbols dead_strip_dylibs: bool, frameworks: []const MachO.Framework, darwin_sdk_layout: ?MachO.SdkLayout, + /// Force load all members of static archives that implement an + /// Objective-C class or category + force_load_objc: bool, - /// (Windows) PDB source path prefix to instruct the linker how to resolve relative + /// Windows-specific linker flags: + /// PDB source path prefix to instruct the linker how to resolve relative /// paths when consolidating CodeView streams into a single PDB file. pdb_source_path: ?[]const u8, - /// (Windows) PDB output path + /// PDB output path pdb_out_path: ?[]const u8, - /// (Windows) .def file to specify when linking + /// .def file to specify when linking module_definition_file: ?[]const u8, pub const Entry = union(enum) { diff --git a/src/link/Coff/lld.zig b/src/link/Coff/lld.zig index b4843ae6cd..90e284900a 100644 --- a/src/link/Coff/lld.zig +++ b/src/link/Coff/lld.zig @@ -70,7 +70,7 @@ pub fn linkWithLLD(self: *Coff, arena: Allocator, prog_node: *std.Progress.Node) man = comp.cache_parent.obtain(); self.base.releaseLock(); - comptime assert(Compilation.link_hash_implementation_version == 11); + comptime assert(Compilation.link_hash_implementation_version == 12); for (comp.objects) |obj| { _ = try man.addFile(obj.path, null); diff --git a/src/link/Elf.zig b/src/link/Elf.zig index 70ed2f76ab..2a130d452a 100644 --- a/src/link/Elf.zig +++ b/src/link/Elf.zig @@ -2380,7 +2380,7 @@ fn linkWithLLD(self: *Elf, arena: Allocator, prog_node: *std.Progress.Node) !voi // We are about to obtain this lock, so here we give other processes a chance first. self.base.releaseLock(); - comptime assert(Compilation.link_hash_implementation_version == 11); + comptime assert(Compilation.link_hash_implementation_version == 12); try man.addOptionalFile(self.linker_script); try man.addOptionalFile(self.version_script); diff --git a/src/link/MachO.zig b/src/link/MachO.zig index c2a098b9f5..e7603e2bde 100644 --- a/src/link/MachO.zig +++ b/src/link/MachO.zig @@ -217,6 +217,7 @@ pub fn createEmpty( .undefined_treatment = if (allow_shlib_undefined) .dynamic_lookup else .@"error", .lib_dirs = options.lib_dirs, .framework_dirs = options.framework_dirs, + .force_load_objc = options.force_load_objc, }; if (use_llvm and comp.config.have_zcu) { self.llvm_object = try LlvmObject.create(arena, comp); @@ -807,6 +808,10 @@ fn dumpArgv(self: *MachO, comp: *Compilation) !void { try argv.append("-dead_strip_dylibs"); } + if (self.force_load_objc) { + try argv.append("-ObjC"); + } + if (self.entry_name) |entry_name| { try argv.appendSlice(&.{ "-e", entry_name }); } @@ -1247,7 +1252,7 @@ fn parseDependentDylibs(self: *MachO) !void { try checked_paths.append(rel_path); var buffer: [std.fs.MAX_PATH_BYTES]u8 = undefined; const full_path = std.fs.realpath(rel_path, &buffer) catch continue; - break :full_path full_path; + break :full_path try arena.dupe(u8, full_path); } } else if (eatPrefix(id.name, "@loader_path/")) |_| { try self.reportParseError2(dylib_index, "TODO handle install_name '{s}'", .{id.name}); @@ -1260,7 +1265,7 @@ fn parseDependentDylibs(self: *MachO) !void { try checked_paths.append(try arena.dupe(u8, id.name)); var buffer: [std.fs.MAX_PATH_BYTES]u8 = undefined; if (std.fs.realpath(id.name, &buffer)) |full_path| { - break :full_path full_path; + break :full_path try arena.dupe(u8, full_path); } else |_| { try self.reportMissingDependencyError( self.getFile(dylib_index).?.dylib.getUmbrella(self).index, diff --git a/src/link/Wasm.zig b/src/link/Wasm.zig index a0cf23579b..9fe8ce417e 100644 --- a/src/link/Wasm.zig +++ b/src/link/Wasm.zig @@ -3511,7 +3511,7 @@ fn linkWithZld(wasm: *Wasm, arena: Allocator, prog_node: *std.Progress.Node) lin // We are about to obtain this lock, so here we give other processes a chance first. wasm.base.releaseLock(); - comptime assert(Compilation.link_hash_implementation_version == 11); + comptime assert(Compilation.link_hash_implementation_version == 12); for (objects) |obj| { _ = try man.addFile(obj.path, null); @@ -4580,7 +4580,7 @@ fn linkWithLLD(wasm: *Wasm, arena: Allocator, prog_node: *std.Progress.Node) !vo // We are about to obtain this lock, so here we give other processes a chance first. wasm.base.releaseLock(); - comptime assert(Compilation.link_hash_implementation_version == 11); + comptime assert(Compilation.link_hash_implementation_version == 12); for (comp.objects) |obj| { _ = try man.addFile(obj.path, null); diff --git a/src/main.zig b/src/main.zig index 8eef42698d..e795666941 100644 --- a/src/main.zig +++ b/src/main.zig @@ -559,6 +559,7 @@ const usage_build_generic = \\ -headerpad_max_install_names (Darwin) set enough space as if all paths were MAXPATHLEN \\ -dead_strip (Darwin) remove functions and data that are unreachable by the entry point or exported symbols \\ -dead_strip_dylibs (Darwin) remove dylibs that are unreachable by the entry point or exported symbols + \\ -ObjC (Darwin) force load all members of static archives that implement an Objective-C class or category \\ --import-memory (WebAssembly) import memory from the environment \\ --export-memory (WebAssembly) export memory to the host (Default unless --import-memory used) \\ --import-symbols (WebAssembly) import missing symbols from the host environment @@ -589,7 +590,7 @@ const usage_build_generic = \\ -rpath [path] Add directory to the runtime library search path \\ -framework [name] (Darwin) link against framework \\ -needed_framework [name] (Darwin) link against framework (even if unused) - \\ -needed_library [lib] link against system library (even if unused) + \\ -needed_library [lib] (Darwin) link against system library (even if unused) \\ -weak_framework [name] (Darwin) link against framework and mark it and all referenced symbols as weak \\ -F[dir] (Darwin) add search path for frameworks \\ --export=[value] (WebAssembly) Force a symbol to be exported @@ -889,6 +890,7 @@ fn buildOutputType( var headerpad_size: ?u32 = null; var headerpad_max_install_names: bool = false; var dead_strip_dylibs: bool = false; + var force_load_objc: bool = false; var contains_res_file: bool = false; var reference_trace: ?u32 = null; var pdb_out_path: ?[]const u8 = null; @@ -1182,6 +1184,8 @@ fn buildOutputType( linker_gc_sections = true; } else if (mem.eql(u8, arg, "-dead_strip_dylibs")) { dead_strip_dylibs = true; + } else if (mem.eql(u8, arg, "-ObjC")) { + force_load_objc = true; } else if (mem.eql(u8, arg, "-T") or mem.eql(u8, arg, "--script")) { linker_script = args_iter.nextOrFatal(); } else if (mem.eql(u8, arg, "-version-script") or mem.eql(u8, arg, "--version-script")) { @@ -2061,6 +2065,7 @@ fn buildOutputType( .force_undefined_symbol => { try force_undefined_symbols.put(arena, it.only_arg, {}); }, + .force_load_objc => force_load_objc = true, .weak_library => try create_module.system_libs.put(arena, it.only_arg, .{ .needed = false, .weak = true, @@ -2167,6 +2172,8 @@ fn buildOutputType( linker_gc_sections = true; } else if (mem.eql(u8, arg, "-dead_strip_dylibs")) { dead_strip_dylibs = true; + } else if (mem.eql(u8, arg, "-ObjC")) { + force_load_objc = true; } else if (mem.eql(u8, arg, "--no-undefined")) { linker_z_defs = true; } else if (mem.eql(u8, arg, "--gc-sections")) { @@ -3246,6 +3253,7 @@ fn buildOutputType( .headerpad_size = headerpad_size, .headerpad_max_install_names = headerpad_max_install_names, .dead_strip_dylibs = dead_strip_dylibs, + .force_load_objc = force_load_objc, .reference_trace = reference_trace, .pdb_out_path = pdb_out_path, .error_limit = error_limit, @@ -6266,6 +6274,7 @@ pub const ClangArgIterator = struct { compress_debug_sections, install_name, undefined, + force_load_objc, }; const Args = struct { |
