Safeguard
Vulnerability Analysis

CVE-2022-29148: Denial of service in .NET Kestrel HTTP stack

CVE-2022-21986 is a CVSS 7.5 denial-of-service flaw in .NET Kestrel's HTTP/2 and HTTP/3 handling. Here's what's affected and how to remediate it.

Vikram Iyer
Security Researcher
7 min read

In February 2022, Microsoft disclosed a denial-of-service vulnerability in the Kestrel web server shipped with .NET, tracked as CVE-2022-21986. The flaw affects how Kestrel processes certain HTTP/2 and HTTP/3 requests: a remote, unauthenticated attacker who sends specially crafted requests can drive the server into a degraded or unresponsive state, disrupting availability for every application hosted behind the affected Kestrel instance. Because Kestrel is the default HTTP server for ASP.NET Core and backs everything from internal APIs to internet-facing production services, the practical blast radius of an unpatched deployment is large — one crafted request stream can take down a process serving many tenants or endpoints at once.

(Note on identifiers: this analysis covers CVE-2022-21986, the ".NET Denial of Service Vulnerability" affecting Kestrel's HTTP/2 and HTTP/3 request handling. CVE-2022-29148 is a separate, unrelated Microsoft advisory — a Visual Studio 2017 remote code execution vulnerability in DDS file parsing — and is not a Kestrel or ASP.NET Core issue.)

What the vulnerability affects

Kestrel is the cross-platform web server built into ASP.NET Core, used either standalone or behind a reverse proxy like IIS, Nginx, or a cloud load balancer. CVE-2022-21986 lives in Kestrel's request-processing pipeline for HTTP/2 and HTTP/3, the newer protocol versions increasingly used for performance-sensitive services and gRPC workloads.

The affected components are:

  • .NET 5.0, versions 5.0.13 and earlier
  • .NET 6.0, versions 6.0.1 and earlier

Any ASP.NET Core application built on these runtimes and exposing Kestrel — directly to the internet or to an internal network — is in scope. This includes self-contained deployments, which bundle their own copy of the runtime and therefore do not benefit from host-level patching; those applications must be explicitly recompiled and redeployed against a fixed SDK.

Severity, exploit likelihood, and known exploitation

Microsoft rated CVE-2022-21986 with a CVSS v3.1 base score of 7.5 (High), reflecting a network attack vector, low attack complexity, no privileges required, and no user interaction — the profile typical of a remotely triggerable availability issue. The impact metric is availability-only (confidentiality and integrity are unaffected), consistent with a denial-of-service classification rather than data exposure or code execution.

Microsoft's own advisory is notably blunt on the mitigation question, stating that no mitigating factors had been identified for the vulnerability at the time of disclosure — meaning there was no configuration workaround, and patching was the only reliable remedy.

On exploitation signals: CVE-2022-21986 has not appeared in CISA's Known Exploited Vulnerabilities (KEV) catalog, and available EPSS scoring has stayed low, indicating no significant observed exploitation activity in the wild. That combination — high theoretical severity, low observed exploitation — is common for DoS bugs in server frameworks: they're easy to weaponize once understood, but attackers have historically found less noisy, higher-value bugs (RCE, auth bypass) more worth their time. That doesn't make the risk theoretical for defenders, though; a service outage triggered by a single crafted request is trivial to reproduce once the mechanism is public, and DoS bugs in widely-deployed frameworks tend to get folded into commodity scanning and stress-testing tools over time.

Timeline

  • February 8, 2022 — Microsoft published the security advisory for CVE-2022-21986 alongside patched .NET runtime and SDK builds, as part of the regular .NET security release cadence (this update shipped together with the .NET 6.0.2 / 5.0.14 servicing release).
  • Same release window — the .NET and ASP.NET Core teams published corresponding GitHub security advisories (tracked in the dotnet/aspnetcore and dotnet/announcements repositories) summarizing the affected versions and required updates for both hosted and self-contained deployments.
  • Ongoing — the CVE record has continued to receive administrative updates (affected-configuration metadata) from NVD well after initial publication, which is normal housekeeping and does not indicate new exploitation findings.

No public proof-of-concept exploit or confirmed in-the-wild attack tied specifically to CVE-2022-21986 has been widely reported since disclosure.

Remediation

The fix ships in the runtime and SDK, not as an application-level code change, which makes remediation straightforward but still requires an active update pass across every deployment target:

  1. Identify exposure. Inventory every service running .NET 5.0 (≤ 5.0.13) or .NET 6.0 (≤ 6.0.1) with Kestrel enabled, including internal services and background workers that happen to expose an HTTP endpoint. Run dotnet --info on hosts to confirm installed runtime versions.
  2. Update framework-dependent deployments. Install .NET 6.0 Runtime 6.0.2 / SDK 6.0.102, or .NET 5.0 Runtime 5.0.14 / SDK 5.0.114 (or SDK 5.0.405, depending on your Visual Studio channel). Framework-dependent apps pick up the fix automatically once the shared runtime on the host is patched — no rebuild required.
  3. Rebuild and redeploy self-contained applications. Self-contained and single-file deployments embed their own runtime copy, so patching the host has no effect. These must be recompiled against the updated SDK and redeployed; track them explicitly, since they're the deployments most likely to be silently missed.
  4. Rebuild container images. Any Docker or OCI image pinned to a vulnerable mcr.microsoft.com/dotnet/aspnet or dotnet/sdk base tag needs to be rebuilt from a patched base image and re-pushed through your pipeline — patching the base registry image alone doesn't help already-built, already-deployed containers.
  5. Verify. After patching, confirm the running process reports the updated framework version (via dotnet --info, deployment manifests, or runtime version telemetry) rather than trusting that a build step succeeded.
  6. Watch for regressions in HTTP/2 and HTTP/3 traffic. Kestrel patches touching protocol-level request handling occasionally interact with proxy or load balancer configurations; validate HTTP/2 and HTTP/3 (if enabled) behavior post-patch in a staging environment before wide rollout.

Because this is a runtime-level fix rather than a first-party application dependency, teams that treat "npm/NuGet audit is clean" as their patching signal will miss it entirely — the vulnerable component here is the .NET runtime and SDK itself, not a package reference in a .csproj or packages.lock.json file.

How Safeguard Helps

CVE-2022-21986 is a textbook example of the visibility gap that pure dependency scanning leaves open: the vulnerable component is the runtime installed on the build agent and baked into the container image, not a line in a manifest file. Safeguard is built to close exactly that gap across the software supply chain, not just the application dependency graph.

  • Runtime and toolchain inventory. Safeguard tracks the actual .NET SDK and runtime versions used across your build infrastructure and container base images — not just what's declared in project files — so a CVE like this one surfaces even when no NuGet package is implicated.
  • Container image provenance and drift detection. For teams shipping ASP.NET Core in containers, Safeguard flags images still built from vulnerable base layers and confirms when a rebuild has actually propagated the fix, rather than assuming a base-image bump was sufficient.
  • Self-contained deployment tracking. Because self-contained apps silently opt out of host-level patching, Safeguard's build and artifact analysis distinguishes framework-dependent from self-contained publishes so security teams can prioritize the deployments that actually require a rebuild.
  • CVSS, EPSS, and KEV context in one view. Safeguard correlates severity scoring, exploit-prediction signals, and CISA KEV status for every vulnerability affecting your build and runtime environment, so teams can separate "patch now" from "patch on the normal cadence" without manually cross-referencing four different feeds.
  • SBOM-backed audit trail. Every remediation — the SDK bump, the rebuilt image, the redeployed self-contained binary — is captured in Safeguard's SBOM and attestation history, giving compliance and audit teams (SOC 2, customer security reviews) a verifiable record that the fix actually shipped, not just that a ticket was closed.

Denial-of-service issues in foundational infrastructure like Kestrel rarely make headlines the way remote code execution does, but they're exactly the class of vulnerability that slips through dependency-only tooling. Safeguard is designed to catch what lives beneath the application layer — the runtimes, build tools, and base images your services actually run on — so a fix like the one for CVE-2022-21986 doesn't depend on someone remembering to check dotnet --info across every host.

Never miss an update

Weekly insights on software supply chain security, delivered to your inbox.