Skip to main content

zip2 EUVDEUVD-2026-109983

| CVE-2026-115906 MEDIUM
Improper Validation of Integrity Check Value (CWE-354)
2026-10-26 GitHub_M
6.5
CVSS 3.1 · Vendor: GitHub_M
View

Attack ChainAIDerived

Hypothetical attack flow derived from CVE metadata – not a confirmed exploit chain

  1. Access
    Intercept or supply AES-encrypted archive
  2. Exploit
    Bit-flip ciphertext and truncate entry to true EOF (or zero payload)
  3. Execution
    Victim decrypts via by_index_decrypt with valid password
  4. Impact
    HMAC check skipped, forged plaintext accepted as authentic

Vulnerability Assessment

Weakness
CWE
OWASP Top 10:2025
A08:2025 - Software or Data Integrity Failures
ASVS 5.0
V15 - Secure Coding and Architecture Integrity verification
Exploitation Conditions

Requires the application to decrypt entries through the password-bearing APIs by_index_decrypt(), by_name_decrypt(), by_path_decrypt(), or by_index_with_options() with a supplied password; bare extract() calls by_index() without a password and rejects AES entries, so it is not affected. The attacker must be able to modify or supply the archive (e.g. tampering in transit) but needs no password, and must craft the entry so the bounded reader hits the archive's true EOF while the attacker-declared compressed_size leaves data_remaining positive, OR make the entry a zero-payload entry - in both cases src/aes.rs returns before reading/comparing the HMAC-SHA1-80 tag. For AE-2 entries the CRC-32 check is also disabled by design, leaving no integrity check at all. Limiting factors: victim must open the crafted archive with a valid password via those specific APIs (UI:R), and only zip2 versions 0.6.0 through < 9.0.0 are affected; AES-CTR malleability makes the actual byte manipulation straightforward once those conditions hold.

Impact

This is a genuine cryptographic authentication-bypass (CWE-354 / CWE-1284), scored CVSS 6.5 (Medium) with vector AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N - integrity-only impact, no confidentiality or availability loss. The signals are mostly consistent: no CISA KEV listing and no EPSS score was provided in the input, so wild-exploitation probability cannot be quantified (this gap is stated rather than assumed to be low), while the vendor's own GHSA advisory ships a working proof-of-concept (three tests reported passing against commit 6f09b30 and release 8.6.0). The vuln.today decision label is 'this_month', i.e. a normal patch-cycle priority rather than emergency/act_now. Real-world risk is raised by PR:N (the attacker needs no password - AES-CTR malleability lets them bit-flip or forge plaintext) and the published PoC, but tempered by UI:R: a victim application must actually decrypt an attacker-supplied/modified archive through the password-bearing APIs (by_index_decrypt, by_name_decrypt, by_path_decrypt, or by_index_with_options with a password). Bare extract() is not affected. Net: a real defect worth remediating this cycle, not a drop-everything RCE. Note a labeling conflict - the input tag 'Information Disclosure' contradicts the CVSS (C:N/I:H) and the mechanism, which is an integrity/authentication bypass, not disclosure.

Exploit ScenarioDerived

An attacker who can modify an AES-encrypted ZIP in transit (or supply a crafted one) rewrites an entry so its data ends exactly at the archive's true EOF while the central-directory compressed_size stays larger, or makes the entry zero-payload; because AES-CTR is malleable they XOR chosen bits onto the ciphertext without knowing the password. When a victim application opens the archive with the correct password via by_index_decrypt/by_name_decrypt/by_path_decrypt (or by_index_with_options with a password), the HMAC-SHA1-80 tag is never read or compared, so the forged plaintext is returned as a clean end-of-stream with no authentication error. A full working PoC with three passing tests is published in the GHSA advisory.

This Month Plan within 30 days. Why: MEDIUM severity (CVSS 4.0-6.9).
Patch available 0.2% exploitation probability (EPSS)

Get an e-mail when this CVE is exploited, patched or re-scored. Free account.

Alert me

AnalysisAIv1 – Oct 26, 2026

