Skip to main content

Boteraser | Website and Server Security Solutions

🛡️ GHSA-r7wm-3cxj-wff9 — jackson-core

🟠 CVSS 8.0 — High ✅ No Known Exploit CWE-770 OSV
8.0
CVSS Score
0 Low4 Medium7 High9 Critical10

Description

jackson-core: Async parser maxNumberLength bypass via chunked digit accumulation (incomplete fix for GHSA-72hv-8253-57qq)

Summary

The fix released in jackson-core 2.18.6 and 2.21.1 for [GHSA-72hv-8253-57qq](https://github.com/FasterXML/jackson-core/security/advisories/GHSA-72hv-8253-57qq) (Number Length Constraint Bypass in Async Parser, published 2026-02-28) is incomplete. The fix commit b0c428e6 (#1555) wired validateIntegerLength into a new _setIntLength helper and called it at every place where the integer portion of a number is *decided* (terminator byte arrived, . / e/E seen, end-of-feed inside a fully-buffered value). It did not call it on the much more attacker-relevant path: "ran out of input while still inside MINOR_NUMBER_INTEGER_DIGITS, return NOT_AVAILABLE to caller".

As a result, an attacker who streams JSON to a non-blocking parser in many small chunks, without ever sending a terminator byte, can keep the parser inside MINOR_NUMBER_INTEGER_DIGITS indefinitely. _textBuffer.expandCurrentSegment() grows on every chunk, and validateIntegerLength is never invoked. The accumulator is only gated by maxStringLength (20 MiB default) — a ~20,000x amplification of the documented maxNumberLength (1000 default).

This is the same vulnerability class, same advisory wording ("Memory Exhaustion: Unbounded allocation in TextBuffer from excessively long numbers"), same parser class — just the streaming path the original fix didn't cover. The fix to the *fraction* path is correct (see _finishFloatFraction at line 1834-1837 of NonBlockingUtf8JsonParserBase.java in 2.18.6, where _setFractLength(fractLen) IS called before the NOT_AVAILABLE return); the equivalent call is missing from every integer-digit path.

Affected versions

Verified on the patched releases:

  • com.fasterxml.jackson.core:jackson-core 2.18.6
  • com.fasterxml.jackson.core:jackson-core 2.21.1

Structurally identical code in tools.jackson.core 3.0.x / 3.1.x — same NonBlockingUtf8JsonParserBase class, same _setIntLength rollout, same NOT_AVAILABLE returns without validation. Not retested but presumed vulnerable.

Affected code

[src/main/java/com/fasterxml/jackson/core/json/async/NonBlockingUtf8JsonParserBase.java](https://github.com/FasterXML/jackson-core/blob/b0c428e6/src/main/java/com/fasterxml/jackson/core/json/async/NonBlockingUtf8JsonParserBase.java) in 2.18.6 / 2.21.1.

Site 1 — _startPositiveNumber(int ch) lines 1320-1330:

```java

if (outPtr >= outBuf.length) {

// NOTE: must expand to ensure contents all in a single buffer (to keep

// other parts of parsing simpler)

outBuf = _textBuffer.expandCurrentSegment();

}

outBuf[outPtr++] = (char) ch;

if (++_inputPtr >= _inputEnd) {

_minorState = MINOR_NUMBER_INTEGER_DIGITS;

_textBuffer.setCurrentLength(outPtr);

return _updateTokenToNA(); // <-- no validateIntegerLength(outPtr)

}

```

Site 2 — _finishNumberIntegralPart lines 1691-1727:

```java

protected JsonToken _finishNumberIntegralPart(char[] outBuf, int outPtr) throws IOException {

int negMod = _numberNegative ? -1 : 0;

while (true) {

if (_inputPtr >= _inputEnd) {

_minorState = MINOR_NUMBER_INTEGER_DIGITS;

_textBuffer.setCurrentLength(outPtr);

return _updateTokenToNA(); // <-- no validateIntegerLength(outPtr + negMod)

}

int ch = getByteFromBuffer(_inputPtr) & 0xFF;

if (ch < INT_0) {

if (ch == INT_PERIOD) {

_setIntLength(outPtr+negMod); // <-- validated here

++_inputPtr;

return _startFloat(outBuf, outPtr, ch);

}

break;

}

if (ch > INT_9) {

if ((ch | 0x20) == INT_e) {

_setIntLength(outPtr+negMod); // <-- validated here

++_inputPtr;

return _startFloat(outBuf, outPtr, ch);

}

break;

}

++_inputPtr;

if (outPtr >= outBuf.length) {

outBuf = _textBuffer.expandCurrentSegment();

}

outBuf[outPtr++] = (char) ch;

}

_setIntLength(outPtr+negMod); // <-- validated here

_textBuffer.setCurrentLength(outPtr);

return _valueComplete(JsonToken.VALUE_NUMBER_INT);

}

```

The pattern recurs at lines 1297, 1329, 1343, 1365, 1395, 1409, 1437, 1467, 1481, 1586, 1644, 1698 — every "ran out of input mid-integer" exit returns to the caller without validating the accumulator length.

Compare with the fraction path that is correct

_finishFloatFraction lines 1827-1838:

```java

while (loop) {

if (ch >= INT_0 && ch <= INT_9) {

++fractLen;

if (outPtr >= outBuf.length) {

outBuf = _textBuffer.expandCurrentSegment();

}

outBuf[outPtr++] = (char) ch;

if (_inputPtr >= _inputEnd) {

_textBuffer.setCurrentLength(outPtr);

_setFractLength(fractLen);

How this vulnerability can be exploited

This issue can be reached over the network, attack complexity is low, an attacker needs no privileges on the target. No user interaction is required. Rated impact: confidentiality none, integrity none, availability high.

Weakness class

GHSA-r7wm-3cxj-wff9 is classified as CWE-770: Allocation of Resources Without Limits. Resources are allocated on request with no cap, so a client can exhaust them.

Affected software

GHSA-r7wm-3cxj-wff9 is recorded against 2 packages.

  • com.fasterxml.jackson.core:jackson-core (from 2.19.0 up to 2.21.4)
  • tools.jackson.core:jackson-core (from 3.0.0 up to 3.1.4)

Timeline and source

Published on 21 July 2026 and last revised on 5 August 2026. No public exploit is currently recorded for this entry. Record sourced from OSV.

References

github.com (Web)
github.com (Web)
github.com (Web)
github.com (Web)
github.com (Web)
github.com (Package)

Details

Severity HIGH
CVSS Score 8.0
CVSS Vector CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
CWE CWE-770
Public Exploit ✅ No
Source OSV
Published 2026-07-21
Updated 2026-08-20
Modified 2026-08-05
Fix URL N/A

Affected Packages

Software From version Fixed in
com.fasterxml.jackson.core:jackson-core 2.19.0 2.21.4
tools.jackson.core:jackson-core 3.0.0 3.1.4

Site Security Check

Is jackson-core part of your stack?

GHSA-r7wm-3cxj-wff9 is rated CVSS 8.0 High. BotEraser scans your installation against known CVE records and tells you whether this vulnerability applies to the versions you actually run.

Scan My Site Free →

No credit card required  ·  Results in minutes

ⓘ Data Notice: The information presented above has been compiled from publicly available internet sources. Boteraser aggregates this data solely for informational purposes and does not independently classify, evaluate, or endorse any findings about the vulnerabilities listed. The accuracy and completeness of this information is the sole responsibility of the original publishers. Boteraser and its operators accept no liability for any decisions made based on this data.