Back to skill

Security audit

Checkmate

Security checks for vulnerabilities and agentic risk

Overview

This skill is openly designed as a powerful automated task loop, but it grants spawned agents broad tool, file, network, OAuth, messaging, and background execution authority with limited containment.

Install only if you are comfortable giving this skill the same practical reach as your OpenClaw agent, including shell, web, installed skills, connected accounts, outbound notifications, and long-running background work. Prefer explicit 'checkmate:' invocations, avoid --no-interactive for sensitive tasks, use a private workspace directory rather than /tmp, and do not paste secrets or untrusted third-party text into checkpoint replies.

Vulnerability Patterns
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
Findings (2)

T05 · Unauthorized Access and Privilege Escalation

Error
Location
prompts/worker.md:23
Finding
Untrusted task content is executed by agents with unrestricted host and OAuth-backed capabilities<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md:25-38`, `prompts/worker.md:23-28`, `scripts/run.py:50-63` **Vulnerability Type**: Violation of least privilege and unsafe delegation of privileged agent capabilities **Risk Level**: High ### Vulnerable Code `SKILL.md:25-38`: ```markdown ## Security & Privilege Model > ⚠️ **This is a high-privilege skill.** Read before using in batch/automated mode. **Spawned workers and judges inherit full host-agent runtime**, including: - `exec` (arbitrary shell commands) - `web_search`, `web_fetch` - All installed skills (including those with OAuth-bound credentials — Gmail, Drive, etc.) - `sessions_spawn` (workers can spawn further sub-agents) This means **the task description you provide directly controls what the worker does** — treat it like code you're about to run, not a message you're about to send. **Batch mode (`--no-interactive`) removes all human gates.** In interactive mode (default), you approve criteria and each checkpoint before the loop continues. In batch mode, criteria are auto-approved and the loop runs to completion autonomously — only use this for tasks and environments you fully trust. ``` `prompts/worker.md:23-28`: ```markdown ## Instructions 1. **Read the criteria before starting.** Internalize what PASS looks like. 2. **If there is judge feedback**, your first priority is to fix the specific gaps identified. Address each gap explicitly. 3. **Do the work.** Use whatever tools you need — exec, web_search, web_fetch, browser, etc. You have access to the full agent runtime. 4. **Write your output** to: `{{OUTPUT_PATH}}` ``` `scripts/run.py:50-63`: ```python def call_agent(prompt: str, session_id: str, timeout_s: int = 3600, max_retries: int = 5, base_backoff: int = 60) -> str: """ Spawn an agent session via the OpenClaw gateway (openclaw agent CLI). Each session gets the full agent runtime: all tools, all skills, OAuth auth. No direct Anthropic API c ...[truncated 3375 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Run workers in an isolated sandbox with a dedicated filesystem root and no access to the host user's home directory by default. 2. Introduce an explicit per-run capability allowlist. Disable `exec`, network access, OAuth-backed skills, and agent spawning unless the task demonstrably requires each capability. 3. Require a separate, informed approval before adding any privileged capability. Approval of task criteria should not implicitly approve shell or connected-account access. 4. Disable autonomous batch mode for privileged runs, or require a signed policy that identifies the exact permitted tools, paths, domains, and integrations. 5. Treat task descriptions, judge output, and checkpoint replies as untrusted data. Delimit them clearly and add higher-priority instructions prohibiting them from changing tool policy. 6. Restrict filesystem operations to the run workspace and enforce outbound network allowlists. 7. Use short-lived, task-scoped OAuth tokens rather than inheriting all authenticated integrations. 8. Produce an auditable record of each privileged tool invocation and require confirmation for destructive operations or external data transmission. 9. Prevent workers from spawning sub-agents unless explicitly required, and ensure any permitted sub-agent receives no broader capabilities than its parent. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/workspace.sh:14
Finding
Predictable temporary workspace permits local data disclosure and file manipulation<![CDATA[ ## Vulnerability Details **File Location**: `scripts/workspace.sh:14-29` **Vulnerability Type**: Predictable temporary directory with non-exclusive creation and no explicit restrictive permissions **Risk Level**: Medium ### Vulnerable Code `scripts/workspace.sh:14-29`: ```bash BASE_DIR="${1:-/tmp}" TASK="${2:-}" TIMESTAMP=$(date +%Y%m%d-%H%M%S) WORKSPACE="${BASE_DIR}/checkmate-${TIMESTAMP}" mkdir -p "${WORKSPACE}" # Write initial state cat > "${WORKSPACE}/state.json" <<EOF {"iteration": 0, "status": "running", "createdAt": "$(date -u +%Y-%m-%dT%H:%M:%SZ)"} EOF # Write task if provided if [ -n "${TASK}" ]; then echo "${TASK}" > "${WORKSPACE}/task.md" fi ``` The script subsequently creates another workspace file at `scripts/workspace.sh:31`: ```bash touch "${WORKSPACE}/feedback.md" ``` ### Technical Analysis The default base directory is `/tmp`, while the workspace name contains only a timestamp with one-second precision. A local attacker can predict the path and create it before the victim. Because `mkdir -p` accepts an existing directory, the script does not detect this condition or verify ownership. The script also does not set a restrictive `umask` or explicitly apply mode `0700` to the workspace and mode `0600` to its files. Resulting access therefore depends on the caller's environment. Under a common `022` umask, the directory and files can be readable by other local users. Redirections and `touch` follow symbolic links. If an attacker can pre-create the predictable workspace and place links such as `task.md`, `state.json`, or `feedback.md` inside it, the script may overwrite attacker-selected files that are writable by the victim. Later Python operations also trust files in the supplied workspace, increasing the possibility of checkpoint or prompt-content manipulation. The workspace can contain task descriptions, criteria, user checkpoint replies, generated deliverables, judge feedback, and final results. These contents may be sens ...[truncated 1768 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Replace timestamp-only directory creation with exclusive secure creation: ```bash umask 077 mkdir -p -- "$BASE_DIR" WORKSPACE="$(mktemp -d "${BASE_DIR%/}/checkmate-XXXXXXXX")" ``` 2. Reject base directories that are symbolic links or are not owned by the invoking user. 3. Verify that the newly created workspace is owned by the current user and has mode `0700`. 4. Create sensitive files with mode `0600`. 5. Do not use `mkdir -p` for the final workspace component. Creation must fail if that path already exists. 6. Use atomic file writes: create a temporary file in the secured workspace with exclusive creation, flush it, and atomically rename it into place. 7. Before reading, writing, unlinking, or touching workspace files, reject symbolic links and verify that resolved paths remain beneath the secured workspace. 8. In `run.py`, validate the ownership and permissions of a user-supplied `--workspace` before trusting cached criteria, output, state, feedback, or checkpoint files. 9. Prefer a private runtime directory, such as a user-owned directory beneath `$XDG_RUNTIME_DIR`, over a shared `/tmp` location. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Rogue AgentSelf-Modification, Session Persistence
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
Findings (20)

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding
The description frames the skill as a quality-enforcement loop, but the body also instructs the agent to discover session IDs, inject messages into live sessions, and send messages to external recipients. This mismatch is dangerous because reviewers or users may invoke the skill expecting harmless orchestration while it actually enables privileged communication and control flows that can leak data or manipulate active sessions.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding
The description frames the skill as a quality-enforcement loop, but the body also instructs the agent to discover session IDs, inject messages into live sessions, and send messages to external recipients. This mismatch is dangerous because reviewers or users may invoke the skill expecting harmless orchestration while it actually enables privileged communication and control flows that can leak data or manipulate active sessions.

Ssd 3

High
Confidence
95% confidence
Finding
This instruction tells the agent to capture the user's next reply verbatim and persist it before any other action, effectively turning ordinary conversation into data exfiltration into workspace storage. In a skill that repeatedly loops through tasks with agent/tool access, this increases the chance that credentials, personal data, or unrelated chat content will be stored and later consumed by workers or judges without clear boundaries.

Ssd 3

High
Confidence
94% confidence
Finding
The relay mechanism instructs the live agent session to forward future user responses into workspace storage as a side effect of ongoing conversation. That is dangerous because it blurs the boundary between normal chat and persisted workflow input, enabling accidental capture of sensitive data and potentially allowing later prompt/tool chains to act on untrusted user content from disk.

Ssd 3

High
Confidence
93% confidence
Finding
The fallback direct message embeds an instruction that any reply should be recorded verbatim into a file, so even outside the injected agent path the design still collects and persists conversational responses without robust scoping. This expands the attack surface because any channel reply may become durable workspace input and influence later autonomous processing.

Vague Triggers

Medium
Confidence
96% confidence
Finding
The trigger list includes generic phrases such as 'until it passes', 'keep iterating until done', and 'quality loop', which are broad enough to appear in normal conversation unrelated to this skill. Because this skill launches a high-privilege orchestration loop with worker access to exec, network, OAuth-bound tools, and sub-agents, accidental activation could cause unintended autonomous actions or long-running background jobs.

Session Persistence

Medium
Category
Rogue Agent
Content
Run in background for long tasks:

```bash
nohup python3 <skill-path>/scripts/run.py \
  --workspace "$WORKSPACE" \
  --task "Your task description" \
  --max-iter 20 \
Confidence
65% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Vague Triggers

Medium
Confidence
91% confidence
Finding
The invocation section says the skill is triggered when the user says 'checkmate: <task>' or 'until it passes', but it does not define clear boundaries for non-activation or require an explicit opt-in beyond those phrases. In a high-privilege skill that can background a Python orchestrator and delegate full-runtime capabilities to sub-agents, ambiguous activation rules increase the risk of unintended execution from ordinary user phrasing.

Lp3

Medium
Category
MCP Least Privilege
Confidence
94% confidence
Finding
The skill performs sensitive actions—shell execution, file reads/writes, session discovery, agent spawning, and outbound messaging—yet does not declare a restrictive tool scope. That gap weakens policy enforcement and makes it easier for the skill to run with broader capabilities than a reviewer or platform guardrail would expect, especially given its explicit `privileges: high` model and inherited worker privileges.

Autonomous Decision Making

Medium
Category
Excessive Agency
Content
This means **the task description you provide directly controls what the worker does** — treat it like code you're about to run, not a message you're about to send.

**Batch mode (`--no-interactive`) removes all human gates.** In interactive mode (default), you approve criteria and each checkpoint before the loop continues. In batch mode, criteria are auto-approved and the loop runs to completion autonomously — only use this for tasks and environments you fully trust.

**User-input bridging writes arbitrary content to disk.** When you reply to a checkpoint, the main agent writes your reply verbatim to `user-input.md` in the workspace. The orchestrator reads it and acts on it. Don't relay untrusted third-party content as checkpoint replies.
Confidence
95% confidence
Finding
Autonomous operation is a real security concern here because `--no-interactive` removes human gates while spawned workers retain full host-agent runtime, including shell, web access, all skills, OAuth-bound resources, and sub-agent spawning. Combined with the warning that task text directly controls worker behavior, this creates a powerful unattended execution path that can amplify prompt injection, data exfiltration, or destructive actions.

Vague Triggers

Medium
Confidence
98% confidence
Finding
Broad trigger phrases like 'don't stop until done' and 'keep going until done' are likely to match ordinary conversation and can unintentionally activate a high-privilege autonomous workflow. In this skill's context, accidental activation is especially risky because workers inherit exec, web, all installed skills, OAuth-backed access, and can continue in batch-like loops.

Description-Behavior Mismatch

Medium
Confidence
93% confidence
Finding
The worker prompt explicitly authorizes use of arbitrary tools ('exec, web_search, web_fetch, browser, etc.') even though the skill’s stated purpose is a completion/judging loop, not broad environment interaction. This expands the attack surface unnecessarily: a user task or embedded prompt content could induce command execution, network access, or other side effects unrelated to producing the deliverable.

Context-Inappropriate Capability

Medium
Confidence
96% confidence
Finding
Granting 'full agent runtime' access including exec and web/network tools gives the worker the ability to perform powerful actions based solely on task text and prior feedback. In a looping skill that repeatedly retries until criteria pass, this can amplify prompt injection or unsafe tasking into repeated command execution, data exfiltration, or external interaction without sufficient justification or guardrails.

Missing User Warnings

Medium
Confidence
88% confidence
Finding
The prompt instructs the worker to write directly to '{{OUTPUT_PATH}}' and potentially create multiple files, but provides no disclosure, confirmation, or constraints on what may be written. In an autonomous loop, this can enable unintended file modification or artifact creation driven by adversarial task content, especially if paths or manifest contents are influenced by untrusted input.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
]
    for attempt in range(1, max_retries + 1):
        try:
            result = subprocess.run(cmd, capture_output=True, text=True, timeout=timeout_s + 30)
            if result.returncode != 0:
                err = result.stderr + result.stdout
                if any(e in err for e in RETRYABLE_ERRORS):
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
"--message", message,
    ]
    try:
        result = subprocess.run(cmd, capture_output=True, text=True, timeout=30)
        if result.returncode == 0:
            log(f"📨 delivered to {recipient} via {channel}")
        else:
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
"--timeout", str(timeout_s),
    ]
    try:
        result = subprocess.run(cmd, capture_output=True, text=True, timeout=timeout_s + 10)
        if result.returncode == 0:
            log(f"⏸  checkpoint injected into agent session (UUID={session_uuid[:8]}…)")
            return True
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Autonomous Decision Making

Medium
Category
Excessive Agency
Content
if not _criteria_approved:
        log(
            f"WARNING: intake: reached max iterations ({max_intake_iter}) without approval — "
            f"proceeding with best-effort criteria"
        )
        if recipient:
Confidence
81% confidence
Finding
Proceeding after failing to obtain criteria approval weakens the intended human-control gate and allows the system to continue autonomously on potentially ambiguous or incorrect success criteria. In this skill context, which explicitly enforces completion and loops until pass/fail, bypassing approval can cause unwanted actions, misleading outputs, or persistence/notification side effects based on an unvalidated goal.

Autonomous Decision Making

Medium
Category
Excessive Agency
Content
notify(
                recipient,
                (
                    f"⚠️ checkmate: goal intake hit max iterations ({max_intake_iter}) without approval.\n"
                    f"Proceeding with best-effort goal statement — results may be less reliable.\n"
                    f"Workspace: {workspace}"
                ),
Confidence
75% confidence
Finding
Skill enables autonomous high-impact decisions without human-in-the-loop verification. Critical operations (destructive commands, financial transactions, data deletion) should require explicit user confirmation.

Missing User Warnings

Low
Confidence
84% confidence
Finding
The orchestrator instructs that the user's next reply be written verbatim to a workspace file, creating silent persistence of potentially sensitive user content. Because the write is triggered by conversational replies and not by an explicit file-upload or consent workflow, users may disclose secrets or personal data that then remain on disk and may be reused by later iterations or other tooling.

Static analysis

No suspicious patterns detected.