Integrity bypass in the zip2 Rust crate (0.6.0 through versions below 9.0.0) lets an attacker who can modify or supply a ZIP archive deliver altered or attacker-chosen plaintext from an AES-encrypted entry that is read through the password-bearing APIs, with no authentication error raised. The HMAC-SHA1-80 tag in src/aes.rs is only checked when the reader's byte counter reaches zero, so a crafted entry that hits true end-of-file while the header-declared compressed_size still leaves data remaining - or an entry with zero payload - returns a clean end of stream and skips the tag comparison entirely; because AES-CTR is malleable, the modification needs no knowledge of the password. Scored CVSS 6.5 (AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N), it is unauthenticated from the attacker's side but requires the victim to open the crafted archive with a valid password through by_index_decrypt, by_name_decrypt, by_path_decrypt, or by_index_with_options; impact is integrity-only, with AE-2 entries additionally losing their by-design-disabled CRC-32 check so no integrity verification of any kind remains. A public PoC reference exists in the form of the advisory's test code; it is not verified as working exploit code outside that context, and no active exploitation is indicated. Fixed in 9.0.0.

RemediationAI

Vendor-released patch: zip2 9.0.0 (https://github.com/zip-rs/zip2/releases/tag/v9.0.0). Upgrade the crate dependency to 9.0.0, or apply commit ec265db0b0602f8ffb9479327397bddefb7e2216 if a pinned fork or vendored copy must be patched in place; the fix makes AesReader::new reject any declared compressed size smaller than the AES metadata overhead, verifies the HMAC immediately when the declared payload length is zero, and returns UnexpectedEof when the underlying reader yields zero bytes while data_remaining is still positive - so truncated or misdeclared entries now fail loudly instead of returning unauthenticated plaintext. Review your call sites: if you use by_index_decrypt(), by_name_decrypt(), by_path_decrypt(), or by_index_with_options() with a password, you need 9.0.0, since no configuration flag turns the vulnerable path off; per the advisory, extracting via bare extract() is not exposed because it uses by_index() without a password and rejects AES entries. Full details are in the advisory at https://github.com/zip-rs/zip2/security/advisories/GHSA-8hxf-qr8p-62x4.

Affected VersionsENISA

zip2 0.6.0, < 9.0.0

Affected Packages

euvd zip2 fix: 9.0.0

Source: OSV (Open Source Vulnerabilities)

Affects your stack

Affects 1 package in euvd

Checking this CVE against your own stacks and servers is part of the Basic plan and up.

Technical ContextAI · show details

The crate implements the WinZip AES (AE-1/AE-2) entry format, where each encrypted entry carries a salt, a two-byte password verifier, the AES-CTR encrypted payload, and a trailing 10-byte HMAC-SHA1-80 authentication code. AesReader computes data_remaining as compressed_size minus the fixed metadata overhead (salt + verifier + tag), taking compressed_size straight from the attacker-controllable central directory, and ZipFileData::find_content() applies only a reader.take(compressed_size) bound - nothing cross-checks the declared span against the archive's real structure. The vulnerable read() loop returns Ok(0) early when data_remaining is already zero and only enters the finalisation branch when the counter lands exactly on zero; if the inner bounded reader reaches true EOF first it returns Ok(0), the subtraction removes nothing, and the tag is never read or compared. The fix routes finalisation through a new verify_hmac() helper, calls it immediately for zero-length payloads, and returns UnexpectedEof when a read yields zero bytes with data_remaining still positive. The root causes are CWE-354 (improper validation of an integrity check value) and CWE-1284 (improper validation of a specified quantity in input, i.e. trusting the declared compressed size). AE-2 entries disable the CRC-32 check by design (Crc32Reader with should_disable = true), so on the bypass path neither the HMAC nor the CRC provides any protection.

Know when Rust 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

Vendor (GitHub_M) PRIMARY 6.5 MEDIUM
AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:N
vuln.today AI 6.5 MEDIUM

No password needed (PR:N) and AES-CTR is malleable (AC:L), but the victim must decrypt the attacker-supplied archive via affected APIs (UI:R); only integrity is broken (I:H, C:N/A:N).

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

Primary rating from Vendor (GitHub_M).

CVSS VectorVendor: GitHub_M

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

Lifecycle Timeline

1
Patch available
Oct 26, 2026 - 17:02 EUVD

DescriptionCVE.org

zip is a zip library for Rust that supports reading and writing simple ZIP files. From 0.6.0 until 9.0.0, the AES entry reader in src/aes.rs verifies its HMAC only when the attacker-controlled data counter reaches zero. If the underlying bounded reader reaches the real end of the archive while data_remaining is still positive, or if an encrypted entry has no payload, the reader can return a clean end of stream without reading and comparing the authentication tag. Applications using by_index_decrypt, by_name_decrypt, by_path_decrypt, or password-enabled by_index_with_options can therefore accept modified plaintext without an authentication error. This issue is fixed in version 9.0.0.

Threat Intelligence Overview

EPSS Score
0.2%
Top 96% exploitable
Prevalence
Medium
de facto standard Rust ZIP crate, but AES-decrypt path narrows real exposure
Data Quality
4 sources
Confidence: Medium

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.

SignalValue
Severity MEDIUM
CISA KEV No
Public POC No
EPSS 0.2%
Patch available Yes
Active threat No
Deciding rule
MEDIUM severity (CVSS 4.0-6.9)
What every action level means
Emergency Immediate action required. Criteria: CRITICAL + in CISA KEV (actively exploited) without patch, OR CRITICAL + EPSS > 30% without patch, OR CRITICAL + active threat signals without patch.
Act Now Prioritize within 24-48h. Criteria: in KEV with patch available, OR CRITICAL + public POC, OR HIGH + EPSS > 10%, OR CRITICAL + active threat, OR any CRITICAL severity.
This Week Schedule remediation this week. Criteria: HIGH severity (CVSS 7.0-8.9). Patch within normal change window.
This Month Plan within 30 days. Criteria: MEDIUM severity (CVSS 4.0-6.9), lower exploitation probability. Include in regular patch cycle.
Monitor Track and reassess. Criteria: LOW severity (CVSS 0.1-3.9), minimal exploitation risk. No immediate action needed.

SSVC AssessmentENISA

SSVC Decision· derived
Scheduled
Exploitation· derived
None
System Exposure· derived
Open
Automatable· derived
No
Human Impact· derived
Medium

Priority Score

32
Low Medium High Critical
KEV: 0
EPSS: 0
CVSS: +32
PoC: 0
Weaponized: 0
Threat intel: 0
Gov advisory: 0

Attack Technique

Information disclosure occurs when an application unintentionally exposes sensitive data that aids attackers in reconnaissance or directly compromises security.

More in Rust

View all
CVE-2024-3566 CRITICAL POC
9.8 Apr 10

Command injection via Windows CreateProcess argument parsing affects multiple language runtimes and tooling (Node.js, PH

CVE-2021-31162 CRITICAL POC
9.8 Apr 14

In the standard library in Rust before 1.52.0, a double free can occur in the Vec::from_iter function if freeing the ele

CVE-2021-28879 CRITICAL POC
9.8 Apr 11

In the standard library in Rust before 1.52.0, the Zip implementation can report an incorrect size due to an integer ove

CVE-2026-58491 CRITICAL POC
9.3 Sep 21

Stored cross-site scripting and open redirect in Warpgate's SSO endpoints (versions prior to 0.25.5) allow an unauthenti

CVE-2021-29922 CRITICAL POC
9.1 Aug 07

library/std/src/net/parser.rs in Rust before 1.53.0 does not properly consider extraneous zero characters at the beginni

CVE-2026-77620 HIGH POC
8.7 Sep 22

Denial of service in the Vector observability pipeline's `logstash` source (versions 0.15.0 through 0.56.x) allows a rem

CVE-2019-12083 HIGH POC
8.1 May 13

The Rust Programming Language Standard Library 1.34.x before 1.34.2 contains a stabilized method which, if overridden, c

CVE-2026-96889 HIGH POC
7.8 Sep 23

Use-after-free in librsvg during rendering of crafted SVG documents with nested XInclude directives and duplicate entity

CVE-2021-28878 HIGH POC
7.5 Apr 11

In the standard library in Rust before 1.52.0, the Zip implementation calls __iterator_get_unchecked() more than once fo

CVE-2021-28875 HIGH POC
7.5 Apr 11

In the standard library in Rust before 1.50.0, read_to_end() does not validate the return value from Read in an unsafe c

CVE-2019-16760 HIGH POC
7.5 Sep 30

Cargo prior to Rust 1.26.0 may download the wrong dependency if your package.toml file uses the `package` configuration

CVE-2026-115905 CRITICAL
10.0 Oct 26

A parser differential in the Rust `zip` crate (zip2) through 9.0.4 lets a crafted archive present different filenames to

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