sandbox

package
v0.22.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 18, 2026 License: Apache-2.0 Imports: 14 Imported by: 0

Documentation

Overview

Package sandbox builds the P4 OS-level cage for running an untrusted command (a future broad-shell/exec tool) confined so it CANNOT bypass the agent's app-level cages. On Linux it self-restricts a re-exec'd worker with: a fresh UNPRIVILEGED user+network namespace (severs ALL egress, including the loopback model/memory services), Landlock filesystem confinement (RO system + RO worktree + RW scratch, inherited by every child and irreversible), and a seccomp denylist + no_new_privs. The cage is built and adversarially PROVEN before any shell capability is granted (cage-before-capability). Non-Linux builds get a stub that reports unavailable and refuses to run (fail-closed).

The whole path is rootless: an unprivileged user namespace grants the namespaced privilege to create the net namespace; Landlock and seccomp are unprivileged by design. No sudo, no firewall, no package installs.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Available

func Available() (bool, string)

Available reports whether the OS cage can be enforced on this host: Landlock present (ABI >= 1), seccomp supported, and unprivileged user namespaces enabled. Used as the capability gate — a future shell tool is granted ONLY when this is true (fail-closed).

func IsWorker

func IsWorker() bool

IsWorker reports whether this process is a re-exec'd sandbox worker.

func RunWorkerFromEnv

func RunWorkerFromEnv()

RunWorkerFromEnv, when this process IS the worker, applies the cage and execs Spec.Argv — it never returns on success. Call it at the very top of main() (and TestMain) so the worker path runs before any normal startup. A no-op when this is not a worker.

Types

type Result

type Result struct {
	Stdout   string
	Stderr   string
	ExitCode int
	Signal   int  // terminating signal number if the command was killed (e.g. SIGSYS=31 from a seccomp KILL), else 0
	Refused  bool // true if the CAGE refused to run (setup failed) — distinct from the command running and exiting non-zero
}

Result is the outcome of a caged run.

func Run

func Run(ctx context.Context, spec Spec) (Result, error)

Run launches cmd (spec.Argv) inside the OS cage: a fresh UNPRIVILEGED user+network+pid+ipc+uts namespace (the user namespace grants the namespaced privilege to make the others; the empty net namespace severs ALL egress, including the loopback model/memory services), then — in the re-exec'd worker — seccomp + Landlock. Returns the command's captured output and exit code.

type Spec

type Spec struct {
	Argv             []string `json:"argv"`              // command to run INSIDE the cage, e.g. ["/bin/sh","-c",cmd]
	Worktree         string   `json:"worktree"`          // the worker's working directory; read-only UNLESS WorktreeWritable
	WorktreeWritable bool     `json:"worktree_writable"` // grant RW (not RO) on Worktree — for a shell that must build/edit in place
	Scratch          string   `json:"scratch"`           // a writable scratch dir (always RW); also HOME/TMPDIR inside the cage
	ReadDirs         []string `json:"read_dirs"`         // extra read-only dirs (the system dirs below are always added)
	ReadFiles        []string `json:"read_files"`        // specific read-only (+executable) files to grant, e.g. a static helper binary
	ABIFloor         int      `json:"abi_floor"`         // minimum achieved Landlock ABI required, else fail-closed (>=1)

	// AllowedExecutables is the base-name allowlist of programs the caged command
	// may launch. WINDOWS ENFORCES it: before spawning, the resolved program's base
	// name (case-insensitive, trailing ".exe" dropped) must be in this list, else
	// Run returns Result{Refused:true} WITHOUT launching. The LINUX cage IGNORES it
	// — there the OS-level containment (namespaces + Landlock + seccomp) is the
	// boundary, not an executable name filter. An empty list on Windows refuses
	// every command (fail-closed).
	AllowedExecutables []string `json:"allowed_executables"`
}

Spec is the cage configuration the parent hands to the re-exec'd worker (serialized into workerEnv). All paths must be absolute.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL