Safeguard
Vulnerability Analysis

Python setuptools package_index ReDoS (CVE-2022-40897)

CVE-2022-40897 is a ReDoS flaw in setuptools' package_index.py that can hang CI pipelines when parsing crafted index pages. Here's how to detect and fix it.

Nayan Dey
Security Researcher
7 min read

A regular expression denial-of-service (ReDoS) flaw in Python's setuptools package — tracked as CVE-2022-40897 — allows an attacker who controls or can influence a package index, "find-links" page, or mirror to cause catastrophic CPU exhaustion on any machine that resolves dependencies against it. The bug lives in setuptools/package_index.py, the module responsible for scanning HTML pages returned by PyPI-style indexes to discover downloadable package links. A crafted HTML response — for example, one served by a compromised internal mirror, a malicious "typosquatted" index, or a man-in-the-middle proxy — can drive the module's comment-stripping regular expression into exponential backtracking, hanging the pip install, easy_install, or setup.py process indefinitely. Because setuptools is a near-universal dependency embedded in virtual environments, CI runners, and container base images, the practical blast radius is large even though the vulnerability itself has no direct code-execution or data-exfiltration impact.

This class of bug is easy to underestimate. It doesn't leak secrets or grant a shell, so it rarely gets the same attention as a deserialization or RCE finding. But for organizations running large fleets of build agents, ReDoS in a core packaging tool translates directly into stalled pipelines, exhausted compute budgets, and — if an attacker times it right — a denial-of-service against release engineering during a critical deployment window. It's also a useful case study in how "quiet" vulnerabilities accumulate risk in the software supply chain simply by being everywhere.

Affected Versions and Components

  • Component: setuptools, specifically the PackageIndex class in setuptools/package_index.py, which parses HTML from index and find-links URLs to locate package download links.
  • Affected versions: All setuptools releases prior to 65.5.1.
  • Fixed version: 65.5.1 and later, which replaced the vulnerable regex-based HTML comment stripping with a more resilient parsing approach.
  • Trigger path: Any workflow that causes setuptools to fetch and parse an HTML index page — including easy_install, direct use of PackageIndex, and certain pip install flows that fall back to legacy index scanning (e.g., --index-url/--find-links against non-standard or self-hosted indexes).

The exposure here is broader than a single package advisory suggests. setuptools is frequently vendored or auto-installed as a build dependency, meaning teams that never explicitly pin it can still be running a vulnerable copy baked into a base Docker image, a virtualenv/venv bootstrap, or an older pip release that bundles it internally. Organizations should not assume "we don't use easy_install" is sufficient to rule this out — SBOM-driven discovery is the only reliable way to confirm exposure across a large estate.

It's also worth noting that package_index.py has been a recurring source of security findings in the setuptools codebase. A separate, more severe remote code execution issue in the same module's URL-handling logic was later addressed as CVE-2024-6345 and patched in setuptools 70.0. Any remediation pass on CVE-2022-40897 is a good opportunity to verify the fix for that later issue is also in place, since both stem from the same historically under-hardened parsing code path.

CVSS, EPSS, and KEV Context

CVE-2022-40897 carries a CVSS v3.1 base score of 7.5 (High), reflecting a network-exploitable, low-complexity attack with no privileges or user interaction required, but with impact limited to availability (AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H). The "High" severity is driven entirely by ease of exploitation and the breadth of affected deployments, not by confidentiality or integrity impact — there is no data exposure or code execution associated with this specific CVE.

From a real-world exploitation standpoint, this vulnerability has not been observed in active, widespread attack campaigns, and it does not appear in CISA's Known Exploited Vulnerabilities (KEV) catalog as of this writing. EPSS scoring for CVE-2022-40897 has consistently sat in the low percentile range, consistent with a resource-exhaustion bug that requires an attacker to control or intercept index responses — a much higher bar than a typical remotely exploitable web vulnerability. That said, EPSS and KEV status are lagging, point-in-time signals; supply-chain-adjacent ReDoS bugs are exactly the kind of low-noise issue that can sit unpatched for years in CI infrastructure precisely because they never trip a "critical" alert, making them attractive for targeted disruption of a specific organization's build pipeline rather than opportunistic mass exploitation.

