- mergeAccessPolicy !base fast-path: scripts["policy"] and per-script entry.policy were
shallow-copied, leaving them as references into the cached _fileCache object.
autoExpandBareDir mutations would propagate back into the cache, violating the invariant
established by the policy-copy fix. Now deep-copied via Object.fromEntries map.
- exec-sandbox-seatbelt: replace hardcoded "file-write*" with SEATBELT_WRITE_OPS constant
in the /tmp write allowance branch, consistent with all other allowance lines in the file.
- Tests added for nested scripts deep-copy invariant.
- bwrap: '---' rules on SYSTEM_RO_BIND_PATHS (/etc /usr /bin /lib /sbin /opt) now emit
--tmpfs in restrictive mode — previously the deny branch was gated to permissive mode
only, leaving syscalls inside the sandbox able to read /etc/passwd etc. despite policy
- seatbelt: bracket globs [abc] now detected as wildcards (/[*?[]/ and strip regex updated);
previously emitted as SBPL literals matching only a file literally named '[abc]'
- access-policy-file: mergeAccessPolicy fast-path (!base) returns shallow copy instead of
reference — autoExpandBareDir was mutating the cached agents['*'].policy in-place,
corrupting all subsequent resolveAccessPolicyForAgent calls in the same process
- access-policy: sha256 comparison normalizes to lowercase (.toLowerCase()) — validation
regex accepts uppercase (/i) but crypto.digest always returns lowercase, causing uppercase
sha256 in config to silently deny exec at runtime with no useful error
- Tests added for all four findings
- permAllowsWrite (bwrap), permToOps/deniedOps (seatbelt): guard all positional perm accesses with VALID_PERM_RE
- catchAllPerm/tmpPerm (seatbelt): validate rawPerm before positional access; fail closed to '---'
- hasScriptOverride (exec-runtime): check entry shape (non-null object, not array) before setting bypass flag
- scripts["policy"] merged into overrideRules in applyScriptPolicyOverride (was silently dropped)
- mergeAccessPolicy: reject non-object script entries before propagating
- validateAccessPolicyFileStructure: recurse into per-script entries to catch removed deny/default fields
- validateAccessPolicyConfig: reject non-object entries, validate sha256 format, emit mid-path wildcard
diagnostics for scripts["policy"] AND per-script policy blocks (previously only config.policy)
- env-prefix regex: handle escaped quotes in double-quoted values ((?:[^"\\]|\\.)*)
- _resetBwrapAvailableCacheForTest: export added for test isolation
- Tests added for all of the above