Keras
CVE-2025-12058
MEDIUM
Attack ChainAIDerived
Hypothetical attack flow derived from CVE metadata – not a confirmed exploit chain
-
AccessCraft malicious .keras with StringLookup vocabulary path/URL
-
DeliveryDistribute via model hub or share with victim
-
ExploitVictim loads model via load_model (safe_mode=True)
-
Executiontf.io.gfile reads local file or fetches remote URL
-
ImpactExfiltrate file contents or trigger server-side SSRF
Vulnerability Assessment
| Weakness |
CWE
OWASP Top 10:2025
A08:2025 - Software or Data Integrity Failures
ASVS 5.0
V1 - Encoding and Sanitization Safe deserialization, type allowlists
MITRE ATT&CK
2 techniques across 2 tactics: Execution, Initial Access The technique list with ATT&CK links and the kill-chain view is part of the Basic plan and up. |
| Exploitation Conditions | Exploitation requires a victim to load an attacker-controlled .keras archive via Keras's load_model (or saving.load_model) where the embedded StringLookup layer's 'vocabulary' argument is set to a local filesystem path or a remote URI handled by tf.io.gfile (e.g. file paths, GCS, HDFS, or HTTP/HTTPS endpoints). Critically, the default mitigation safe_mode=True does NOT prevent this, so no non-default configuration is needed on the victim side. The primary limiting factor is the supply-chain/trust step: the attacker must get the target to load an untrusted model file; impact is bounded to arbitrary local file read (incorporated into model state) and SSRF to endpoints reachable from the host - it is not remote code execution. SSRF reach additionally depends on the host having the relevant network access and gfile handlers (GCS/HDFS/HTTP) available. |
| Impact | This is a moderate-severity deserialization-class flaw (CWE-502) in Keras model loading, scored CVSS 4.0 5.9 by the reporter. The supplied CVSS 4.0 vector (AV:A/AC:H/AT:P/PR:L/UI:P) paints a fairly constrained picture - adjacent network, high complexity, a specific attack requirement, low privileges and passive user interaction - which pulls the score down despite the high confidentiality impact (VC:H, SC:H). No EPSS score, KEV listing, or public POC was provided, so there is no public exploit identified at time of analysis and no evidence of active exploitation; the risk is primarily latent rather than imminent. The most important signal lives in the description rather than the metrics: the mitigation users rely on (safe_mode=True) does NOT block this path, so environments that believed they were protected are not. I disagree with the reporter's AV:A/AC:H framing - malicious .keras files are typically distributed over the network (model hubs, downloads, shared artifacts) and loaded without special conditions, so I assess this closer to AV:N/AC:L with UI:R; the realistic limiter is that a victim must load an attacker-supplied model, not network adjacency. Bottom line: a real but non-emergency priority - patch promptly because a trusted default mitigation is bypassed, but the absence of KEV/POC/EPSS suggests no widespread exploitation yet. |
| Exploit ScenarioDerived | An attacker publishes a trojanized .keras model (e.g. on a public model hub, or sends it directly to an ML engineer) whose StringLookup layer sets its vocabulary to a sensitive local path such as /etc/passwd or to an internal URL. When a victim loads it with keras.models.load_model - even with the default safe_mode=True - Keras reads that file (retrievable via get_vocabulary()) or fetches that endpoint via tf.io.gfile, yielding local file disclosure or attacker-directed internal requests (SSRF). No public exploit code was provided, but the linked GHSA advisory and PR #21751 test cases effectively demonstrate the mechanism. |
Get an e-mail when this CVE is exploited, patched or re-scored. Free account.
Alert meAnalysisAIv1 – Oct 19, 2026
Keras Model.load_model fails to enforce safe_mode=True for the StringLookup layer's vocabulary path handling, so a malicious .keras archive can cause arbitrary local file reads and server-side requests when a victim loads it. This CWE-502 deserialization-class flaw affects the Keras model-loading path and is assessed as confidentiality-focused, requiring user interaction to load the untrusted model; SSRF reach depends on the host's network access and available tf.io.gfile handlers. No public exploit was identified at time of analysis.
RemediationAI
Apply the upstream fix from PR #21751 and advisory GHSA-qg93-c7p6-gg7f; a specific released patched version was not independently confirmed in the provided data. Until a fixed release is confirmed, do not load .keras models from untrusted sources, and inspect archives for StringLookup or IndexLookup configurations where vocabulary is a string path or URI rather than an inline list or bundled asset. For trusted legacy models that require external vocabularies, pass safe_mode=False only after provenance validation and archive review, noting that this re-enables unsafe deserialization behavior. Alternatively, rebuild the archive with the vocabulary embedded as an asset or inline list. Restrict filesystem permissions and outbound network access on hosts that load models to limit local-file-read and SSRF impact, with the trade-off that legitimate GCS, HDFS, or HTTP vocabulary/asset loading may be disrupted.
Affected Packages
Source: OSV (Open Source Vulnerabilities)
Affects your stack
Affects 1 package in pypi
Checking this CVE against your own stacks and servers is part of the Basic plan and up.
Technical ContextAI · show details
Keras .keras archives serialize layer configurations, and the StringLookup/IndexLookup preprocessing layer accepts a vocabulary argument that can be either an inline list or a string path/URI. During model loading, Keras uses tf.io.gfile to resolve file operations, which supports local paths and remote handlers such as GCS, HDFS, and HTTP/HTTPS; the fetched content is incorporated into model state and can be retrieved via get_vocabulary(). The safe_mode=True guard did not block this external vocabulary loading during deserialization, turning model loading into a local-file-read and SSRF primitive. The upstream fix in PR #21751 adds a serialization_lib.in_safe_mode() check in set_vocabulary and serializes external vocabularies as model assets while clearing the original path/URL. The root cause class is CWE-502 unsafe deserialization of attacker-controlled model configuration. The assessed CVSS 3.1 vector is AV:N/AC:L/PR:N/UI:R/S:C/C:H/I:N/A:N, with confidentiality impact only and no integrity or availability impact; no CPE data was supplied, but the affected code is in keras/src/layers/preprocessing/index_lookup.py and string_lookup handling.
Know when Keras gets its next vulnerability
- Watch products and get an email when something new is published
- Check this CVE against your own stack and servers
- Exploit and PoC references, threat intelligence from 22 sources
No credit card · 7-day full trial
Severity by source
CVSS:4.0/AV:A/AC:H/AT:P/PR:L/UI:P/VC:H/VI:L/VA:L/SC:H/SI:L/SA:L
Malicious models are network-distributed and load without special conditions (AV:N/AC:L/PR:N), but a victim must load the file (UI:R); file read plus SSRF reaches beyond the component (S:C) with arbitrary read (C:H) and no integrity or availability impact.
Primary rating from Vendor (google).
CVSS VectorVendor: google
DescriptionCVE.org
The Keras.Model.load_model method, including when executed with the intended security mitigation safe_mode=True, is vulnerable to arbitrary local file loading and Server-Side Request Forgery (SSRF).
This vulnerability stems from the way the StringLookup layer is handled during model loading from a specially crafted .keras archive. The constructor for the StringLookup layer accepts a vocabulary argument that can specify a local file path or a remote file path.
- Arbitrary Local File Read: An attacker can create a malicious .keras file that embeds a local path in the StringLookup layer's configuration. When the model is loaded, Keras will attempt to read the content of the specified local file and incorporate it into the model state (e.g., retrievable via get_vocabulary()), allowing an attacker to read arbitrary local files on the hosting system.
- Server-Side Request Forgery (SSRF): Keras utilizes tf.io.gfile for file operations. Since tf.io.gfile supports remote filesystem handlers (such as GCS and HDFS) and HTTP/HTTPS protocols, the same mechanism can be leveraged to fetch content from arbitrary network endpoints on the server's behalf, resulting in an SSRF condition.
The security issue is that the feature allowing external path loading was not properly restricted by the safe_mode=True flag, which was intended to prevent such unintended data access.
Threat Intelligence Overview
How this decision was reached
The engine reads each signal below and applies a fixed list of rules from top to bottom. The first rule that matches sets the recommended action – like a statement, every line is shown.
What every action level means
SSVC AssessmentENISA
Priority Score
Attack Technique
Server-Side Request Forgery exploits applications that fetch remote resources based on user-supplied URLs.
Insecure deserialization occurs when an application converts serialized data (a stream of bytes representing an object's state) back into a living object without proper validation.
The Keras Model.load_model method can be exploited to achieve arbitrary code execution, even with safe_mode=True. Rated
Deserialization of untrusted data in Keras 3.11.0 through 3.11.2 allows remote code execution when a victim loads a mali
A arbitrary code injection vulnerability in TensorFlow's Keras framework (<2.13) allows attackers to execute arbitrary c
Directory traversal in Keras through 3.11.3 allows an attacker who supplies a crafted tar archive to keras.utils.get_fil
The Keras Model.load_model method can be exploited to achieve arbitrary code execution, even with safe_mode=True. Rated
Path traversal in Keras archive extraction utilities prior to version 3.14.0 allows remote attackers to write files outs
Memory-exhaustion denial of service in Google Keras 3.0.0 through 3.13.0 lets a remote attacker crash the Python interpr
Arbitrary local file disclosure in Keras 3.0.0 through 3.13.1 allows a remote attacker to read sensitive files from a vi
A safe mode bypass vulnerability in the `Model.load_model` method in Keras versions 3.0.0 through 3.10.0 allows an attac
An issue in keras 3.7.0 allows attackers to write arbitrary files to the user's machine via downloading a crafted tar fi
NVD
CVE.org
EPSS
GitHub
Exploit-DB