CVE-2026-47691 - Netty DNS bailiwick cache poisoning

Netty disclosed two related DNS resolver cache-poisoning issues in io.netty:netty-resolver-dns. CVE-2026-47691 covers insufficient bailiwick validation for NS records. CVE-2026-45674 covers missing bailiwick validation for CNAME records. Both can let DNS data from a server that is authoritative for one name be cached as if it were authoritative for a broader or different name.

This is not just a dependency bump. A reviewer-ready fix should also prove which applications actually use Netty’s asynchronous DNS resolver, align Netty modules through the same release train, restart long-lived JVMs that may hold resolver caches, and document whether DNS results feed outbound trust decisions such as webhook delivery, service discovery, proxy routing, SSRF allowlists, model-provider egress, OIDC endpoints, package registries, or internal admin APIs.

TLS hostname verification, mTLS, service identity, and strict egress policy can reduce impact, but they are not substitutes for the fixed resolver. Plain HTTP, misconfigured TLS, DNS-based authorization, and resolver-cache reuse can still turn poisoned DNS data into confidentiality or integrity loss.

When to use it

Use this recipe when a Java repository may resolve io.netty:netty-resolver-dns directly or through Reactor Netty, Spring Gateway/WebFlux, gRPC Netty, Vert.x, async HTTP clients, gateways, proxies, service discovery, or agent runtimes. It is most important when DNS results influence outbound trust decisions such as webhooks, tenant callbacks, OIDC/SAML discovery, package or model downloads, SSRF controls, egress allowlists, or internal API routing.

Use it to upgrade and align Netty, document resolver-cache restart actions, and audit DNS-sensitive trust boundaries without poisoning live DNS.

Inputs

  • Maven/Gradle manifests, version catalogs, BOMs, locks, shaded JAR configs, Dockerfiles, CI images, generated dependency reports, SBOMs, and release scripts that may pin Netty or a Netty-owning framework.
  • Resolved versions for netty-resolver-dns, netty-common, netty-buffer, netty-transport, netty-codec-dns, netty-resolver, framework BOMs, and shaded/vendored Netty copies.
  • Resolver selection evidence: DnsNameResolver, DnsAddressResolverGroup, Reactor Netty resolver(...), Spring Gateway, gRPC Netty, Vert.x, custom clients, service-discovery clients, sidecars, and agent runtime egress.
  • DNS-sensitive outbound path inventory, including callback/webhook targets, identity metadata, package/model registries, object stores, internal admin APIs, databases, and metadata-blocking logic.
  • Restart/cache-flush requirements for JVMs, gateways, workers, sidecars, and resolver groups that may hold stale DNS cache state.

Affected versions

  • Vulnerable package: io.netty:netty-resolver-dns <=4.1.134.Final
  • Vulnerable package: io.netty:netty-resolver-dns >=4.2.0.Final, <=4.2.14.Final
  • Fixed package: io.netty:netty-resolver-dns 4.1.135.Final+ or 4.2.15.Final+ on the selected Netty release line
  • Related CVEs: CVE-2026-47691 / GHSA-5pvg-856g-cp85 for NS records and CVE-2026-45674 / GHSA-676x-f7gg-47vc for CNAME records
  • Affected surface: applications using Netty’s DNS resolver, directly or through frameworks, clients, gateways, proxies, or service-discovery stacks

Indicator-of-exposure

  • The dependency graph resolves io.netty:netty-resolver-dns in an affected range, whether directly, through io.netty:netty-all, through a Netty BOM, or transitively through Reactor Netty, Spring WebFlux/Gateway, gRPC, Vert.x, async HTTP clients, custom proxies, service discovery, or agent runtimes.
  • Code configures DnsNameResolver, DnsNameResolverBuilder, DnsAddressResolverGroup, RoundRobinDnsAddressResolverGroup, NameResolverProvider, custom AddressResolverGroup wiring, or framework resolver hooks that select the Netty DNS resolver.
  • Long-lived JVMs, gateways, workers, agent runtimes, sidecars, or proxies reuse Netty resolver groups across many outbound requests.
  • Resolved hostnames influence security boundaries: tenant callback delivery, webhook targets, OAuth/OIDC issuer discovery, SAML metadata, package and model downloads, egress allowlists, SSRF controls, service mesh routing, internal admin endpoints, Redis/database hosts, or cloud metadata blocking.
  • Netty versions are not aligned, for example netty-resolver-dns is upgraded but netty-common, netty-buffer, netty-transport, or framework-managed Netty modules remain on an older release train.

