Repository navigation
Renovate: Update module github.com/distribution/distribution/v3 to v3.1.2 [SECURITY] - #76
Open
renovate[bot] wants to merge 1 commit into
Conversation
Contributor
Author
ℹ️ Artifact update noticeFile name: go.modIn order to perform the update(s) described in the table above, Renovate ran the
Details:
|
renovate
Bot
force-pushed
the
renovate/go-github.com-distribution-distribution-v3-vulnerability
branch
from
October 20, 2026 15:56
e29ee79 to
2a31e7e
Compare
renovate
Bot
force-pushed
the
renovate/go-github.com-distribution-distribution-v3-vulnerability
branch
from
October 23, 2026 18:27
2a31e7e to
697f7d8
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR contains the following updates:
v3.1.1→v3.1.2Distribution: Client
manifests.Get()does not verify returned content against requested digestCVE-2026-85747 / GHSA-685w-q87j-wqw3
More information
Details
Summary
registry/client.(*manifests).Get(ctx, dgst, …)fetches a manifest by digest but never hashes the returned body and compares it against the requested digest. A malicious or compromised registry, or any MITM on the registry connection, can serve arbitrary manifest bytes in response to a digest-pinned request and the client returns the substituted content transparently to the caller. Any application relying on digest pinning for supply-chain integrity — image policy controllers, mirrors, pull-through caches — is silently undermined. The bundled pull-through proxy (registry/proxy/proxymanifeststore.go) is itself an unguarded consumer and is directly exploitable.Details
Root cause:
registry/client/repository.go:488-505reads the response body and passes it directly todistribution.UnmarshalManifestwithout ever computingdigest.FromBytes(body)and comparing against the caller-supplieddgst. TheDocker-Content-Digestresponse header is parsed (lines 251-292 indescriptorFromResponse) only to populate an out-parameter (ReturnContentDigest) and is itself server-supplied — it is never recomputed from the body, so a lying server can set it to whatever value the caller requested while delivering different bytes.Attack path: An attacker who controls the registry endpoint (malicious registry, compromised upstream, DNS hijack, or TLS MITM) responds to
GET /v2/{name}/manifests/{digest}with:Docker-Content-Digest: <requested-digest>(forged header)The client calls
distribution.UnmarshalManifeston the substituted body, returns the attacker's manifest as if it were the pinned content, and the caller has no way to detect the substitution.Why it matters: The entire value of digest pinning is to guarantee content-addressable integrity against exactly this threat model (hostile or MITM server). The
registry/proxy/proxymanifeststore.go:42-87pull-through cache callsremoteManifests.Get(ctx, dgst)and immediately writes the result to local storage with no re-verification — so a poisoned remote can permanently inject a bad manifest into the mirror cache, affecting all subsequent consumers.Relevant code path (
repository.go, simplified):PoC
go.mod:
main.go:
Output (v2.8.3+incompatible):
Impact
Any application that calls
registry/client.(*manifests).Get()with a digest argument — and relies on that digest to guarantee which image content it receives — is affected. This includes image policy controllers that enforce allowed digests, pull-through cache/mirror implementations (including the bundledregistry/proxy), and any CI/CD tooling that pins images by digest for reproducibility or security.An attacker who controls or can MITM the registry endpoint can substitute arbitrary manifest content — changing image layers, entrypoints, or referenced blobs — and the client will accept and act on the substituted content without warning. The bundled pull-through proxy will cache and re-serve the poisoned manifest to all downstream clients.
Exploitation requires either control of the registry endpoint the victim is configured to use, or a MITM/TLS-breaking position on that connection. No authentication is needed beyond whatever the registry normally requires.
Severity
CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:C/C:N/I:H/A:NReferences
This data is provided by the GitHub Advisory Database (CC-BY 4.0).
Distribution: Client
manifests.Get()does not verify returned content against requested digestBIT-distribution-2026-85747 / CVE-2026-85747 / GHSA-685w-q87j-wqw3
More information
Details
Summary
registry/client.(*manifests).Get(ctx, dgst, …)fetches a manifest by digest but never hashes the returned body and compares it against the requested digest. A malicious or compromised registry, or any MITM on the registry connection, can serve arbitrary manifest bytes in response to a digest-pinned request and the client returns the substituted content transparently to the caller. Any application relying on digest pinning for supply-chain integrity — image policy controllers, mirrors, pull-through caches — is silently undermined. The bundled pull-through proxy (registry/proxy/proxymanifeststore.go) is itself an unguarded consumer and is directly exploitable.Details
Root cause:
registry/client/repository.go:488-505reads the response body and passes it directly todistribution.UnmarshalManifestwithout ever computingdigest.FromBytes(body)and comparing against the caller-supplieddgst. TheDocker-Content-Digestresponse header is parsed (lines 251-292 indescriptorFromResponse) only to populate an out-parameter (ReturnContentDigest) and is itself server-supplied — it is never recomputed from the body, so a lying server can set it to whatever value the caller requested while delivering different bytes.Attack path: An attacker who controls the registry endpoint (malicious registry, compromised upstream, DNS hijack, or TLS MITM) responds to
GET /v2/{name}/manifests/{digest}with:Docker-Content-Digest: <requested-digest>(forged header)The client calls
distribution.UnmarshalManifeston the substituted body, returns the attacker's manifest as if it were the pinned content, and the caller has no way to detect the substitution.Why it matters: The entire value of digest pinning is to guarantee content-addressable integrity against exactly this threat model (hostile or MITM server). The
registry/proxy/proxymanifeststore.go:42-87pull-through cache callsremoteManifests.Get(ctx, dgst)and immediately writes the result to local storage with no re-verification — so a poisoned remote can permanently inject a bad manifest into the mirror cache, affecting all subsequent consumers.Relevant code path (
repository.go, simplified):PoC
go.mod:
main.go:
Output (v2.8.3+incompatible):
Impact
Any application that calls
registry/client.(*manifests).Get()with a digest argument — and relies on that digest to guarantee which image content it receives — is affected. This includes image policy controllers that enforce allowed digests, pull-through cache/mirror implementations (including the bundledregistry/proxy), and any CI/CD tooling that pins images by digest for reproducibility or security.An attacker who controls or can MITM the registry endpoint can substitute arbitrary manifest content — changing image layers, entrypoints, or referenced blobs — and the client will accept and act on the substituted content without warning. The bundled pull-through proxy will cache and re-serve the poisoned manifest to all downstream clients.
Exploitation requires either control of the registry endpoint the victim is configured to use, or a MITM/TLS-breaking position on that connection. No authentication is needed beyond whatever the registry normally requires.
Severity
CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:C/C:N/I:H/A:NReferences
This data is provided by OSV and the GitHub Advisory Database (CC-BY 4.0).
Release Notes
distribution/distribution (github.com/distribution/distribution/v3)
v3.1.2Compare Source
Welcome to the
v3.1.2release of registry!This is a stable release
This patch release includes security fixes, storage and pagination fixes, and dependency updates.
Please try out the release binaries and report any issues at
https://github.com/distribution/distribution/issues.
Notable Changes
Build Updates
See the changelog below for the full list of changes.
What's Changed
DeleteManifestwhenDeletereturnsErrDigestUnsupportedby @joonas in #4802New Contributors
Full Changelog: distribution/distribution@v3.1.1...v3.1.2
Configuration
📅 Schedule: (UTC)
🚦 Automerge: Disabled by config. Please merge this manually once you are satisfied.
♻ Rebasing: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.
🔕 Ignore: Close this PR and you won't be reminded about this update again.
This PR was generated by Mend Renovate. View the repository job log.