Skip to content

CVE-2026-32316: Verified Reproduction

CVE-2026-32316: jq: integer overflow in jv string concat triggers heap buffer overflow on large strings

CVE-2026-32316 is verified against jq · github. Affected versions: <= 1.8.1. Fixed in 1.8.2. Vulnerability class: Buffer Overflow. This high reproduction includes runnable sandbox proof, artifacts, and a plain-text agent view under REPRO-2026-00170.

REPRO-2026-00170 jq · github Buffer Overflow May 28, 2026 CVE entry .txt
Severity
HIGH
CVSS
8.2
Confidence
HIGH
Reproduced in
32m 33s
Tool calls
182
Spend
$1.56
01 · Overview

What Is CVE-2026-32316?

CVE-2026-32316 is a high-severity integer overflow in jq's jv_string_concat (used by the + string operator and by add over an array of strings) that leads to a heap buffer overflow when concatenated strings exceed 2^31 bytes. Pruva reproduced it (reproduction REPRO-2026-00170).

02 · Severity & CVSS

CVE-2026-32316 Severity & CVSS Score

CVE-2026-32316 is rated high severity, with a CVSS base score of 8.2 out of 10.

HIGH threat level
8.2 / 10 CVSS base
Weakness CWE-122

High — serious impact or readily exploitable. Prioritize remediation.

03 · Affected Versions

Affected jq Versions

jq · github versions <= 1.8.1 are affected.

How to Reproduce CVE-2026-32316

$ pruva-verify REPRO-2026-00170
or curl -O https://www.pruva.dev/api/v1/reproductions/REPRO-2026-00170/artifacts/bundle/repro/reproduction_steps.sh && chmod +x reproduction_steps.sh && ./reproduction_steps.sh
Run in a VM or disposable container. This exploits a real vulnerability.
06 · Proof of Reproduction

Proof of Reproduction for CVE-2026-32316

Reproduced
How the agent worked 678 events · 182 tool calls · 33 min
33 minDuration
182Tool calls
163Reasoning steps
678Events
4Dead-ends
Agent activity over 33 min
Support
18
Repro
288
Variant
368
0:0032:33

Root Cause and Exploit Chain for CVE-2026-32316

Versions: <= 1.8.1

CVE-2026-32316 is an integer overflow vulnerability in jq's string concatenation path (jvp_string_append in src/jv.c). When two strings whose combined length exceeds INT_MAX (2,147,483,647 bytes) are concatenated, the allocation size (currlen + len) * 2 overflows uint32_t and wraps to a tiny value. A subsequent memcpy then writes gigabytes of data into the undersized heap buffer, causing a heap-based buffer overflow (CWE-190 → CWE-122).

  • Package/component affected: jq (command-line JSON processor), specifically jv_string_concat / jvp_string_append in src/jv.c
  • Affected versions: <= 1.8.1
  • Risk level: High (CVSS 3.1: 7.5)
  • Consequences: Any service or pipeline that runs jq filters on attacker-controlled input can be crashed or have heap memory corrupted when the attacker supplies JSON strings that, when concatenated, exceed INT_MAX bytes. This is reachable in common patterns such as add over an array of large strings or direct + operations.

Root Cause

In src/jv.c, jvp_string_append computes the new allocation size using 32-bit unsigned arithmetic:

uint32_t allocsz = (currlen + len) * 2;

When currlen + len >= INT_MAX (≈ 2.1 GB), the product can exceed UINT32_MAX and wrap around to a very small number (as small as 0, which is then clamped to 32 bytes). The function then allocates this tiny buffer via jvp_string_alloc(allocsz) and copies the full concatenated length with memcpy, writing far past the allocated region.

The same overflow pattern existed in jvp_string_copy_replace_bad, where length * 3 + 1 could wrap uint32_t for very large inputs.

Fix commit: e47e56d226519635768e6aab2f38f0ab037c09e5 — adds explicit 64-bit overflow checks:

if ((uint64_t)currlen + len >= INT_MAX) {
    jv_free(string);
    return jv_invalid_with_msg(jv_string("String too long"));
}

Reproduction Steps

  1. Execute repro/reproduction_steps.sh
  2. The script clones the jq repository, builds two binaries with AddressSanitizer:
    • Vulnerable: tag jq-1.8.1
    • Fixed: commit e47e56d226519635768e6aab2f38f0ab037c09e5
  3. The script runs the trigger program on both binaries:
    "A" * 1073741824 as $a | $a + $a
    
    This creates a 1 GB string and concatenates it with another 1 GB string, producing a total length of 2 GB (> INT_MAX).
  4. Expected evidence:
    • Vulnerable build: AddressSanitizer reports heap-buffer-overflow in jvp_string_append (called from jv_string_concatbinop_plus)
    • Fixed build: jq exits gracefully with the error message String too long

Evidence

  • Vulnerable ASAN output: logs/vulnerable_stderr.txt

    ==7265==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x506000001311
    WRITE of size 1073741824 at 0x506000001311 thread T0
        #0 memcpy
        #1 jvp_string_append src/jv.c:1191
        #2 jv_string_concat src/jv.c:1501
        #3 binop_plus src/builtin.c:96
    

    The buffer allocated was only 49 bytes, confirming the integer-overflow-induced undersized allocation.

  • Fixed output: logs/fixed_stderr.txt

    jq: error (at <unknown>): String too long
    
  • Runtime manifest: repro/runtime_manifest.json

