CVEReports
CVEReports

Automated vulnerability intelligence platform. Comprehensive reports for high-severity CVEs generated by AI.

Product

  • Home
  • Sitemap
  • RSS Feed

Company

  • About
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CVEReports. All rights reserved.

Made with love by Amit Schendel & Alon Barad



GHSA-QRV3-253H-G69C

GHSA-QRV3-253H-G69C: Path Traversal and Arbitrary Symlink Creation via configDependencies in pnpm

Amit Schendel
Amit Schendel
Senior Security Researcher

Jun 27, 2026·7 min read·14 visits

Executive Summary (TL;DR)

A path traversal vulnerability in pnpm's configDependencies handling allows malicious lockfiles to create arbitrary directories and symbolic links outside of node_modules, bypassing the execution boundaries of --ignore-scripts during package installation.

A high-severity path traversal vulnerability exists in the pnpm package manager. By crafting a malicious lockfile (pnpm-lock.yaml) with path traversal characters in the configDependencies block, an attacker can create arbitrary directories and symlinks outside the project's node_modules/.pnpm-config directory. This exploitation happens automatically during pnpm installation, even when executing with scripts disabled via the --ignore-scripts flag.

Vulnerability Overview & Attack Surface Analysis

The pnpm package manager utilizes a unique virtual store layout inside node_modules/.pnpm and manages global packages using hard links to minimize disk space consumption. To support environment-specific properties and isolated configuration setups, the pnpm lockfile format (pnpm-lock.yaml) implements a configDependencies section. Under standard operational conditions, these configurations are isolated under a dedicated subdirectory: node_modules/.pnpm-config.

Because the installer processes dependencies declared in local workspace lockfiles under the assumption that they represent validated states, the keys and version strings within this configuration section are parsed directly to build directory trees. When users clone and inspect open-source or third-party repositories, they run installation commands to configure local packages. The installation stage represents a significant security boundary because it executes code before manual inspection can occur.

To limit risks associated with third-party software, security frameworks and automated testing pipelines often enforce the --ignore-scripts flag during installation to block life-cycle script executions (e.g., preinstall, postinstall). However, this path traversal bypasses those blocks. Because the installation code path itself handles the generation of these directory hierarchies, directory creation and symbolic link mapping occur regardless of whether script execution is restricted or disabled.

Root Cause Analysis of Path Traversal

The root cause of this vulnerability lies in the lack of validation and sanitization of user-controlled parameters extracted from configDependencies during workspace setup. In vulnerable versions, pnpm reads the package names and version keys declared inside pnpm-lock.yaml and directly utilizes them to construct output filesystem paths using Node.js's standard utility function path.join.

The application constructs the output configuration workspace using a base path defined as const configModulesDir = path.join(opts.rootDir, 'node_modules/.pnpm-config'). When iterating over the keys in the dependency structure, pnpm evaluates path.join(configModulesDir, pkgName). Because Node.js's path.join resolves relative directory segments natively, any package name containing upward path traversal sequences (such as ../../) will escape the restricted base directory.

This behavior means that instead of creating directories and mapping links inside the protected node_modules/.pnpm-config directory, pnpm evaluates the destination path relative to the workspace root or the wider host filesystem depending on the number of traversal sequences used. The application then proceeds to execute the directory creation and symlink linkage (symlinkDir) using these resolved out-of-bounds target destinations, allowing arbitrary system structures to be modified or created based solely on the contents of the lockfile.

Code-Level Patch & Verification Analysis

The vulnerability was resolved by introducing explicit strict validations within the package installer's parsing flow. The fix, implemented in commit 352ae489f1b14ffdc19d2c6eacb1b06b098c2ddc, adds verification checks that validate both the configuration names and versions before any path processing or folder creation functions are invoked.

Specifically, the patch enforces validation in normalizeConfigDeps.ts using two new assertion files: assertValidConfigDepName.ts and assertValidConfigDepVersion.ts. Below is the logical implementation introduced to validate names:

// config/deps-installer/src/assertValidConfigDepName.ts
import { PnpmError } from '@pnpm/error'
import validateNpmPackageName from 'validate-npm-package-name'
 
export function assertValidConfigDepName (name: string): void {
  // Verify that the dependency name conforms to legitimate npm package name standards
  if (!validateNpmPackageName(name).validForOldPackages) {
    throw new PnpmError(
      'INVALID_DEPENDENCY_NAME',
      `The configDependencies in pnpm-workspace.yaml contains a dependency with an invalid name: ${JSON.stringify(name)}`,
      {
        hint: 'A dependency name must be a valid npm package name — a single `name` or `@scope/name` consisting of URL-friendly characters, with no leading `.` or `_`, and not equal to reserved names such as `node_modules`.',
      }
    )
  }
}