Quick checks:

rg -n "netty-resolver-dns|netty-all|io.netty|DnsNameResolver|DnsAddressResolverGroup|RoundRobinDnsAddressResolverGroup|NameResolverProvider|AddressResolverGroup|reactor.netty|resolver\(" .
mvn -q dependency:tree -Dincludes=io.netty:netty-resolver-dns,io.netty:netty-all
./gradlew dependencies --configuration runtimeClasspath | rg "io.netty|netty-resolver-dns|netty-all"
rg -n "netty.version|netty-bom|reactor-netty|spring-cloud-gateway|grpc-netty|vertx|async-http-client" pom.xml build.gradle* gradle.lockfile *.versions.toml . 2>/dev/null

Windows:

rg -n "netty-resolver-dns|netty-all|io.netty|DnsNameResolver|DnsAddressResolverGroup|RoundRobinDnsAddressResolverGroup|NameResolverProvider|AddressResolverGroup|reactor.netty|resolver\(" .
mvn -q dependency:tree -Dincludes=io.netty:netty-resolver-dns,io.netty:netty-all
.\gradlew dependencies --configuration runtimeClasspath | rg "io.netty|netty-resolver-dns|netty-all"
rg -n "netty.version|netty-bom|reactor-netty|spring-cloud-gateway|grpc-netty|vertx|async-http-client" pom.xml build.gradle* gradle.lockfile *.versions.toml .

Do not validate exposure by running a malicious authoritative DNS server, poisoning a shared resolver cache, redirecting live traffic, disabling TLS, or probing production callback targets.

Remediation strategy

  • Upgrade every controlled Netty DNS resolver dependency to 4.1.135.Final+ or 4.2.15.Final+ on the existing Netty release line.
  • Prefer dependency management through io.netty:netty-bom or the owning framework BOM so all Netty modules resolve to one compatible fixed train.
  • Refresh lockfiles, generated dependency reports, SBOMs, container images, shaded JARs, framework platform files, deployment manifests, and operator docs that pin Netty or a Netty-owning framework.
  • Restart long-lived JVMs, gateways, workers, sidecars, and agent runtimes that may hold Netty DnsCache or AuthoritativeDnsServerCache state. Document any platform-managed cache flush or rolling restart requirement.
  • Audit outbound clients where DNS resolution is part of a trust decision. Do not rely on DNS alone for identity; keep TLS hostname verification enabled, require mTLS or signed service identity where available, and enforce egress policy after canonical hostname and resolved-address checks.
  • If upgrade is temporarily blocked, contain by disabling repository-owned Netty async DNS resolver usage where the framework supports a safe fallback, routing through a trusted recursive resolver, limiting outbound egress to expected IP ranges, and reducing DNS TTL/cache reuse. Treat this as temporary containment, not remediation.
  • Add safe regression or policy checks that prove fixed Netty versions, aligned Netty modules, no vulnerable shaded artifacts, documented restart/cache actions, and no DNS-only security decisions on sensitive outbound paths.

The prompt

You are remediating CVE-2026-47691 / GHSA-5pvg-856g-cp85 and
CVE-2026-45674 / GHSA-676x-f7gg-47vc, Netty DNS resolver cache-poisoning
issues caused by insufficient bailiwick validation for NS and CNAME records.
Produce exactly one output:

- A reviewer-ready PR/change request that upgrades and aligns every controlled
  Netty DNS resolver runtime, refreshes generated artifacts, restarts or flushes
  resolver-cache state, adds safe dependency and resolver-boundary checks, and
  documents DNS-sensitive outbound trust decisions, or
- TRIAGE.md if this repository does not control an affected Netty DNS resolver,
  runtime, framework dependency, shaded artifact, or deployment path.

## Rules

