CVE-2026-49114: ONNX: TOCTOU symlink bug allows arbitrary file overwrite

HIGH
Published August 21, 2026
CISO Take

ONNX before 1.21.0 builds the external-data file path from an attacker-influenceable model field and opens it for writing without O_NOFOLLOW/O_EXCL, after a non-atomic os.path.isfile() check — a classic TOCTOU symlink race. A local attacker who shares a filesystem with the victim (multi-tenant training server, CI runner, shared notebook environment) can pre-plant a symlink at the predicted external-data path so the victim's own save operation is redirected to overwrite files like ~/.ssh/authorized_keys or cron entries, potentially escalating to the victim's privileges. There's no EPSS score yet given the recency, it isn't in CISA KEV, and no public exploit or Nuclei template exists, but the bug requires no privileges and only low complexity to trigger once a symlink is staged — the constraining factor is local access and victim interaction (running save_external_data), not exploit difficulty. Because ONNX is a foundational serialization format across the ML tooling ecosystem (model export, conversion pipelines, MLOps CI/CD), any shared compute environment running ONNX export jobs on behalf of multiple users is exposed. Upgrade to onnx >= 1.21.0 immediately, and until then treat any directory where multiple local users can write as unsafe for model serialization output.

Sources: NVD GitHub Advisory CISA ATLAS

What is the risk?

High severity (CVSS 7.1) but scoped to local attack vector — exploitation requires the attacker to already have local write access to the directory where the victim serializes an ONNX model with external data, plus the victim triggering a save operation (UI:R) in that directory. This is not remotely exploitable and has no confidentiality impact, but the integrity and availability impact is high because a successful race lets the attacker fully control what gets overwritten, up to and including SSH authorized_keys or cron files, which functionally becomes privilege escalation or persistence as the victim. Real-world risk concentrates in shared/multi-tenant AI infrastructure: shared GPU training boxes, JupyterHub/SageMaker-style notebook servers, and CI/CD runners that serialize models on behalf of multiple pipelines or users. No public PoC, no KEV listing, and no EPSS data suggest exploitation is not yet observed in the wild, but the vulnerability class (predictable path + non-atomic check + no O_NOFOLLOW) is well-understood and trivial to weaponize once an attacker has co-located access.

How does the attack unfold?

Local Reconnaissance
Attacker with local access to a shared training/CI host identifies a victim workflow that will call ONNX's save_external_data and predicts the output file path.
AML.T0007
Symlink Pre-plant
Attacker creates a symlink at the predicted external-data path pointing to a sensitive target file the victim can write, such as ~/.ssh/authorized_keys.
AML.T0079
TOCTOU Exploitation
Victim's save_external_data call passes the non-atomic isfile() check and opens the path without O_NOFOLLOW/O_EXCL, following the symlink instead of writing a fresh file.
AML.T0018.002
File Overwrite / Privilege Escalation
Model data is appended to the target file, corrupting or hijacking it (e.g., injecting an attacker SSH key), giving the attacker persistence or elevated access as the victim.
AML.T0112

What systems are affected?

Package Ecosystem Vulnerable Range Patched
ONNX pip No patch
21.3K OpenSSF 8.7 1.1K dependents Pushed 5d ago 80% patched ~41d to patch Full package profile →

Do you use ONNX? You're affected.

How severe is it?

CVSS 3.1
7.1 / 10
EPSS
N/A
Exploitation Status
No known exploitation
Sophistication
Moderate

What is the attack surface?

AV AC PR UI S C I A
AV Local
AC Low
PR None
UI Required
S Unchanged
C None
I High
A High

What should I do?

1 step
  1. 1) Upgrade the onnx package to >= 1.21.0, which fixes the symlink handling in save_external_data. 2) Until patched, never run ONNX model export/save operations in world-writable or multi-tenant-shared directories — use per-job, per-user isolated temp directories with restrictive permissions (0700). 3) On shared training/CI infrastructure, audit for pre-existing symlinks in directories used for model output before running export jobs, and consider mount options or filesystem policies that disallow following symlinks from untrusted users (e.g., separate volumes per tenant). 4) Detection: monitor for unexpected symlinks appearing in model-export working directories, and alert on writes to sensitive files (~/.ssh/authorized_keys, crontabs, application config) that correlate with ONNX export job execution. 5) In CI/CD, ensure export jobs run in ephemeral, single-tenant containers rather than persistent shared build hosts.

How is it classified?

Which compliance frameworks are affected?

This CVE is relevant to:

EU AI Act
Article 15 - Accuracy, Robustness and Cybersecurity
ISO 42001
A.6.2.6 - Third-party and customer relationships
NIST AI RMF
GOVERN 6.1 - Third-party risk management
OWASP LLM Top 10
LLM05:2025 - Supply Chain Vulnerabilities

Frequently Asked Questions

What is CVE-2026-49114?