Timeline

  • Pre-2022: The vulnerable comment-stripping regex in package_index.py exists largely unchanged across many setuptools release cycles, unnoticed as a security issue.
  • 2022 (pre-disclosure): A security researcher identifies the catastrophic backtracking pattern in the HTML parsing logic used by PackageIndex and reports it privately to the setuptools/pypa maintainers via a GitHub Security Advisory.
  • November 2022: setuptools 65.5.1 is released, replacing the regex-based comment stripper with a safer implementation and closing the ReDoS path.
  • November 15–16, 2022: CVE-2022-40897 and the corresponding advisory (GHSA-cx63-2mw6-8hw5) are published publicly, along with remediation guidance for downstream consumers.
  • Following months: Linux distributions, container base image maintainers, and CI vendors begin shipping updated setuptools versions; security scanners and SBOM tools add detection rules for the vulnerable version range.
  • 2024: A related but distinct issue in the same module's download-URL handling is disclosed and tracked as CVE-2024-6345, patched in setuptools 70.0, reinforcing package_index.py as an area worth continued scrutiny.

Remediation Steps

  1. Upgrade setuptools to 65.5.1 or later — and ideally to the current release line, since later versions also carry the fix for CVE-2024-6345. Run pip show setuptools across your environments to confirm the installed version before assuming you're clear.
  2. Upgrade pip itself. Older pip releases vendor their own internal copy of setuptools; upgrading pip (pip install --upgrade pip) ensures the bundled copy is also patched, independent of what's declared in your project's dependency files.
  3. Pin and rebuild. Add an explicit setuptools>=65.5.1 (or your chosen safe floor) to constraints files, pyproject.toml build requirements, and Dockerfile base image update steps, then rebuild and redeploy affected images rather than relying on runtime pip install upgrades alone.
  4. Audit CI/CD base images and cached virtual environments. Base images built months or years ago frequently carry stale setuptools. Inventory build agents, Docker images, and any long-lived venvs or Lambda layers for the vulnerable range.
  5. Restrict and authenticate package sources. Avoid pointing --index-url or --find-links at untrusted or unauthenticated endpoints. Use TLS-verified internal mirrors and pull-through caches so an attacker cannot easily serve a crafted HTML page into your build process in the first place.
  6. Apply resource limits as a defense-in-depth measure. Where immediate upgrades aren't feasible across every runner, bound CPU/time for install steps (e.g., cgroup limits, per-job timeouts in CI) so a ReDoS trigger fails fast instead of stalling a pipeline indefinitely.
  7. Re-scan after remediation. Confirm the fix landed everywhere it needed to — including transitively vendored copies — rather than trusting a single requirements.txt update to have propagated.

How Safeguard Helps

Safeguard is built to catch exactly this kind of quietly-everywhere dependency risk before it becomes an incident. Our SBOM generation and ingest pipeline automatically inventories every setuptools instance across your repositories, containers, and build environments — including versions vendored inside pip or baked into base images — so you don't have to manually chase down where a vulnerable copy is hiding. Reachability analysis then determines whether your actual build and install workflows exercise the vulnerable PackageIndex HTML-parsing path (versus, say, only ever resolving from a fully trusted, pinned index), letting your team prioritize the environments where CVE-2022-40897 is genuinely exploitable over those where it's theoretical noise. Griffin AI, Safeguard's contextual triage engine, correlates that reachability signal with your EPSS and exposure data to rank this finding correctly against the rest of your backlog instead of treating every "High" CVSS score as equally urgent. When remediation is confirmed, Safeguard can generate auto-fix pull requests that bump setuptools (and pip, where relevant) across affected manifests and Dockerfiles in one coordinated pass, closing the loop from detection to a merged fix without manual triage overhead.

Never miss an update

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