Skip to content

CVE-2026-32978 — OpenClaw before 2026.3.11 contains an approval integrity vulnerability where system.run…

Key facts

CVE-2026-32978 is a High (8.0) vulnerability: OpenClaw before 2026.3.11 contains an approval integrity vulnerability where system.run…. This entry ships ready-to-deploy detection and prevention rules (Snort, YARA, Nginx, Apache, Sigma) plus a detection-only PoC and a Docker test lab.

CVE CVE-2026-32978
Severity High (8.0)
Detection / prevention Snort, YARA, Nginx, Apache, Sigma
PoC poc.py
Source 2026/CVE-2026-32978/

Details

CVE-2026-32978 is a High (8.0) vulnerability: OpenClaw before 2026.3.11 contains an approval integrity vulnerability where system.run…. This entry ships a detection-only proof-of-concept (PoC), a Docker test lab, and ready-to-deploy detection and prevention rules (Snort, YARA, Nginx, Apache) — see Detection and prevention below. Source: NVD record.

English | 한국어

Description

OpenClaw before 2026.3.11 contains an approval integrity vulnerability where system.run approvals fail to bind mutable file operands for certain script runners like tsx and jiti. Attackers can obtain approval for benign script commands, rewrite referenced scripts on disk, and execute modified code under the approved run context.

Vulnerability Details

Property Value
CVE ID CVE-2026-32978
CVSS Score 8.0

Proof of Concept

Download

# Download PoC script
curl -O https://raw.githubusercontent.com/fankh/vulnerability-poc/main/2026/CVE-2026-32978/poc.py

Usage

# Run PoC against target
python3 poc.py --target <TARGET_URL>

# With authentication
python3 poc.py --target <TARGET_URL> --username <USER> --password <PASS>

⚠️ Warning: This PoC is for authorized security testing only. It uses detection-only techniques and does not exploit or damage target systems.

Test Lab

This repository includes a Docker-based test environment with both vulnerable and patched applications.

Quick Start

# Clone and navigate to CVE directory
cd CVE-2026-32978

# Start both applications
docker-compose up -d

# Run tests
./run-tests.sh    # Linux/Mac
./run-tests.ps1   # Windows PowerShell

Application Endpoints

Application URL Status
Vulnerable App http://localhost:8080 Shows vulnerability
Patched App http://localhost:8081 Demonstrates fix

Directory Structure

├── README.md           # English documentation
├── README_KO.md        # Korean documentation
├── poc.py              # PoC detection script
├── docker-compose.yml  # Container orchestration
├── run-tests.sh        # Linux/Mac test runner
├── run-tests.ps1       # Windows test runner
├── vulnerable-app/     # Vulnerable version
│   ├── app.py
│   ├── Dockerfile
│   └── requirements.txt
└── patched-app/        # Fixed version
    ├── app.py
    ├── Dockerfile
    └── requirements.txt

References

  • https://github.com/openclaw/openclaw/security/advisories/GHSA-qc36-x95h-7j53
  • https://www.vulncheck.com/advisories/openclaw-approval-bypass-via-unrecognized-script-runners

Generated by PoC Generator on 2026-04-10T16:01:12.355938293

Detection and prevention

Ready-to-deploy defensive rules for CVE-2026-32978, for authorized testing and blue-team detection engineering:

References: NVD — CVE-2026-32978 · full write-up on the searchable site

Detection & prevention rules

alert tcp any any -> any any (msg:"CVE-2026-32978 OpenClaw approval integrity vulnerability - system.run detection"; flow:established,to_server; content:"system.run"; nocase; content:"tsx"; distance:0; within:200; classtype:attempted-admin; sid:1000000; rev:1; priority:1;)

alert tcp any any -> any any (msg:"CVE-2026-32978 OpenClaw approval integrity vulnerability - jiti runner detection"; flow:established,to_server; content:"system.run"; nocase; content:"jiti"; distance:0; within:200; classtype:attempted-admin; sid:1000001; rev:1; priority:1;)

alert tcp any any -> any any (msg:"CVE-2026-32978 OpenClaw file operand manipulation attempt"; flow:established,to_server; content:"system.run"; nocase; pcre:"/system\.run.*(?:tsx|jiti).*\.(js|ts|mjs)$/i"; classtype:attempted-admin; sid:1000002; rev:1; priority:2;)

alert tcp any any -> any any (msg:"CVE-2026-32978 OpenClaw approval bypass pattern"; flow:established,to_server; content:"approval"; nocase; content:"system.run"; distance:0; within:100; pcre:"/approval.*system\.run.*(?:tsx|jiti)/i"; classtype:policy-violation; sid:1000003; rev:1; priority:2;)

alert tcp any any -> any any (msg:"CVE-2026-32978 OpenClaw mutable file operand exploitation"; flow:established,to_server; pcre:"/system\.run.*--.*(?:tsx|jiti).*\.(js|ts|jsx|tsx)$/i"; classtype:attempted-admin; sid:1000004; rev:1; priority:1;)

:material-file-download: prevention/snort.rules