Additionally, the patch enforces that the configuration versions match exact semantic version formats (semver) to prevent an attacker from nesting directory traversal sequences in the version fields. This validation prevents attackers from exploiting variables used to organize the virtual store folders:

// config/deps-installer/src/assertValidConfigDepVersion.ts
import { PnpmError } from '@pnpm/error'
import semver from 'semver'
 
export function assertValidConfigDepVersion (name: string, version: string): void {
  // Block non-semver compliant characters (preventing traversal inside version strings)
  if (semver.valid(version) == null) {
    throw new PnpmError(
      'INVALID_CONFIG_DEP_VERSION',
      `The config dependency "${name}" has an invalid version "${version}"`,
      { hint: 'A config dependency version must be an exact semver version.' }
    )
  }
}

These checks guarantee that characters like . and / cannot be leveraged inside configuration dependency identifiers, thereby resolving the path traversal vulnerability. The fix is considered complete because it restricts inputs to safe, standardized schemas (npm package names and SemVer specs) before they reach any filesystem sink.

Exploitation Mechanics & Payload Engineering

An attacker targets this vulnerability by modifying a project's pnpm-lock.yaml file to inject path traversal structures into the keys mapped within the configDependencies block. The target project is then uploaded to a version control hosting service or distributed through standard channels, waiting for a victim or automated system to run an installation command.

importers:
  .:
    configDependencies:
      legit-config-dep:
        specifier: '1.0.0'
        version: '1.0.0'
      '../../PWNED_CFGDEP':
        specifier: '1.0.0'
        version: '1.0.0'

When a victim clones the repository and runs pnpm install, the installer parses the configuration structures and triggers path resolution. This execution path is represented by the following logical process flow:

Once the path resolution completes, the installer executes filesystem changes to map the cache directory to the local folder. If an attacker directs the path traversal to critical targets, they can create and link to folders that manipulate or overlay development settings, build configurations, or localized tooling directories.

Threat Landscape & Impact Assessment

The impact of this vulnerability is significant for multi-tenant CI/CD systems, automated analysis sandboxes, and developer workstations. In modern software engineering workflows, testing pipelines pull external code and run pnpm install automatically to construct test environments. Even when administrators disable post-install scripting mechanisms, the creation of arbitrary directories and symlinks still proceeds because it occurs inside pnpm's core binary routines.

