fast-jwt: Incomplete patch of CVE-2026-34950: Non-whitespace key-prefix re-enables RSA→HS256 algorithm confusion
### Summary The fix for CVE-2026-34950 (CVSS 9.1, released in v6.2.0) is **incomplete**. It adds `key.trim()` to the PEM-detection path in `src/crypto.js`, but `String.prototype.trim()` only strips characters classified as whitespace by the ECMAScript specification. The subsequent `^`-anchored regex (`/^-----BEGIN(?: (RSA))? PUBLIC KEY-----/`) still requires the PEM header at position 0 — so **any non-whitespace leading byte** (control chars, zero-width unicode, `#` comments, HTTP-style headers, PGP wrappers) bypasses detection and falls through to the HMAC verification path, using the RSA public key as the HMAC shared secret. Net result: the **exact same RSA→HS256 algorithm-confusion attack** the original CVE addressed is fully re-enabled with a slightly different leading byte. **Attack prerequisites are identical to CVE-2026-34950**: attacker knows the target's public RSA key (which is public by definition), and the target loads that key from a source whose content may have a non-whitespace prefix (DB column with corrupted encoding, YAML config with inline comment, copy-paste from formatted document, etc.). **Verified on fast-jwt@6.2.2 (latest as of 2026-04-23) with a 10-line PoC.** ### Details Post-patch code (`src/crypto.js`, lines ~74-171 in `performDetectPublicKeyAlgorithms`): ```js function performDetectPublicKeyAlgorithms(key) { const trimmedKey = key.trim() // <-- CVE-2026-34950 patch added this if (publicKeyPemMatcher.test(trimmedKey)) { // treat as RSA/EC public ke
- Products
- fast-jwt
- Affected versions
- Not specified
- Fixed versions
- 6.3.0
- CVEs
- CVE-2026-107722
- Confirmed fixed CVEs
- Not specified
- Updated in this feed
- 28 Oct 2026, 10:06 UTC · Revision 1
Source evidence
fast-jwt: Incomplete patch of CVE-2026-34950: Non-whitespace key-prefix re-enables RSA→HS256 algorithm confusion
core-osv · Original sourcePublished 8 Oct 2026, 22:02 UTC
### Summary The fix for CVE-2026-34950 (CVSS 9.1, released in v6.2.0) is **incomplete**. It adds `key.trim()` to the PEM-detection path in `src/crypto.js`, but `String.prototype.trim()` only strips characters classified as whitespace by the ECMAScript specification. The subsequent `^`-anchored regex (`/^-----BEGIN(?: (RSA))? PUBLIC KEY-----/`) still requires the PEM header at position 0 — so **any non-whitespace leading byte** (control chars, zero-width unicode, `#` comments, HTTP-style headers, PGP wrappers) bypasses detection and falls through to the HMAC verification path, using the RSA public key as the HMAC shared secret. Net result: the **exact same RSA→HS256 algorithm-confusion attack** the original CVE addressed is fully re-enabled with a slightly different leading byte. **Attack prerequisites are identical to CVE-2026-34950**: attacker knows the target's public RSA key (which is public by definition), and the target loads that key from a source whose content may have a non-whitespace prefix (DB column with corrupted encoding, YAML config with inline comment, copy-paste from formatted document, etc.). **Verified on fast-jwt@6.2.2 (latest as of 2026-04-23) with a 10-line PoC.** ### Details Post-patch code (`src/crypto.js`, lines ~74-171 in `performDetectPublicKeyAlgorithms`): ```js function performDetectPublicKeyAlgorithms(key) { const trimmedKey = key.trim() // <-- CVE-2026-34950 patch added this if (publicKeyPemMatcher.test(trimmedKey)) { // treat as RSA/EC public ke
osv:GHSA-ww5h-9m49-7xx4
fast-jwt
Fixed versions: 6.3.0
Complete source record
{
"id": "097aa1a498bd675023cd7b933d7376c85279f3c807113f661dbb47f887c78928",
"url": "https://osv.dev/vulnerability/GHSA-ww5h-9m49-7xx4",
"method": "structured",
"payload": {
"kind": "advisory",
"title": "fast-jwt: Incomplete patch of CVE-2026-34950: Non-whitespace key-prefix re-enables RSA→HS256 algorithm confusion",
"summary": "### Summary The fix for CVE-2026-34950 (CVSS 9.1, released in v6.2.0) is **incomplete**. It adds `key.trim()` to the PEM-detection path in `src/crypto.js`, but `String.prototype.trim()` only strips characters classified as whitespace by the ECMAScript specification. The subsequent `^`-anchored regex (`/^-----BEGIN(?: (RSA))? PUBLIC KEY-----/`) still requires the PEM header at position 0 — so **any non-whitespace leading byte** (control chars, zero-width unicode, `#` comments, HTTP-style headers, PGP wrappers) bypasses detection and falls through to the HMAC verification path, using the RSA public key as the HMAC shared secret. Net result: the **exact same RSA→HS256 algorithm-confusion attack** the original CVE addressed is fully re-enabled with a slightly different leading byte. **Attack prerequisites are identical to CVE-2026-34950**: attacker knows the target's public RSA key (which is public by definition), and the target loads that key from a source whose content may have a non-whitespace prefix (DB column with corrupted encoding, YAML config with inline comment, copy-paste from formatted document, etc.). **Verified on fast-jwt@6.2.2 (latest as of 2026-04-23) with a 10-line PoC.** ### Details Post-patch code (`src/crypto.js`, lines ~74-171 in `performDetectPublicKeyAlgorithms`): ```js function performDetectPublicKeyAlgorithms(key) { const trimmedKey = key.trim() // <-- CVE-2026-34950 patch added this if (publicKeyPemMatcher.test(trimmedKey)) { // treat as RSA/EC public ke",
"evidence": "osv:GHSA-ww5h-9m49-7xx4",
"products": [
{
"name": {
"value": "fast-jwt",
"evidence": "/affected/0/package/name"
},
"prerequisites": [],
"fixed_versions": [
{
"value": "6.3.0",
"evidence": "/affected/0/ranges"
}
],
"affected_versions": []
}
],
"severity": "critical",
"structured": {
"id": "GHSA-ww5h-9m49-7xx4",
"aliases": [
"CVE-2026-107722",
"GHSA-ww5h-9m49-7xx4"
],
"metrics": [
{
"type": "CVSS_V3",
"score": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H"
}
],
"affected": [
{
"ranges": [
{
"type": "SEMVER",
"events": [
{
"introduced": "6.2.0"
},
{
"fixed": "6.3.0"
}
]
}
],
"package": {
"name": "fast-jwt",
"purl": "pkg:npm/fast-jwt",
"ecosystem": "npm"
},
"database_specific": {
"source": "https://github.com/github/advisory-database/blob/main/advisories/github-reviewed/2026/10/GHSA-ww5h-9m49-7xx4/GHSA-ww5h-9m49-7xx4.json",
"last_known_affected_version_range": "<= 6.2.4"
}
}
],
"modified": "2026-10-08T22:15:05.895384054Z",
"provider": "osv",
"references": [
"https://github.com/nearform/fast-jwt/security/advisories/GHSA-ww5h-9m49-7xx4",
"https://github.com/nearform/fast-jwt/pull/632",
"https://github.com/nearform/fast-jwt/commit/d96bbc6c5336055a6dbfa318fdbab01197264cfa",
"https://github.com/nearform/fast-jwt",
"https://github.com/nearform/fast-jwt/releases/tag/v6.3.0"
],
"provider_metadata": {
"cwe_ids": [
"CWE-347"
],
"severity": "CRITICAL",
"github_reviewed": true,
"nvd_published_at": null,
"github_reviewed_at": "2026-10-08T22:02:07Z"
}
},
"related_cves": [
{
"value": "CVE-2026-107722",
"evidence": "/aliases"
}
],
"security_relevant": true,
"severity_evidence": "/database_specific/severity"
},
"source_id": "core-osv",
"document_id": 104810,
"published_at": "2026-10-08T22:02:07+00:00"
}