- Scope only CVE-2026-47691, CVE-2026-45674, and directly related Netty DNS
  resolver, bailiwick, dependency-alignment, resolver-cache, and outbound
  trust-boundary controls.
- Treat hostnames, resolved IPs, tenant callback URLs, webhook targets, OIDC
  and SAML metadata URLs, package and model registry URLs, proxy settings,
  service-discovery records, internal service names, credentials, headers, and
  network logs as sensitive.
- Do not run malicious authoritative DNS servers, poison shared resolver
  caches, redirect live traffic, downgrade TLS, disable hostname verification,
  capture production DNS traffic, or probe production callback targets.
- Do not remove SSRF controls, egress policy, TLS hostname verification,
  service identity, dependency locks, or resolver tests to silence the alert.
- Do not auto-merge.

## Steps

1. Inventory all Java dependency inputs controlled by the repository:
   `pom.xml`, `build.gradle`, Gradle version catalogs, Maven/Gradle locks,
   Netty BOMs, Spring/Reactor/Vert.x/gRPC platform BOMs, shaded JAR configs,
   Dockerfiles, generated dependency manifests, SBOMs, CI images, and release
   scripts.
2. Determine every resolved `io.netty:netty-resolver-dns` version. A target is
   vulnerable if it resolves to `<=4.1.134.Final` or to
   `>=4.2.0.Final, <=4.2.14.Final`.
3. Check Netty module alignment. Record whether `netty-common`,
   `netty-buffer`, `netty-transport`, `netty-codec-dns`,
   `netty-resolver`, `netty-resolver-dns`, framework BOMs, and shaded copies
   resolve to one fixed release train.
4. Search for actual Netty DNS resolver use:
   `DnsNameResolver`, `DnsNameResolverBuilder`, `DnsAddressResolverGroup`,
   `RoundRobinDnsAddressResolverGroup`, `NameResolverProvider`,
   `AddressResolverGroup`, Reactor Netty `resolver(...)`, Spring Gateway
   resolver config, gRPC Netty channels, Vert.x address resolver options,
   custom proxy clients, service-discovery clients, and agent runtime egress.
5. Identify DNS-sensitive outbound paths: webhooks, tenant callbacks, OAuth or
   OIDC issuer discovery, SAML metadata, package registries, model registries,
   object stores, Redis/database hosts, internal admin APIs, service-mesh
   routing, cloud metadata blocking, and SSRF or egress allowlists.
6. If Netty DNS resolver is absent, fixed, externally owned, or provably unused
   because the runtime uses only the JVM/OS resolver, stop with `TRIAGE.md`
   listing checked files, resolved versions, resolver selection evidence, and
   the owning team for external runtimes.
7. Upgrade on the current compatible train:
   - `4.1.x` deployments to `4.1.135.Final+`;
   - `4.2.x` deployments to `4.2.15.Final+`;
   - framework-managed deployments by upgrading the owning platform BOM or
     adding a narrow Netty override only when that is the repository's accepted
     dependency pattern.
8. Refresh all generated artifacts: Maven/Gradle locks, dependency reports,
   SBOMs, shaded artifacts, container images, deployment manifests, release
   notes, and operator docs.
9. Add safe policy checks:
   - dependency tree rejects vulnerable `netty-resolver-dns` ranges;
   - all Netty modules are version-aligned;
   - shaded or vendored Netty copies are fixed or absent;
   - sensitive outbound clients do not treat DNS alone as service identity;
   - restart or cache-flush steps are documented for long-lived JVMs.
10. Where the repository owns resolver code, forks, or wrappers, add mocked or
    in-memory tests that reject out-of-bailiwick NS and CNAME records without
    querying public DNS, running an authoritative test server, or touching
    shared resolver caches.
11. Harden DNS-sensitive outbound clients:
    - keep TLS hostname verification enabled;
    - use mTLS, signed service identity, or pinned trust roots where available;
    - validate callback and webhook hostnames before resolution and resolved
      addresses after resolution;
    - block private, loopback, link-local, multicast, metadata, and internal
      ranges unless explicitly intended;
    - avoid reusing poisoned resolver state across tenants or security domains.
