Back to Blog
critical SEVERITY6 min read

How Denial of Service via Malformed JSON Input happens in Go and how to fix it

A Denial of Service vulnerability (CVE-2026-32285) was discovered in the `github.com/buger/jsonparser` dependency used by this Go application, where crafted malformed JSON input could cause the parser to crash or hang, potentially taking down any service that processes untrusted JSON. The fix upgrades the dependency from v1.1.1 to v1.1.2 in `go.mod` and `go.sum`, closing the attack vector without changing any valid-input behavior. This is a practical reminder that transitive dependencies carry r

O
By Orbis AppSec
Published August 26, 2026Reviewed August 26, 2026

Answer Summary

CVE-2026-32285 is a Denial of Service vulnerability (CWE-400: Uncontrolled Resource Consumption) in the Go library `github.com/buger/jsonparser` v1.1.1, where specially crafted malformed JSON input can cause the parser to crash or consume excessive resources, disrupting any Go service that processes untrusted JSON. The fix is a one-line upgrade in `go.mod` from `github.com/buger/jsonparser v1.1.1` to `v1.1.2`, accompanied by updated checksums in `go.sum`. Developers should audit all indirect Go dependencies for known CVEs using tools like `govulncheck` or Trivy, since vulnerable transitive dependencies are just as dangerous as vulnerable first-party code.

Vulnerability at a Glance

cweCWE-400
fixUpgrade github.com/buger/jsonparser from v1.1.1 to v1.1.2 in go.mod and go.sum
riskAn attacker supplying malformed JSON to any endpoint that uses buger/jsonparser can crash or hang the service
languageGo
root causebuger/jsonparser v1.1.1 does not safely handle certain malformed JSON byte sequences, leading to uncontrolled resource consumption or panic
vulnerabilityDenial of Service via Malformed JSON Input

Introduction

The go.mod file in any Go project is deceptively simple — a list of module names and version pins. But each line is a trust decision. When the Trivy scanner flagged github.com/buger/jsonparser v1.1.1 in this project's dependency tree, it revealed that a single indirect dependency version pin was exposing every JSON-parsing code path to a potential Denial of Service attack.

This post walks through exactly what CVE-2026-32285 is, how the vulnerable version of buger/jsonparser could be exploited against a running Go service, and what the one-line go.mod change actually does to close the door.


The Vulnerability Explained

What is buger/jsonparser and why is it here?

github.com/buger/jsonparser is a high-performance, zero-allocation JSON parsing library for Go. It is widely used as a transitive dependency — meaning your code may not call it directly, but another library in your dependency graph does. In this project it appears as an // indirect dependency:

// go.mod (before fix)
github.com/buger/jsonparser v1.1.1 // indirect

The // indirect comment is Go's way of saying: "We don't import this ourselves, but something we depend on does." That does not mean the vulnerability is unreachable — it means the attack surface is wherever the parent dependency passes untrusted data through jsonparser.

CVE-2026-32285: Denial of Service via Malformed JSON

In buger/jsonparser v1.1.1, certain sequences of malformed or truncated JSON bytes are not handled defensively. When the parser encounters these sequences, it can:

  • Panic — causing the Go runtime to crash the goroutine (or the whole process if not recovered)
  • Loop or stall — consuming CPU in an uncontrolled way (CWE-400: Uncontrolled Resource Consumption)

The root cause is insufficient bounds-checking and error-path handling inside the library's byte-level parsing routines when input does not conform to expected JSON structure.

A Concrete Attack Scenario

Consider a Go service that accepts JSON payloads over HTTP — a REST API endpoint, a webhook receiver, or a message queue consumer. Internally, one of its dependencies uses buger/jsonparser to extract fields from those payloads.

An attacker sends a crafted HTTP request body:

POST /api/ingest HTTP/1.1
Content-Type: application/json

