{"id":"GHSA-q6j5-fjx5-2mc3","summary":"pnpm Has an Integrity Check Bypass via Missing Lockfile Integrity Field","details":"## Summary\n\npnpm's tarball extraction worker skips integrity verification when the `integrity` field is absent from the lockfile resolution. If an attacker can both modify `pnpm-lock.yaml` to remove the `integrity:` field and cause the referenced registry URL to serve altered package content, `pnpm install --frozen-lockfile` can install the altered package without an integrity error. npm's `npm ci` enforces integrity by default; pnpm's behavior of silently skipping verification is a pnpm-specific fail-open gap.\n\n## Vulnerability Details\n\nThe `addTarballToStore` function in `worker/src/start.ts` (lines 189-204) checks `if (integrity)` before verifying the tarball hash. The `TarballResolution` type declares `integrity` as optional (`integrity?: string`). When the lockfile omits the `integrity` field, the guard evaluates to `false`, skipping hash verification entirely. The worker then computes a new hash from the unverified content and stores it as legitimate.\n\n```typescript\n// worker/src/start.ts:189-204\nfunction addTarballToStore ({ buffer, storeDir, integrity, ... }: TarballExtractMessage) {\n  if (integrity) {           // false when integrity is undefined\n    const { algorithm, hexDigest } = parseIntegrity(integrity)\n    const calculatedHash = crypto.hash(algorithm, buffer, 'hex')\n    if (calculatedHash !== hexDigest) {\n      return { status: 'error', error: { type: 'integrity_validation_failed', ... } }\n    }\n  }\n  return {\n    status: 'success',\n    value: { integrity: integrity ?? calcIntegrity(buffer) },\n  }\n}\n```\n\n## Proof of Concept\n\n```bash\nbash autofyn_audit/exploits/vuln1_integrity_bypass/exploit.sh\n# Publishes a package, generates lockfile, republishes tampered version,\n# strips integrity field, re-runs install --frozen-lockfile.\n# Result: PASS -- tampered package installed without integrity error.\n```\n\n## Impact\n\nSupply chain compromise in environments where an attacker can both alter the lockfile and cause the referenced registry URL to serve altered package content. The `--frozen-lockfile` flag does not fail closed when the integrity field is missing.\n\n## Suggested Remediation\n\nRequire an `integrity` field for remote tarball resolutions. Change the `if (integrity)` guard to fail when integrity is absent for non-local packages. When `--frozen-lockfile` is active, reject lockfile entries that lack integrity for remote packages.\n\n---\n\n\u003e Discovered by [AutoFyn](https://github.com/SignalPilot-Labs/AutoFyn)\n\u003e Full audit report: [audit_report.md](https://github.com/tempcollab/pnpm/blob/main/autofyn_audit/audit_report.md)\n\u003e Exploit script: [exploit.sh](https://github.com/tempcollab/pnpm/blob/main/autofyn_audit/exploits/vuln1_integrity_bypass/exploit.sh)","aliases":["CVE-2026-50021"],"modified":"2026-06-26T23:11:29.613886Z","published":"2026-06-26T22:53:01Z","database_specific":{"severity":"MODERATE","github_reviewed":true,"github_reviewed_at":"2026-06-26T22:53:01Z","nvd_published_at":"2026-06-25T18:16:39Z","cwe_ids":["CWE-354"]},"references":[{"type":"WEB","url":"https://github.com/pnpm/pnpm/security/advisories/GHSA-q6j5-fjx5-2mc3"},{"type":"ADVISORY","url":"https://nvd.nist.gov/vuln/detail/CVE-2026-50021"},{"type":"PACKAGE","url":"https://github.com/pnpm/pnpm"}],"affected":[{"package":{"name":"pnpm","ecosystem":"npm","purl":"pkg:npm/pnpm"},"ranges":[{"type":"SEMVER","events":[{"introduced":"11.0.0"},{"fixed":"11.4.0"}]}],"database_specific":{"source":"https://github.com/github/advisory-database/blob/main/advisories/github-reviewed/2026/06/GHSA-q6j5-fjx5-2mc3/GHSA-q6j5-fjx5-2mc3.json"}},{"package":{"name":"pnpm","ecosystem":"npm","purl":"pkg:npm/pnpm"},"ranges":[{"type":"SEMVER","events":[{"introduced":"0"},{"fixed":"10.34.1"}]}],"database_specific":{"source":"https://github.com/github/advisory-database/blob/main/advisories/github-reviewed/2026/06/GHSA-q6j5-fjx5-2mc3/GHSA-q6j5-fjx5-2mc3.json"}}],"schema_version":"1.9.0","severity":[{"type":"CVSS_V3","score":"CVSS:3.1/AV:N/AC:H/PR:L/UI:N/S:U/C:H/I:H/A:N"}]}