bhanu.fyi
/blogNovember 10, 2026

a tool needs a room


part of the agent runtime lab.

before you hand someone a set of keys, it helps to know which doors they open.

a tool call has the same problem. the interesting question is what the program can reach once it starts running.

for my small agent runtime, i started with one useful job: run JavaScript that reads a synthetic notes file and returns its contents.

the agent loop runs on the host. it owns the database connection and provider configuration. when it receives a run_javascript call, it sends the program into a fresh gVisor sandbox with a dedicated workspace.

The host retains database and provider access; only the JavaScript tool runs inside the bounded sandbox.

the workspace is read-only. so is the root filesystem. networking is disabled, and the host's environment and credentials are not passed into the tool process.

the program gets a five-second deadline and a combined output limit of 16 KiB. it also has fixed memory, CPU, and process limits. those bounds make a small file-reading tool possible without giving it the full set of things the host process can do.

the local demo used an offline provider to choose the tool call, then actually ran the JavaScript inside gVisor. the program read notes.txt, and its output included the sandbox's kernel information. a missing-file attempt was recorded as a tool failure.

the choice of tool was reproducible. the execution boundary was real.

the isolation checks also cover attempts to read a host-only file, inspect a synthetic parent environment variable, and write to the mounted workspace. timeout and output-overflow checks exercise the limits. these are specific checks of the configured boundary; they do not establish resistance to every possible escape.

read-only access still grants access to the contents. i treat every file placed in that workspace as available to the tool. choosing the workspace is part of choosing the tool's authority.

there is another boundary worth keeping visible: only this JavaScript tool goes into gVisor. the agent loop and the separate read_file tool remain on the host. drawing a box around the whole agent would describe a different system.

the next question is what happens when a tool needs to write a patch. it will need somewhere writable, a record of what changed, and a decision about which changes leave that workspace.

for now, i can point to one room, one useful program, and the doors it can open.

inspect the local sandbox-demo receipt


👀

Getting page views