{"key": "\x00\xff\xfe

This truncated, byte-mangled payload is valid enough to pass a naive Content-Type check but malformed enough to trigger the vulnerable code path inside buger/jsonparser v1.1.1. The result: the parsing goroutine panics or stalls. With enough concurrent requests, the service becomes unavailable — a classic application-layer DoS.

Because buger/jsonparser is an indirect dependency, developers often don't realize their service is exposed until a scanner like Trivy surfaces it.


The Fix

The fix is surgical and low-risk: bump github.com/buger/jsonparser from v1.1.1 to v1.1.2 in both go.mod and go.sum.

go.mod Change

- github.com/buger/jsonparser v1.1.1 // indirect
+ github.com/buger/jsonparser v1.1.2 // indirect

v1.1.2 patches the malformed-input handling so that the parser returns a proper error instead of panicking or looping. Valid JSON inputs are completely unaffected — the change only tightens behavior on the invalid-input path.

go.sum Change

+ github.com/buger/jsonparser v1.1.2 h1:frqHqw7otoVbk5M8LlE/L7HTnIq2v9RX6EJ48i9AxJk=
+ github.com/buger/jsonparser v1.1.2/go.mod h1:6RYKKt7H4d4+iWqouImQ9R2FZql3VbhNgx27UK13J/0=

The go.sum file stores cryptographic hashes (SHA-256) of every module version that enters the build. Adding the v1.1.2 hashes here is mandatory: Go's module system will refuse to use a version whose hash is not recorded in go.sum, preventing supply-chain tampering. The old v1.1.1 entries remain in go.sum for historical auditability but are no longer selected by the build.

Why Two Files?

File Role What Changed
go.mod Declares the minimum required version Version pin updated from v1.1.1v1.1.2
go.sum Cryptographic integrity ledger Hash entries for v1.1.2 appended

Both changes are required. Updating only go.mod without go.sum would cause go build to fail with a checksum mismatch error.


Prevention & Best Practices

1. Run govulncheck in CI

Go's official vulnerability checker scans your module graph against the Go Vulnerability Database:

go install golang.org/x/vuln/cmd/govulncheck@latest
govulncheck ./...

Unlike Trivy, govulncheck performs call-graph analysis and can distinguish between a vulnerable symbol that is actually reachable versus one that is pulled in but never called.

2. Add Trivy or Snyk to Your Pipeline

# Example GitHub Actions step
- name: Scan dependencies
  uses: aquasecurity/trivy-action@master
  with:
    scan-type: 'fs'
    scan-ref: '.'
    exit-code: '1'
    severity: 'HIGH,CRITICAL'

This catches CVEs in go.mod before they reach production.

3. Set go.mod Minimum Version Constraints Deliberately

When you pin an indirect dependency, prefer the latest patched minor version rather than the version your dependency manager first resolves to:

go get github.com/buger/jsonparser@v1.1.2
go mod tidy

4. Size-Limit and Pre-Validate Incoming JSON

Even with a patched library, defense in depth matters. Reject payloads that exceed a reasonable size before they reach any parser:

http.MaxBytesReader(w, r.Body, 1<<20) // 1 MB limit

5. Relevant Standards

  • CWE-400: Uncontrolled Resource Consumption — https://cwe.mitre.org/data/definitions/400.html
  • CWE-20: Improper Input Validation — https://cwe.mitre.org/data/definitions/20.html
  • OWASP: Denial of Service Cheat Sheet — https://cheatsheetseries.owasp.org/cheatsheets/Denial_of_Service_Cheat_Sheet.html

Key Takeaways

  • Indirect Go dependencies carry real CVE risk. The // indirect label in go.mod does not mean "safe to ignore" — it means your attack surface includes code you didn't write and may not have reviewed.
  • go.sum is a security control, not just bookkeeping. The hash entries for v1.1.2 ensure the exact patched bytes are used at build time; never skip updating go.sum when changing go.mod.
  • Malformed JSON DoS is a realistic threat for any HTTP-facing Go service. If your service accepts JSON from untrusted clients, the parsing library version matters as much as your own input-validation logic.
  • govulncheck can tell you if the vulnerable symbol is actually reachable, saving triage time when you have many flagged indirect dependencies.
  • A one-line version bump in go.mod closed a critical availability gap — the cost of the fix was near zero; the cost of ignoring it could have been a production outage.

How Orbis AppSec Detected This

  • Source: Any HTTP endpoint or message consumer in the application that accepts untrusted JSON payloads and routes them through a dependency that calls buger/jsonparser.
  • Sink: The byte-parsing routines inside github.com/buger/jsonparser v1.1.1 that process raw JSON bytes without adequate bounds-checking on malformed input sequences.
  • Missing control: No version constraint in go.mod required the patched v1.1.2 release; the project was locked to the vulnerable v1.1.1.
  • CWE: CWE-400 — Uncontrolled Resource Consumption.
  • Fix: Updated go.mod to require github.com/buger/jsonparser v1.1.2 and added the corresponding cryptographic checksums to go.sum.

Orbis AppSec automatically detected this vulnerability and opened a pull request with the fix. Try Orbis AppSec on your repositories to find and fix issues like this automatically.


Conclusion

CVE-2026-32285 is a textbook example of why dependency hygiene is a security practice, not just a maintenance chore. The vulnerable code wasn't written by the application team — it lived two layers deep in the dependency graph — but it was fully capable of taking down the service. The fix required changing exactly one version string in go.mod and adding two lines to go.sum. That's a remarkably low cost for closing an availability risk that could have manifested as a production incident.

The broader lesson: treat every line in go.mod as a security decision. Automate scanning, enforce version floors in CI, and don't let // indirect lull you into a false sense of safety.


References

Frequently Asked Questions

What is a Denial of Service via malformed JSON input?

It is an attack where a client sends specially crafted, invalid JSON to a service. If the JSON parser does not handle malformed input safely, it may panic, loop indefinitely, or consume excessive CPU/memory, making the service unavailable to legitimate users.

How do you prevent JSON-based DoS in Go?

Keep JSON parsing libraries up to date, validate and size-limit incoming JSON before parsing, and use Go's `govulncheck` tool or a scanner like Trivy in CI to catch known CVEs in dependencies early.

What CWE is Denial of Service via malformed input?

CWE-400 (Uncontrolled Resource Consumption), sometimes also mapped to CWE-20 (Improper Input Validation) depending on the root mechanism.

Is input validation alone enough to prevent this vulnerability?

Not always. Even if your application-layer code validates inputs, a vulnerable parsing library may panic before your validation logic runs. Keeping the library patched is the most reliable control.

Can static analysis detect this vulnerability?

Yes. Tools like Trivy, Snyk, and `govulncheck` scan your `go.mod` dependency tree against known CVE databases and flag vulnerable versions like buger/jsonparser v1.1.1 without requiring the vulnerable code path to be traced manually.

View the Security Fix

Check out the pull request that fixed this vulnerability

View PR #2

Related Articles

high

How Denial of Service via Unbounded Intermediate Arrays happens in JavaScript and how to fix it

CVE-2026-69152 is a high-severity Denial of Service vulnerability in the `brace-expansion` npm package (versions prior to 1.1.18/2.1.4/3.0.6/5.0.9) that allows attackers to crash a Node.js application by crafting glob patterns that generate unbounded intermediate arrays, effectively bypassing the earlier CVE-2026-14257 mitigation. The fix upgrades `brace-expansion` from 1.1.14 to 1.1.18 in `frontend/package-lock.json`, closing the bypass and restoring safe memory bounds during pattern expansion.

high

How Quadratic CPU Consumption happens in JavaScript YAML parsing and how to fix it

A high-severity denial-of-service vulnerability (GHSA-5p4m-2wfm-xmqj) was discovered in js-yaml affecting both the 3.x and 4.x branches, where parsing YAML documents containing `!!omap` tags triggers quadratic CPU consumption. The fix upgrades js-yaml from `^4.1.1` to `5.2.0` in the project's GitHub Actions workflow dependencies, closing the attack surface for any untrusted YAML input processed by CI/CD tooling.

critical

How Missing Rate Limiting happens in Express.js and how to fix it

Two public API endpoints in `server.js` — `/api/health` and `/api/contact` — were exposed without any rate limiting middleware, allowing attackers to exhaust server resources or spam an SMTP server with unlimited requests. The fix adds rate limiting to both endpoints, with stricter controls on the resource-intensive `/api/contact` route that triggers email sending operations. This change closes a directly exploitable denial-of-service vector in a production web service.

high

How Denial of Service via Specific Input Sequence happens in JavaScript (marked) and how to fix it

CVE-2026-41680 is a high-severity Denial of Service vulnerability in the marked Markdown parsing library, affecting versions prior to 18.0.2. By supplying a crafted input sequence to the parser, an attacker can cause the application to hang or exhaust resources, making the frontend unavailable. Upgrading marked from 18.0.0 to 18.0.2 in both `package.json` and `package-lock.json` closes the vulnerability without affecting valid Markdown rendering.

high

How Quadratic CPU Consumption happens in JavaScript YAML parsing and how to fix it

A high-severity denial-of-service vulnerability in js-yaml (GHSA-5p4m-2wfm-xmqj) caused quadratic CPU consumption when resolving `!!omap` YAML types in both the 3.x and 4.x branches. The fix upgrades js-yaml from 3.14.2 to 3.15.1 and from 4.1.1 to 4.3.1, eliminating the algorithmic complexity exploit while leaving all valid YAML inputs unaffected.

high

How Denial of Service via Unbounded Data Happens in JavaScript and how to fix it

CVE-2025-58754 is a high-severity Denial of Service vulnerability in the popular axios HTTP client library, caused by the absence of a data size check on incoming response or request payloads. An attacker who can influence the size of data processed by axios could exhaust server memory or CPU, bringing down dependent Node.js applications. The fix upgrades axios from version 1.8.4 to 1.18.0, closing the unbounded data processing path.