12. Add a PR body section named `CVE-2026-47691 operator actions` that states:
    - Netty DNS resolver versions before and after;
    - whether CVE-2026-45674 is covered by the same fixed version;
    - which framework or BOM owns Netty version selection;
    - which Netty DNS resolver call sites or framework settings were found;
    - whether any shaded or vendored Netty copies exist;
    - which JVMs, gateways, workers, sidecars, or agent runtimes need restart
      or resolver-cache flush;
    - which DNS-sensitive outbound paths were reviewed;
    - whether temporary resolver or egress containment remains;
    - which validation commands passed.
13. Run available validation: Maven/Gradle dependency tree, lockfile integrity,
    unit and integration tests, safe resolver wrapper tests, framework config
    tests, container build, deployment rendering, SBOM refresh, and dependency
    or vulnerability scans.
14. Use PR title:
    `fix(sec): remediate Netty DNS bailiwick cache poisoning`.

## Stop conditions

- No affected Netty DNS resolver package, framework dependency, shaded artifact,
  resolver configuration, or deployment artifact is controlled by this
  repository.
- The affected runtime is owned by another platform team; name the owner and
  required fixed Netty release in `TRIAGE.md`.
- The repository cannot safely override Netty without a broader framework or
  platform migration.
- Validation would require DNS poisoning, live traffic redirection, production
  DNS capture, disabling TLS, printing secrets, or probing tenant callback
  targets.
- Validation fails for unrelated pre-existing reasons; document those failures
  instead of broadening scope.

Verification - what the reviewer looks for

  • No controlled dependency tree, lockfile, image, SBOM, shaded artifact, or generated dependency report resolves io.netty:netty-resolver-dns below 4.1.135.Final on the 4.1.x train or below 4.2.15.Final on the 4.2.x train.
  • Netty modules are aligned through the same fixed BOM or framework-managed platform. There is no split train where only netty-resolver-dns was bumped.
  • The PR identifies whether Netty’s DNS resolver is actually selected at runtime, directly or through Reactor Netty, Spring Gateway, gRPC, Vert.x, or custom client code.
  • Long-lived JVMs and gateways have restart or cache-flush operator actions so stale resolver state does not survive the upgrade.
  • DNS-sensitive outbound clients keep TLS hostname verification and egress policy intact, and they do not use DNS alone as the trust boundary.
  • Tests and validation do not poison live DNS, redirect traffic, disable TLS, or expose sensitive hostnames, tokens, headers, or tenant callback data.

Watch for

  • Bumping netty-resolver-dns directly while a framework BOM later downgrades it or other Netty modules remain vulnerable.
  • Shaded Netty copies in fat JARs, CLI tools, agent runtimes, plugins, or embedded gateway images that dependency scans miss.
  • Assuming “we use HTTPS” fully mitigates DNS poisoning while webhook delivery, OAuth discovery, package/model downloads, internal service calls, or SSRF allowlists still trust DNS results.
  • Updating build files but not refreshing lockfiles, generated manifests, SBOMs, images, or deployment docs.
  • Leaving JVM resolver caches, Netty resolver groups, sidecars, or gateway workers alive after deploying the fixed artifact.
  • Tests that require a real malicious authoritative DNS server or shared cache poisoning instead of safe mocked resolver records.

Output contract

Return one of:

  • A reviewer-ready PR/change request that upgrades netty-resolver-dns to 4.1.135.Final+ or 4.2.15.Final+, aligns all Netty modules, refreshes generated artifacts, documents resolver-cache restart/flush actions, adds safe dependency/resolver-boundary checks, and reviews DNS-sensitive outbound trust decisions.
  • TRIAGE.md when no controlled affected Netty DNS resolver, framework dependency, shaded artifact, resolver configuration, or deployment path exists.

The output must list versions before/after, owning BOM/framework, actual resolver usage, shaded/vendored copies, restart/cache actions, DNS-sensitive paths reviewed, temporary containment, and validation commands. It must not run malicious DNS servers, poison shared caches, redirect live traffic, disable TLS, capture production DNS logs, or expose sensitive hostnames, headers, tokens, or tenant callback data.

References