TurnExecutionSecuritySnapshot, and the tools runtime enforces that snapshot before side effects run.
The snapshot combines user-visible permission behavior with concrete execution controls:
- tool actions can be allowed, denied, or routed through an approval prompt;
- file tools are checked against resolved read/write roots before opening paths;
- web tools are checked against the turn network policy before network access;
- shell commands receive a process policy for cwd, environment filtering, timeout, and command risk;
- native shell execution can use the
nonosandbox backend on Linux/macOS or a restricted-token backend on Windows when the resolved snapshot requires a native sandbox; - CLI-backed runtimes use their provider-native sandbox and approval capabilities when available;
- every decision is auditable through durable turn events.
Main types
The public protocol types live incrates/protocol/src/turn.rs, with policy compilation helpers in crates/protocol/src/turn_permissions.rs.
Permission modes
The desktop composer exposes the same three protocol modes in this order:
The policy vocabulary has three behaviors:
Current built-in modes use
allow and ask; the protocol and evaluator also support deny.
Execution security snapshot
TurnExecutionSecuritySnapshot is the executable form of the permission choice. The gateway builds it in crates/gateway/src/turn_security.rs before the agent turn runs and attaches it to tool invocations.
The built-in resolver maps modes to snapshots as follows:
For native API-provider turns, restricted modes use the native sandbox backend:
nono on Linux/macOS and Windows restricted tokens on Windows. For CLI-backed turns, the gateway records the runtime provider’s sandbox and approval capabilities and marks enforcement active, partially active, or unavailable based on what that runtime can enforce.
Profile sources
TurnPermissionProfileSource records why a profile exists:
The source is persisted with the profile snapshot and repeated in permission audit events. Clients can show both the policy that applied and where it came from.
Evaluation flow
Permission evaluation happens inside the normal tools runtime, not in individual client shells. The evaluator classifies tool calls intoTurnPermissionActionKind:
file_readfile_writeshell_commandnetworkmcp_readmcp_write_or_unknowndynamic_skill_toolcomputer_usetask_subagentinternalunknown
scope_hash, a machine-readable reason, an optional summary, display details, and visible_thread_ids when the approval UI should associate the request with more than one visible thread. The scope_hash is used for the allow_for_turn cache: if the user allows the same normalized action scope for the rest of the turn, later matching asks can proceed without opening another prompt.
Filesystem, network, and process enforcement
The permission evaluator answers “may this kind of tool action proceed now?” The security snapshot answers “what resource boundary applies if it proceeds?” Filesystem tools callFilePolicyChecker before reading, listing, grepping, writing, editing, applying patches, or writing downloads. The checker resolves relative paths against sandbox.cwd, canonicalizes existing paths, handles new write targets through the canonical parent directory, rejects paths outside allowed roots, rejects write attempts under read-only roots, and rejects symlink escapes.
Web tools call NetworkPolicyChecker before search, fetch, or download. It accepts HTTP and HTTPS URLs only, checks denied domains before allow rules, rejects disabled network access, and supports restricted allowlists plus localhost policy. download_url also checks the destination path through the filesystem policy before opening the network request.
Shell execution builds a ProcessSpawnPlan from the snapshot before spawning. The plan enforces shell enablement, denied/allowed command-family rules, cwd access, environment filtering, and timeout caps. Native shell execution then prepares the native sandbox backend when one is selected. A provider-native sandbox snapshot is rejected on the native shell path because that backend can protect provider-runtime execution, not a Pioneer-spawned local process.
Approval can also add scoped grants. If the user approves a filesystem or network action once, the current invocation receives the grant. If the user approves it for the turn, matching grants are cached for the same turn and merged into later invocations without widening unrelated scopes.
Approval responses
Clients respond throughturn/permission/request/respond with one of:
The gateway resolves pending requests idempotently. It publishes
turn/permission/request/resolved after a response, cancellation, or expiry so clients can clear actionable UI.
Audit events
Permission decisions are durable turn events. The main event kinds are:
Audit events include profile mode/source, optional item/tool ids, action kind, optional request key, decision, reason, and whether a cached approval was used. They are persisted through
pioneer-crud, replayable through turn item/history APIs, and projected by the shared client core into timeline rows when the event should be visible.
Prompt integration
Restricted profiles are also described to the model.pioneer-promt renders a Current Permissions runtime section for non-default or narrowed policies. The section tells the model which actions may require approval and instructs it to continue with allowed alternatives when an action is denied.
The default unconstrained full_access profile does not add this prompt section, which keeps ordinary full-access turns from paying a prompt cost for redundant policy text.
CLI runtime mapping
CLI-backed turns use the same Pioneer permission profile at the protocol boundary. The gateway then maps that profile into the runtime-specific approval policy:
Codex currently has no distinct policy that matches Pioneer’s
auto_accept_edits exactly, so the adapter intentionally uses the stricter on-request fallback and records that mapping quality.
CLI runtime requests opened by the native runtime still use the CLI runtime pending-request surface (cli_runtime/request/respond). Pioneer turn permission requests from the native tools runtime use turn/permission/request/respond.
Tasks and subagents
Task-backed child turns receive a security cap. The task runtime can derive aTurnPermissionProfileCap and TaskAgentSecurityCap from the parent profile or task policy, and child runs are materialized with source task_permission_cap or inherited source data.
Policy intersection is restrictive: deny wins over ask, ask wins over allow, and the most restrictive mode wins in the order supervised, auto_accept_edits, full_access. Sandbox mode, network policy, process policy, and filesystem roots are also intersected against the parent/task cap. This prevents delegated or scheduled child work from silently expanding access beyond the parent/task contract.
Developer rules
- Treat permission profiles as part of
turn/startsemantics, not client-only UI state. - Resolve and persist the execution security snapshot before depending on in-memory execution state.
- Route side-effecting tool calls through the tools runtime so action classification, approval, audit, retry, and output policy stay consistent.
- Do not implement one-off approval prompts inside a tool handler. Add action classification and use the shared approval broker instead.
- Keep user-facing safety copy precise: permission modes, sandbox snapshots, native/provider sandbox backends, file policy, network policy, process policy, and audit events are real enforcement layers; stronger deployment boundaries still come from choosing the right gateway host and OS account.
- When adding a protocol field, action kind, decision reason, or notification, update protocol schemas, client reducers/FFI projections, and Turns API.
Related pages
- Tools System explains where permission evaluation sits in tool execution.
- Agent Loop explains how permission profiles enter agent turns and prompt compilation.
- Protocol Layer explains the JSON-RPC method and notification contract.
- CLI Runtime Architecture explains runtime-specific approval mapping.
- Tasks And Subagents explains delegated child turns and task execution.