authorgravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2025-10-05 17:47:27+02:00
committergravatar for alex@alexrp.comAlex Rønne Petersen <alex@alexrp.com> 2025-10-05 23:33:12+02:00
log9e61a64033c4a8e085629fbf81c9238d51f17cc8
tree3f8683174d0e7eeb2196a5559d2e698ded78e733
parent5969d6180fb6cbff4016e57894e92e558ce61b83
signaturebadge-check Signed by SSH key SHA256:7B/LJ7bpR1eX8aCXSr4mtd5M45VMPKcx9zY8e95b5QM

std.zig.system: add OS checks for QEMU in getExternalExecutor()

FreeBSD doesn't support the same number of platforms as Linux, and even then, only has usermode emulation for a subset of its supported platforms. NetBSD's usermode emulation support is apparently just broken at the moment.

1 files changed, 56 insertions(+), 42 deletions(-)

lib/std/zig/system.zig+56-42
......@@ -81,53 +81,67 @@ pub fn getExternalExecutor(
8181 // If the OS matches, we can use QEMU to emulate a foreign architecture.
8282 if (options.allow_qemu and os_match and (!cpu_ok or options.qemu_fixes_dl)) {
8383 return switch (candidate.cpu.arch) {
84 .aarch64 => Executor{ .qemu = "qemu-aarch64" },
85 .aarch64_be => Executor{ .qemu = "qemu-aarch64_be" },
86 .arm, .thumb => Executor{ .qemu = "qemu-arm" },
87 .armeb, .thumbeb => Executor{ .qemu = "qemu-armeb" },
88 .hexagon => Executor{ .qemu = "qemu-hexagon" },
89 .loongarch64 => Executor{ .qemu = "qemu-loongarch64" },
90 .m68k => Executor{ .qemu = "qemu-m68k" },
91 .mips => Executor{ .qemu = "qemu-mips" },
92 .mipsel => Executor{ .qemu = "qemu-mipsel" },
93 .mips64 => Executor{
94 .qemu = switch (candidate.abi) {
95 .gnuabin32, .muslabin32 => "qemu-mipsn32",
96 else => "qemu-mips64",
97 },
98 },
99 .mips64el => Executor{
100 .qemu = switch (candidate.abi) {
101 .gnuabin32, .muslabin32 => "qemu-mipsn32el",
102 else => "qemu-mips64el",
103 },
104 },
105 .or1k => Executor{ .qemu = "qemu-or1k" },
106 .powerpc => Executor{ .qemu = "qemu-ppc" },
107 .powerpc64 => Executor{ .qemu = "qemu-ppc64" },
108 .powerpc64le => Executor{ .qemu = "qemu-ppc64le" },
109 .riscv32 => Executor{ .qemu = "qemu-riscv32" },
110 .riscv64 => Executor{ .qemu = "qemu-riscv64" },
111 .s390x => Executor{ .qemu = "qemu-s390x" },
112 .sparc => Executor{
113 .qemu = if (candidate.cpu.has(.sparc, .v8plus))
114 "qemu-sparc32plus"
115 else
116 "qemu-sparc",
84 inline .aarch64,
85 .arm,
86 .riscv64,
87 .x86,
88 .x86_64,
89 => |t| switch (candidate.os.tag) {
90 .linux,
91 .freebsd,
92 => .{ .qemu = switch (t) {
93 .x86 => "qemu-i386",
94 .x86_64 => switch (candidate.abi) {
95 .gnux32, .muslx32 => return bad_result,
96 else => "qemu-x86_64",
97 },
98 else => "qemu-" ++ @tagName(t),
99 } },
100 else => bad_result,
117101 },
118 .sparc64 => Executor{ .qemu = "qemu-sparc64" },
119 .x86 => Executor{ .qemu = "qemu-i386" },
120 .x86_64 => switch (candidate.abi) {
121 .gnux32, .muslx32 => return bad_result,
122 else => Executor{ .qemu = "qemu-x86_64" },
102 inline .aarch64_be,
103 .armeb,
104 .hexagon,
105 .loongarch64,
106 .m68k,
107 .mips,
108 .mipsel,
109 .mips64,
110 .mips64el,
111 .or1k,
112 .powerpc,
113 .powerpc64,
114 .powerpc64le,
115 .riscv32,
116 .s390x,
117 .sparc,
118 .sparc64,
119 .thumb,
120 .thumbeb,
121 .xtensa,
122 => |t| switch (candidate.os.tag) {
123 .linux,
124 => .{ .qemu = switch (t) {
125 .powerpc => "qemu-ppc",
126 .powerpc64 => "qemu-ppc64",
127 .powerpc64le => "qemu-ppc64le",
128 .mips64, .mips64el => switch (candidate.abi) {
129 .gnuabin32, .muslabin32 => if (t == .mips64el) "qemu-mipsn32el" else "qemu-mipsn32",
130 else => "qemu-" ++ @tagName(t),
131 },
132 .sparc => if (candidate.cpu.has(.sparc, .v8plus)) "qemu-sparc32plus" else "qemu-sparc",
133 .thumb => "qemu-arm",
134 .thumbeb => "qemu-armeb",
135 else => "qemu-" ++ @tagName(t),
136 } },
137 else => bad_result,
123138 },
124 .xtensa => Executor{ .qemu = "qemu-xtensa" },
125139 else => bad_result,
126140 };
127141 }
128142
129143 if (options.allow_wasmtime and candidate.cpu.arch.isWasm()) {
130 return Executor{ .wasmtime = "wasmtime" };
144 return .{ .wasmtime = "wasmtime" };
131145 }
132146
133147 switch (candidate.os.tag) {
......@@ -143,7 +157,7 @@ pub fn getExternalExecutor(
143157 .x86_64 => host.cpu.arch == .x86_64,
144158 else => false,
145159 };
146 return if (wine_supported) Executor{ .wine = "wine" } else bad_result;
160 return if (wine_supported) .{ .wine = "wine" } else bad_result;
147161 }
148162 return bad_result;
149163 },
......@@ -155,7 +169,7 @@ pub fn getExternalExecutor(
155169 if (candidate.cpu.arch != host.cpu.arch) {
156170 return bad_result;
157171 }
158 return Executor{ .darling = "darling" };
172 return .{ .darling = "darling" };
159173 }
160174 return bad_result;
161175 },