| author | |
| committer | |
| log | d41c16930df6fad85f2a63fec2e8e02b128cb1ed |
| tree | c677266726928e512a2fd782d27f92d92d737100 |
| parent | 1e616096d42fc793f463acd44b81489987a69934 |
| parent | d22231c039ce8f087b2499a97eb769fb800f2000 |
Reviewed-on: https://codeberg.org/ziglang/zig/pulls/30073
Reviewed-by: mlugg <mlugg@noreply.codeberg.org>6 files changed, 189 insertions(+), 14 deletions(-)
ci/x86_64-linux-debug-llvm.sh+4-1| ... | ... | @@ -34,7 +34,10 @@ cmake .. \ |
| 34 | 34 | -DZIG_STATIC=ON \ |
| 35 | 35 | -DZIG_NO_LIB=ON \ |
| 36 | 36 | -DZIG_EXTRA_BUILD_ARGS="-Duse-llvm=true" \ |
| 37 | -GNinja | |
| 37 | -GNinja \ | |
| 38 | -DCMAKE_C_LINKER_DEPFILE_SUPPORTED=FALSE \ | |
| 39 | -DCMAKE_CXX_LINKER_DEPFILE_SUPPORTED=FALSE | |
| 40 | # https://github.com/ziglang/zig/issues/22213 | |
| 38 | 41 | |
| 39 | 42 | # Now cmake will use zig as the C/C++ compiler. We reset the environment variables |
| 40 | 43 | # so that installation and testing do not get affected by them. |
ci/x86_64-linux-debug.sh+4-1| ... | ... | @@ -33,7 +33,10 @@ cmake .. \ |
| 33 | 33 | -DZIG_TARGET_MCPU="$MCPU" \ |
| 34 | 34 | -DZIG_STATIC=ON \ |
| 35 | 35 | -DZIG_NO_LIB=ON \ |
| 36 | -GNinja | |
| 36 | -GNinja \ | |
| 37 | -DCMAKE_C_LINKER_DEPFILE_SUPPORTED=FALSE \ | |
| 38 | -DCMAKE_CXX_LINKER_DEPFILE_SUPPORTED=FALSE | |
| 39 | # https://github.com/ziglang/zig/issues/22213 | |
| 37 | 40 | |
| 38 | 41 | # Now cmake will use zig as the C/C++ compiler. We reset the environment variables |
| 39 | 42 | # so that installation and testing do not get affected by them. |
ci/x86_64-linux-release.sh+8-2| ... | ... | @@ -39,7 +39,10 @@ cmake .. \ |
| 39 | 39 | -DZIG_TARGET_MCPU="$MCPU" \ |
| 40 | 40 | -DZIG_STATIC=ON \ |
| 41 | 41 | -DZIG_NO_LIB=ON \ |
| 42 | -GNinja | |
| 42 | -GNinja \ | |
| 43 | -DCMAKE_C_LINKER_DEPFILE_SUPPORTED=FALSE \ | |
| 44 | -DCMAKE_CXX_LINKER_DEPFILE_SUPPORTED=FALSE | |
| 45 | # https://github.com/ziglang/zig/issues/22213 | |
| 43 | 46 | |
| 44 | 47 | # Now cmake will use zig as the C/C++ compiler. We reset the environment variables |
| 45 | 48 | # so that installation and testing do not get affected by them. |
| ... | ... | @@ -97,7 +100,10 @@ cmake .. \ |
| 97 | 100 | -DZIG_TARGET_MCPU="$MCPU" \ |
| 98 | 101 | -DZIG_STATIC=ON \ |
| 99 | 102 | -DZIG_NO_LIB=ON \ |
| 100 | -GNinja | |
| 103 | -GNinja \ | |
| 104 | -DCMAKE_C_LINKER_DEPFILE_SUPPORTED=FALSE \ | |
| 105 | -DCMAKE_CXX_LINKER_DEPFILE_SUPPORTED=FALSE | |
| 106 | # https://github.com/ziglang/zig/issues/22213 | |
| 101 | 107 | |
| 102 | 108 | unset CC |
| 103 | 109 | unset CXX |
lib/std/Build/Cache.zig+1-1| ... | ... | @@ -123,7 +123,7 @@ pub const HexDigest = [hex_digest_len]u8; |
| 123 | 123 | |
| 124 | 124 | /// This is currently just an arbitrary non-empty string that can't match another manifest line. |
| 125 | 125 | const manifest_header = "0"; |
| 126 | const manifest_file_size_max = 100 * 1024 * 1024; | |
| 126 | pub const manifest_file_size_max = 100 * 1024 * 1024; | |
| 127 | 127 | |
| 128 | 128 | /// The type used for hashing file contents. Currently, this is SipHash128(1, 3), because it |
| 129 | 129 | /// provides enough collision resistance for the Manifest use cases, while being one of our |
src/Compilation.zig+82| ... | ... | @@ -173,6 +173,7 @@ verbose_llvm_bc: ?[]const u8, |
| 173 | 173 | verbose_cimport: bool, |
| 174 | 174 | verbose_llvm_cpu_features: bool, |
| 175 | 175 | verbose_link: bool, |
| 176 | link_depfile: ?[]const u8, | |
| 176 | 177 | disable_c_depfile: bool, |
| 177 | 178 | stack_report: bool, |
| 178 | 179 | debug_compiler_runtime_libs: bool, |
| ... | ... | @@ -1403,6 +1404,7 @@ pub const MiscTask = enum { |
| 1403 | 1404 | compiler_rt, |
| 1404 | 1405 | libzigc, |
| 1405 | 1406 | analyze_mod, |
| 1407 | link_depfile, | |
| 1406 | 1408 | docs_copy, |
| 1407 | 1409 | docs_wasm, |
| 1408 | 1410 | |
| ... | ... | @@ -1732,6 +1734,7 @@ pub const CreateOptions = struct { |
| 1732 | 1734 | verbose_generic_instances: bool = false, |
| 1733 | 1735 | verbose_llvm_ir: ?[]const u8 = null, |
| 1734 | 1736 | verbose_llvm_bc: ?[]const u8 = null, |
| 1737 | link_depfile: ?[]const u8 = null, | |
| 1735 | 1738 | verbose_cimport: bool = false, |
| 1736 | 1739 | verbose_llvm_cpu_features: bool = false, |
| 1737 | 1740 | debug_compiler_runtime_libs: bool = false, |
| ... | ... | @@ -2247,6 +2250,7 @@ pub fn create(gpa: Allocator, arena: Allocator, io: Io, diag: *CreateDiagnostic, |
| 2247 | 2250 | .verbose_generic_instances = options.verbose_generic_instances, |
| 2248 | 2251 | .verbose_llvm_ir = options.verbose_llvm_ir, |
| 2249 | 2252 | .verbose_llvm_bc = options.verbose_llvm_bc, |
| 2253 | .link_depfile = options.link_depfile, | |
| 2250 | 2254 | .verbose_cimport = options.verbose_cimport, |
| 2251 | 2255 | .verbose_llvm_cpu_features = options.verbose_llvm_cpu_features, |
| 2252 | 2256 | .verbose_link = options.verbose_link, |
| ... | ... | @@ -3099,6 +3103,15 @@ pub fn update(comp: *Compilation, main_progress_node: std.Progress.Node) UpdateE |
| 3099 | 3103 | } |
| 3100 | 3104 | } |
| 3101 | 3105 | |
| 3106 | if (comp.link_depfile) |depfile_path| if (comp.bin_file) |lf| { | |
| 3107 | assert(comp.file_system_inputs != null); | |
| 3108 | comp.createDepFile(depfile_path, lf.emit) catch |err| comp.setMiscFailure( | |
| 3109 | .link_depfile, | |
| 3110 | "unable to write linker dependency file: {t}", | |
| 3111 | .{err}, | |
| 3112 | ); | |
| 3113 | }; | |
| 3114 | ||
| 3102 | 3115 | if (anyErrors(comp)) { |
| 3103 | 3116 | // Skip flushing and keep source files loaded for error reporting. |
| 3104 | 3117 | return; |
| ... | ... | @@ -5208,6 +5221,43 @@ pub fn separateCodegenThreadOk(comp: *const Compilation) bool { |
| 5208 | 5221 | return zcu.backendSupportsFeature(.separate_thread); |
| 5209 | 5222 | } |
| 5210 | 5223 | |
| 5224 | fn createDepFile( | |
| 5225 | comp: *Compilation, | |
| 5226 | depfile: []const u8, | |
| 5227 | binfile: Cache.Path, | |
| 5228 | ) anyerror!void { | |
| 5229 | var buf: [4096]u8 = undefined; | |
| 5230 | var af = try std.fs.cwd().atomicFile(depfile, .{ .write_buffer = &buf }); | |
| 5231 | defer af.deinit(); | |
| 5232 | ||
| 5233 | comp.writeDepFile(binfile, &af.file_writer.interface) catch return af.file_writer.err.?; | |
| 5234 | ||
| 5235 | try af.finish(); | |
| 5236 | } | |
| 5237 | ||
| 5238 | fn writeDepFile( | |
| 5239 | comp: *Compilation, | |
| 5240 | binfile: Cache.Path, | |
| 5241 | w: *std.Io.Writer, | |
| 5242 | ) std.Io.Writer.Error!void { | |
| 5243 | const prefixes = comp.cache_parent.prefixes(); | |
| 5244 | const fsi = comp.file_system_inputs.?.items; | |
| 5245 | ||
| 5246 | try w.print("{f}:", .{binfile}); | |
| 5247 | ||
| 5248 | { | |
| 5249 | var it = std.mem.splitScalar(u8, fsi, 0); | |
| 5250 | while (it.next()) |input| try w.print(" \\\n {f}{s}", .{ prefixes[input[0] - 1], input[1..] }); | |
| 5251 | } | |
| 5252 | ||
| 5253 | { | |
| 5254 | var it = std.mem.splitScalar(u8, fsi, 0); | |
| 5255 | while (it.next()) |input| try w.print("\n\n{f}{s}:", .{ prefixes[input[0] - 1], input[1..] }); | |
| 5256 | } | |
| 5257 | ||
| 5258 | try w.writeByte('\n'); | |
| 5259 | } | |
| 5260 | ||
| 5211 | 5261 | fn workerDocsCopy(comp: *Compilation) void { |
| 5212 | 5262 | docsCopyFallible(comp) catch |err| return comp.lockAndSetMiscFailure( |
| 5213 | 5263 | .docs_copy, |
| ... | ... | @@ -6369,6 +6419,38 @@ fn updateCObject(comp: *Compilation, c_object: *CObject, c_obj_prog_node: std.Pr |
| 6369 | 6419 | |
| 6370 | 6420 | if (out_dep_path) |dep_file_path| { |
| 6371 | 6421 | const dep_basename = fs.path.basename(dep_file_path); |
| 6422 | ||
| 6423 | if (comp.file_system_inputs != null) { | |
| 6424 | // Use the same file size limit as the cache code does for dependency files. | |
| 6425 | const dep_file_contents = try zig_cache_tmp_dir.readFileAlloc(dep_basename, gpa, .limited(Cache.manifest_file_size_max)); | |
| 6426 | defer gpa.free(dep_file_contents); | |
| 6427 | ||
| 6428 | var str_buf: std.ArrayList(u8) = .empty; | |
| 6429 | defer str_buf.deinit(gpa); | |
| 6430 | ||
| 6431 | var it: std.Build.Cache.DepTokenizer = .{ .bytes = dep_file_contents }; | |
| 6432 | while (it.next()) |token| { | |
| 6433 | const input_path: Compilation.Path = switch (token) { | |
| 6434 | .target, .target_must_resolve => continue, | |
| 6435 | .prereq => |file_path| try .fromUnresolved(arena, comp.dirs, &.{file_path}), | |
| 6436 | .prereq_must_resolve => p: { | |
| 6437 | try token.resolve(gpa, &str_buf); | |
| 6438 | break :p try .fromUnresolved(arena, comp.dirs, &.{str_buf.items}); | |
| 6439 | }, | |
| 6440 | else => |err| { | |
| 6441 | try err.printError(gpa, &str_buf); | |
| 6442 | log.err("failed parsing {s}: {s}", .{ dep_basename, str_buf.items }); | |
| 6443 | return error.InvalidDepFile; | |
| 6444 | }, | |
| 6445 | }; | |
| 6446 | ||
| 6447 | // There may be concurrent calls to `appendFileSystemInput` from other C objects. | |
| 6448 | comp.mutex.lock(); | |
| 6449 | defer comp.mutex.unlock(); | |
| 6450 | try comp.appendFileSystemInput(input_path); | |
| 6451 | } | |
| 6452 | } | |
| 6453 | ||
| 6372 | 6454 | // Add the files depended on to the cache system. |
| 6373 | 6455 | try man.addDepFilePost(zig_cache_tmp_dir, dep_basename); |
| 6374 | 6456 | switch (comp.cache_use) { |
src/main.zig+90-9| ... | ... | @@ -814,6 +814,7 @@ fn buildOutputType( |
| 814 | 814 | var verbose_generic_instances = false; |
| 815 | 815 | var verbose_llvm_ir: ?[]const u8 = null; |
| 816 | 816 | var verbose_llvm_bc: ?[]const u8 = null; |
| 817 | var link_depfile: ?[]const u8 = null; | |
| 817 | 818 | var verbose_cimport = false; |
| 818 | 819 | var verbose_llvm_cpu_features = false; |
| 819 | 820 | var time_report = false; |
| ... | ... | @@ -2063,6 +2064,8 @@ fn buildOutputType( |
| 2063 | 2064 | .wl => { |
| 2064 | 2065 | var split_it = mem.splitScalar(u8, it.only_arg, ','); |
| 2065 | 2066 | while (split_it.next()) |linker_arg| { |
| 2067 | // Unfortunately duplicated with the `for_linker` handling below. | |
| 2068 | ||
| 2066 | 2069 | // Handle nested-joined args like `-Wl,-rpath=foo`. |
| 2067 | 2070 | // Must be prefixed with 1 or 2 dashes. |
| 2068 | 2071 | if (linker_arg.len >= 3 and |
| ... | ... | @@ -2072,6 +2075,10 @@ fn buildOutputType( |
| 2072 | 2075 | if (mem.indexOfScalar(u8, linker_arg, '=')) |equals_pos| { |
| 2073 | 2076 | const key = linker_arg[0..equals_pos]; |
| 2074 | 2077 | const value = linker_arg[equals_pos + 1 ..]; |
| 2078 | ||
| 2079 | // We have to handle these here because they would be ambiguous | |
| 2080 | // if split and added to `linker_args`, as there are argument-less | |
| 2081 | // variants of them. | |
| 2075 | 2082 | if (mem.eql(u8, key, "--build-id")) { |
| 2076 | 2083 | build_id = std.zig.BuildId.parse(value) catch |err| { |
| 2077 | 2084 | fatal("unable to parse --build-id style '{s}': {s}", .{ |
| ... | ... | @@ -2084,22 +2091,19 @@ fn buildOutputType( |
| 2084 | 2091 | // is done below. |
| 2085 | 2092 | continue; |
| 2086 | 2093 | } |
| 2094 | ||
| 2087 | 2095 | try linker_args.append(key); |
| 2088 | 2096 | try linker_args.append(value); |
| 2089 | 2097 | continue; |
| 2090 | 2098 | } |
| 2091 | 2099 | } |
| 2092 | if (mem.eql(u8, linker_arg, "--build-id")) { | |
| 2093 | build_id = .fast; | |
| 2094 | } else if (mem.eql(u8, linker_arg, "--as-needed")) { | |
| 2100 | ||
| 2101 | // These options are handled inline because their order matters for | |
| 2102 | // other non-linker options. | |
| 2103 | if (mem.eql(u8, linker_arg, "--as-needed")) { | |
| 2095 | 2104 | needed = false; |
| 2096 | 2105 | } else if (mem.eql(u8, linker_arg, "--no-as-needed")) { |
| 2097 | 2106 | needed = true; |
| 2098 | } else if (mem.eql(u8, linker_arg, "-no-pie")) { | |
| 2099 | create_module.opts.pie = false; | |
| 2100 | } else if (mem.eql(u8, linker_arg, "--sort-common")) { | |
| 2101 | // from ld.lld(1): --sort-common is ignored for GNU compatibility, | |
| 2102 | // this ignores plain --sort-common | |
| 2103 | 2107 | } else if (mem.eql(u8, linker_arg, "--whole-archive") or |
| 2104 | 2108 | mem.eql(u8, linker_arg, "-whole-archive")) |
| 2105 | 2109 | { |
| ... | ... | @@ -2272,7 +2276,74 @@ fn buildOutputType( |
| 2272 | 2276 | disable_c_depfile = true; |
| 2273 | 2277 | try cc_argv.append(arena, "-###"); |
| 2274 | 2278 | }, |
| 2275 | .for_linker => try linker_args.append(it.only_arg), | |
| 2279 | .for_linker => blk: { | |
| 2280 | // Unfortunately duplicated with the `wl` handling above. | |
| 2281 | ||
| 2282 | // Handle joined args like `--dependency-file=foo.d`. | |
| 2283 | // Must be prefixed with 1 or 2 dashes. | |
| 2284 | if (it.only_arg.len >= 3 and it.only_arg[0] == '-' and it.only_arg[2] != '-') { | |
| 2285 | if (mem.indexOfScalar(u8, it.only_arg, '=')) |equals_pos| { | |
| 2286 | const key = it.only_arg[0..equals_pos]; | |
| 2287 | const value = it.only_arg[equals_pos + 1 ..]; | |
| 2288 | ||
| 2289 | // We have to handle these here because they would be ambiguous | |
| 2290 | // if split and added to `linker_args`, as there are argument-less | |
| 2291 | // variants of them. | |
| 2292 | if (mem.eql(u8, key, "--build-id")) { | |
| 2293 | build_id = std.zig.BuildId.parse(value) catch |err| { | |
| 2294 | fatal("unable to parse --build-id style '{s}': {s}", .{ | |
| 2295 | value, @errorName(err), | |
| 2296 | }); | |
| 2297 | }; | |
| 2298 | continue; | |
| 2299 | } else if (mem.eql(u8, key, "--sort-common")) { | |
| 2300 | // this ignores --sort-common=<anything> | |
| 2301 | continue; | |
| 2302 | } | |
| 2303 | ||
| 2304 | try linker_args.append(key); | |
| 2305 | try linker_args.append(value); | |
| 2306 | break :blk; | |
| 2307 | } | |
| 2308 | } | |
| 2309 | ||
| 2310 | // These options are handled inline because their order matters for | |
| 2311 | // other non-linker options. | |
| 2312 | if (mem.eql(u8, it.only_arg, "--as-needed")) { | |
| 2313 | needed = false; | |
| 2314 | } else if (mem.eql(u8, it.only_arg, "--no-as-needed")) { | |
| 2315 | needed = true; | |
| 2316 | } else if (mem.eql(u8, it.only_arg, "--whole-archive") or | |
| 2317 | mem.eql(u8, it.only_arg, "-whole-archive")) | |
| 2318 | { | |
| 2319 | must_link = true; | |
| 2320 | } else if (mem.eql(u8, it.only_arg, "--no-whole-archive") or | |
| 2321 | mem.eql(u8, it.only_arg, "-no-whole-archive")) | |
| 2322 | { | |
| 2323 | must_link = false; | |
| 2324 | } else if (mem.eql(u8, it.only_arg, "-Bdynamic") or | |
| 2325 | mem.eql(u8, it.only_arg, "-dy") or | |
| 2326 | mem.eql(u8, it.only_arg, "-call_shared")) | |
| 2327 | { | |
| 2328 | lib_search_strategy = .no_fallback; | |
| 2329 | lib_preferred_mode = .dynamic; | |
| 2330 | } else if (mem.eql(u8, it.only_arg, "-Bstatic") or | |
| 2331 | mem.eql(u8, it.only_arg, "-dn") or | |
| 2332 | mem.eql(u8, it.only_arg, "-non_shared") or | |
| 2333 | mem.eql(u8, it.only_arg, "-static")) | |
| 2334 | { | |
| 2335 | lib_search_strategy = .no_fallback; | |
| 2336 | lib_preferred_mode = .static; | |
| 2337 | } else if (mem.eql(u8, it.only_arg, "-search_paths_first")) { | |
| 2338 | lib_search_strategy = .paths_first; | |
| 2339 | lib_preferred_mode = .dynamic; | |
| 2340 | } else if (mem.eql(u8, it.only_arg, "-search_dylibs_first")) { | |
| 2341 | lib_search_strategy = .mode_first; | |
| 2342 | lib_preferred_mode = .dynamic; | |
| 2343 | } else { | |
| 2344 | try linker_args.append(it.only_arg); | |
| 2345 | } | |
| 2346 | }, | |
| 2276 | 2347 | .linker_input_z => { |
| 2277 | 2348 | try linker_args.append("-z"); |
| 2278 | 2349 | try linker_args.append(it.only_arg); |
| ... | ... | @@ -2402,6 +2473,13 @@ fn buildOutputType( |
| 2402 | 2473 | } |
| 2403 | 2474 | } |
| 2404 | 2475 | provided_name = name[prefix..end]; |
| 2476 | } else if (mem.eql(u8, arg, "--build-id")) { | |
| 2477 | build_id = .fast; | |
| 2478 | } else if (mem.eql(u8, arg, "-no-pie")) { | |
| 2479 | create_module.opts.pie = false; | |
| 2480 | } else if (mem.eql(u8, arg, "--sort-common")) { | |
| 2481 | // from ld.lld(1): --sort-common is ignored for GNU compatibility, | |
| 2482 | // this ignores plain --sort-common | |
| 2405 | 2483 | } else if (mem.eql(u8, arg, "-rpath") or mem.eql(u8, arg, "--rpath") or mem.eql(u8, arg, "-R")) { |
| 2406 | 2484 | try create_module.rpath_list.append(arena, linker_args_it.nextOrFatal()); |
| 2407 | 2485 | } else if (mem.eql(u8, arg, "--subsystem")) { |
| ... | ... | @@ -2697,6 +2775,8 @@ fn buildOutputType( |
| 2697 | 2775 | { |
| 2698 | 2776 | emit_implib = .{ .yes = linker_args_it.nextOrFatal() }; |
| 2699 | 2777 | emit_implib_arg_provided = true; |
| 2778 | } else if (mem.eql(u8, arg, "--dependency-file")) { | |
| 2779 | link_depfile = linker_args_it.nextOrFatal(); | |
| 2700 | 2780 | } else if (mem.eql(u8, arg, "-Brepro") or mem.eql(u8, arg, "/Brepro")) { |
| 2701 | 2781 | linker_repro = true; |
| 2702 | 2782 | } else if (mem.eql(u8, arg, "-undefined")) { |
| ... | ... | @@ -3472,6 +3552,7 @@ fn buildOutputType( |
| 3472 | 3552 | .verbose_generic_instances = verbose_generic_instances, |
| 3473 | 3553 | .verbose_llvm_ir = verbose_llvm_ir, |
| 3474 | 3554 | .verbose_llvm_bc = verbose_llvm_bc, |
| 3555 | .link_depfile = link_depfile, | |
| 3475 | 3556 | .verbose_cimport = verbose_cimport, |
| 3476 | 3557 | .verbose_llvm_cpu_features = verbose_llvm_cpu_features, |
| 3477 | 3558 | .time_report = time_report, |