Description
Description
PR: fix(sandbox): restrict /sandbox to read-only via Landlock
The sandbox-base Docker image (ghcr.io/nvidia/nemoclaw/sandbox-base:latest) does not enforce read-only permissions on /sandbox/.openclaw/openclaw.json and /sandbox/.openclaw/.config-hash for the sandbox user. The sandbox user can successfully write to and delete both config files, violating the intended security model.
According to the production Dockerfile on the security/read-only-sandbox-filesystem branch, these files should be:
- Owned by
root:root - Permission
444 (read-only for all) - Additionally protected by Landlock LSM at runtime
However, the current sandbox-base image does not apply these permission restrictions, meaning these hardening steps are either missing from the base image layer or have not been merged and published yet.
Environment
- OS: Ubuntu (Linux 6.17.0-1008-nvidia, aarch64)
- Node.js: v22.22.2
- Docker: 29.1.3
- NemoClaw: v0.1.0
- Branch:
security/read-only-sandbox-filesystem (commit 0d85225) - Image:
ghcr.io/nvidia/nemoclaw/sandbox-base:latest (46581a73edba)
Steps to Reproduce
- Pull the current
sandbox-base image:
docker pull ghcr.io/nvidia/nemoclaw/sandbox-base:latest
- Run the SEC-3 validation command:
docker run --rm --entrypoint "" ghcr.io/nvidia/nemoclaw/sandbox-base:latest gosu sandbox python3 -c "
import os
for path in ['/sandbox/.openclaw/openclaw.json', '/sandbox/.openclaw/.config-hash']:
name = os.path.basename(path)
for op, fn in [
('WRITE', lambda p=path: open(p, 'w').write('x')),
('DELETE', lambda p=path: os.unlink(p)),
('RENAME', lambda p=path: os.rename(p, p + '.bak'))
]:
try:
fn()
print(f'{op}_{name}=SUCCEEDED')
except (PermissionError, OSError):
print(f'{op}_{name}=BLOCKED')
" - Observe output:
WRITE_openclaw.json=SUCCEEDED
DELETE_openclaw.json=SUCCEEDED
RENAME_openclaw.json=BLOCKED
WRITE_.config-hash=SUCCEEDED
DELETE_.config-hash=SUCCEEDED
RENAME_.config-hash=BLOCKED
Analysis
The production Dockerfile on the security/read-only-sandbox-filesystem branch contains the correct permission hardening:
chmod 444 /sandbox/.openclaw/openclaw.json
chown root:root /sandbox/.openclaw/openclaw.json
chmod 444 /sandbox/.openclaw/.config-hash
chown root:root /sandbox/.openclaw/.config-hash
These settings are not present in the published sandbox-base image. The fix requires either:
- Moving the permission hardening into the base image build (
Dockerfile.base), or - Rebuilding and republishing the image from the production Dockerfile that already includes these changes.
Expected Behavior
All 6 operations should be blocked:
WRITE_openclaw.json=BLOCKED
DELETE_openclaw.json=BLOCKED
RENAME_openclaw.json=BLOCKED
WRITE_.config-hash=BLOCKED
DELETE_.config-hash=BLOCKED
RENAME_.config-hash=BLOCKED
Actual Behavior
WRITE and DELETE succeed for both files. Only RENAME is blocked because the files were already deleted by the preceding DELETE operation.
Bug Details
| Field |
Value |
| Priority |
Unprioritized |
| Action |
Dev - Open - To fix |
| Disposition |
Open issue |
| Module |
Machine Learning - NemoClaw |
| Keyword |
NemoClaw, NEMOCLAW_GH_SYNC_APPROVAL, NemoClaw-SWQA-RelBlckr-Recommended |
[NVB# 6059424]
[NVB#6059424]
Description
Description
PR:
fix(sandbox): restrict /sandbox to read-only via LandlockThe
sandbox-baseDocker image (ghcr.io/nvidia/nemoclaw/sandbox-base:latest) does not enforce read-only permissions on/sandbox/.openclaw/openclaw.jsonand/sandbox/.openclaw/.config-hashfor thesandboxuser. The sandbox user can successfully write to and delete both config files, violating the intended security model.According to the production Dockerfile on the
security/read-only-sandbox-filesystembranch, these files should be:root:root444(read-only for all)However, the current
sandbox-baseimage does not apply these permission restrictions, meaning these hardening steps are either missing from the base image layer or have not been merged and published yet.Environment
security/read-only-sandbox-filesystem(commit0d85225)ghcr.io/nvidia/nemoclaw/sandbox-base:latest(46581a73edba)Steps to Reproduce
sandbox-baseimage:docker run --rm --entrypoint "" ghcr.io/nvidia/nemoclaw/sandbox-base:latest gosu sandbox python3 -c " import os for path in ['/sandbox/.openclaw/openclaw.json', '/sandbox/.openclaw/.config-hash']: name = os.path.basename(path) for op, fn in [ ('WRITE', lambda p=path: open(p, 'w').write('x')), ('DELETE', lambda p=path: os.unlink(p)), ('RENAME', lambda p=path: os.rename(p, p + '.bak')) ]: try: fn() print(f'{op}_{name}=SUCCEEDED') except (PermissionError, OSError): print(f'{op}_{name}=BLOCKED') "Analysis
The production Dockerfile on the
security/read-only-sandbox-filesystembranch contains the correct permission hardening:These settings are not present in the published
sandbox-baseimage. The fix requires either:Dockerfile.base), orExpected Behavior
All 6 operations should be blocked:
Actual Behavior
WRITEandDELETEsucceed for both files. OnlyRENAMEis blocked because the files were already deleted by the precedingDELETEoperation.Bug Details
[NVB# 6059424]
[NVB#6059424]