TL;DR for defenders. If you run LiteLLM, patch to
1.83.7 or later now - it's actively exploited and in CISA KEV with a remediation due
date of June 22, 2026. Can't patch immediately? Block POST /mcp-rest/test/connection and
POST /mcp-rest/test/tools/list at your reverse proxy. To detect, watch two things: requests
to those endpoints in your proxy logs, and - far higher fidelity - the LiteLLM process spawning
a shell or recon binary, which a Python web proxy has no legitimate reason to do. Both Sigma
rules are below and in sigma-pack.
Also patch Starlette to 1.0.1+ to break the unauthenticated chain.
Why this one matters
LiteLLM is an open-source "AI gateway": a proxy that exposes 100+ LLM providers behind a single OpenAI-compatible API, with centralized keys, budgets, and routing. That role makes it a high-value target by position - it typically holds provider API keys, sits in the request path of everything AI in the org, and is increasingly internet-facing so that distributed teams and apps can reach it. Compromising the gateway means the credentials and the traffic in one move.
CVE-2026-42271 is a command injection (CWE-78) rated CVSS 3.1 8.8 / 4.0 8.7 (High), affecting LiteLLM from 1.74.2 up to but not including 1.83.7. It was published on May 8, 2026, and CISA added it to KEV on June 8 with a federal remediation deadline of June 22 - the signal that it is being exploited in the wild, not just theoretically exploitable.
The mechanism, at a defender's depth
LiteLLM can act as a client to MCP (Model Context Protocol) servers - the tool-providing
backends that agentic features call. One MCP transport is stdio: instead of talking to a
network service, LiteLLM launches a local command and speaks to it over standard input/output. An MCP
server defined for stdio therefore carries three telling fields: command (the binary to
run), args, and env.
To let an administrator preview an MCP server before saving it, LiteLLM exposed two endpoints that accept a full server configuration in the request body and try connecting to it:
POST /mcp-rest/test/connection
POST /mcp-rest/test/tools/list
Here is the whole bug: for a stdio server, "try connecting to it" means
spawn the supplied command as a subprocess on the proxy host, with the
privileges of the LiteLLM process. And unlike the endpoint that saves an MCP server, these two
preview endpoints carried no role check - any caller holding a valid LiteLLM API key,
including a low-privilege one minted for an app or a teammate, could reach them. A key meant for making
model calls became a key for running commands on the box.
Scope note. This is a defensive writeup. The description above is the level of detail in the vendor advisory and the CVE record - enough to log, detect, and contain the issue. It deliberately contains no request body, payload, or working exploit. UMBRASEC publishes defense, not offense.
The chain: from authenticated to unauthenticated RCE
On its own, CVE-2026-42271 needs a valid API key. That requirement disappears when it is chained with
CVE-2026-48710,
an authentication-bypass bug in Starlette - the Python ASGI framework LiteLLM is built
on - nicknamed "BadHost". In Starlette before 1.0.1, the HTTP Host header
was not validated before being used to reconstruct request.url (CWE-444, CVSS 6.5), letting
a malformed header create a mismatch between the real request path and the URL that authorization checks
were evaluating.
Researchers at Horizon3.ai demonstrated that abusing BadHost lets an attacker slip past LiteLLM's API-key requirement and reach the vulnerable MCP preview endpoints unauthenticated - converting an authenticated command injection into unauthenticated RCE against an exposed gateway. Note the two clocks here: patching LiteLLM to 1.83.7 closes the command injection, but you should also upgrade Starlette to 1.0.1+ to remove the bypass that makes the whole class worse - it affects far more than LiteLLM.
Public reporting (Horizon3.ai, The Hacker News, Help Net Security) confirms active exploitation of CVE-2026-42271 and documents the chain, but does not publish indicators from the in-the-wild attacks. So rather than chase IOCs that aren't public, detect the behavior - which is durable anyway.
Are you affected? Find it first
You can't defend an asset you don't know you run, which is the whole point of knowing what you own. LiteLLM often arrives as a container or a developer-stood-up service rather than something procurement signed off, so look in a few places:
- Container inventories and registries for
litellm/ghcr.io/berriai/litellmimages; check the tag against 1.83.7. - Running services exposing the LiteLLM proxy (default port 4000), and anything fronting it - reverse proxies, ingress, API gateways.
- The version banner: a deployment reports its version, and the
/healthand OpenAPI routes confirm a LiteLLM instance. - Most important: is it reachable from untrusted networks? An internet-exposed gateway is the unauthenticated-RCE scenario; an internal-only one is still exploitable by any API-key holder, so it is in scope either way - just with a smaller blast radius.
What to log
Two data sources carry this, and they sit at different points of the kill chain. Collect both if you can - the host-based one is the high-fidelity detection and the network one is the early, noisier signal.
- Process creation on the LiteLLM host - Linux
execvetelemetry from the Linux Auditd framework, Sysmon for Linux, or your EDR. This captures the actual impact: the proxy spawning a child process. If you run LiteLLM in a container, that's container runtime / EDR process visibility. This is the one that matters most. - HTTP access logs from whatever sits in front of LiteLLM - reverse proxy (nginx,
Caddy, Traefik), ingress controller, or API gateway - capturing method, URI path, source, and ideally
the
Hostheader. This catches the attempt at the front door. - LiteLLM's own logs, for the authenticated context: which API key / user made the request. Useful for scoping once an alert fires.
Detection
Same philosophy as every UMBRASEC writeup: layer from highest precision to broadest. Both Sigma rules below are in sigma-pack and validated in CI; convert them to your SIEM with sigma-cli.
1. The LiteLLM process spawns a shell or recon binary (high fidelity)
This is the detection that survives obfuscation, new payloads, and the unauthenticated chain alike,
because it watches the effect rather than the request. A LiteLLM proxy is a Python web service;
under normal operation it does not launch /bin/sh, curl, or nc.
A child process like that, parented to the proxy, is the command injection landing.
title: LiteLLM Proxy Spawning Shell or Recon Utility
id: 7b3a1f02-9c5d-4e88-a1b6-2f4c7d9e0a13
status: experimental
description: >
The LiteLLM proxy process (Python/uvicorn/gunicorn) spawned a shell
or common recon/download utility. A web proxy has no legitimate
reason to do this; consistent with exploitation of CVE-2026-42271,
where MCP stdio preview endpoints spawn an attacker-supplied command.
references:
- https://nvd.nist.gov/vuln/detail/CVE-2026-42271
- https://umbrasec.dev/research/detecting-litellm-command-injection.html
author: UMBRASEC
date: 2026/06/13
tags:
- attack.initial_access
- attack.t1190
- attack.execution
- attack.t1059
logsource:
category: process_creation
product: linux
detection:
selection_parent:
ParentImage|endswith:
- '/python'
- '/python3'
- '/uvicorn'
- '/gunicorn'
selection_child:
Image|endswith:
- '/sh'
- '/bash'
- '/dash'
- '/curl'
- '/wget'
- '/nc'
- '/ncat'
- '/nohup'
condition: selection_parent and selection_child
falsepositives:
- Init/entrypoint scripts that legitimately shell out at container start
- Health-check or sidecar tooling that wraps the proxy in a shell
level: high
Tuning note. Parenting on a generic python is broad, so
scope this rule to your LiteLLM hosts or containers (by host tag, image name, or a more specific
ParentCommandLine|contains: 'litellm' if your telemetry includes the command line). Baseline
in report-only mode first: container start-up frequently runs a shell entrypoint once, so allowlist that
known parent/child pair and the rest is quiet. The signal you care about is a shell or network utility
appearing under the proxy at request time, long after startup.
2. Requests to the vulnerable MCP preview endpoints (front-door signal)
Earlier in the chain, and useful even if you can't get host telemetry off the box: the two endpoints are an administrator-only preview feature, so in most environments any request to them is worth surfacing - and a burst of them from an unexpected source is a strong exploitation signal.
title: LiteLLM MCP Test Endpoint Requested
id: 2c8e5b41-6d77-4a90-bb1e-3f0a9c2d4e56
status: experimental
description: >
A request hit one of LiteLLM's MCP preview endpoints. These accept a
full MCP server config and, for stdio transport, spawn the supplied
command (CVE-2026-42271). They are an admin-only preview feature, so
requests - especially from untrusted sources - warrant review.
references:
- https://nvd.nist.gov/vuln/detail/CVE-2026-42271
- https://github.com/BerriAI/litellm/security/advisories/GHSA-v4p8-mg3p-g94g
- https://umbrasec.dev/research/detecting-litellm-command-injection.html
author: UMBRASEC
date: 2026/06/13
tags:
- attack.initial_access
- attack.t1190
logsource:
category: webserver
detection:
selection:
cs-method: 'POST'
cs-uri-stem|contains:
- '/mcp-rest/test/connection'
- '/mcp-rest/test/tools/list'
condition: selection
falsepositives:
- An administrator legitimately previewing an MCP server in the UI
- Vulnerability scanners probing the path after public disclosure
level: medium
Tuning note. Adapt the field names to your proxy's log schema
(cs-method / cs-uri-stem are the Sigma webserver taxonomy; nginx and others
name them differently). If you know which admin source addresses legitimately use the preview feature,
exclude them and treat everything else as high. Pair this with rule #1: the front-door request
plus a shell spawning under the proxy is exploitation with very little doubt left.
3. Host-header anomalies for the BadHost chain (supporting)
Because the unauthenticated path rides CVE-2026-48710, malformed or mismatched Host headers
reaching the gateway are a supporting signal. This is noisier - scanners and misconfigured clients
generate odd Host headers constantly - so treat it as triage context, not a pager rule: a request whose
Host header doesn't match your gateway's expected hostname(s), arriving alongside a hit on
rule #2, raises confidence that you're looking at the unauthenticated chain rather than an
authorized admin preview. Allowlist your real hostnames and alert on the remainder only in correlation.
If a rule fires: contain it
Treat a confirmed hit on rule #1 as host compromise of a system that holds your LLM provider keys. Working from your incident response plan:
- Isolate the LiteLLM host/container via EDR rather than wiping it - preserve the process tree and logs for scoping.
- Rotate every secret the gateway held: all upstream LLM provider API keys, the LiteLLM master key, database credentials, and any cloud role the host could assume. Assume disclosure - that's what the gateway exists to store.
- Revoke and reissue LiteLLM API keys, and review who held low-privilege keys; the authenticated path needs only one.
- Patch then redeploy from a known-good image at 1.83.7+ (and Starlette 1.0.1+), rather than cleaning in place.
- Scope the reporting question early. If provider keys or customer data were within reach, your notification clocks may have started - decide that with the plan, not at 2am.
Mitigation, in priority order
- Patch LiteLLM to 1.83.7+. The fix adds the missing role check: both preview
endpoints now require the
PROXY_ADMINrole, matching the save endpoint. This is the fix. - Patch Starlette to 1.0.1+ to close BadHost (CVE-2026-48710) and break the unauthenticated chain - relevant well beyond LiteLLM.
- If you can't patch yet, block
POST /mcp-rest/test/connectionandPOST /mcp-rest/test/tools/listat the reverse proxy or API gateway - the vendor's own interim workaround. - Get the gateway off the public internet where the architecture allows. An internal-only LiteLLM removes the unauthenticated scenario entirely and shrinks the authenticated one to insiders and footholds.
- Least-privilege the process. Run LiteLLM as a non-root user in a constrained container so that command execution lands somewhere with little to reach - defense in depth for the next bug in this class, which agentic, tool-spawning software will keep producing.
Honest limitations
- Rule #1 needs host or container process telemetry, which many LiteLLM deployments - a container someone stood up fast - don't yet collect. If that's you, this CVE is the business case for fixing it; rule #2 is your stopgap until then.
- The endpoint rule can be evaded by the chain's framing. The path itself is stable, but rely on rule #2 alone and a clever request shape or a future variant can slip it - which is exactly why the host-based effect rule leads.
- No public IOCs from the in-the-wild attacks. These detections target the technique, not a campaign; that's a strength for durability and a caveat if you were hoping to retro-hunt specific infrastructure.
- This is timely, and timeliness ages. Patch status is the real control; detection is for the window before you've patched and the assets you haven't found yet. Re-run the inventory step after you think you're done.
References
- NVD - CVE-2026-42271 (LiteLLM command injection)
- BerriAI - GitHub Security Advisory GHSA-v4p8-mg3p-g94g
- LiteLLM - v1.83.7-stable release (the fix)
- CISA - Known Exploited Vulnerabilities Catalog
- NVD - CVE-2026-48710 (Starlette "BadHost" Host header bypass)
- Starlette - GitHub Security Advisory GHSA-86qp-5c8j-p5mr
- The Hacker News - LiteLLM flaw CVE-2026-42271 exploited in the wild, chains to unauthenticated RCE (Jun 2026)
- Help Net Security - LiteLLM vulnerability under active attack, CISA warns (Jun 2026)
- MITRE ATT&CK - T1190 Exploit Public-Facing Application
Found an error? If a detection misfires in your environment or a detail here is wrong, that feedback is welcome - open an issue. Corrections are credited.