---
title: "Shell guard"
description: "A text scan over shell commands that blocks mentions of denied paths, and the four cases it is known to miss."
url: https://barestate.xyz/docs/security/shell-guard
---

# Shell guard

> A text scan over shell commands that blocks mentions of denied paths, and the four cases it is known to miss.

A shell command can read a key file in more ways than anyone can list, so OMS cannot check a `bash` call the way it checks a file path. This page explains what the text scan catches, the four tested cases it misses, and what you should rely on instead.

Because a shell command cannot be fully understood, the guard scans its text for `bash`. It lower-cases the command and looks for needles built from each denied or protected root. A match blocks the call with the rule `denied_root` or `protected_write`.

**Warning:**
The guard is "best effort by construction". The real control is the operating system sandbox or Docker. A command can build a path at run time.

## What counts as a match

| Needle | Example it catches |
|---|---|
| The path as given, expanded, absolute and real | `~/.ssh/id`, `~/.config/solana/id.json` |
| `$HOME` forms | `$HOME/.ssh/id`, `${HOME}/.ssh/id`, `"$HOME"/.gnupg/x` |
| Last two path parts, and the bare last name | `/.config/solana`, `/solana`, `/.ssh` |
| Dotted parent folder | `cd ~/.config && cat solana/id.json` |
| Bare dotted name after a space, quote, `;` or `=` | `cd ~ && cat .ssh/id_ed25519` |

A needle shorter than 3 characters is dropped. A needle that ends in a name character must be followed by a non-name character or the end of text, so `/solana` matches `~/.config/solana/id.json` but not a public checkout named `/solana-labs__solana-program-library`.

Host worktrees live under `.oms`, so in host mode the guard skips a needle that equals a folder on the task's own path.

## Tested attempts

The test runs 36 attempts and 3 controls. The attempts include `$HOME` forms, `..` inside the path, globs, brace expansion, quote splicing, `$(echo solana)`, a variable, Python `expanduser` with string concatenation, `find ... -exec cat`, `grep -r`, `ln -s`, `cd ... && cat`, `pushd`, `tar` and upper-case `~/.SSH`. The controls must stay allowed.

## Known gaps

The test asserts that exactly four of the 36 attempts slip past the guard.

1. `cd ~ && cat .s*/id_ed25519`, a glob over the dotted name.
2. A symlink inside a `solana-*` folder that points to `~/.config/solana`, read by its full path.
3. The same symlink, reached by a relative path after `cd`.
4. The same symlink, with `--` and `./`.

Cases 2 to 4 need a symlink in a `solana-*` folder. `source_fetch` drops links, so nothing can plant that symlink without already reading the key another way.

Not covered by that test: a command that builds a path at run time, and key locations outside the four default roots.

## Host approval

Since the scan can miss things, host mode adds a human check. Every model shell command needs your approval, and the terminal app asks. Headless runs default to `--host-approval deny`. OMS adds warnings for `sudo`, credential or wallet paths, a download piped into a shell, paths outside the worktree, recursive removal and writes outside the worktree. If nothing matches, it still warns: "unsandboxed command can access host files and network". These are disclosures, not a shell security boundary.

Tests: yes, including 11 commands in allow and deny cases.