Because the CVSS vector is rated as CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:N/I:H/A:L (CVSS Base Score: 8.3), the exploitation of this vulnerability has direct implications for integrity. The Scope Change (S:C) metric is particularly important: it means pnpm can write symbolic links outside of its designated sandbox (the workspace's node_modules directory), potentially affecting parent directories or system-wide configuration folders.

An attacker can utilize this primitive to execute symbolic link overwriting attacks, targeting adjacent folders in shared CI/CD agents or placing malicious symlinks that point to sensitive files. This can lead to local configuration hijacking or unauthorized file writing across build steps, depending on the permissions of the user execution context under which the installer is running.

Detection, Remediation, and Defense-in-Depth

Organizations should prioritize upgrading global and local pnpm installations. To secure systems running active workflows, update the package manager to the designated patched versions: version 10.34.4 or later for the v10 release branch, and version 11.8.0 or later for the v11 release branch.

Security teams can identify potential exploitation attempts in existing repositories by scanning lockfiles for structural path traversal sequences. Using standard command-line tools, administrators can audit codebase histories to detect anomalous entries within the target blocks:

grep -E "configDependencies:" -A 10 pnpm-lock.yaml | grep -E "\.\./"

As a defense-in-depth measure, automated build environments and CI systems should enforce strict engine constraints in project settings, preventing local execution on insecure pnpm runtimes. This configuration can be formalized in the project's package.json file to block installation attempts if an obsolete version is detected:

"engines": {
  "pnpm": ">=11.8.0"
}

Official Patches

pnpmFix patch commit introduced to validate configDependencies
pnpmRelease notes for version 11.8.0
pnpmRelease notes for version 10.34.4

Fix Analysis (1)

Technical Appendix

CVSS Score
8.3/ 10
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:N/I:H/A:L

Affected Systems

pnpm package manager for Node.js

Affected Versions Detail

Product
Affected Versions
Fixed Version
pnpm
pnpm
>= 0 < 10.34.410.34.4
pnpm
pnpm
>= 11.0.0 < 11.8.011.8.0
AttributeDetail
CWE IDCWE-22
Attack VectorNetwork (AV:N)
CVSS v3.1 Score8.3
EPSS ScoreN/A
ImpactIntegrity (High)
Exploit StatusProof of Concept (PoC) Available
KEV StatusNot Listed

MITRE ATT&CK Mapping

T1190Exploit Public-Facing Application
Initial Access
T1036Masquerading
Defense Evasion
T1222.002File and Directory Permissions Modification: Linux and Mac Permissions
Defense Evasion
T1059Command and Scripting Interpreter
Execution
CWE-22
Improper Limitation of a Pathname to a Restricted Directory ('Path Traversal')

The software uses external input to construct a pathname that is intended to identify a file or directory that is located beneath a restricted parent directory, but the software does not properly neutralize special elements within the pathname that can cause the pathname to resolve to a location outside of the restricted directory.

Known Exploits & Detection

GitHub Security AdvisoryExploit methodology and execution summary detail showing the traversal behavior of configuration installer keys.

Vulnerability Timeline

Vulnerability fixed internally under commit 352ae48
2026-06-18
Advisory publicly published to GitHub Security Advisory Database
2026-06-27

References & Sources

  • [1]GitHub Security Advisory GHSA-QRV3-253H-G69C
  • [2]pnpm Project Repository
  • [3]OSV Vulnerability Record

Attack Flow Diagram

Press enter or space to select a node. You can then use the arrow keys to move the node around. Press delete to remove it and escape to cancel.
Press enter or space to select an edge. You can then press delete to remove it or escape to cancel.

More Reports

•1 day ago•CVE-2026-54068
5.9

CVE-2026-54068: Unauthenticated Server-Side Template Injection and SQLite Exfiltration in SiYuan PKM

An authentication bypass in the SiYuan personal knowledge management system before version 3.7.0 exposes a dynamic icon rendering endpoint. This endpoint processes client-supplied Go template directives. By submitting a crafted request, an unauthenticated remote attacker can leverage registered database template functions to execute arbitrary read-only SQL queries and exfiltrate workspace contents.

Amit Schendel
Amit Schendel
12 views•5 min read
•1 day ago•CVE-2026-54069
9.1

CVE-2026-54069: Authentication Bypass in SiYuan Note via Origin Header Spoofing

CVE-2026-54069 is a critical authentication bypass vulnerability in the SiYuan Note personal knowledge management system. The flaw is located in the HTTP server's middleware handling API authorization, which unconditionally trusts requests carrying a 'chrome-extension://' scheme in the Origin HTTP header, granting administrative access without validating API tokens.

Alon Barad
Alon Barad
10 views•5 min read
•2 days ago•CVE-2026-54089
9.1

CVE-2026-54089: Authentication Bypass by Spoofing in File Browser

CVE-2026-54089 is a critical authentication bypass vulnerability in File Browser affecting instances configured with proxy-based authentication. An unauthenticated remote attacker with direct network access can impersonate arbitrary users or register new accounts by spoofing configured HTTP headers.

Amit Schendel
Amit Schendel
8 views•7 min read
•2 days ago•GHSA-99J7-FHR2-XFJ4
10.0

GHSA-99J7-FHR2-XFJ4: Malicious Remote Code Execution Payload in 'exploration' Cargo Crate

The malicious Cargo package 'exploration' was uploaded to the crates.io registry. During compilation or package import, the crate executes code designed to establish an outbound TCP/HTTP connection, download an external second-stage binary, and execute the binary locally on the host machine. This creates an unauthenticated remote code execution vector impacting developer environments and continuous integration pipelines.

Amit Schendel
Amit Schendel
11 views•6 min read
•2 days ago•CVE-2026-54088
9.3

CVE-2026-54088: Pre-Authentication Remote Code Execution in File Browser Hook Authentication

CVE-2026-54088 is a critical command injection vulnerability in File Browser prior to version 2.63.6. When Hook Authentication is enabled, the application interpolates unsanitized credentials into a shell command, allowing unauthenticated remote code execution.

Alon Barad
Alon Barad
9 views•6 min read
•2 days ago•GHSA-QV4M-M73M-8HJ7
8.8

GHSA-qv4m-m73m-8hj7: Authenticated Arbitrary File Upload leading to Remote Code Execution in NotrinosERP

An authenticated remote code execution vulnerability exists in NotrinosERP (versions up to and including 1.0.0) within the Human Resource Management (HRM) module. Users with employee management permissions can upload arbitrary file types, including PHP scripts, which are written directly to a web-accessible directory. This allows for arbitrary code execution in the context of the web-server user.

Alon Barad
Alon Barad
8 views•6 min read