rule OpenClaw_Approval_Integrity_CVE_2026_32978 {
    meta:
        cve = "CVE-2026-32978"
        author = "Security Engineer"
        description = "Detects OpenClaw approval integrity vulnerability exploitation attempts"
        date = "2024-01-01"
        severity = "high"

    strings:
        $openclaw_binary = "openclaw" nocase
        $system_run_cmd = "system.run" nocase
        $tsx_runner = "tsx" nocase
        $jiti_runner = "jiti" nocase

        $approval_pattern1 = /system\.run\s+[^\s]+\.(tsx|ts|js)/
        $approval_pattern2 = /--runner\s+(tsx|jiti)/

        $file_rewrite_indicators = {
            66 73 2e 77 72 69 74 65 46 69 6c 65 53 79 6e 63  // fs.writeFileSync
        }

        $script_modification = /require\(['"][^'"]*\.tsx?['"]\)/
        $dynamic_import = /import\(['"][^'"]*\.tsx?['"]\)/

        $suspicious_timing = {
            73 79 73 74 65 6d 2e 72 75 6e  // system.run
            [0-50]
            77 72 69 74 65 46 69 6c 65      // writeFile
        }

        $mutable_operand_bypass = /\$\{[^}]*\}/

    condition:
        (
            $openclaw_binary and 
            ($system_run_cmd and ($tsx_runner or $jiti_runner))
        ) or
        (
            ($approval_pattern1 or $approval_pattern2) and 
            ($file_rewrite_indicators or $script_modification or $dynamic_import)
        ) or
        (
            $suspicious_timing and $mutable_operand_bypass
        ) or
        (
            2 of ($approval_pattern*, $file_rewrite_indicators, $script_modification) 
        )
}

rule OpenClaw_Script_Race_Condition_CVE_2026_32978 {
    meta:
        cve = "CVE-2026-32978"
        author = "Security Engineer"
        description = "Detects script race condition exploitation in OpenClaw approval system"
        date = "2024-01-01"

    strings:
        $race_setup1 = "system.run" nocase
        $race_setup2 = /\.tsx?\s*&&/

        $file_ops_hex = {
            77 72 69 74 65 46 69 6c 65 53 79 6e 63  // writeFileSync
            [0-20]
            73 79 73 74 65 6d 2e 72 75 6e           // system.run
        }

        $temp_script_pattern = /\/tmp\/[a-zA-Z0-9]+\.tsx?/
        $approval_bypass = "approved_script" nocase

        $timing_attack = {
            73 6c 65 65 70  // sleep
            [0-10]
            77 72 69 74 65  // write
        }

    condition:
        ($race_setup1 and $race_setup2) or
        $file_ops_hex or
        ($temp_script_pattern and $approval_bypass) or
        $timing_attack
}

