Jun 15, 2026·6 min read·21 visits
A type-confusion vulnerability in node-tmp version 0.2.6 allows path traversal checks to be bypassed using non-string options (such as arrays). This results in arbitrary file and directory creation outside the temporary workspace, potentially leading to unauthorized writes and host compromise.
A high-severity type-confusion path traversal vulnerability (CVE-2026-49982 / GHSA-7c78-jf6q-g5cm) exists in the node-tmp package version 0.2.6. The vulnerability allows remote attackers to bypass path validation checks by passing non-string data types such as Arrays or duck-typed Objects into options like prefix, postfix, or template. Because the library relies on the .includes() method without verifying the input type, standard array checks evaluate differently than string checks. Downstream string coercion subsequently restores the traversal sequence, allowing files and directories to be created outside the designated temporary directory root. This can result in arbitrary file writes and potential local file execution depending on application context.
The tmp library is a widely used Node.js utility designed to facilitate the secure generation of temporary files and directories. Applications routinely utilize this package to process untrusted uploads, cache session state, or parse ephemeral datasets. Because these operations occur within administrative directory structures, the library is responsible for ensuring that generated resources do not escape their assigned, isolated namespaces.
To prevent directory traversal attacks, version 0.2.6 of the library introduced an internal path validation guard named _assertPath. This guard is designed to audit incoming parameters—such as custom prefixes, postfixes, and path templates—and throw an exception if directory traversal sequences like .. are present. Despite this addition, the validation layer is critically weakened by a lack of input type enforcement.
Because the input validation assumes all arguments are primitive strings, it fails to account for alternative JavaScript data structures. If an application routes raw JSON bodies or complex query objects directly to tmp API interfaces, an attacker can submit non-string objects. This triggers a type-confusion state, allowing directory traversal sequences to bypass the protection routine while maintaining their functionality downstream in the operating system's filesystem layers.
The root cause of CVE-2026-49982 lies within the implementation of the _assertPath function and how JavaScript handles prototype method calls. In Node.js environments, web frameworks often convert input payloads into complex arrays or custom objects based on query parser configurations. When these structures are supplied to tmp.file(), they are evaluated against the validation logic in lib/tmp.js.
The vulnerable code executes path.includes("..") directly on the input argument. If the input is a primitive string containing ../, JavaScript invokes String.prototype.includes, which checks for the substring and correctly throws an error. However, if the input is an array (such as ['../escape']), JavaScript redirects the call to Array.prototype.includes. This array method performs an element-by-element equality check. Since the string '../escape' is not strictly equal to '..', the check returns false, and the execution continues.
Following validation, the library normalizes the options inside _generateTmpName. The components of the filename are placed into a container array and consolidated using Array.prototype.join(''). This join operation forces all sub-elements to undergo implicit string coercion. The array ['../escape'] stringifies back to '../escape'. When Node's native path.join() links the base directory with the coerced string, the traversal sequence resolves to the parent directory, allowing the boundaries of the safe folder to be escaped completely.
An analysis of the vulnerable codebase in version 0.2.6 reveals the following validation routines inside lib/tmp.js:
// lib/tmp.js:533-539 (Vulnerable version 0.2.6)
function _assertPath(path) {
// Bug: No type assertion is executed before calling .includes().
if (path.includes("..")) {
throw new Error("Relative value not allowed");
}
return path;
}The initialization routines consume the output of this function directly, without validating the output structure:
// lib/tmp.js:577-580
options.prefix = _isUndefined(options.prefix) ? '' : _assertPath(options.prefix);
options.postfix = _isUndefined(options.postfix) ? '' : _assertPath(options.postfix);The fix introduced in 0.2.7 addresses this directly by implementing a strict type-assertion pattern:
// lib/tmp.js:531-542 (Patched version 0.2.7)
function _assertPath(option, value) {
// Patch: Ensures the value is strictly a primitive string before validating content
if (typeof value !== 'string') {
throw new Error(`${option} option must be a string, got "${typeof value}".`);
}
if (value.includes("..")) {
throw new Error("Relative value not allowed");
}
return value;
}This patch completely mitigates the type-confusion attack vector. By enforcing that typeof value === 'string', arrays, duck-typed objects, buffers, or alternative payloads are immediately rejected. The method dispatch is guaranteed to bind to String.prototype.includes, executing the substring validation reliably.
Exploitation of CVE-2026-49982 is highly reliable and requires no authentication if the target application processes remote client inputs directly. In standard Express frameworks using parsed bodies or query arrays, input structures can be coerced to exploit this mechanism. For example, a POST request containing JSON arrays can bypass directory path sanitization.
// Standalone PoC demonstrating bypass with different payload styles
const tmp = require('tmp');
const path = require('path');
const fs = require('fs');
const baseDir = fs.mkdtempSync('/tmp/isolated-env-');
// Bypass vector 1: Using an array payload
try {
const res = tmp.fileSync({ tmpdir: baseDir, prefix: ['../hijack'] });
console.log('File successfully escaped to:', res.name);
res.removeCallback();
} catch (err) {
console.log('Blocked:', err.message);
}
// Bypass vector 2: Duck-typed object utilizing a customized toString mapping
try {
const res = tmp.fileSync({
tmpdir: baseDir,
prefix: { toString: () => '../complex-bypass', includes: () => false }
});
console.log('File successfully escaped to:', res.name);
res.removeCallback();
} catch (err) {
console.log('Blocked:', err.message);
}An attacker can use this behavior to generate file descriptors in administrative file trees such as webroots (/var/www/html/), user cron structures, or local user paths. If the server writes user-controlled values to the returned file paths, an attacker can overwrite critical scripts or inject a web shell, leading to unauthorized system control.
The impact of CVE-2026-49982 depends on how the application handles the temporary file reference after creation. If the application writes user-controlled text directly to the file descriptor provided by tmp, the attacker can achieve arbitrary file write capabilities. This allows the attacker to write data anywhere on the server's filesystem, limited only by the host process's active user permissions.
If the application creates directories rather than files, the path traversal allows attackers to pre-create workspace directories. This can lead to local privilege escalation or file manipulation vulnerabilities through symlink attacks, directory hijacking, or workspace modification.
The CVSS score is 8.2 (High) with a vector of CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:H/A:L. This score reflects the high impact on data integrity, as arbitrary file writes can modify the system configuration, while data confidentiality remains unaffected directly by this specific mechanism.
The primary resolution is to upgrade the tmp dependency to version 0.2.7 or above. This version implements strict string type checks on the prefix, postfix, and template fields. The upgrade is backward-compatible and does not require changes to normal application logic.
If upgrading is not immediately possible, you can implement type validation in your application code before invoking tmp functions. Enforcing primitive type validation ensures that complex input objects are rejected before they reach the library's validation checks.
// Manual type validation workaround
function safeTmpFile(options, callback) {
const fields = ['prefix', 'postfix', 'template'];
for (const field of fields) {
if (options[field] !== undefined && typeof options[field] !== 'string') {
throw new TypeError(`The ${field} option must be a primitive string`);
}
}
return tmp.file(options, callback);
}Additionally, you can configure Web Application Firewalls (WAFs) to inspect incoming API requests for multi-dimensional parameters (such as prefix[] or JSON representations using nested structures) directed at file management endpoints.
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:H/A:L| Product | Affected Versions | Fixed Version |
|---|---|---|
tmp raszi | = 0.2.6 | 0.2.7 |
| Attribute | Detail |
|---|---|
| CWE ID | CWE-20, CWE-22 |
| Attack Vector | Network |
| CVSS | 8.2 (High) |
| EPSS Score | 0.00447 |
| Impact | Integrity (High), Availability (Low) |
| Exploit Status | Proof of Concept (PoC) available |
| KEV Status | Not listed |
Improper limitation of a pathname to a restricted directory ('Path Traversal')
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.
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.
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.
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.
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.
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.