Fickling MLAllowlist analysis pass rendered inoperative by shared mutable state in AnalysisContext.shorten_code()
Summary
| CVE | CVE-2026-14535 |
|---|---|
| State | PUBLISHED |
| Assigner | BombadilSystems |
| Source Priority | CVE Program / NVD first with legacy fallback |
| Published | 2026-07-04 14:16:29 UTC |
| Updated | 2026-07-04 14:16:29 UTC |
| Description | In Trail of Bits fickling versions up to and including 0.1.11, the UnsafeImportsML analysis pass unconditionally calls AnalysisContext.shorten_code(node) on every import node it inspects, regardless of whether the import is flagged as unsafe. This call registers the shortened code representation in the shared AnalysisContext.reported_shortened_code set. When the MLAllowlist analysis pass subsequently runs, it calls the same shorten_code() method, receives already_reported=True for every import, and executes a continue statement that skips its allowlist check entirely. This renders MLAllowlist dead code for all imports — it never evaluates whether an import is in the ML allowlist or not. The MLAllowlist pass was designed to catch imports of modules outside the known-safe ML ecosystem (torch, numpy, transformers, etc.) that slip past the UnsafeImports denylist. With MLAllowlist inoperative, any standard library module not in the UNSAFE_IMPORTS denylist can be invoked via pickle deserialization while fickling's check_safety() returns LIKELY_SAFE. The fickling.load() API chains check_safety() into pickle.loads() as an explicit security gate, meaning a LIKELY_SAFE verdict causes the payload to be deserialized and executed. The root cause is shared mutable state between independently-correct analysis passes — UnsafeImportsML works as designed in isolation, MLAllowlist works as designed in isolation, but the shared reported_shortened_code set causes UnsafeImportsML to poison MLAllowlist's deduplication logic. |
Risk And Classification
Primary CVSS: v3.1 8.8 HIGH from aa17e1a1-c329-4d6e-a1ed-8d0188aea082
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H
Problem Types: CWE-693 | CWE-693 CWE-693 Protection Mechanism Failure
| Version | Source | Type | Score | Severity | Vector |
|---|---|---|---|---|---|
| 3.1 | aa17e1a1-c329-4d6e-a1ed-8d0188aea082 | Secondary | 8.8 | HIGH | CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H |
| 3.1 | CNA | CVSS | 8.8 | HIGH | CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H |
CVSS v3.1 Breakdown
Attack Vector
NetworkAttack Complexity
LowPrivileges Required
NoneUser Interaction
RequiredScope
UnchangedConfidentiality
HighIntegrity
HighAvailability
HighCVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H
Vendor Declared Affected Products
| Source | Vendor | Product | Version | Platforms |
|---|---|---|---|---|
| CNA | Trailofbits | Fickling | affected 0.1.11 custom | Not specified |
| CNA | Trailofbits | Fickling | unaffected 0.1.12 custom | Not specified |
References
| Reference | Source | Link | Tags |
|---|---|---|---|
| github.com/trailofbits/fickling/commit/41ce7cb01edd97072994039574a2301eb... | aa17e1a1-c329-4d6e-a1ed-8d0188aea082 | github.com | |
| github.com/trailofbits/fickling/security/advisories/GHSA-cffv-grgg-g429 | aa17e1a1-c329-4d6e-a1ed-8d0188aea082 | github.com | |
| github.com/trailofbits/fickling/pull/278 | aa17e1a1-c329-4d6e-a1ed-8d0188aea082 | github.com | |
| github.com/trailofbits/fickling/releases/tag/v0.1.12 | aa17e1a1-c329-4d6e-a1ed-8d0188aea082 | github.com | |
| CVE Program record | CVE.ORG | www.cve.org | canonical |
| NVD vulnerability detail | NVD | nvd.nist.gov | canonical, analysis |
Vendor Comments And Credit
Discovery Credit
CNA: Christopher Aziz (Bombadil Systems LLC) (en)
There are currently no legacy QID mappings associated with this CVE.