rule OpenClaw_Malicious_Script_Payload_CVE_2026_32978 {
    meta:
        cve = "CVE-2026-32978"
        author = "Security Engineer" 
        description = "Detects malicious payloads in OpenClaw script files"
        date = "2024-01-01"

    strings:
        $payload_marker1 = "// BENIGN_APPROVED" nocase
        $payload_marker2 = "/* SAFE_SCRIPT */" nocase

        $malicious_content = /eval\s*\(\s*['"]/
        $shell_exec = /exec\s*\(\s*['"`]/
        $file_inclusion = /require\s*\(\s*process\.argv/

        $obfuscation1 = /String\.fromCharCode\s*\(/
        $obfuscation2 = /atob\s*\(/
        $obfuscation3 = /Buffer\.from\s*\([^,]+,\s*['"]base64['"]/

        $persistence = /setInterval\s*\(/
        $network_call = /fetch\s*\(\s*['"`]https?:/

        $env_manipulation = /process\.env\[['"]/

    condition:
        (
            ($payload_marker1 or $payload_marker2) and
            ($malicious_content or $shell_exec or $file_inclusion)
        ) or
        (
            2 of ($obfuscation*) and
            ($persistence or $network_call or $env_manipulation)
        ) or
        (
            $malicious_content and $env_manipulation
        )
}

:material-file-download: prevention/yara.yar

# Block OpenClaw vulnerable script execution patterns
location ~* \.(tsx?|js|mjs|cjs)$ {
    # Block requests targeting OpenClaw script runners
    if ($request_uri ~* "system\.run|approval|operand") {
        return 403;
    }

    # Block suspicious file modification patterns
    if ($args ~* "(tsx|jiti|runner|script|execute|modify|rewrite)") {
        return 403;
    }
}

# Protect against approval bypass attempts
location ~* /api/(approval|system|run) {
    # Block requests with suspicious file operation parameters
    if ($request_body ~* "(mutable|operand|bind|file|script|tsx|jiti)") {
        return 403;
    }

    # Block potential approval manipulation
    if ($args ~* "(approval.*script|system\.run.*file|operand.*modify)") {
        return 403;
    }

    # Add security headers
    add_header X-Content-Type-Options nosniff;
    add_header X-Frame-Options DENY;
}

# Block direct access to OpenClaw system functions
location ~* /(system|approval)/(run|execute) {
    # Deny access to vulnerable endpoints
    if ($request_method ~* "POST|PUT|PATCH") {
        return 403;
    }

    # Block script runner parameters
    if ($request_body ~* "(tsx|jiti|runner|file.*operand)") {
        return 403;
    }
}

# Prevent malicious script file modifications
location ~* \.(config|json|yaml|yml)$ {
    # Block requests targeting script configuration
    if ($request_body ~* "(system\.run|approval|script.*runner)") {
        return 403;
    }

    # Block file binding manipulation
    if ($args ~* "(operand|bind.*file|mutable.*script)") {
        return 403;
    }
}

# General OpenClaw vulnerability protection
location / {
    # Block approval integrity bypass patterns
    if ($request_uri ~* "approval.*rewrite|system\.run.*modify") {
        return 403;
    }

    # Block script execution manipulation
    if ($http_user_agent ~* "(openclaw|script.*runner|approval.*bypass)") {
        return 403;
    }

    # Add general security headers
    add_header X-XSS-Protection "1; mode=block";
    add_header Strict-Transport-Security "max-age=31536000; includeSubDomains";
    add_header Referrer-Policy "strict-origin-when-cross-origin";
}

:material-file-download: prevention/nginx.conf

# ModSecurity rules for CVE-2026-32978 - OpenClaw approval integrity vulnerability
# Protects against script manipulation attacks targeting system.run approvals

# Rule 1000000: Block requests containing OpenClaw system.run patterns with suspicious file operations
SecRule REQUEST_BODY "@rx (?i)system\.run.*(?:tsx|jiti).*(?:write|modify|rewrite|overwrite)" \
    "id:1000000,\
    phase:2,\
    block,\
    severity:'HIGH',\
    msg:'CVE-2026-32978: OpenClaw system.run approval integrity attack detected',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

# Rule 1000001: Detect approval bypass attempts with script runner combinations
SecRule ARGS "@rx (?i)(?:approval|approve).*system\.run.*(?:tsx|jiti)" \
    "id:1000001,\
    phase:2,\
    block,\
    severity:'HIGH',\
    msg:'CVE-2026-32978: OpenClaw approval system manipulation attempt',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

# Rule 1000002: Block requests with file rewrite operations targeting approved scripts
SecRule REQUEST_BODY "@rx (?i)(?:rewrite|overwrite|modify).*(?:\.ts|\.js|\.tsx|\.jsx).*(?:approved|approval)" \
    "id:1000002,\
    phase:2,\
    block,\
    severity:'MEDIUM',\
    msg:'CVE-2026-32978: File rewrite operation on approved script detected',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

# Rule 1000003: Detect suspicious script runner invocations with mutable file operands
SecRule ARGS "@rx (?i)(?:tsx|jiti).*(?:--write|--modify|--overwrite|fs\.write|fs\.writeFile)" \
    "id:1000003,\
    phase:2,\
    block,\
    severity:'HIGH',\
    msg:'CVE-2026-32978: Script runner with mutable file operand detected',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

# Rule 1000004: Block approval context manipulation patterns
SecRule REQUEST_BODY "@rx (?i)(?:approval.*context|context.*approval).*(?:execute|run|exec)" \
    "id:1000004,\
    phase:2,\
    block,\
    severity:'MEDIUM',\
    msg:'CVE-2026-32978: Approval context manipulation attempt',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

# Rule 1000005: Detect OpenClaw version patterns indicating vulnerable versions
SecRule REQUEST_HEADERS:User-Agent "@rx (?i)openclaw.*(?:202[0-5]|2026\.[0-2]|2026\.3\.(?:[0-9]|10))" \
    "id:1000005,\
    phase:1,\
    warn,\
    severity:'INFO',\
    msg:'CVE-2026-32978: Potentially vulnerable OpenClaw version detected',\
    logdata:'Matched Data: %{MATCHED_VAR} found within %{MATCHED_VAR_NAME}',\
    tag:'application-multi',\
    tag:'language-multi',\
    tag:'platform-multi',\
    tag:'attack-injection',\
    tag:'CVE-2026-32978'"

:material-file-download: prevention/httpd.conf

Frequently asked questions

What is CVE-2026-32978?

CVE-2026-32978 is a High (8.0) vulnerability: OpenClaw before 2026.3.11 contains an approval integrity vulnerability where system.run…. This entry ships ready-to-deploy detection and prevention rules (Snort, YARA, Nginx, Apache, Sigma) plus a detection-only PoC and a Docker test lab.

How do I detect CVE-2026-32978?

Deploy the Snort and YARA detection rule included with this entry (see Detection & prevention rules below), then validate it against the detection-only PoC in the Docker test lab.

How do I block or mitigate CVE-2026-32978?

Apply the Nginx and Apache mitigation config included with this entry, and upgrade to a fixed version per the vendor advisory (see the NVD record for affected versions).


For authorized security testing and research only. See the full source and NVD record.