anthropic
A poisoned repo escaped Claude Code's sandbox in one message
Promtime
anthropicTurn Claude Code's sandbox on and it stops asking permission before each command. That is exactly why Accomplish saw no prompt when a command from the repository they had just opened ran on their Mac, outside the sandbox, after one short message.
At a glance
- Accomplish reported the escape on July 13, 2026; Anthropic triaged it the same day, shipped partial hardening in 2.1.223 on August 6, and closed the hole fully in 2.1.247 on August 26.
- The harness indexes an open repository with its own git calls outside Seatbelt, and one of them, git ls-files, did not blank core.fsmonitor, the config entry git runs as a shell command.
- Four protections stood in the way and each had a gap, including a missing Seatbelt rule that let a setup script rename a poisoned git folder into .git inside a subfolder.
If you missed the earlier episode, this is the second time Accomplish has taken apart an Anthropic sandbox. According to the company, its SharedRoot writeup described connecting a folder to a fresh Claude Cowork session, sending one short message, and watching the agent reach the host Mac to read and write files with no prompt. That report was closed as Informative, and Cowork now runs in the cloud by default, so the local path described there does not appear to apply.
Turning the sandbox on is what removed the prompt
With the sandbox on, according to Anthropic's Claude Code documentation, commands stop going through approval one at a time: you declare which files and which domains commands may touch, and the operating system enforces that boundary for every Bash command and the processes it starts. On macOS the enforcement is Seatbelt, built into the system, with nothing to install.
The catch is what Seatbelt wraps: the Bash tool. The harness runs its own git commands in the background to index the repository you opened, and those sit outside the wrapper. So a repo that can get one of those calls to execute something has execution on your Mac, and with the sandbox on, nothing asks first. Accomplish says the chain can also arrive through an indirect prompt injection.
Git runs whatever core.fsmonitor points at
core.fsmonitor is a speed setting. Rather than checking every file for changes, git asks a small helper program, and the path to that helper lives in the repository's own .git/config. Git reads it and runs it as a shell command whenever it looks at the working tree.
Picture a note pinned inside the repo's settings that says: before you look at the files, run this for me. Git does not ask who pinned it. The security firm Cobalt describes the same setting as blind trust in local configuration, and demonstrates the trick against IDEs that run git status automatically the moment a folder is opened.
Four defenses stood in the way, and each had a gap
The git commands the harness runs outside the sandbox pass flags that blank core.fsmonitor and other dangerous options, so the config never executes. The command that refreshes the file index, git ls-files, was left unhardened.
The .git folder is protected too: Claude's file tools refuse to write into it, Seatbelt blocks bash from writing there, a fresh clone never carries the remote's config, and renaming another folder into .git is blocked. But only at the project root.
The Seatbelt rule covering a nested .git was missing, so a setup script can build a git folder under another name, write core.fsmonitor into its config, and rename it to .git inside a subfolder.
The harness runs git in whatever directory the Bash tool used last, so the script changes into that subfolder. Then it needs the refresh to fire: its last line tells Claude to read a build report there. Reading a file makes Claude scan the folder for skills, loading a skill triggers a file index refresh, and that refresh is git ls-files, in the poisoned directory.
The full fix landed in 2.1.247 on August 26
Anthropic triaged the report on the day it arrived, July 13, 2026. A first round of hardening shipped on August 6 in 2.1.223, but it missed some of the git calls and the escape moved to another one; the researchers sent over the calls still open. The full fix came on August 26 in 2.1.247, and every git command the harness runs now blanks core.fsmonitor.
Accomplish's own answer is architectural. It puts the whole agent inside a VM: bash, git and every process they spawn. Real credentials never enter the guest, the agent holds placeholders, and its traffic leaves through a proxy on the host that the agent cannot reconfigure. A poisoned core.fsmonitor still runs, just not on your Mac.
The writeup is a macOS story: Seatbelt, a Mac, a nested .git. It does not say whether the Linux and WSL2 sandbox, which Anthropic's docs describe as bubblewrap plus socat, had the same missing rename rule, and it offers no sense of how many repositories in the wild ever carried such a payload. In our view the sharpest detail is that rename block, which covered the .git at the project root and not the ones a level down.
Where the pattern could reappear The shape of this bug is generic: a background process that reads a repository's own config and runs what it finds. Version 2.1.247 closes this instance, and the open question is whether anything else the harness runs outside Seatbelt still reads repo-controlled settings. The writeup sets no date beyond August 26, so the only checkpoint on offer is the version number you are running.
Comments
No comments yet. Be the first.
Join the conversation
Sign in with Google to leave a comment. Your name and avatar come from your Google profile, and the comment appears after moderation.
We only use your name and avatar from Google. We never store your email address.
