From 4f507070249342243e4639419b715edf642419a3 Mon Sep 17 00:00:00 2001 From: Luna Schwalbe Date: Fri, 15 Aug 2025 22:12:35 +0200 Subject: [PATCH 1/2] android: detect native ABI and API level correctly ABI detection previously did not take into account the non-standard directory structure of Android. This has been fixed. The API level is detected by running `getprop ro.build.version.sdk`, since we don't want to depend on bionic, and reading system properties ourselves is not trivially possible. --- lib/std/Target.zig | 4 +++ lib/std/zig/system.zig | 68 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 72 insertions(+) diff --git a/lib/std/Target.zig b/lib/std/Target.zig index 60f0b2e30407..582eb7b5232c 100644 --- a/lib/std/Target.zig +++ b/lib/std/Target.zig @@ -2045,6 +2045,10 @@ pub inline fn isMuslLibC(target: *const Target) bool { return target.os.tag == .linux and target.abi.isMusl(); } +pub inline fn isBionicLibC(target: *const Target) bool { + return target.os.tag == .linux and target.abi.isAndroid(); +} + pub inline fn isDarwinLibC(target: *const Target) bool { return switch (target.abi) { .none, .macabi, .simulator => target.os.tag.isDarwin(), diff --git a/lib/std/zig/system.zig b/lib/std/zig/system.zig index 549f3653211f..24b28c32aab5 100644 --- a/lib/std/zig/system.zig +++ b/lib/std/zig/system.zig @@ -172,6 +172,8 @@ pub const DetectError = error{ OSVersionDetectionFail, Unexpected, ProcessNotFound, + /// Android-only. Querying API level through `getprop` failed. + ApiLevelQueryFailed, }; /// Given a `Target.Query`, which specifies in detail which parts of the @@ -448,6 +450,29 @@ pub fn resolveTargetQuery(query: Target.Query) DetectError!Target { } } + if (builtin.os.tag == .linux and result.isBionicLibC() and query.os_tag == null and query.android_api_level == null) { + result.os.version_range.linux.android = detectAndroidApiLevel() catch |err| return switch (err) { + error.InvalidWtf8, + error.CurrentWorkingDirectoryUnlinked, + error.InvalidBatchScriptArg, + error.InvalidHandle, + => unreachable, // Windows-only + error.ApiLevelQueryFailed => |e| e, + else => blk: { + std.log.err("spawning or reading from getprop failed ({s})", .{@errorName(err)}); + switch (err) { + error.SystemResources, + error.FileSystem, + error.ProcessFdQuotaExceeded, + error.SystemFdQuotaExceeded, + error.SymLinkLoop, + => |e| break :blk e, + else => break :blk error.ApiLevelQueryFailed, + } + }, + }; + } + return result; } @@ -1146,6 +1171,11 @@ fn detectAbiAndDynamicLinker( error.FileTooBig, error.Unexpected, => |e| { + if (e == error.FileNotFound and os.tag == .linux and mem.eql(u8, file_name, "/usr/bin/env")) { + // Android does not have a /usr directory, so try again + file_name = "/system/bin/env"; + continue; + } std.log.warn("Encountered error: {s}, falling back to default ABI and dynamic linker.", .{@errorName(e)}); return defaultAbiAndDynamicLinker(cpu, os, query); }, @@ -1293,6 +1323,44 @@ fn elfInt(is_64: bool, need_bswap: bool, int_32: anytype, int_64: anytype) @Type } } +fn detectAndroidApiLevel() !u32 { + comptime if (builtin.os.tag != .linux) unreachable; + + // `child.spawn()` uses an arena and the exact memory requirement isn't easily determined, + // so we give it 128 * 3 bytes, which was shown in testing to be enough. + var alloc_buf: [128 * 3]u8 = undefined; + var fba = std.heap.FixedBufferAllocator.init(&alloc_buf); + var child = std.process.Child.init(&.{ "/system/bin/getprop", "ro.build.version.sdk" }, fba.allocator()); + // pass empty EnvMap, no allocator and deinit() required + child.env_map = &std.process.EnvMap.init(undefined); + child.stdin_behavior = .Ignore; + child.stdout_behavior = .Pipe; + child.stderr_behavior = .Ignore; + + try child.spawn(); + errdefer _ = child.kill() catch {}; + + // PROP_VALUE_MAX is 92, output is value + newline. + // Currently API levels are two-digit numbers, but we want to make sure we never read a partial value. + var stdout_buf: [92 + 1]u8 = undefined; + var reader = child.stdout.?.readerStreaming(&.{}); + const n = try reader.interface.readSliceShort(&stdout_buf); + const api_level = std.fmt.parseInt(u32, stdout_buf[0 .. n - 1], 10) catch |e| { + std.log.err( + "Could not parse API level, unexpected getprop output '{s}' ({s})", + .{ stdout_buf[0 .. n - 1], @errorName(e) }, + ); + return error.ApiLevelQueryFailed; + }; + + const term = try child.wait(); + if (term != .Exited or term.Exited != 0) { + std.log.err("getprop terminated abnormally: {}", .{term}); + return error.ApiLevelQueryFailed; + } + return api_level; +} + const builtin = @import("builtin"); const std = @import("../std.zig"); const mem = std.mem; From 7a72618fb584adcb72a22458181a87e641b9b8e0 Mon Sep 17 00:00:00 2001 From: Luna Schwalbe Date: Fri, 5 Sep 2025 16:36:14 +0200 Subject: [PATCH 2/2] Pass allocator to zig.system.resolveTargetQuery For now the allocator is only used in `detectAndroidApiLevel`, but there are probably other places in the detection logic that could benefit from this too. --- lib/compiler/aro/aro/Driver.zig | 2 +- lib/compiler/aro/aro/Value.zig | 4 ++-- lib/compiler/aro/aro/toolchains/Linux.zig | 2 +- lib/compiler/build_runner.zig | 2 +- lib/compiler/libc.zig | 2 +- lib/compiler/resinator/main.zig | 4 ++-- lib/compiler/std-docs.zig | 5 ++++- lib/std/Build.zig | 2 +- lib/std/Build/Step/Options.zig | 2 +- lib/std/Build/WebServer.zig | 5 ++++- lib/std/Target/Query.zig | 10 +++++----- lib/std/zig.zig | 4 ++-- lib/std/zig/system.zig | 15 +++++++------- src/Compilation.zig | 5 ++++- src/main.zig | 23 +++++++++++----------- src/print_env.zig | 2 +- test/src/Cases.zig | 10 +--------- tools/doctest.zig | 8 +++----- tools/fetch_them_macos_headers.zig | 2 +- tools/generate_c_size_and_align_checks.zig | 2 +- tools/incr-check.zig | 4 ++-- 21 files changed, 57 insertions(+), 58 deletions(-) diff --git a/lib/compiler/aro/aro/Driver.zig b/lib/compiler/aro/aro/Driver.zig index a6e3503b72c9..cd03d522639c 100644 --- a/lib/compiler/aro/aro/Driver.zig +++ b/lib/compiler/aro/aro/Driver.zig @@ -407,7 +407,7 @@ pub fn parseArgs( try d.comp.addDiagnostic(.{ .tag = .cli_invalid_target, .extra = .{ .str = arg } }, &.{}); continue; }; - const target = std.zig.system.resolveTargetQuery(query) catch |e| { + const target = std.zig.system.resolveTargetQuery(query, d.comp.gpa) catch |e| { return d.fatal("unable to resolve target: {s}", .{errorDescription(e)}); }; d.comp.target = target; diff --git a/lib/compiler/aro/aro/Value.zig b/lib/compiler/aro/aro/Value.zig index adc3f0881288..6016fd9c753b 100644 --- a/lib/compiler/aro/aro/Value.zig +++ b/lib/compiler/aro/aro/Value.zig @@ -71,7 +71,7 @@ test "minUnsignedBits" { var comp = Compilation.init(std.testing.allocator, std.fs.cwd()); defer comp.deinit(); const target_query = try std.Target.Query.parse(.{ .arch_os_abi = "x86_64-linux-gnu" }); - comp.target = try std.zig.system.resolveTargetQuery(target_query); + comp.target = try std.zig.system.resolveTargetQuery(target_query, comp.gpa); try Test.checkIntBits(&comp, 0, 0); try Test.checkIntBits(&comp, 1, 1); @@ -106,7 +106,7 @@ test "minSignedBits" { var comp = Compilation.init(std.testing.allocator, std.fs.cwd()); defer comp.deinit(); const target_query = try std.Target.Query.parse(.{ .arch_os_abi = "x86_64-linux-gnu" }); - comp.target = try std.zig.system.resolveTargetQuery(target_query); + comp.target = try std.zig.system.resolveTargetQuery(target_query, comp.gpa); try Test.checkIntBits(&comp, -1, 1); try Test.checkIntBits(&comp, -2, 2); diff --git a/lib/compiler/aro/aro/toolchains/Linux.zig b/lib/compiler/aro/aro/toolchains/Linux.zig index fe6272b6b4fb..6ff721eea186 100644 --- a/lib/compiler/aro/aro/toolchains/Linux.zig +++ b/lib/compiler/aro/aro/toolchains/Linux.zig @@ -423,7 +423,7 @@ test Linux { const raw_triple = "x86_64-linux-gnu"; const target_query = try std.Target.Query.parse(.{ .arch_os_abi = raw_triple }); - comp.target = try std.zig.system.resolveTargetQuery(target_query); + comp.target = try std.zig.system.resolveTargetQuery(target_query, arena); comp.langopts.setEmulatedCompiler(.gcc); var driver: Driver = .{ .comp = &comp }; diff --git a/lib/compiler/build_runner.zig b/lib/compiler/build_runner.zig index 5fcb8081b7dc..d37fac332990 100644 --- a/lib/compiler/build_runner.zig +++ b/lib/compiler/build_runner.zig @@ -79,7 +79,7 @@ pub fn main() !void { .zig_lib_directory = zig_lib_directory, .host = .{ .query = .{}, - .result = try std.zig.system.resolveTargetQuery(.{}), + .result = try std.zig.system.resolveTargetQuery(.{}, arena), }, .time_report = false, }; diff --git a/lib/compiler/libc.zig b/lib/compiler/libc.zig index ef3aabb6dcd5..5aab7f9005eb 100644 --- a/lib/compiler/libc.zig +++ b/lib/compiler/libc.zig @@ -66,7 +66,7 @@ pub fn main() !void { const target_query = std.zig.parseTargetQueryOrReportFatalError(gpa, .{ .arch_os_abi = target_arch_os_abi, }); - const target = std.zig.resolveTargetQueryOrFatal(target_query); + const target = std.zig.resolveTargetQueryOrFatal(target_query, gpa); if (print_includes) { const libc_installation: ?*LibCInstallation = libc: { diff --git a/lib/compiler/resinator/main.zig b/lib/compiler/resinator/main.zig index 1d87f21d2bf1..b1345d2c68f1 100644 --- a/lib/compiler/resinator/main.zig +++ b/lib/compiler/resinator/main.zig @@ -582,7 +582,7 @@ fn getIncludePaths(arena: std.mem.Allocator, auto_includes_option: cli.Options.A .cpu_arch = includes_arch, .abi = .msvc, }; - const target = std.zig.resolveTargetQueryOrFatal(target_query); + const target = std.zig.resolveTargetQueryOrFatal(target_query, arena); const is_native_abi = target_query.isNativeAbi(); const detected_libc = std.zig.LibCDirs.detect(arena, zig_lib_dir, &target, is_native_abi, true, null) catch { if (includes == .any) { @@ -608,7 +608,7 @@ fn getIncludePaths(arena: std.mem.Allocator, auto_includes_option: cli.Options.A .cpu_arch = includes_arch, .abi = .gnu, }; - const target = std.zig.resolveTargetQueryOrFatal(target_query); + const target = std.zig.resolveTargetQueryOrFatal(target_query, arena); const is_native_abi = target_query.isNativeAbi(); const detected_libc = std.zig.LibCDirs.detect(arena, zig_lib_dir, &target, is_native_abi, true, null) catch |err| switch (err) { error.OutOfMemory => |e| return e, diff --git a/lib/compiler/std-docs.zig b/lib/compiler/std-docs.zig index b6696b568034..2badcc3f4066 100644 --- a/lib/compiler/std-docs.zig +++ b/lib/compiler/std-docs.zig @@ -258,7 +258,10 @@ fn serveWasm( .target = &(std.zig.system.resolveTargetQuery(std.Build.parseTargetQuery(.{ .arch_os_abi = autodoc_arch_os_abi, .cpu_features = autodoc_cpu_features, - }) catch unreachable) catch unreachable), + }) catch unreachable, gpa) catch |err| switch (err) { + error.OutOfMemory => |e| return e, + else => unreachable, + }), .output_mode = .Exe, }); // std.http.Server does not have a sendfile API yet. diff --git a/lib/std/Build.zig b/lib/std/Build.zig index 2644b79dcde6..92a721038999 100644 --- a/lib/std/Build.zig +++ b/lib/std/Build.zig @@ -2650,7 +2650,7 @@ pub fn resolveTargetQuery(b: *Build, query: Target.Query) ResolvedTarget { } return .{ .query = query, - .result = std.zig.system.resolveTargetQuery(query) catch + .result = std.zig.system.resolveTargetQuery(query, b.allocator) catch @panic("unable to resolve target query"), }; } diff --git a/lib/std/Build/Step/Options.zig b/lib/std/Build/Step/Options.zig index fd6194f7ff7b..2871feb1beb9 100644 --- a/lib/std/Build/Step/Options.zig +++ b/lib/std/Build/Step/Options.zig @@ -546,7 +546,7 @@ test Options { .global_cache_root = .{ .path = "test", .handle = std.fs.cwd() }, .host = .{ .query = .{}, - .result = try std.zig.system.resolveTargetQuery(.{}), + .result = try std.zig.system.resolveTargetQuery(.{}, arena.allocator()), }, .zig_lib_directory = std.Build.Cache.Directory.cwd(), .time_report = false, diff --git a/lib/std/Build/WebServer.zig b/lib/std/Build/WebServer.zig index 1b3e3bfe82cc..62b9d826db23 100644 --- a/lib/std/Build/WebServer.zig +++ b/lib/std/Build/WebServer.zig @@ -666,7 +666,10 @@ fn buildClientWasm(ws: *WebServer, arena: Allocator, optimize: std.builtin.Optim .target = &(std.zig.system.resolveTargetQuery(std.Build.parseTargetQuery(.{ .arch_os_abi = arch_os_abi, .cpu_features = cpu_features, - }) catch unreachable) catch unreachable), + }) catch unreachable, ws.gpa) catch |err| switch (err) { + error.OutOfMemory => |e| return e, + else => unreachable, + }), .output_mode = .Exe, }); return base_path.join(arena, bin_name); diff --git a/lib/std/Target/Query.zig b/lib/std/Target/Query.zig index aa6671b65f29..14e9b0e1672f 100644 --- a/lib/std/Target/Query.zig +++ b/lib/std/Target/Query.zig @@ -648,7 +648,7 @@ test parse { .arch_os_abi = "x86_64-linux-gnu", .cpu_features = "x86_64-sse-sse2-avx-cx8", }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, std.testing.allocator); try std.testing.expect(target.os.tag == .linux); try std.testing.expect(target.abi == .gnu); @@ -673,7 +673,7 @@ test parse { .arch_os_abi = "arm-linux-musleabihf", .cpu_features = "generic+v8a", }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, std.testing.allocator); try std.testing.expect(target.os.tag == .linux); try std.testing.expect(target.abi == .musleabihf); @@ -690,7 +690,7 @@ test parse { .arch_os_abi = "aarch64-linux.3.10...4.4.1-gnu.2.27", .cpu_features = "generic+v8a", }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, std.testing.allocator); try std.testing.expect(target.cpu.arch == .aarch64); try std.testing.expect(target.os.tag == .linux); @@ -713,7 +713,7 @@ test parse { const query = try Query.parse(.{ .arch_os_abi = "aarch64-linux.3.10...4.4.1-android.30", }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, std.testing.allocator); try std.testing.expect(target.cpu.arch == .aarch64); try std.testing.expect(target.os.tag == .linux); @@ -734,7 +734,7 @@ test parse { const query = try Query.parse(.{ .arch_os_abi = "x86-windows.xp...win8-msvc", }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, std.testing.allocator); try std.testing.expect(target.cpu.arch == .x86); try std.testing.expect(target.os.tag == .windows); diff --git a/lib/std/zig.zig b/lib/std/zig.zig index c8eea995cd0f..b0c8523f3884 100644 --- a/lib/std/zig.zig +++ b/lib/std/zig.zig @@ -619,8 +619,8 @@ pub fn putAstErrorsIntoBundle( try wip_errors.addZirErrorMessages(zir, tree, tree.source, path); } -pub fn resolveTargetQueryOrFatal(target_query: std.Target.Query) std.Target { - return std.zig.system.resolveTargetQuery(target_query) catch |err| +pub fn resolveTargetQueryOrFatal(target_query: std.Target.Query, gpa: Allocator) std.Target { + return std.zig.system.resolveTargetQuery(target_query, gpa) catch |err| std.process.fatal("unable to resolve target: {s}", .{@errorName(err)}); } diff --git a/lib/std/zig/system.zig b/lib/std/zig/system.zig index 24b28c32aab5..40ec56f8acb5 100644 --- a/lib/std/zig/system.zig +++ b/lib/std/zig/system.zig @@ -163,6 +163,7 @@ pub fn getExternalExecutor( } pub const DetectError = error{ + OutOfMemory, FileSystem, SystemResources, SymLinkLoop, @@ -181,7 +182,7 @@ pub const DetectError = error{ /// and which are provided explicitly, this function resolves the native /// components by detecting the native system, and then resolves /// standard/default parts relative to that. -pub fn resolveTargetQuery(query: Target.Query) DetectError!Target { +pub fn resolveTargetQuery(query: Target.Query, gpa: Allocator) DetectError!Target { // Until https://github.com/ziglang/zig/issues/4592 is implemented (support detecting the // native CPU architecture as being different than the current target), we use this: const query_cpu_arch = query.cpu_arch orelse builtin.cpu.arch; @@ -451,7 +452,7 @@ pub fn resolveTargetQuery(query: Target.Query) DetectError!Target { } if (builtin.os.tag == .linux and result.isBionicLibC() and query.os_tag == null and query.android_api_level == null) { - result.os.version_range.linux.android = detectAndroidApiLevel() catch |err| return switch (err) { + result.os.version_range.linux.android = detectAndroidApiLevel(gpa) catch |err| return switch (err) { error.InvalidWtf8, error.CurrentWorkingDirectoryUnlinked, error.InvalidBatchScriptArg, @@ -461,6 +462,7 @@ pub fn resolveTargetQuery(query: Target.Query) DetectError!Target { else => blk: { std.log.err("spawning or reading from getprop failed ({s})", .{@errorName(err)}); switch (err) { + error.OutOfMemory, error.SystemResources, error.FileSystem, error.ProcessFdQuotaExceeded, @@ -1323,14 +1325,10 @@ fn elfInt(is_64: bool, need_bswap: bool, int_32: anytype, int_64: anytype) @Type } } -fn detectAndroidApiLevel() !u32 { +fn detectAndroidApiLevel(gpa: Allocator) !u32 { comptime if (builtin.os.tag != .linux) unreachable; - // `child.spawn()` uses an arena and the exact memory requirement isn't easily determined, - // so we give it 128 * 3 bytes, which was shown in testing to be enough. - var alloc_buf: [128 * 3]u8 = undefined; - var fba = std.heap.FixedBufferAllocator.init(&alloc_buf); - var child = std.process.Child.init(&.{ "/system/bin/getprop", "ro.build.version.sdk" }, fba.allocator()); + var child = std.process.Child.init(&.{ "/system/bin/getprop", "ro.build.version.sdk" }, gpa); // pass empty EnvMap, no allocator and deinit() required child.env_map = &std.process.EnvMap.init(undefined); child.stdin_behavior = .Ignore; @@ -1364,6 +1362,7 @@ fn detectAndroidApiLevel() !u32 { const builtin = @import("builtin"); const std = @import("../std.zig"); const mem = std.mem; +const Allocator = mem.Allocator; const elf = std.elf; const fs = std.fs; const assert = std.debug.assert; diff --git a/src/Compilation.zig b/src/Compilation.zig index 85c4f49bf656..5986de7d525f 100644 --- a/src/Compilation.zig +++ b/src/Compilation.zig @@ -5369,7 +5369,10 @@ fn workerDocsWasmFallible(comp: *Compilation, prog_node: std.Progress.Node) SubU //.simd128, // .tail_call, not supported by Safari }), - }) catch unreachable, + }, gpa) catch |err| switch (err) { + error.OutOfMemory => |e| return e, + else => unreachable, + }, .is_native_os = false, .is_native_abi = false, diff --git a/src/main.zig b/src/main.zig index eef7b75fd0e7..f05cbeca12aa 100644 --- a/src/main.zig +++ b/src/main.zig @@ -343,7 +343,7 @@ fn mainArgs(gpa: Allocator, arena: Allocator, args: []const []const u8) !void { return cmdInit(gpa, arena, cmd_args); } else if (mem.eql(u8, cmd, "targets")) { dev.check(.targets_command); - const host = std.zig.resolveTargetQueryOrFatal(.{}); + const host = std.zig.resolveTargetQueryOrFatal(.{}, gpa); var stdout_writer = fs.File.stdout().writer(&stdout_buffer); try @import("print_targets.zig").cmdTargets(arena, cmd_args, &stdout_writer.interface, &host); return stdout_writer.interface.flush(); @@ -379,7 +379,7 @@ fn mainArgs(gpa: Allocator, arena: Allocator, args: []const []const u8) !void { } else if (mem.eql(u8, cmd, "ast-check")) { return cmdAstCheck(arena, cmd_args); } else if (mem.eql(u8, cmd, "detect-cpu")) { - return cmdDetectCpu(cmd_args); + return cmdDetectCpu(gpa, cmd_args); } else if (build_options.enable_debug_extensions and mem.eql(u8, cmd, "changelist")) { return cmdChangelist(arena, cmd_args); } else if (build_options.enable_debug_extensions and mem.eql(u8, cmd, "dump-zir")) { @@ -3803,7 +3803,7 @@ fn createModule( } const target_query = std.zig.parseTargetQueryOrReportFatalError(arena, target_parse_options); - const target = std.zig.resolveTargetQueryOrFatal(target_query); + const target = std.zig.resolveTargetQueryOrFatal(target_query, gpa); break :t .{ .result = target, .is_native_os = target_query.isNativeOs(), @@ -4353,7 +4353,7 @@ fn runOrTest( std.debug.lockStdErr(); const err = process.execve(gpa, argv.items, &env_map); std.debug.unlockStdErr(); - try warnAboutForeignBinaries(arena, arg_mode, target, link_libc); + try warnAboutForeignBinaries(gpa, arena, arg_mode, target, link_libc); const cmd = try std.mem.join(arena, " ", argv.items); fatal("the following command failed to execve with '{s}':\n{s}", .{ @errorName(err), cmd }); } else if (process.can_spawn) { @@ -4374,7 +4374,7 @@ fn runOrTest( break :t child.spawnAndWait(); }; const term = term_result catch |err| { - try warnAboutForeignBinaries(arena, arg_mode, target, link_libc); + try warnAboutForeignBinaries(gpa, arena, arg_mode, target, link_libc); const cmd = try std.mem.join(arena, " ", argv.items); fatal("the following command failed with '{s}':\n{s}", .{ @errorName(err), cmd }); }; @@ -5093,7 +5093,7 @@ fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !void { .arch_os_abi = triple, }); break :t .{ - .result = std.zig.resolveTargetQueryOrFatal(target_query), + .result = std.zig.resolveTargetQueryOrFatal(target_query, gpa), .is_native_os = false, .is_native_abi = false, .is_explicit_dynamic_linker = false, @@ -5101,7 +5101,7 @@ fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !void { } } break :t .{ - .result = std.zig.resolveTargetQueryOrFatal(.{}), + .result = std.zig.resolveTargetQueryOrFatal(.{}, gpa), .is_native_os = true, .is_native_abi = true, .is_explicit_dynamic_linker = false, @@ -5522,7 +5522,7 @@ fn jitCmd( const target_query: std.Target.Query = .{}; const resolved_target: Package.Module.ResolvedTarget = .{ - .result = std.zig.resolveTargetQueryOrFatal(target_query), + .result = std.zig.resolveTargetQueryOrFatal(target_query, gpa), .is_native_os = true, .is_native_abi = true, .is_explicit_dynamic_linker = false, @@ -6318,7 +6318,7 @@ fn cmdAstCheck( } } -fn cmdDetectCpu(args: []const []const u8) !void { +fn cmdDetectCpu(gpa: Allocator, args: []const []const u8) !void { dev.check(.detect_cpu_command); const detect_cpu_usage = @@ -6363,7 +6363,7 @@ fn cmdDetectCpu(args: []const []const u8) !void { const cpu = try detectNativeCpuWithLLVM(builtin.cpu.arch, name, features); try printCpu(cpu); } else { - const host_target = std.zig.resolveTargetQueryOrFatal(.{}); + const host_target = std.zig.resolveTargetQueryOrFatal(.{}, gpa); try printCpu(host_target.cpu); } } @@ -6631,13 +6631,14 @@ fn parseIntSuffix(arg: []const u8, prefix_len: usize) u64 { } fn warnAboutForeignBinaries( + gpa: Allocator, arena: Allocator, arg_mode: ArgMode, target: *const std.Target, link_libc: bool, ) !void { const host_query: std.Target.Query = .{}; - const host_target = std.zig.resolveTargetQueryOrFatal(host_query); + const host_target = std.zig.resolveTargetQueryOrFatal(host_query, gpa); switch (std.zig.system.getExternalExecutor(&host_target, target, .{ .link_libc = link_libc })) { .native => return, diff --git a/src/print_env.zig b/src/print_env.zig index e1b2b1eb83b8..ec9cba3fa1d1 100644 --- a/src/print_env.zig +++ b/src/print_env.zig @@ -39,7 +39,7 @@ pub fn cmdEnv( const zig_std_dir = try dirs.zig_lib.join(arena, &.{"std"}); const global_cache_dir = dirs.global_cache.path orelse ""; - const host = try std.zig.system.resolveTargetQuery(.{}); + const host = try std.zig.system.resolveTargetQuery(.{}, arena); const triple = try host.zigTriple(arena); var serializer: std.zon.Serializer = .{ .writer = out }; diff --git a/test/src/Cases.zig b/test/src/Cases.zig index fcdade09a37e..4e7ff1d48b59 100644 --- a/test/src/Cases.zig +++ b/test/src/Cases.zig @@ -618,7 +618,7 @@ pub fn lowerToBuildSteps( parent_step: *std.Build.Step, options: CaseTestOptions, ) void { - const host = std.zig.system.resolveTargetQuery(.{}) catch |err| + const host = std.zig.system.resolveTargetQuery(.{}, b.allocator) catch |err| std.debug.panic("unable to detect native host: {s}\n", .{@errorName(err)}); const cases_dir_path = b.build_root.join(b.allocator, &.{ "test", "cases" }) catch @panic("OOM"); @@ -1127,14 +1127,6 @@ const TestManifest = struct { } }; -fn resolveTargetQuery(query: std.Target.Query) std.Build.ResolvedTarget { - return .{ - .query = query, - .target = std.zig.system.resolveTargetQuery(query) catch - @panic("unable to resolve target query"), - }; -} - fn knownFileExtension(filename: []const u8) bool { // List taken from `Compilation.classifyFileExt` in the compiler. for ([_][]const u8{ diff --git a/tools/doctest.zig b/tools/doctest.zig index ccdbc6b065c9..4439b3305c7a 100644 --- a/tools/doctest.zig +++ b/tools/doctest.zig @@ -123,7 +123,7 @@ fn printOutput( var env_map = try process.getEnvMap(arena); try env_map.put("CLICOLOR_FORCE", "1"); - const host = try std.zig.system.resolveTargetQuery(.{}); + const host = try std.zig.system.resolveTargetQuery(.{}, arena); const obj_ext = builtin.object_format.fileExt(builtin.cpu.arch); const print = std.debug.print; @@ -238,7 +238,7 @@ fn printOutput( const target_query = try std.Target.Query.parse(.{ .arch_os_abi = code.target_str orelse "native", }); - const target = try std.zig.system.resolveTargetQuery(target_query); + const target = try std.zig.system.resolveTargetQuery(target_query, arena); const path_to_exe = try std.fmt.allocPrint(arena, "./{s}{s}", .{ code_name, target.exeFileExt(), @@ -316,9 +316,7 @@ fn printOutput( const target_query = try std.Target.Query.parse(.{ .arch_os_abi = triple, }); - const target = try std.zig.system.resolveTargetQuery( - target_query, - ); + const target = try std.zig.system.resolveTargetQuery(target_query, arena); switch (getExternalExecutor(&host, &target, .{ .link_libc = code.link_libc, })) { diff --git a/tools/fetch_them_macos_headers.zig b/tools/fetch_them_macos_headers.zig index 3c070e849ff3..4c0dd8f22419 100644 --- a/tools/fetch_them_macos_headers.zig +++ b/tools/fetch_them_macos_headers.zig @@ -85,7 +85,7 @@ pub fn main() anyerror!void { } const sysroot_path = sysroot orelse blk: { - const target = try std.zig.system.resolveTargetQuery(.{}); + const target = try std.zig.system.resolveTargetQuery(.{}, gpa); break :blk std.zig.system.darwin.getSdk(allocator, &target) orelse fatal("no SDK found; you can provide one explicitly with '--sysroot' flag", .{}); }; diff --git a/tools/generate_c_size_and_align_checks.zig b/tools/generate_c_size_and_align_checks.zig index 8c278407e483..ec9f43e0780f 100644 --- a/tools/generate_c_size_and_align_checks.zig +++ b/tools/generate_c_size_and_align_checks.zig @@ -40,7 +40,7 @@ pub fn main() !void { } const query = try std.Target.Query.parse(.{ .arch_os_abi = args[1] }); - const target = try std.zig.system.resolveTargetQuery(query); + const target = try std.zig.system.resolveTargetQuery(query, gpa); var buffer: [2000]u8 = undefined; var stdout_writer = std.fs.File.stdout().writerStreaming(&buffer); diff --git a/tools/incr-check.zig b/tools/incr-check.zig index ed7443046a11..3e8af557b1fd 100644 --- a/tools/incr-check.zig +++ b/tools/incr-check.zig @@ -86,7 +86,7 @@ pub fn main() !void { else null; - const host = try std.zig.system.resolveTargetQuery(.{}); + const host = try std.zig.system.resolveTargetQuery(.{}, arena); const debug_log_verbose = debug_zcu or debug_dwarf or debug_link; @@ -696,7 +696,7 @@ const Case = struct { }, }) catch fatal("line {d}: invalid target query '{s}'", .{ line_n, query }); - const resolved = try std.zig.system.resolveTargetQuery(parsed_query); + const resolved = try std.zig.system.resolveTargetQuery(parsed_query, arena); try targets.append(arena, .{ .query = query,