Recommendations / Next Steps

  1. Upgrade jq to 1.8.2 or later (or any build containing commit e47e56d). The fix is minimal and precisely targeted at the overflow conditions.
  2. Input size limits: For deployments that cannot immediately upgrade, enforce maximum JSON input sizes well below 2 GB to reduce the likelihood of triggering the overflow.
  3. Regression testing: Add automated tests that attempt string concatenation near INT_MAX boundaries to prevent re-introduction of this bug class.
  4. Audit other integer size calculations: Review other uses of uint32_t for buffer-size math in src/jv.c (e.g., jvp_string_copy_replace_bad) to ensure similar overflows are not present elsewhere.

Additional Notes

  • Idempotency confirmed: repro/reproduction_steps.sh was run twice consecutively; both runs produced identical ASAN crash output on the vulnerable build and identical graceful error output on the fixed build.
  • Edge cases / limitations: The reproduction requires a host with enough RAM to hold two ~1 GB strings plus ASAN overhead (≈ 3–4 GB peak). On memory-constrained systems, the trigger can be adjusted by reducing the multiplier, but the combined concatenated length must still exceed INT_MAX (2,147,483,647 bytes) to hit the vulnerable code path.

CVE-2026-32316 Reproduction Transcript

The agent's step-by-step process — every tool call, every handoff, the moment the exploit fired.

Full session Replay every step — scrub the timeline or play it back.

Event 1/40
0:000:48
0:00
session startedaccounts/fireworks/models/kimi-k2p6 · cve-2026-32316 · cve-2026
0:22
0:22
0:22
error

Unknown error

0:23
0:23
web search
0:23
error

Unknown error

0:35
0:35
extract_facts
no facts extracted
0:35
0:35
0:35
supportrepro
0:37
0:38
0:38
0:38
0:39
0:39
0:39
0:39
0:46
0:47
$git clone --depth=100 https://github.com/jqlang/jq.git external/jq && cd external/jq && git log --oneline --all | head -20
1.1s
{"cwd":"/root/.pruva/runs/cve-2026-32316_20260528-102301","duration_ms":1138,"exit_code":0,"stderr":"Cloning into 'external/jq'...\n","stdout":"df924ea Fix undefined pointer arithmetic in UTF-8 helpers\na829f67 Fix one-byte over-read in BASE64_DECODE_TABLE (#3547)\n7122866 Guard deep structural equality and comparison recursion (#3539)\nf58787c Detect circular module imports to prevent stack overflow\n9d223f1 Reject embedded NUL bytes in module import paths\n9761ceb Reject numeric literals longer than DEC_MAX_DIGITS (999999999)\n532ccea Limit recursive object merge depth to prevent stack overflow\n33d7bce Avoid stack overflow when freeing deeply nested values\n7316e5c Fix CI to add `artifact-metadata` permission for actions/attest (#3530)\n63751f8 Fix signed-int overflow in `tokenadd` to prevent buffer overflow\n5f2a14d docs: fix \"happened\" spelling in tutorial changelog entries (#3525)\n5a015de Fix NUL truncation in program files loaded with -f\n01b3cde Fix signed-int overflow in `stack_reallocate`\nd1a1256 Limit the containment check depth\n8702073 build(deps): bump lxml from 6.0.2 to 6.1.0 in /docs (#3526)\n1eaa31a build(deps): bump actions/upload-pages-artifact from 4 to 5 in… [truncated]
0:48
08 · How to Fix

How to Fix CVE-2026-32316

Upgrade jq · github to 1.8.2 or later.

Coming soon

Step-by-step mitigation and hardening guidance for CVE-2026-32316 — configuration checks, workarounds where no patch exists, and how to verify you're protected — is on the way.

10 · FAQ

FAQ: CVE-2026-32316

How does the jq string-concatenation heap overflow work?

A jq filter (e.g. add over an array of strings, or repeated + concatenation) is run over attacker-controlled JSON strings whose combined length exceeds roughly 2.1 GB. The 32-bit size computation in jvp_string_append wraps around to a tiny allocation, and the following memcpy writes gigabytes of data past the undersized heap buffer, corrupting adjacent heap memory (CWE-190 to CWE-122).

Which versions of jq are affected by CVE-2026-32316, and where is it fixed?

Versions <= 1.8.1 are affected. It is fixed in 1.8.2.

How severe is CVE-2026-32316?

High severity (CVSS 3.1: 7.5) -- any service or pipeline that runs jq filters over attacker-controlled input (CI pipelines, log shippers, observability stacks, k8s admission webhooks) can be crashed or have heap memory corrupted, given the attacker can supply roughly 2 GB of string content.

How can I reproduce CVE-2026-32316?

Download the verified script from this page and run it in an isolated environment against jq <= 1.8.1 with sufficient available memory. It concatenates JSON strings whose combined length exceeds INT_MAX bytes via add/+ and shows the resulting heap buffer overflow.
11 · References

References for CVE-2026-32316

Authoritative sources for CVE-2026-32316 — official vulnerability databases and the upstream advisory. Pruva's reproduction verifies the issue firsthand; these are the primary records to corroborate it.