Skip to main content

LLaMA-Factory CVE-2025-61784

HIGH
Path Traversal (CWE-22)
2025-10-07 security-advisories@github.com
8.1
CVSS 3.1 · NVD
Share

Severity by source

NVD PRIMARY
8.1 HIGH
AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:N
vuln.today AI
6.5 MEDIUM

Network endpoint, trivial to trigger, requires an authenticated API user (PR:L); SSRF/LFI yields high confidentiality but GET-only fetches give no real integrity or availability impact.

3.1 AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:N/A:N
4.0 AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:N/VA:N/SC:N/SI:N/SA:N

Primary rating from NVD.

CVSS VectorNVD

Attack Vector
Network
Attack Complexity
Low
Privileges Required
Low
User Interaction
None
Scope
Unchanged
Confidentiality
High
Integrity
High
Availability
None

Lifecycle Timeline

2
Analysis Generated
Oct 08, 2026 - 13:31 vuln.today
CVE Published
Oct 07, 2025 - 19:15 nvd
HIGH 8.1

DescriptionNVD

LLaMA-Factory is a tuning library for large language models. Prior to version 0.9.4, a Server-Side Request Forgery (SSRF) vulnerability in the chat API allows any authenticated user to force the server to make arbitrary HTTP requests to internal and external networks. This can lead to the exposure of sensitive internal services, reconnaissance of the internal network, or interaction with third-party services. The same mechanism also allows for a Local File Inclusion (LFI) vulnerability, enabling users to read arbitrary files from the server's filesystem. The vulnerability exists in the _process_request function within src/llamafactory/api/chat.py. This function is responsible for processing incoming multimodal content, including images, videos, and audio provided via URLs. The function checks if the provided URL is a base64 data URI or a local file path (os.path.isfile). If neither is true, it falls back to treating the URL as a web URI and makes a direct HTTP GET request using requests.get(url, stream=True).raw without any validation or sanitization of the URL. Version 0.9.4 fixes the underlying issue.

AnalysisAI

Server-side request forgery and local file inclusion in LLaMA-Factory through 0.9.3 let a user of the public /v1/chat/completions endpoint force the server to issue arbitrary outbound HTTP requests and read files from the server's filesystem. The flaw sits in the multimodal media handling path of _process_request, which accepts image_url, video_url and audio_url fields and passes any value that is not a base64 data URI or an existing local file straight into requests.get() with no scheme, host or address validation; the advisory frames the attacker as 'any authenticated user' (PR:L), so a valid API bearer token is the gating factor, but deployments started without an API key leave the endpoint effectively reachable by anyone who can route to it. Publicly available exploit code exists (the advisory ships a curl payload aimed at the AWS instance metadata service), no CISA KEV entry is associated with this CVE, and the risk is rated 8.1 under CVSS 3.1 AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:N, while the independently assessed vector scores integrity impact as none and treats confidentiality loss as the primary consequence.

Technical ContextAI

LLaMA-Factory is a Python LLM fine-tuning and serving library that exposes an OpenAI-compatible chat API through FastAPI; the vulnerable code lives in src/llamafactory/api/chat.py, where _process_request inspects each multimodal input item and classifies a supplied media reference as a base64 data URI, a local file path (via os.path.isfile), or otherwise a 'web URI'. The final branch performs requests.get(url, stream=True).raw with no validation, and the result flows into create_chat_completion_response and create_stream_chat_completion_response, which are wired to the public /v1/chat/completions route in src/llamafactory/api/app.py. That is a classic CWE-918 server-side request forgery, and because the same unvalidated string can be a filesystem path the advisory also classifies it as CWE-22 path traversal / local file inclusion; the NVD-supplied CWE is CWE-22, reflecting the file-read angle. CPE data (cpe:2.3:a:hiyouga:llama-factory:*:*:*:*:*:*:*:*) covers all releases up to and including 0.9.3. The 0.9.4 fix adds two guards in src/llamafactory/api/common.py: check_ssrf_url() parses the URL, restricts it to http/https, resolves the hostname with socket.getaddrinfo and rejects any address where ipaddress.ip_address(ip).is_global is false, and check_lfi_path() realpath-resolves the target and requires it to sit under a SAFE_MEDIA_PATH allowlist, with local file access additionally governed by the ALLOW_LOCAL_FILES environment flag (default enabled). Both helpers are invoked for image_url, video_url and audio_url inputs, and violations raise HTTPException with 400/403 responses. Note that the address check is performed at validation time against a single resolved address, so deployments should still pair it with network-layer egress controls.

RemediationAI

Vendor-released patch: upgrade to LLaMA-Factory 0.9.4 (for example, pip install --upgrade llamafactory==0.9.4) as documented in advisory GHSA-527m-2xhr-j27g, which applies the check_ssrf_url and check_lfi_path guards from commit 95b7188090a1018935c9dc072bfc97f24f1c96e9; upgrading fixes both the SSRF and the local file read because the two share one unvalidated code path. If an immediate upgrade is not possible, compensating controls are: always start the API server with an API key configured so the PR:L prerequisite is genuinely enforced, since the endpoint is effectively open when no key is set (trade-off: key management overhead and breakage for clients that expect unauthenticated access); keep the chat API off untrusted networks by binding it to localhost or a private interface and fronting it with a reverse proxy that restricts who can reach /v1/chat/completions (trade-off: reduces convenience for legitimate remote users); and apply network egress filtering so the serving host cannot reach RFC1918 ranges, loopback, link-local addresses such as the AWS/cloud metadata address 169.254.169.254, or internal admin planes (trade-off: legitimate third-party media URLs hosted on internal or split-horizon networks will fail to load). Running the API in a sandbox or container with a read-only root filesystem and only the intended media directory mounted provides additional containment for the LFI half of the issue. After upgrading, set ALLOW_LOCAL_FILES=0 to disable local media file access entirely and point SAFE_MEDIA_PATH at a dedicated directory if local media is not required; note that the ALLOW_LOCAL_FILES and SAFE_MEDIA_PATH controls ship with the 0.9.4 fix and are not available in 0.9.3 or earlier.

Share

CVE-2025-61784 vulnerability details – vuln.today

This site uses cookies essential for authentication and security. No tracking or analytics cookies are used. Privacy Policy