diff --git a/lib/compiler/Maker/Step/Run.zig b/lib/compiler/Maker/Step/Run.zig index fe58c6f287ddea387549ccf12435971865d238e3..d0ecd2eccf36d9ae78fe55206e68bba632232a81 100644 --- a/lib/compiler/Maker/Step/Run.zig +++ b/lib/compiler/Maker/Step/Run.zig @@ -65,6 +65,12 @@ pub fn make( } } + for (conf_run.preopen_names.slice, conf_run.preopen_paths.slice) |name, path| { + man.hash.addBytesZ(name.slice(conf)); + const cwd_path = try maker.resolveLazyPathIndex(arena, path, run_index); + man.hash.addBytes(try cwd_path.toString(arena)); + } + man.hash.add(graph.fuzzing); man.hash.add(conf_run.flags.color); man.hash.add(conf_run.flags.disable_zig_progress); @@ -1912,9 +1918,15 @@ fn runCommand( }, .wasmtime => |bin_name| { if (graph.enable_wasmtime) { - try interp_argv.ensureUnusedCapacity(arena, 3 + argv.len); + try interp_argv.ensureUnusedCapacity(arena, 3 + argv.len + conf_run.preopen_names.slice.len); interp_argv.appendAssumeCapacity(bin_name); interp_argv.appendAssumeCapacity("--dir=."); + for (conf_run.preopen_names.slice, conf_run.preopen_paths.slice) |name, lazy_path| { + const path = try maker.resolveLazyPath(arena, lazy_path.get(conf), run_index); + path.root_dir.handle.createDirPath(io, path.subPathOrDot()) catch |e| + return step.fail(maker, "failed creating directory {f}: {t}", .{ path, e }); + interp_argv.appendAssumeCapacity(try allocPrint(arena, "--dir={f}::{s}", .{ path, name.slice(conf) })); + } // Wasmtime doeesn't inherit environment variables from the parent process // by default. '-S inherit-env' was added in Wasmtime version 20. interp_argv.appendAssumeCapacity("-Sinherit-env"); diff --git a/lib/compiler/configurer.zig b/lib/compiler/configurer.zig index edb176efd12ceaa5aeea0532237764477b01586a..cce216eeb394d0976b7af3303859749ebaba8215 100644 --- a/lib/compiler/configurer.zig +++ b/lib/compiler/configurer.zig @@ -1070,6 +1070,8 @@ fn serialize(b: *std.Build, wc: *Configuration.Wip, writer: *Io.Writer) !void { .file_inputs = .{ .slice = try s.initLazyPathList(run.file_inputs.items) }, .args = .{ .slice = try s.initArgsList(run.argv.items) }, .cwd = .{ .value = try s.addOptionalLazyPath(run.cwd) }, + .preopen_names = .{ .slice = try s.initStringList(run.preopens.keys()) }, + .preopen_paths = .{ .slice = try s.initLazyPathList(run.preopens.values()) }, .captured_stdout = .{ .value = if (run.captured_stdout) |cs| .{ .basename = try wc.addString(cs.basename), .generated_file = cs.generated_file, diff --git a/lib/std/Build/Configuration.zig b/lib/std/Build/Configuration.zig index 6f917aecc0c3eacf7e4c8ba12558dee36800a389..9fb9cb481d53395e8722eb4f2a57ae77d21902a4 100644 --- a/lib/std/Build/Configuration.zig +++ b/lib/std/Build/Configuration.zig @@ -571,6 +571,8 @@ pub const Step = extern struct { flags2: Flags2, args: Storage.LengthPrefixedList(Arg.Index), cwd: Storage.FlagOptional(.flags, .cwd, LazyPath.Index), + preopen_names: Storage.LengthPrefixedList(String), + preopen_paths: Storage.LengthPrefixedList(LazyPath.Index), captured_stdout: Storage.FlagOptional(.flags, .captured_stdout, CapturedStream), captured_stderr: Storage.FlagOptional(.flags, .captured_stderr, CapturedStream), file_inputs: Storage.LengthPrefixedList(LazyPath.Index), diff --git a/lib/std/Build/Step/Run.zig b/lib/std/Build/Step/Run.zig index 619ba2780470d26ad27dca6245b61b35981ab1b3..d0eeb2d20f6058e80874f31c2d0423a7f8ae69b2 100644 --- a/lib/std/Build/Step/Run.zig +++ b/lib/std/Build/Step/Run.zig @@ -26,6 +26,10 @@ cwd: ?Build.LazyPath, /// Override this field to modify the environment, or use setEnvironmentVariable environ_map: ?*EnvMap, +/// Named files that will be provided to the parent process. +/// See `std.process.Preopens`. +preopens: std.array_hash_map.String(Build.LazyPath), + /// Controls the `NO_COLOR` and `CLICOLOR_FORCE` environment variables. color: Color = .auto, @@ -200,6 +204,7 @@ pub fn create(owner: *std.Build, name: []const u8) *Run { .argv = .empty, .cwd = null, .environ_map = null, + .preopens = .empty, .disable_zig_progress = false, .stdio = .infer_from_args, .stdin = .none, @@ -615,6 +620,17 @@ pub fn removeEnvironmentVariable(run: *Run, key: []const u8) void { _ = run.getEnvMap().swapRemove(key); } +pub fn setPreopen(run: *Run, name: []const u8, resource: Build.LazyPath) void { + const graph = run.step.owner.graph; + const arena = graph.arena; + resource.addStepDependencies(&run.step); + run.preopens.put( + arena, + graph.dupeString(name), + resource.dupe(graph), + ) catch @panic("OOM"); +} + /// Adds a check for exact stderr match. Does not add any other checks. pub fn expectStdErrEqual(run: *Run, bytes: []const u8) void { const graph = run.step.owner.graph;