diff --git a/internal/pkg/exec.go b/internal/pkg/exec.go index 4865c71a..7760668a 100644 --- a/internal/pkg/exec.go +++ b/internal/pkg/exec.go @@ -27,6 +27,11 @@ import ( // AbsWork is the container pathname [TContext.GetWorkDir] is mounted on. var AbsWork = fhs.AbsRoot.Append("work/") +// EnvJobs is the name of the environment variable holding a decimal +// representation of the preferred job count. Its value must not affect cure +// outcome. +const EnvJobs = "CURE_JOBS" + // ExecPath is a slice of [Artifact] and the [check.Absolute] pathname to make // it available at under in the container. type ExecPath struct { @@ -397,7 +402,7 @@ const SeccompPresets = std.PresetStrict & func (a *execArtifact) makeContainer( ctx context.Context, msg message.Msg, - flags int, + flags, jobs int, hostNet bool, temp, work *check.Absolute, getArtifact GetArtifactFunc, @@ -432,8 +437,8 @@ func (a *execArtifact) makeContainer( z.Hostname = "cure-net" } z.Uid, z.Gid = (1<<10)-1, (1<<10)-1 - - z.Dir, z.Env, z.Path, z.Args = a.dir, a.env, a.path, a.args + z.Dir, z.Path, z.Args = a.dir, a.path, a.args + z.Env = slices.Concat(a.env, []string{EnvJobs + "=" + strconv.Itoa(jobs)}) z.Grow(len(a.paths) + 4) for i, b := range a.paths { @@ -563,6 +568,7 @@ func (c *Cache) EnterExec( z, err = e.makeContainer( ctx, c.msg, c.flags, + c.jobs, hostNet, temp, work, func(a Artifact) (*check.Absolute, unique.Handle[Checksum]) { @@ -602,7 +608,7 @@ func (a *execArtifact) cure(f *FContext, hostNet bool) (err error) { msg := f.GetMessage() var z *container.Container if z, err = a.makeContainer( - ctx, msg, f.cache.flags, hostNet, + ctx, msg, f.cache.flags, f.GetJobs(), hostNet, f.GetTempDir(), f.GetWorkDir(), f.GetArtifact, f.cache.Ident, diff --git a/internal/pkg/testdata/main.go b/internal/pkg/testdata/main.go index c969474d..f79f7917 100644 --- a/internal/pkg/testdata/main.go +++ b/internal/pkg/testdata/main.go @@ -9,7 +9,9 @@ import ( "os" "path/filepath" "reflect" + "runtime" "slices" + "strconv" "strings" "hakurei.app/check" @@ -21,6 +23,10 @@ func main() { log.SetFlags(0) log.SetPrefix("testtool: ") + environ := slices.DeleteFunc(slices.Clone(os.Environ()), func(s string) bool { + return s == "CURE_JOBS="+strconv.Itoa(runtime.NumCPU()) + }) + var hostNet, layers, promote bool if len(os.Args) == 2 && os.Args[0] == "testtool" { switch os.Args[1] { @@ -48,15 +54,15 @@ func main() { var overlayRoot bool wantEnv := []string{"HAKUREI_TEST=1"} - if len(os.Environ()) == 2 { + if len(environ) == 2 { overlayRoot = true if !layers && !promote { log.SetPrefix("testtool(overlay root): ") } wantEnv = []string{"HAKUREI_TEST=1", "HAKUREI_ROOT=1"} } - if !slices.Equal(wantEnv, os.Environ()) { - log.Fatalf("Environ: %q, want %q", os.Environ(), wantEnv) + if !slices.Equal(wantEnv, environ) { + log.Fatalf("Environ: %q, want %q", environ, wantEnv) } var overlayWork bool