ONNX before 1.21.0 builds the external-data file path from an attacker-influenceable model field and opens it for writing without O_NOFOLLOW/O_EXCL, after a non-atomic os.path.isfile() check — a classic TOCTOU symlink race. A local attacker who shares a filesystem with the victim (multi-tenant training server, CI runner, shared notebook environment) can pre-plant a symlink at the predicted external-data path so the victim's own save operation is redirected to overwrite files like ~/.ssh/authorized_keys or cron entries, potentially escalating to the victim's privileges. There's no EPSS score yet given the recency, it isn't in CISA KEV, and no public exploit or Nuclei template exists, but the bug requires no privileges and only low complexity to trigger once a symlink is staged — the constraining factor is local access and victim interaction (running save_external_data), not exploit difficulty. Because ONNX is a foundational serialization format across the ML tooling ecosystem (model export, conversion pipelines, MLOps CI/CD), any shared compute environment running ONNX export jobs on behalf of multiple users is exposed. Upgrade to onnx >= 1.21.0 immediately, and until then treat any directory where multiple local users can write as unsafe for model serialization output.

Is CVE-2026-49114 actively exploited?

No confirmed active exploitation of CVE-2026-49114 has been reported, but organizations should still patch proactively.

How to fix CVE-2026-49114?

1) Upgrade the `onnx` package to >= 1.21.0, which fixes the symlink handling in save_external_data. 2) Until patched, never run ONNX model export/save operations in world-writable or multi-tenant-shared directories — use per-job, per-user isolated temp directories with restrictive permissions (0700). 3) On shared training/CI infrastructure, audit for pre-existing symlinks in directories used for model output before running export jobs, and consider mount options or filesystem policies that disallow following symlinks from untrusted users (e.g., separate volumes per tenant). 4) Detection: monitor for unexpected symlinks appearing in model-export working directories, and alert on writes to sensitive files (~/.ssh/authorized_keys, crontabs, application config) that correlate with ONNX export job execution. 5) In CI/CD, ensure export jobs run in ephemeral, single-tenant containers rather than persistent shared build hosts.

What systems are affected by CVE-2026-49114?

This vulnerability affects the following AI/ML architecture patterns: model serving, training pipelines, CI/CD model export pipelines.

What is the CVSS score for CVE-2026-49114?

CVE-2026-49114 has a CVSS v3.1 base score of 7.1 (HIGH).

What is the AI security impact?

Affected AI Architectures

model servingtraining pipelinesCI/CD model export pipelines

MITRE ATLAS Techniques

AML.T0010.003 Model
AML.T0011 User Execution
AML.T0018.002 Embed Malware

Compliance Controls Affected

EU AI Act: Article 15
ISO 42001: A.6.2.6
NIST AI RMF: GOVERN 6.1
OWASP LLM Top 10: LLM05:2025

What are the technical details?

Original Advisory

In ONNX before 1.21.0, the 'save_external_data' function builds the external-data file path from the model's external_data location field and opens it for writing without 'O_NOFOLLOW/O_EXCL', after a non-atomic 'os.path.isfile()' check. A local attacker with write access to the directory where a victim serializes external data can deterministically pre-plant a symlink that is being followed, causing the victim's write to append to any file the victim can write, e.g. ~/.ssh/authorized_keys, cron files, or application configs. Fixed in 1.21.0.

Exploitation Scenario

An attacker holds a low-privileged local account on a shared ML training server or CI runner alongside a victim who periodically exports models to ONNX with external data (e.g., a scheduled fine-tuning pipeline). The attacker predicts or observes the output path the victim's job will use for the external-data file, and pre-creates a symlink at that exact path pointing to the victim's ~/.ssh/authorized_keys. When the victim's export job next runs onnx.save_model(), ONNX's non-atomic isfile() check passes, the file is opened for writing without O_NOFOLLOW/O_EXCL, and the write follows the symlink — appending model tensor bytes into authorized_keys. If the attacker can also influence the model content being saved (e.g., the victim is converting or re-serializing a third-party/untrusted ONNX model supplied by the attacker), the appended bytes can be crafted to resemble a valid SSH public key, giving the attacker persistent SSH access as the victim and full compromise of the shared host.

Weaknesses (CWE)

CWE-22 — Improper Limitation of a Pathname to a Restricted Directory ('Path Traversal'): The product uses external input to construct a pathname that is intended to identify a file or directory that is located underneath a restricted parent directory, but the product does not properly neutralize special elements within the pathname that can cause the pathname to resolve to a location that is outside of the restricted directory.

  • [Implementation] Assume all input is malicious. Use an "accept known good" input validation strategy, i.e., use a list of acceptable inputs that strictly conform to specifications. Reject any input that does not strictly conform to specifications, or transform it into something that does. When performing input validation, consider all potentially relevant properties, including length, type of input, the full range of acceptable values, missing or extra inputs, syntax, consistency across related fields, and conformance to business rules. As an example of business rule logic, "boat" may be syntactically valid because it only contains alphanumeric characters, but it is not valid if the input is only expected to contain colors such as "red" or "blue." Do not rely exclusively on looking for malicious or malformed inputs. This is likely to miss at least one undesirable input, especially if the code's environment changes. This can give attackers enough room to bypass the intended validation. However, denylis
  • [Architecture and Design] For any security checks that are performed on the client side, ensure that these checks are duplicated on the server side, in order to avoid CWE-602. Attackers can bypass the client-side checks by modifying values after the checks have been performed, or by changing the client to remove the client-side checks entirely. Then, these modified values would be submitted to the server.

Source: MITRE CWE corpus.

CVSS Vector

CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H

Timeline

Published
August 21, 2026
Last Modified
August 21, 2026
First Seen
August 21, 2026

Related Vulnerabilities