CWE-345
DiscouragedInsufficient Verification of Data Authenticity
Abstraction: Class · Status: Draft
The product does not sufficiently verify the origin or authenticity of data, in a way that causes it to accept invalid data.
939 vulnerabilities reference this CWE, most recent first.
GHSA-RC6V-5RMX-W5MV
Vulnerability from github – Published: 2026-05-15 18:13 – Updated: 2026-06-09 10:34Summary
Three medium-severity issues in arnika affecting the UDP key-rotation protocol, PQC key file handling, and KMS TLS client. All require specific preconditions to exploit and do not allow direct code execution or immediate key extraction. A self-contained PoC is attached.
Details
1) ACK timestamp not validated: udpserver.go:185
udpClient() verifies HMAC and packet type but never checks ackPkt.Timestamp. A MITM can capture one ACK, drop all subsequent DATA packets, and replay the stale ACK indefinitely. Primary advances PSK each rotation, backup stays on key 1, tunnel breaks. No PSK knowledge needed. The server side already has this check, the client does not.
Fix: mirror the timestamp check already present on the server side.
2) Empty PQC key file silently accepted: repositories/pqc.go:29
os.ReadFile follows symlinks. Empty file to base64.Decode("") = []byte{}, nil. HKDF runs on the QKD key alone while arnika logs [OK] HKDF derivation completed for QKD+PQC key. Requires write access to the directory containing PQC_PSK_FILE.
Fix: validate decoded key is non-empty before derivation; enforce parent directory permissions in SECURITY.md.
3) InsecureSkipVerify: true hardcoded: repositories/kms.go:61
KMS HTTP client unconditionally sets InsecureSkipVerify: true, overriding RootCAs. CA_CERTIFICATE is loaded but never consulted (dead code). Requires MITM between arnika and the KMS endpoint, which in typical deployments are co-located.
Fix: remove the flag; RootCAs already holds the correct pool when CA_CERTIFICATE is configured.
PoC
See arnika_exploit.tar.gz. PoC shows observable behavior for each attack; the third one (KMS MITM) needs no custom code, any HTTPS proxy with a self-signed cert is enough.
Impact
Issues require network MITM or local directory write access to exploit. No direct key extraction or code execution. Primary impact is tunnel desync and silent security downgrade in hybrid QKD+PQC mode.
{
"affected": [
{
"database_specific": {
"last_known_affected_version_range": "\u003c= 1.0.0"
},
"package": {
"ecosystem": "Go",
"name": "github.com/arnika-project/arnika"
},
"ranges": [
{
"events": [
{
"introduced": "0"
},
{
"fixed": "1.0.1"
}
],
"type": "ECOSYSTEM"
}
]
}
],
"aliases": [],
"database_specific": {
"cwe_ids": [
"CWE-294",
"CWE-295",
"CWE-345"
],
"github_reviewed": true,
"github_reviewed_at": "2026-05-15T18:13:57Z",
"nvd_published_at": null,
"severity": "MODERATE"
},
"details": "### Summary\nThree medium-severity issues in arnika affecting the UDP key-rotation protocol, PQC key file handling, and KMS TLS client. All require specific preconditions to exploit and do not allow direct code execution or immediate key extraction. A self-contained PoC is attached.\n\n### Details\n1) ACK timestamp not validated: `udpserver.go:185`\n`udpClient()` verifies HMAC and packet type but never checks `ackPkt.Timestamp`. A MITM can capture one ACK, drop all subsequent DATA packets, and replay the stale ACK indefinitely. Primary advances PSK each rotation, backup stays on key 1, tunnel breaks. No PSK knowledge needed. The server side already has this check, the client does not.\n**Fix**: mirror the timestamp check already present on the server side.\n\n2) Empty PQC key file silently accepted: `repositories/pqc.go:29`\n`os.ReadFile` follows symlinks. Empty file to `base64.Decode(\"\") = []byte{}, nil`. HKDF runs on the QKD key alone while arnika logs `[OK] HKDF derivation completed for QKD+PQC key`. Requires write access to the directory containing `PQC_PSK_FILE`.\n**Fix**: validate decoded key is non-empty before derivation; enforce parent directory permissions in `SECURITY.md`.\n\n3) `InsecureSkipVerify: true` hardcoded: `repositories/kms.go:61`\nKMS HTTP client unconditionally sets `InsecureSkipVerify: true`, overriding `RootCAs`. `CA_CERTIFICATE` is loaded but never consulted (dead code). Requires MITM between arnika and the KMS endpoint, which in typical deployments are co-located.\n**Fix**: remove the flag; `RootCAs` already holds the correct pool when `CA_CERTIFICATE` is configured.\n\n### PoC\nSee [arnika_exploit.tar.gz](https://github.com/user-attachments/files/27585454/arnika_exploit.tar.gz). PoC shows observable behavior for each attack; the third one (KMS MITM) needs no custom code, any HTTPS proxy with a self-signed cert is enough.\n\n### Impact\nIssues require network MITM or local directory write access to exploit. No direct key extraction or code execution. Primary impact is tunnel desync and silent security downgrade in hybrid QKD+PQC mode.",
"id": "GHSA-rc6v-5rmx-w5mv",
"modified": "2026-06-09T10:34:05Z",
"published": "2026-05-15T18:13:57Z",
"references": [
{
"type": "WEB",
"url": "https://github.com/arnika-project/arnika/security/advisories/GHSA-rc6v-5rmx-w5mv"
},
{
"type": "WEB",
"url": "https://github.com/arnika-project/arnika/commit/efbd980d8b636cb59f60f2d6ece1b80a9cf36535"
},
{
"type": "PACKAGE",
"url": "https://github.com/arnika-project/arnika"
},
{
"type": "WEB",
"url": "https://github.com/arnika-project/arnika/releases/tag/v1.0.1"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:P/AC:L/PR:H/UI:R/S:U/C:L/I:L/A:N",
"type": "CVSS_V3"
},
{
"score": "CVSS:4.0/AV:N/AC:L/AT:P/PR:N/UI:N/VC:N/VI:N/VA:L/SC:N/SI:N/SA:N",
"type": "CVSS_V4"
}
],
"summary": "arnika is affected by medium-severity issues in UDP rotation, PQC handling, and KMS TLS"
}
GHSA-RC6X-59RR-4G8R
Vulnerability from github – Published: 2022-05-24 17:07 – Updated: 2023-05-11 15:30A bug in Nextcloud Server 17.0.1 causes the workflow rules to depend their behaviour on the file extension when checking file mimetypes.
{
"affected": [],
"aliases": [
"CVE-2019-15613"
],
"database_specific": {
"cwe_ids": [
"CWE-20",
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2020-02-04T20:15:00Z",
"severity": "MODERATE"
},
"details": "A bug in Nextcloud Server 17.0.1 causes the workflow rules to depend their behaviour on the file extension when checking file mimetypes.",
"id": "GHSA-rc6x-59rr-4g8r",
"modified": "2023-05-11T15:30:20Z",
"published": "2022-05-24T17:07:56Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2019-15613"
},
{
"type": "WEB",
"url": "https://hackerone.com/reports/697959"
},
{
"type": "WEB",
"url": "https://nextcloud.com/security/advisory/?id=NC-SA-2020-002"
},
{
"type": "WEB",
"url": "http://lists.opensuse.org/opensuse-security-announce/2020-02/msg00019.html"
},
{
"type": "WEB",
"url": "http://lists.opensuse.org/opensuse-security-announce/2020-02/msg00022.html"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:N/AC:L/PR:L/UI:R/S:U/C:H/I:H/A:H",
"type": "CVSS_V3"
}
]
}
GHSA-RCCH-4525-RQ2F
Vulnerability from github – Published: 2024-09-23 15:31 – Updated: 2024-09-23 15:31Sony XAV-AX5500 Insufficient Firmware Update Validation Remote Code Execution Vulnerability. This vulnerability allows physically present attackers to execute arbitrary code on affected installations of Sony XAV-AX5500 devices. Authentication is not required to exploit this vulnerability.
The specific flaw exists within the handling of software updates. The issue results from the lack of proper validation of software update packages. An attacker can leverage this vulnerability to execute code in the context of the device.
Was ZDI-CAN-22939
{
"affected": [],
"aliases": [
"CVE-2024-23922"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2024-09-23T15:15:13Z",
"severity": "MODERATE"
},
"details": "Sony XAV-AX5500 Insufficient Firmware Update Validation Remote Code Execution Vulnerability. This vulnerability allows physically present attackers to execute arbitrary code on affected installations of Sony XAV-AX5500 devices. Authentication is not required to exploit this vulnerability.\n\nThe specific flaw exists within the handling of software updates. The issue results from the lack of proper validation of software update packages. An attacker can leverage this vulnerability to execute code in the context of the device.\n\nWas ZDI-CAN-22939",
"id": "GHSA-rcch-4525-rq2f",
"modified": "2024-09-23T15:31:00Z",
"published": "2024-09-23T15:31:00Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2024-23922"
},
{
"type": "WEB",
"url": "https://www.sony.com/electronics/support/mobile-cd-players-digital-media-players-xav-series/xav-ax5500/software/00274156"
},
{
"type": "WEB",
"url": "https://www.zerodayinitiative.com/advisories/ZDI-24-874"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:P/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H",
"type": "CVSS_V3"
}
]
}
GHSA-RF7J-W28R-V7M8
Vulnerability from github – Published: 2022-05-24 17:40 – Updated: 2022-05-24 17:40Monal before 4.9 does not implement proper sender verification on MAM and Message Carbon (XEP-0280) results. This allows a remote attacker (able to send stanzas to a victim) to inject arbitrary messages into the local history, with full control over the sender and receiver displayed to the victim.
{
"affected": [],
"aliases": [
"CVE-2020-26547"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2021-02-01T02:15:00Z",
"severity": "CRITICAL"
},
"details": "Monal before 4.9 does not implement proper sender verification on MAM and Message Carbon (XEP-0280) results. This allows a remote attacker (able to send stanzas to a victim) to inject arbitrary messages into the local history, with full control over the sender and receiver displayed to the victim.",
"id": "GHSA-rf7j-w28r-v7m8",
"modified": "2022-05-24T17:40:44Z",
"published": "2022-05-24T17:40:44Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2020-26547"
},
{
"type": "WEB",
"url": "https://github.com/anurodhp/Monal/commits/develop"
},
{
"type": "WEB",
"url": "https://monal.im/blog/cve-2020-26547"
}
],
"schema_version": "1.4.0",
"severity": []
}
GHSA-RGPQ-8HGG-5C2Q
Vulnerability from github – Published: 2022-05-17 03:57 – Updated: 2022-05-17 03:57McAfee Advanced Threat Defense (ATD) before 3.4.8.178 might allow remote attackers to bypass malware detection by leveraging information about the parent process.
{
"affected": [],
"aliases": [
"CVE-2016-3983"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2016-04-08T15:59:00Z",
"severity": "HIGH"
},
"details": "McAfee Advanced Threat Defense (ATD) before 3.4.8.178 might allow remote attackers to bypass malware detection by leveraging information about the parent process.",
"id": "GHSA-rgpq-8hgg-5c2q",
"modified": "2022-05-17T03:57:21Z",
"published": "2022-05-17T03:57:21Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2016-3983"
},
{
"type": "WEB",
"url": "https://kc.mcafee.com/corporate/index?page=content\u0026id=SB10149"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.0/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:H/A:N",
"type": "CVSS_V3"
}
]
}
GHSA-RGV9-38W5-X798
Vulnerability from github – Published: 2022-05-24 17:19 – Updated: 2024-04-04 02:52A vulnerability in the hardware crypto driver of Cisco IOS XE Software for Cisco 4300 Series Integrated Services Routers and Cisco Catalyst 9800-L Wireless Controllers could allow an unauthenticated, remote attacker to disconnect legitimate IPsec VPN sessions to an affected device. The vulnerability is due to insufficient verification of authenticity of received Encapsulating Security Payload (ESP) packets. An attacker could exploit this vulnerability by tampering with ESP cleartext values as a man-in-the-middle.
{
"affected": [],
"aliases": [
"CVE-2020-3220"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2020-06-03T18:15:00Z",
"severity": "HIGH"
},
"details": "A vulnerability in the hardware crypto driver of Cisco IOS XE Software for Cisco 4300 Series Integrated Services Routers and Cisco Catalyst 9800-L Wireless Controllers could allow an unauthenticated, remote attacker to disconnect legitimate IPsec VPN sessions to an affected device. The vulnerability is due to insufficient verification of authenticity of received Encapsulating Security Payload (ESP) packets. An attacker could exploit this vulnerability by tampering with ESP cleartext values as a man-in-the-middle.",
"id": "GHSA-rgv9-38w5-x798",
"modified": "2024-04-04T02:52:29Z",
"published": "2022-05-24T17:19:07Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2020-3220"
},
{
"type": "WEB",
"url": "https://tools.cisco.com/security/center/content/CiscoSecurityAdvisory/cisco-sa-iosxe-vpn-dos-edOmW28Z"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:C/C:N/I:N/A:H",
"type": "CVSS_V3"
}
]
}
GHSA-RH2H-7W4M-MHHP
Vulnerability from github – Published: 2025-02-05 18:34 – Updated: 2025-02-05 18:34An insufficient verification of data authenticity vulnerability exists in BIG-IP APM Access Policy endpoint inspection that may allow an attacker to bypass endpoint inspection checks for VPN connection initiated thru BIG-IP APM browser network access VPN client for Windows, macOS and Linux.
Note: Software versions which have reached End of Technical Support (EoTS) are not evaluated.
{
"affected": [],
"aliases": [
"CVE-2025-23415"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2025-02-05T18:15:32Z",
"severity": "LOW"
},
"details": "An insufficient verification of data authenticity vulnerability exists in BIG-IP APM Access Policy endpoint inspection that may allow an attacker to bypass endpoint inspection checks for VPN connection initiated thru BIG-IP APM browser network access VPN client for Windows, macOS and Linux.\n\n \n\n\n\n\nNote: Software versions which have reached End of Technical Support (EoTS) are not evaluated.",
"id": "GHSA-rh2h-7w4m-mhhp",
"modified": "2025-02-05T18:34:46Z",
"published": "2025-02-05T18:34:46Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2025-23415"
},
{
"type": "WEB",
"url": "https://my.f5.com/manage/s/article/K000139656"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:N/AC:H/PR:N/UI:R/S:U/C:N/I:L/A:N",
"type": "CVSS_V3"
},
{
"score": "CVSS:4.0/AV:N/AC:L/AT:P/PR:N/UI:P/VC:N/VI:L/VA:N/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X",
"type": "CVSS_V4"
}
]
}
GHSA-RHXF-5PW9-Q4GM
Vulnerability from github – Published: 2022-05-13 01:07 – Updated: 2022-05-13 01:07Hex package manager version 0.14.0 through 0.18.2 contains a Signing oracle vulnerability in Package registry verification that can result in Package modifications not detected, allowing code execution. This attack appears to be exploitable via victim fetches packages from malicious/compromised mirror. This vulnerability appears to have been fixed in 0.19.
{
"affected": [],
"aliases": [
"CVE-2019-1000012"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2019-02-04T21:29:00Z",
"severity": "HIGH"
},
"details": "Hex package manager version 0.14.0 through 0.18.2 contains a Signing oracle vulnerability in Package registry verification that can result in Package modifications not detected, allowing code execution. This attack appears to be exploitable via victim fetches packages from malicious/compromised mirror. This vulnerability appears to have been fixed in 0.19.",
"id": "GHSA-rhxf-5pw9-q4gm",
"modified": "2022-05-13T01:07:56Z",
"published": "2022-05-13T01:07:56Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2019-1000012"
},
{
"type": "WEB",
"url": "https://github.com/hexpm/hex/pull/646"
},
{
"type": "WEB",
"url": "https://github.com/hexpm/hex/pull/651"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.0/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H",
"type": "CVSS_V3"
}
]
}
GHSA-RMXF-C923-96H6
Vulnerability from github – Published: 2022-02-10 00:00 – Updated: 2022-02-17 00:01Select Dell Client Commercial and Consumer platforms are vulnerable to an insufficient verification of data authenticity vulnerability. An authenticated malicious user may exploit this vulnerability in order to install modified BIOS firmware.
{
"affected": [],
"aliases": [
"CVE-2022-22567"
],
"database_specific": {
"cwe_ids": [
"CWE-345"
],
"github_reviewed": false,
"github_reviewed_at": null,
"nvd_published_at": "2022-02-09T20:15:00Z",
"severity": "MODERATE"
},
"details": "Select Dell Client Commercial and Consumer platforms are vulnerable to an insufficient verification of data authenticity vulnerability. An authenticated malicious user may exploit this vulnerability in order to install modified BIOS firmware.",
"id": "GHSA-rmxf-c923-96h6",
"modified": "2022-02-17T00:01:26Z",
"published": "2022-02-10T00:00:20Z",
"references": [
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2022-22567"
},
{
"type": "WEB",
"url": "https://www.dell.com/support/kbdoc/en-us/000195905/dsa-2022-028"
}
],
"schema_version": "1.4.0",
"severity": []
}
GHSA-RP9M-7R4C-75QG
Vulnerability from github – Published: 2026-04-03 04:07 – Updated: 2026-04-08 11:54NOTE: While the library exposes a mechanism which could introduce the vulnerability, this issue is created by developer-supplied code and not by the library itself. We will add a warning and some education for users around the possible issues however since the defaults work we will not be updating the library beyond that for this advisory.
Impact
Setting up a custom cacheKeyBuilder method which does not properly create unique keys for different tokens can lead to cache collisions. This could cause tokens to be mis-identified during the verification process leading to:
- Valid tokens returning claims from different valid tokens
- Users being mis-identified as other users based on the wrong token
This could result in: - User impersonation - UserB receives UserA's identity and permissions - Privilege escalation - Low-privilege users inherit admin-level access - Cross-tenant data access - Users gain access to other tenants' resources - Authorization bypass - Security decisions made on wrong user identity
Affected Configurations
This vulnerability ONLY affects applications that BOTH:
- Enable caching using the cache option
- Use custom cacheKeyBuilder functions that can produce collisions
VULNERABLE examples:
// Collision-prone: same audience = same cache key
cacheKeyBuilder: (token) => {
const { aud } = parseToken(token)
return `aud=${aud}`
}
// Collision-prone: grouping by user type
cacheKeyBuilder: (token) => {
const { aud } = parseToken(token)
return aud.includes('admin') ? 'admin-users' : 'regular-users'
}
// Collision-prone: tenant + service grouping
cacheKeyBuilder: (token) => {
const { iss, aud } = parseToken(token)
return `${iss}-${aud}`
}
SAFE examples:
// Default hash-based (recommended)
createVerifier({ cache: true }) // Uses secure default
// Include unique user identifier
cacheKeyBuilder: (token) => {
const { sub, aud, iat } = parseToken(token)
return `${sub}-${aud}-${iat}`
}
// No caching (always safe)
createVerifier({ cache: false })
Not Affected
- Applications using default caching
- Applications with caching disabled
Assessment Guide
To determine if you're affected:
- Check if caching is enabled: Look for cache: true or cache: in verifier configuration
- Check for custom cache key builders: Look for cacheKeyBuilder function in configuration
- Analyze collision potential: Review if your cacheKeyBuilder can produce identical keys for different users/tokens
- If no custom cacheKeyBuilder: You are NOT affected (default is safe)
Mitigations
Mitigations include:
- Ensure uniqueness of keys produced in cacheKeyBuilder
- Remove custom cacheKeyBuilder method
- Disable caching
fast-jwt allows enabling a verification cache through the cache option. The cache key is derived from the token via cacheKeyBuilder.
When a custom cacheKeyBuilder produces collisions between different tokens, the verifier may return the cached payload of a previous token instead of validating and returning the payload of the current token.
This results in cross-token payload reuse and identity confusion.
Two distinct valid JWTs can be verified successfully but mapped to the same cached entry, causing the verifier to return claims belonging to a different token.
This affects authentication and authorization decisions when applications trust the returned payload.
Affected component
src/verifier.js
Relevant logic:
cache enabled via createCache
cache population via cacheSet
lookup based on cacheKeyBuilder(token)
cached payload returned without re-verification
Impact
Identity / authorization confusion via cache collision.
If two tokens generate the same cache key:
token A is verified → payload stored in cache
token B is verified → cache hit occurs
verifier returns payload from token A instead of B
Observed effect:
subject mismatch
claim mismatch
authorization decision performed on wrong identity
Potential real-world consequences:
user impersonation (logical)
privilege confusion
incorrect RBAC evaluation
gateway / middleware auth inconsistencies
This is especially dangerous when:
cache is enabled (recommended for performance)
custom cacheKeyBuilder is used
identity claims (sub / aud / iss) drive authorization
Root cause
The verifier assumes the cache key uniquely identifies the token and its claims.
However:
cacheKeyBuilder is user-controlled
collisions are not detected
cache entries store decoded payload
cached payload is returned without binding validation
This creates a trust boundary break between:
token → cache key → cached payload
Proof of concept
Environment:
fast-jwt: 6.1.0
Node.js: v24.13.1
PoC:
const { createSigner, createVerifier } = require('fast-jwt')
const sign = createSigner({ key: 'secret' })
// Two distinct tokens const t1 = sign({ sub: 'userA', aud: 'admin' }) const t2 = sign({ sub: 'userB', aud: 'admin' })
// Deliberately unsafe cache key builder (collision) const verify = createVerifier({ key: 'secret', cache: true, cacheKeyBuilder: () => 'static-key' })
console.log('verify t1') const p1 = verify(t1) console.log('t1 PASS sub=', p1.sub)
console.log('verify t2') const p2 = verify(t2) console.log('t2 PASS sub=', p2.sub)
console.log('verify t2 again') const p3 = verify(t2) console.log('t2-again PASS sub=', p3.sub)
console.log('verify t1 again') const p4 = verify(t1) console.log('t1-again PASS sub=', p4.sub)
Observed output:
verify t1 t1 PASS sub= userA
verify t2 t2 PASS sub= userA
verify t2 again t2-again PASS sub= userA
verify t1 again t1-again PASS sub= userA
The verifier returns payload from userA when verifying userB.
Expected behavior
Cache must not allow returning claims from a different token.
Verification must remain bound to the actual token being validated.
Even if cache collisions occur, the verifier should:
revalidate signature
re-decode payload
or invalidate cache entry
Why this is not “just misuse”
This is not merely a user mistake.
Reasons:
fast-jwt explicitly exposes cacheKeyBuilder as an extension point.
The documentation suggests performance tuning via custom key builders.
No safeguards exist against collisions.
No verification binding is performed between:
cached payload
original token
The verifier trusts cache output as authoritative identity.
This creates a security-sensitive invariant:
"cache key uniqueness"
which is neither enforced nor validated.
Security-critical libraries must assume extension hooks can be misused and implement defensive checks, especially when identity decisions are derived from cached values.
Security classification
logical authorization flaw
cache confusion vulnerability
identity boundary break
Closest CWE:
CWE-440 — Expected Behavior Violation
Suggested fix (minimal and safe)
Bind cache entries to token integrity.
Option A — safest:
Store token hash along with payload and verify match before returning cache.
Conceptual patch:
const tokenHash = hashToken(token)
cache.set(key, { tokenHash, payload })
...
const entry = cache.get(key)
if (entry && entry.tokenHash === hashToken(token)) { return entry.payload }
Option B — simpler:
Disable cache usage when custom cacheKeyBuilder is provided.
Option C — defensive:
Always re-validate signature when cache hit occurs.
Notes
Default cacheKeyBuilder is safe (hash-based).
Issue appears when custom builders are used — a documented and supported feature.
Impact increases in:
API gateways
auth middleware
RBAC layers relying on payload.sub / payload.aud
This vulnerability is independent from:
RegExp statefulness issue
ReDoS claim validation issue
It is a separate flaw in cache design and trust model.
PoC did on my computer: 'use strict'
const fs = require('node:fs') const path = require('node:path') const { createSigner, createVerifier } = require('./src')
function nowSec() { return Math.floor(Date.now() / 1000) }
const sign = createSigner({ key: 'secret' }) const t1 = sign({ sub: 'userA', aud: 'admin', iat: nowSec() }) const t2 = sign({ sub: 'userB', aud: 'admin', iat: nowSec() })
function badKeyBuilder() { return 'aud=admin' }
const verify = createVerifier({ key: 'secret', cache: true, cacheTTL: 60000, cacheKeyBuilder: badKeyBuilder })
function run(tok) { try { const out = verify(tok) return { ok: true, sub: out.sub, aud: out.aud } } catch (e) { return { ok: false, code: e.code || String(e), message: e.message } } }
const results = [] results.push({ step: 'verify(t1)', token: 't1', result: run(t1) }) results.push({ step: 'verify(t2)', token: 't2', result: run(t2) }) results.push({ step: 'verify(t2) again', token: 't2', result: run(t2) }) results.push({ step: 'verify(t1) again', token: 't1', result: run(t1) })
const evidence = { title: 'fast-jwt cache confusion when cacheKeyBuilder collisions occur', environment: { node: process.version, fastJwt: require('./package.json').version }, config: { cache: true, cacheTTL: 60000, cacheKeyBuilder: "returns constant key 'aud=admin' (realistic collision pattern)" }, tokens: { t1: { claims: { sub: 'userA', aud: 'admin' }, jwt: t1 }, t2: { claims: { sub: 'userB', aud: 'admin' }, jwt: t2 } }, observed: results }
const outPath = path.join(process.cwd(), 'evidence-cache-keybuilder-confusion.json') fs.writeFileSync(outPath, JSON.stringify(evidence, null, 2)) console.log('Wrote evidence to:', outPath)
for (const r of results) {
console.log(r.step, '=>', r.result.ok ? PASS sub=${r.result.sub} : FAIL ${r.result.code})
}
Output: PS C:\Users\Franciny Rojas\Desktop\crypto-research\fast-jwt> node poc_cache_keybuilder_confusion_evidence.js Wrote evidence to: C:\Users\Franciny Rojas\Desktop\crypto-research\fast-jwt\evidence-cache-keybuilder-confusion.json verify(t1) => PASS sub=userA verify(t2) => PASS sub=userA verify(t2) again => PASS sub=userA verify(t1) again => PASS sub=userA PS C:\Users\Franciny Rojas\Desktop\crypto-research\fast-jwt>
{
"affected": [
{
"package": {
"ecosystem": "npm",
"name": "fast-jwt"
},
"ranges": [
{
"events": [
{
"introduced": "0.0.1"
},
{
"fixed": "6.2.0"
}
],
"type": "ECOSYSTEM"
}
]
}
],
"aliases": [
"CVE-2026-35039"
],
"database_specific": {
"cwe_ids": [
"CWE-1289",
"CWE-345",
"CWE-706"
],
"github_reviewed": true,
"github_reviewed_at": "2026-04-03T04:07:09Z",
"nvd_published_at": "2026-04-06T17:17:13Z",
"severity": "CRITICAL"
},
"details": "_NOTE_: While the library exposes a mechanism which could introduce the vulnerability, this issue is created by developer-supplied code and not by the library itself. We will add a warning and some education for users around the possible issues however since the defaults work we will not be updating the library beyond that for this advisory.\n\n## Impact\n\nSetting up a custom cacheKeyBuilder method which does not properly create unique keys for different tokens can lead to cache collisions. This could cause tokens to be mis-identified during the verification process leading to:\n\n- Valid tokens returning claims from different valid tokens\n- Users being mis-identified as other users based on the wrong token\n\nThis could result in:\n- User impersonation - UserB receives UserA\u0027s identity and permissions\n- Privilege escalation - Low-privilege users inherit admin-level access\n- Cross-tenant data access - Users gain access to other tenants\u0027 resources\n- Authorization bypass - Security decisions made on wrong user identity\n\n## Affected Configurations\n\nThis vulnerability ONLY affects applications that BOTH:\n\n1. Enable caching using the cache option\n2. Use custom cacheKeyBuilder functions that can produce collisions\n\nVULNERABLE examples:\n```\n// Collision-prone: same audience = same cache key\ncacheKeyBuilder: (token) =\u003e {\n const { aud } = parseToken(token)\n return `aud=${aud}`\n}\n\n// Collision-prone: grouping by user type\ncacheKeyBuilder: (token) =\u003e {\n const { aud } = parseToken(token)\n return aud.includes(\u0027admin\u0027) ? \u0027admin-users\u0027 : \u0027regular-users\u0027\n}\n\n// Collision-prone: tenant + service grouping\ncacheKeyBuilder: (token) =\u003e {\n const { iss, aud } = parseToken(token)\n return `${iss}-${aud}`\n}\n```\n\nSAFE examples:\n```\n// Default hash-based (recommended)\ncreateVerifier({ cache: true }) // Uses secure default\n\n// Include unique user identifier\ncacheKeyBuilder: (token) =\u003e {\n const { sub, aud, iat } = parseToken(token)\n return `${sub}-${aud}-${iat}`\n}\n\n// No caching (always safe)\ncreateVerifier({ cache: false })\n```\n### Not Affected\n\n- Applications using **default caching**\n- Applications with **caching disabled**\n \n## Assessment Guide\n\nTo determine if you\u0027re affected:\n\n1. Check if caching is enabled: Look for cache: true or cache: \u003cnumber\u003e in verifier configuration\n2. Check for custom cache key builders: Look for cacheKeyBuilder function in configuration\n3. Analyze collision potential: Review if your cacheKeyBuilder can produce identical keys for different users/tokens\n4. If no custom cacheKeyBuilder: You are NOT affected (default is safe)\n\n## Mitigations\n\nMitigations include:\n\n- Ensure uniqueness of keys produced in cacheKeyBuilder\n- Remove custom cacheKeyBuilder method\n- Disable caching\n\n---\n\nfast-jwt allows enabling a verification cache through the cache option.\nThe cache key is derived from the token via cacheKeyBuilder.\n\nWhen a custom cacheKeyBuilder produces collisions between different tokens, the verifier may return the cached payload of a previous token instead of validating and returning the payload of the current token.\n\nThis results in cross-token payload reuse and identity confusion.\n\nTwo distinct valid JWTs can be verified successfully but mapped to the same cached entry, causing the verifier to return claims belonging to a different token.\n\nThis affects authentication and authorization decisions when applications trust the returned payload.\n\nAffected component\n\nsrc/verifier.js\n\nRelevant logic:\n\ncache enabled via createCache\n\ncache population via cacheSet\n\nlookup based on cacheKeyBuilder(token)\n\ncached payload returned without re-verification\n\nImpact\n\nIdentity / authorization confusion via cache collision.\n\nIf two tokens generate the same cache key:\n\ntoken A is verified \u2192 payload stored in cache\n\ntoken B is verified \u2192 cache hit occurs\n\nverifier returns payload from token A instead of B\n\nObserved effect:\n\nsubject mismatch\n\nclaim mismatch\n\nauthorization decision performed on wrong identity\n\nPotential real-world consequences:\n\nuser impersonation (logical)\n\nprivilege confusion\n\nincorrect RBAC evaluation\n\ngateway / middleware auth inconsistencies\n\nThis is especially dangerous when:\n\ncache is enabled (recommended for performance)\n\ncustom cacheKeyBuilder is used\n\nidentity claims (sub / aud / iss) drive authorization\n\nRoot cause\n\nThe verifier assumes the cache key uniquely identifies the token and its claims.\n\nHowever:\n\ncacheKeyBuilder is user-controlled\n\ncollisions are not detected\n\ncache entries store decoded payload\n\ncached payload is returned without binding validation\n\nThis creates a trust boundary break between:\n\ntoken \u2192 cache key \u2192 cached payload\n\nProof of concept\n\nEnvironment:\n\nfast-jwt: 6.1.0\n\nNode.js: v24.13.1\n\nPoC:\n\nconst { createSigner, createVerifier } = require(\u0027fast-jwt\u0027)\n\nconst sign = createSigner({ key: \u0027secret\u0027 })\n\n// Two distinct tokens\nconst t1 = sign({ sub: \u0027userA\u0027, aud: \u0027admin\u0027 })\nconst t2 = sign({ sub: \u0027userB\u0027, aud: \u0027admin\u0027 })\n\n// Deliberately unsafe cache key builder (collision)\nconst verify = createVerifier({\n key: \u0027secret\u0027,\n cache: true,\n cacheKeyBuilder: () =\u003e \u0027static-key\u0027\n})\n\nconsole.log(\u0027verify t1\u0027)\nconst p1 = verify(t1)\nconsole.log(\u0027t1 PASS sub=\u0027, p1.sub)\n\nconsole.log(\u0027verify t2\u0027)\nconst p2 = verify(t2)\nconsole.log(\u0027t2 PASS sub=\u0027, p2.sub)\n\nconsole.log(\u0027verify t2 again\u0027)\nconst p3 = verify(t2)\nconsole.log(\u0027t2-again PASS sub=\u0027, p3.sub)\n\nconsole.log(\u0027verify t1 again\u0027)\nconst p4 = verify(t1)\nconsole.log(\u0027t1-again PASS sub=\u0027, p4.sub)\n\nObserved output:\n\nverify t1\nt1 PASS sub= userA\n\nverify t2\nt2 PASS sub= userA\n\nverify t2 again\nt2-again PASS sub= userA\n\nverify t1 again\nt1-again PASS sub= userA\n\nThe verifier returns payload from userA when verifying userB.\n\nExpected behavior\n\nCache must not allow returning claims from a different token.\n\nVerification must remain bound to the actual token being validated.\n\nEven if cache collisions occur, the verifier should:\n\nrevalidate signature\n\nre-decode payload\n\nor invalidate cache entry\n\nWhy this is not \u201cjust misuse\u201d\n\nThis is not merely a user mistake.\n\nReasons:\n\nfast-jwt explicitly exposes cacheKeyBuilder as an extension point.\n\nThe documentation suggests performance tuning via custom key builders.\n\nNo safeguards exist against collisions.\n\nNo verification binding is performed between:\n\ncached payload\n\noriginal token\n\nThe verifier trusts cache output as authoritative identity.\n\nThis creates a security-sensitive invariant:\n\n\"cache key uniqueness\"\n\nwhich is neither enforced nor validated.\n\nSecurity-critical libraries must assume extension hooks can be misused and implement defensive checks, especially when identity decisions are derived from cached values.\n\nSecurity classification\n\nlogical authorization flaw\n\ncache confusion vulnerability\n\nidentity boundary break\n\nClosest CWE:\n\nCWE-440 \u2014 Expected Behavior Violation\n\nSuggested fix (minimal and safe)\n\nBind cache entries to token integrity.\n\nOption A \u2014 safest:\n\nStore token hash along with payload and verify match before returning cache.\n\nConceptual patch:\n\nconst tokenHash = hashToken(token)\n\ncache.set(key, { tokenHash, payload })\n\n...\n\nconst entry = cache.get(key)\n\nif (entry \u0026\u0026 entry.tokenHash === hashToken(token)) {\n return entry.payload\n}\n\nOption B \u2014 simpler:\n\nDisable cache usage when custom cacheKeyBuilder is provided.\n\nOption C \u2014 defensive:\n\nAlways re-validate signature when cache hit occurs.\n\nNotes\n\nDefault cacheKeyBuilder is safe (hash-based).\n\nIssue appears when custom builders are used \u2014 a documented and supported feature.\n\nImpact increases in:\n\nAPI gateways\n\nauth middleware\n\nRBAC layers relying on payload.sub / payload.aud\n\nThis vulnerability is independent from:\n\nRegExp statefulness issue\n\nReDoS claim validation issue\n\nIt is a separate flaw in cache design and trust model.\n\nPoC did on my computer:\n\u0027use strict\u0027\n\nconst fs = require(\u0027node:fs\u0027)\nconst path = require(\u0027node:path\u0027)\nconst { createSigner, createVerifier } = require(\u0027./src\u0027)\n\nfunction nowSec() {\n return Math.floor(Date.now() / 1000)\n}\n\nconst sign = createSigner({ key: \u0027secret\u0027 })\nconst t1 = sign({ sub: \u0027userA\u0027, aud: \u0027admin\u0027, iat: nowSec() })\nconst t2 = sign({ sub: \u0027userB\u0027, aud: \u0027admin\u0027, iat: nowSec() })\n\nfunction badKeyBuilder() {\n return \u0027aud=admin\u0027\n}\n\nconst verify = createVerifier({\n key: \u0027secret\u0027,\n cache: true,\n cacheTTL: 60000,\n cacheKeyBuilder: badKeyBuilder\n})\n\nfunction run(tok) {\n try {\n const out = verify(tok)\n return { ok: true, sub: out.sub, aud: out.aud }\n } catch (e) {\n return { ok: false, code: e.code || String(e), message: e.message }\n }\n}\n\nconst results = []\nresults.push({ step: \u0027verify(t1)\u0027, token: \u0027t1\u0027, result: run(t1) })\nresults.push({ step: \u0027verify(t2)\u0027, token: \u0027t2\u0027, result: run(t2) })\nresults.push({ step: \u0027verify(t2) again\u0027, token: \u0027t2\u0027, result: run(t2) })\nresults.push({ step: \u0027verify(t1) again\u0027, token: \u0027t1\u0027, result: run(t1) })\n\nconst evidence = {\n title: \u0027fast-jwt cache confusion when cacheKeyBuilder collisions occur\u0027,\n environment: {\n node: process.version,\n fastJwt: require(\u0027./package.json\u0027).version\n },\n config: {\n cache: true,\n cacheTTL: 60000,\n cacheKeyBuilder: \"returns constant key \u0027aud=admin\u0027 (realistic collision pattern)\"\n },\n tokens: {\n t1: { claims: { sub: \u0027userA\u0027, aud: \u0027admin\u0027 }, jwt: t1 },\n t2: { claims: { sub: \u0027userB\u0027, aud: \u0027admin\u0027 }, jwt: t2 }\n },\n observed: results\n}\n\nconst outPath = path.join(process.cwd(), \u0027evidence-cache-keybuilder-confusion.json\u0027)\nfs.writeFileSync(outPath, JSON.stringify(evidence, null, 2))\nconsole.log(\u0027Wrote evidence to:\u0027, outPath)\n\nfor (const r of results) {\n console.log(r.step, \u0027=\u003e\u0027, r.result.ok ? `PASS sub=${r.result.sub}` : `FAIL ${r.result.code}`)\n}\n\nOutput:\nPS C:\\Users\\Franciny Rojas\\Desktop\\crypto-research\\fast-jwt\u003e node poc_cache_keybuilder_confusion_evidence.js\nWrote evidence to: C:\\Users\\Franciny Rojas\\Desktop\\crypto-research\\fast-jwt\\evidence-cache-keybuilder-confusion.json\nverify(t1) =\u003e PASS sub=userA\nverify(t2) =\u003e PASS sub=userA\nverify(t2) again =\u003e PASS sub=userA\nverify(t1) again =\u003e PASS sub=userA\nPS C:\\Users\\Franciny Rojas\\Desktop\\crypto-research\\fast-jwt\u003e",
"id": "GHSA-rp9m-7r4c-75qg",
"modified": "2026-04-08T11:54:56Z",
"published": "2026-04-03T04:07:09Z",
"references": [
{
"type": "WEB",
"url": "https://github.com/nearform/fast-jwt/security/advisories/GHSA-rp9m-7r4c-75qg"
},
{
"type": "ADVISORY",
"url": "https://nvd.nist.gov/vuln/detail/CVE-2026-35039"
},
{
"type": "WEB",
"url": "https://github.com/nearform/fast-jwt/commit/de121056c6415b58770c60640881eaec67ac4ceb"
},
{
"type": "PACKAGE",
"url": "https://github.com/nearform/fast-jwt"
}
],
"schema_version": "1.4.0",
"severity": [
{
"score": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:N",
"type": "CVSS_V3"
}
],
"summary": "fast-jwt: Cache Confusion via cacheKeyBuilder Collisions Can Return Claims From a Different Token (Identity/Authorization Mixup)"
}
No mitigation information available for this CWE.
CAPEC-111: JSON Hijacking (aka JavaScript Hijacking)
An attacker targets a system that uses JavaScript Object Notation (JSON) as a transport mechanism between the client and the server (common in Web 2.0 systems using AJAX) to steal possibly confidential information transmitted from the server back to the client inside the JSON object by taking advantage of the loophole in the browser's Same Origin Policy that does not prohibit JavaScript from one website to be included and executed in the context of another website.
CAPEC-141: Cache Poisoning
An attacker exploits the functionality of cache technologies to cause specific data to be cached that aids the attackers' objectives. This describes any attack whereby an attacker places incorrect or harmful material in cache. The targeted cache can be an application's cache (e.g. a web browser cache) or a public cache (e.g. a DNS or ARP cache). Until the cache is refreshed, most applications or clients will treat the corrupted cache value as valid. This can lead to a wide range of exploits including redirecting web browsers towards sites that install malware and repeatedly incorrect calculations based on the incorrect value.
CAPEC-142: DNS Cache Poisoning
A domain name server translates a domain name (such as www.example.com) into an IP address that Internet hosts use to contact Internet resources. An adversary modifies a public DNS cache to cause certain names to resolve to incorrect addresses that the adversary specifies. The result is that client applications that rely upon the targeted cache for domain name resolution will be directed not to the actual address of the specified domain name but to some other address. Adversaries can use this to herd clients to sites that install malware on the victim's computer or to masquerade as part of a Pharming attack.
CAPEC-148: Content Spoofing
An adversary modifies content to make it contain something other than what the original content producer intended while keeping the apparent source of the content unchanged. The term content spoofing is most often used to describe modification of web pages hosted by a target to display the adversary's content instead of the owner's content. However, any content can be spoofed, including the content of email messages, file transfers, or the content of other network communication protocols. Content can be modified at the source (e.g. modifying the source file for a web page) or in transit (e.g. intercepting and modifying a message between the sender and recipient). Usually, the adversary will attempt to hide the fact that the content has been modified, but in some cases, such as with web site defacement, this is not necessary. Content Spoofing can lead to malware exposure, financial fraud (if the content governs financial transactions), privacy violations, and other unwanted outcomes.
CAPEC-218: Spoofing of UDDI/ebXML Messages
An attacker spoofs a UDDI, ebXML, or similar message in order to impersonate a service provider in an e-business transaction. UDDI, ebXML, and similar standards are used to identify businesses in e-business transactions. Among other things, they identify a particular participant, WSDL information for SOAP transactions, and supported communication protocols, including security protocols. By spoofing one of these messages an attacker could impersonate a legitimate business in a transaction or could manipulate the protocols used between a client and business. This could result in disclosure of sensitive information, loss of message integrity, or even financial fraud.
CAPEC-384: Application API Message Manipulation via Man-in-the-Middle
An attacker manipulates either egress or ingress data from a client within an application framework in order to change the content of messages. Performing this attack can allow the attacker to gain unauthorized privileges within the application, or conduct attacks such as phishing, deceptive strategies to spread malware, or traditional web-application attacks. The techniques require use of specialized software that allow the attacker to perform adversary-in-the-middle (CAPEC-94) communications between the web browser and the remote system. Despite the use of AiTH software, the attack is actually directed at the server, as the client is one node in a series of content brokers that pass information along to the application framework. Additionally, it is not true "Adversary-in-the-Middle" attack at the network layer, but an application-layer attack the root cause of which is the master applications trust in the integrity of code supplied by the client.
CAPEC-385: Transaction or Event Tampering via Application API Manipulation
An attacker hosts or joins an event or transaction within an application framework in order to change the content of messages or items that are being exchanged. Performing this attack allows the attacker to manipulate content in such a way as to produce messages or content that look authentic but may contain deceptive links, substitute one item or another, spoof an existing item and conduct a false exchange, or otherwise change the amounts or identity of what is being exchanged. The techniques require use of specialized software that allow the attacker to man-in-the-middle communications between the web browser and the remote system in order to change the content of various application elements. Often, items exchanged in game can be monetized via sales for coin, virtual dollars, etc. The purpose of the attack is for the attack to scam the victim by trapping the data packets involved the exchange and altering the integrity of the transfer process.
CAPEC-386: Application API Navigation Remapping
An attacker manipulates either egress or ingress data from a client within an application framework in order to change the destination and/or content of links/buttons displayed to a user within API messages. Performing this attack allows the attacker to manipulate content in such a way as to produce messages or content that looks authentic but contains links/buttons that point to an attacker controlled destination. Some applications make navigation remapping more difficult to detect because the actual HREF values of images, profile elements, and links/buttons are masked. One example would be to place an image in a user's photo gallery that when clicked upon redirected the user to an off-site location. Also, traditional web vulnerabilities (such as CSRF) can be constructed with remapped buttons or links. In some cases navigation remapping can be used for Phishing attacks or even means to artificially boost the page view, user site reputation, or click-fraud.
CAPEC-387: Navigation Remapping To Propagate Malicious Content
An adversary manipulates either egress or ingress data from a client within an application framework in order to change the content of messages and thereby circumvent the expected application logic.
CAPEC-388: Application API Button Hijacking
An attacker manipulates either egress or ingress data from a client within an application framework in order to change the destination and/or content of buttons displayed to a user within API messages. Performing this attack allows the attacker to manipulate content in such a way as to produce messages or content that looks authentic but contains buttons that point to an attacker controlled destination.
CAPEC-665: Exploitation of Thunderbolt Protection Flaws
An adversary leverages a firmware weakness within the Thunderbolt protocol, on a computing device to manipulate Thunderbolt controller firmware in order to exploit vulnerabilities in the implementation of authorization and verification schemes within Thunderbolt protection mechanisms. Upon gaining physical access to a target device, the adversary conducts high-level firmware manipulation of the victim Thunderbolt controller SPI (Serial Peripheral Interface) flash, through the use of a SPI Programing device and an external Thunderbolt device, typically as the target device is booting up. If successful, this allows the adversary to modify memory, subvert authentication mechanisms, spoof identities and content, and extract data and memory from the target device. Currently 7 major vulnerabilities exist within Thunderbolt protocol with 9 attack vectors as noted in the Execution Flow.
CAPEC-701: Browser in the Middle (BiTM)
An adversary exploits the inherent functionalities of a web browser, in order to establish an unnoticed remote desktop connection in the victim's browser to the adversary's system. The adversary must deploy a web client with a remote desktop session that the victim can access.