| Internet-Draft | Local Tool Call Proof | October 2026 |
| Lee, et al. | Expires 10 April 2027 | [Page] |
AI agents increasingly act through local tool servers that run on the same host and are reached over inter-process channels such as the stdio transport of the Model Context Protocol (MCP). These channels are outside the scope of HTTP-based authorization: the tool server cannot tell whether a given invocation passed any policy decision, and reusable credentials typically sit in the agent's process memory.¶
This document defines a per-call proof for local tool invocation. A Call Authority that runs outside the agent process evaluates policy, issues a short-lived, single-use proof bound to the exact tool name and arguments through a canonical action digest, and verifies that proof on behalf of the tool server. The tool server rejects invocations whose proof is missing or does not verify. The proof format is opaque to the agent and the tool server; concrete formats are defined as evidence type profiles. An MCP stdio binding is provided.¶
This note is to be removed before publishing as an RFC.¶
Status information for this document may be found at https://datatracker.ietf.org/doc/draft-lee-wimse-local-tool-call-proof/.¶
Discussion of this document takes place on the Workload Identity in Multi System Environments (WIMSE) Working Group mailing list (mailto:wimse@ietf.org), which is archived at https://mailarchive.ietf.org/arch/browse/wimse/. Subscribe at https://www.ietf.org/mailman/listinfo/wimse/.¶
This Internet-Draft is submitted in full conformance with the provisions of BCP 78 and BCP 79.¶
Internet-Drafts are working documents of the Internet Engineering Task Force (IETF). Note that other groups may also distribute working documents as Internet-Drafts. The list of current Internet-Drafts is at https://datatracker.ietf.org/drafts/current/.¶
Internet-Drafts are draft documents valid for a maximum of six months and may be updated, replaced, or obsoleted by other documents at any time. It is inappropriate to use Internet-Drafts as reference material or to cite them other than as "work in progress."¶
This Internet-Draft will expire on 10 April 2027.¶
Copyright (c) 2026 IETF Trust and the persons identified as the document authors. All rights reserved.¶
This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (https://trustee.ietf.org/license-info) in effect on the date of publication of this document. Please review these documents carefully, as they describe your rights and restrictions with respect to this document. Code Components extracted from this document must include Revised BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Revised BSD License.¶
The AI Identity Management System [I-D.ietf-wimse-aims] composes workload identity, short-lived credentials, transport and application layer authentication, and OAuth-based delegation into a model for authenticating and authorizing AI agents. Its focus is on interactions that cross network boundaries.¶
A large share of agent actions, however, never cross a network boundary. An agent host commonly spawns local tool servers (filesystem access, shell execution, database and SaaS connectors) and talks to them over a local inter-process channel. In MCP [MCP], this is the stdio transport, and the authorization specification states that implementations using it "SHOULD NOT follow this specification, and instead retrieve credentials from the environment" [MCP-AUTHZ]. The MCP local server guidance describes the agent client and a stdio server as sharing one trust domain [MCP-LOCAL].¶
That model is adequate for a single user on a personal device. It is not adequate when:¶
an agent host runs on shared infrastructure and acts on behalf of many users;¶
local tool servers hold long-lived credentials and broad filesystem access; and¶
the agent's decisions are driven by untrusted content such as issues, pull requests, documents and web pages.¶
In that setting the agent is the most exposed component, and the local tool server is the last point at which an invocation can be checked before it reaches a resource. Network enforcement points never see calls to local resources such as files and shell commands.¶
This document specifies:¶
a canonical action digest that identifies exactly one tool invocation (Section 5);¶
a Call Authority outside the agent process that issues and verifies per-call proofs (Section 6);¶
an enforcement obligation on tool servers to reject invocations without a valid proof (Section 7);¶
a binding for the MCP stdio transport (Section 10).¶
The mechanism does not prevent prompt injection. It confines the effects of an injected or compromised agent to actions that policy permits, removes reusable secrets from the agent process, and makes every invocation attributable.¶
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.¶
A software component that decides, typically with the help of a language model, which tools to invoke and with which arguments. In MCP terms, the client embedded in an agent host.¶
A local process that executes tool invocations requested by the Agent, for example an MCP server reached over stdio.¶
A component that runs outside the Agent process, evaluates Policy, issues Call Proofs and verifies them. It holds all key material used for Call Proofs.¶
A signed document loaded by the Call Authority that states which callers may invoke which tools with which argument constraints, and which actions require human approval. The policy language is out of scope.¶
A short-lived, single-use value that commits to one Action Digest and attests that the Call Authority authorized that invocation.¶
A canonical hash of an invocation's method, tool name and arguments (Section 5).¶
An identifier naming the format and semantics of a Call Proof, defined by an evidence type profile (Section 9).¶
T1. Injected instructions. Content processed by the Agent causes it to request a tool invocation outside its intended role, for example reading a credential file and sending its contents through another tool.¶
T2. Theft of reusable secrets. Code execution inside the Agent process (for example through a compromised dependency) is used to extract credentials that remain usable after the compromise ends.¶
T3. Policy bypass and proof reuse. An invocation is sent without passing a policy check, or a proof obtained for one invocation is presented for another.¶
T4. Policy tampering. The policy is modified so that a denied action becomes allowed.¶
A malicious or compromised Tool Server. A Tool Server that ignores verification cannot be constrained by this mechanism.¶
Credentials that the Tool Server itself uses to reach remote resources. Those are covered by network-level controls and the mechanisms in [I-D.ietf-wimse-aims].¶
Compromise of the Call Authority or of the policy signing key.¶
Prevention of prompt injection itself, and actions that the policy permits.¶
Protection against T2 requires that the Agent run in a separate isolation boundary (a different operating system user, container or virtual machine) from the Tool Server and the Call Authority. If they share one boundary, code execution in the Agent can read the Tool Server's environment or start a Tool Server without verification. In that configuration this mechanism still addresses T1, T3 and T4, where the Agent's code is intact but its decisions are not.¶
+---------+ (1) issue(method,name,args) +----------------+
| Agent | -----------------------------> | Call Authority |
| (no | <----------------------------- | policy, keys, |
| secrets)| (2) Call Proof | replay cache, |
+---------+ | audit log |
| +----------------+
| (3) invocation + Call Proof ^ |
v | |
+-------------+ (4) verify(action_digest, proof) | |
| Tool Server | -----------------------------------+ |
| + enforce- | <---------------------------------------+
| ment hook | (5) valid / invalid(reason)
+-------------+
| (6) execute only if valid
v
local resources (files, shell, local services)
The Agent asks the Call Authority to issue a proof for an intended invocation.¶
The Call Authority identifies the calling process from the platform, evaluates Policy and, if allowed, returns a Call Proof. The proof never passes through the Call Authority again on the way to the Tool Server.¶
The Agent sends the invocation to the Tool Server with the Call Proof attached.¶
The Tool Server computes the Action Digest from the invocation as received and asks the Call Authority to verify the proof against it.¶
The Call Authority checks binding, freshness and single use, records the decision, and answers.¶
The Tool Server executes the invocation only if the answer is valid.¶
Verification is delegated to the Call Authority so that the Tool Server needs no key material and no knowledge of evidence formats. This allows symmetric and asymmetric evidence types to coexist and keeps replay tracking and audit in one place.¶
The Action Digest identifies exactly one invocation. It is computed as:¶
action_digest = BASE64URL( SHA-256( JCS( {
"method": <invocation method>,
"name": <tool name>,
"arguments": <arguments object, or {} if absent>
} ) ) )
¶
where:¶
The arguments MUST be taken exactly as transmitted, as a JSON [RFC8259] value. Implementations MUST NOT normalize argument values (for example by resolving file system paths) before computing the digest. Semantic normalization belongs to policy evaluation, not to the digest.¶
The same construction is used by proposals in the MCP community for argument commitments ([MCP-SEP-2787], [MCP-SEP-2672]); aligning on one definition allows evidence produced under those proposals to serve as Evidence Types under this document.¶
A Tool Server that requires Call Proofs MUST, for each covered invocation and before any side effect:¶
compute the Action Digest from the invocation as received;¶
reject the invocation if no Call Proof is present;¶
otherwise call verify and reject the invocation unless the result is valid; and¶
reject the invocation if the Call Authority cannot be reached (fail closed).¶
A Tool Server MAY operate in an audit mode in which it verifies proofs that are present and executes invocations without a proof, to support staged deployment. Audit mode does not provide the protections described in Section 3.¶
For tools that operate on file system paths, Tool Servers SHOULD resolve and re-check paths at execution time where tool semantics allow, to reduce time-of-check to time-of-use risk.¶
Policy MAY mark actions as requiring human approval. For such actions, the Call Authority MUST NOT issue a Call Proof until an approver designated by Policy has approved the specific Action Digest. Evidence type profiles define the approval channel. Profiles SHOULD present a human-readable summary of the action to the approver and SHOULD bind the approval to the Action Digest. Approval channels that do not require the Call Authority to accept inbound network connections are RECOMMENDED.¶
An evidence type profile MUST specify:¶
the Evidence Type identifier, using a namespaced form under a domain controlled by the profile author (for example com.example/token);¶
the format of the proof value;¶
how the proof commits to the Action Digest;¶
the validity window, which SHOULD be 30 seconds or less;¶
how keys are provisioned to and protected by the Call Authority; and¶
how single use is enforced.¶
Profiles SHOULD keep proof values compact. Local channels such as stdio carry one message per line, and per-call evidence such as certificate chains adds overhead to every invocation.¶
Anticipated profiles include (informative):¶
a JWS envelope issued by the Call Authority, aligned with [MCP-SEP-2787];¶
a passkey approval for approval-bound actions, aligned with [MCP-SEP-2672]; and¶
a compact one-time authentication code derived inside a hardware root of trust, in the lineage of HOTP [RFC4226] and TOTP [RFC6238], to be specified separately.¶
An MCP server that supports this mechanism advertises the extension io.modelcontextprotocol/call-proof in its capabilities:¶
{ "capabilities": { "tools": {},
"extensions": { "io.modelcontextprotocol/call-proof": {
"required": true,
"methods": ["tools/call"],
"authority": "unix:///run/mcp-call-authority.sock" } } } }
¶
required set to true selects enforcement as described in Section 7; false selects audit mode. methods lists covered request methods; tools/call MUST be included. authority optionally names the Call Authority endpoint.¶
The extension identifier is shown with the MCP official prefix for illustration. Until the extension is accepted by the MCP project, implementations SHOULD use an identifier under their own vendor prefix.¶
The Call Proof is carried in the request _meta object:¶
{ "jsonrpc": "2.0", "id": 7, "method": "tools/call",
"params": { "name": "read_file",
"arguments": { "path": "repo/src/main.ts" },
"_meta": { "io.modelcontextprotocol/callProof": {
"type": "com.example/token",
"value": "<opaque>" } } } }
¶
For MCP, the Action Digest method is the JSON-RPC method, the name is params.name, and the arguments are params.arguments.¶
A rejected invocation returns a JSON-RPC error whose data.reason is missing, authorityUnavailable, or a reason returned by the Call Authority:¶
{ "jsonrpc": "2.0", "id": 7,
"error": { "code": -32021, "message": "Call proof rejected",
"data": { "reason": "missing" } } }
¶
The numeric error code is a placeholder pending coordination with the MCP project. Verification MAY be implemented as a server-side validator in the MCP interceptor model [MCP-SEP-1763].¶
AIMS [I-D.ietf-wimse-aims] addresses agent identity, credential provisioning, authentication and delegation across network boundaries. This document addresses the local invocation boundary that AIMS does not cover, and reuses workload identity for caller identification at the Call Authority.¶
DPoP [RFC9449] and HTTP Message Signatures [RFC9421] bind proofs to HTTP requests. Local inter-process channels have no HTTP request to bind to, and DPoP does not cover the request content. The Action Digest plays the role of the bound request representation.¶
Proposals in the MCP community define argument-bound attestation for audit [MCP-SEP-2787] and per-call human approval [MCP-SEP-2672]. This document adds the enforcement obligation on the tool server and the requirement that issuing keys reside outside the agent process, and treats those formats as candidate evidence types.¶
The unit of protection is a single tool invocation. Agents decompose a user request into separate invocations, and each one is authorized and verified independently, so a request that combines permitted and forbidden steps is stopped at the forbidden step. Most tool servers expose one operation per tool (for example, separate tools to read, write or send), which lets Policy decide by tool name and arguments. General-purpose tools, such as shell execution, arbitrary database queries or code execution, and workflow tools that perform several effects in one invocation, cannot be separated this way. Policy for such tools needs to evaluate their arguments, and deployments should treat them as high risk, subject them to approval (Section 8), or not grant them to roles that do not need them.¶
When a later invocation in a sequence is denied, earlier invocations have already run. Data they returned remains available to the Agent, although the denied invocation cannot carry it further. This document does not provide authorization of a multi-step plan as a whole.¶
The protections of this mechanism depend on the isolation assumption in Section 3.3. Deployments that cannot separate the Agent from the Tool Server and Call Authority obtain protection against injected instructions and proof reuse, but not against extraction of Tool Server credentials by code running in the Agent process.¶
The Call Authority is a high-value component. Its compromise is equivalent to Policy compromise. Hardware-protected keys, signed Policy with rollback protection, and fail-closed behavior limit the impact of partial failures but not of full compromise.¶
JCS removes representation differences (member order, whitespace, number and string encoding) but not semantic equivalence. Two semantically equal argument sets can produce different digests; Policy must be written against arguments as transmitted or must evaluate semantic forms explicitly.¶
Short validity windows and single-use enforcement limit replay. Clock skew between the Call Authority's issue and verify operations is not a concern because both run in the same component.¶
Fail-closed behavior makes the Call Authority a dependency for every covered invocation. Its availability should be monitored like any other enforcement component.¶
Approval channels can be targeted by social engineering. Summaries shown to approvers should be generated by the Call Authority from the invocation, not supplied by the Agent.¶
The Call Authority records caller identity, tool names, Action Digests and approver identities. The audit log can reveal user activity and should be protected and retained according to applicable policy. Action Digests do not reveal argument values directly, but low-entropy arguments can be recovered by guessing; logs should be protected accordingly.¶
This document has no IANA actions. Evidence Types use namespaced identifiers under domains controlled by profile authors.¶
A code-review agent is permitted by Policy to read files under repo/ and to post review comments. Content in a pull request instructs it to read ~/.aws/credentials.¶
The Agent requests issue for read_file with path ~/.aws/credentials.¶
The Call Authority identifies the caller as the code-review agent, evaluates Policy, denies, and records the attempt.¶
If the Agent sends the invocation anyway, the Tool Server finds no Call Proof and rejects it.¶
If the Agent replays a proof issued earlier for repo/README.md, the Tool Server computes a different Action Digest and the Call Authority returns mismatch.¶
This section records the status of known implementations per [RFC7942] and is to be removed before publication.¶
A reference implementation consisting of a Call Authority daemon, MCP server-side enforcement, client-side issuance and two evidence type profiles is in development. Repository location: TBD.¶
Whether the Call Authority interface belongs in this document or a companion document.¶
Coverage of additional MCP methods such as resources/read and prompts/get.¶
Error code coordination with the MCP project.¶
Alignment of the Action Digest definition with MCP community proposals.¶
Whether an IANA registry for Evidence Types is warranted.¶
Plan-level authorization: evaluating a declared sequence of invocations before the first one runs, and its relation to intent declaration proposals in the OAuth working group.¶
Guidance for tools that combine several effects in one invocation.¶
TBD.¶