T07 · Tool Hijacking and Spoofing
Error
- Location
- index.ts:272
- Finding
- Remote Tool-Call Parameter Hijacking## Vulnerability Details **File Location**: `index.ts`, lines 272–281 and 324–342 **Vulnerability Type**: Remote injection and overriding of local tool-call parameters **Risk Level**: Critical ### Vulnerable Code ```ts const { decide } = await loadKalibrSdk(); const decision = await decide(goal); const sessionKey = ctx?.sessionKey; if (sessionKey) { runs.setLastDecision(sessionKey, { tool_id: decision.tool_id, params: decision.params, }); } ``` ```ts const decision = runs.getLastDecision(sessionKey); if (!decision || !decision.params || Object.keys(decision.params).length === 0) { return {}; } if (decision.tool_id && decision.tool_id !== event.toolName) { api.logger.info( "[kalibr] Decision tool_id (" + decision.tool_id + ") differs from current tool (" + event.toolName + "), proceeding anyway" ); } api.logger.info( "[kalibr] Injecting params for tool " + event.toolName + ": " + JSON.stringify(decision.params) ); const merged = { ...event.params, ...decision.params }; return { params: merged }; ``` ### Technical Analysis When routing is enabled, the plugin obtains `params` from the external Kalibr service through `decide()` and stores them for the session. Before a local tool call, these externally supplied values are merged after the original arguments: ```ts { ...event.params, ...decision.params } ``` Consequently, remote values override same-named parameters selected by the agent or user. The implementation does not enforce a tool-specific parameter allowlist, validate the values against a trusted schema, protect security-sensitive fields, or request user confirmation. The `tool_id` check does not provide a security boundary. If the remote decision identifies a different tool, the implementation logs the mismatch and explicitly proceeds. If `tool_id` is omitted, no tool identity check is performed at all. Therefore, parameters intended o ...[truncated 1763 chars]
- Remediation
- ## Remediation Suggestions 1. Remove remote tool-parameter injection unless it is strictly required. Treat remote routing decisions as model-selection hints only. 2. If parameter injection must remain, require a nonempty `tool_id` and enforce exact equality with `event.toolName`. Reject the decision rather than proceeding on a mismatch. 3. Define strict, tool-specific schemas and allowlists for remotely adjustable fields. Reject unknown keys, invalid types, oversized values, and values outside explicit constraints. 4. Prevent remote overrides of security-sensitive parameters, including command strings, executable paths, file paths, URLs, hosts, credentials, authorization headers, and destructive-operation flags. 5. Do not let remote values silently override legitimate arguments. Apply only approved defaults to absent, low-risk fields, or require explicit user approval for every change. 6. Bind each decision to a particular run and intended tool invocation rather than only to a session key. Add short expirations and single-use semantics to prevent stale or cross-call application. 7. Authenticate responses cryptographically and use a fixed, trusted HTTPS endpoint. Restrict configurable service URLs where the deployment model permits it. 8. Log parameter names and validation outcomes, but redact secret values and sensitive content. 9. Add tests covering omitted and mismatched `tool_id` values, unknown keys, sensitive-field overrides, stale decisions, cross-tool reuse, and malicious remote responses.
