Skip to content

fix(security): Predictable global cache directory in /tmp enables symlink/hijack risks#1314

Open
tuanaiseo wants to merge 1 commit intovercel:mainfrom
tuanaiseo:contribai/fix/security/predictable-global-cache-directory-in-tm
Open

fix(security): Predictable global cache directory in /tmp enables symlink/hijack risks#1314
tuanaiseo wants to merge 1 commit intovercel:mainfrom
tuanaiseo:contribai/fix/security/predictable-global-cache-directory-in-tm

Conversation

@tuanaiseo
Copy link
Copy Markdown

Problem

The cache directory is a fixed, shared path (/tmp/ncc-cache). On multi-user systems this can be pre-created or manipulated by another user (symlink/hardlink attacks), potentially causing cache poisoning, unintended file writes, or data leakage between builds/users depending on how cache files are later written.

Severity: medium
File: src/utils/ncc-cache-dir.js

Solution

Use a per-user/per-project cache directory with secure creation semantics (e.g., fs.mkdtemp under user-owned base dir), enforce permissions (0700), and verify path is not a symlink before writing.

Changes

  • src/utils/ncc-cache-dir.js (modified)

Testing

  • Existing tests pass
  • Manual review completed
  • No new warnings/errors introduced

The cache directory is a fixed, shared path (`/tmp/ncc-cache`). On multi-user systems this can be pre-created or manipulated by another user (symlink/hardlink attacks), potentially causing cache poisoning, unintended file writes, or data leakage between builds/users depending on how cache files are later written.

Affected files: ncc-cache-dir.js

Signed-off-by: tuanaiseo <221258316+tuanaiseo@users.noreply.github.com>
@tuanaiseo tuanaiseo requested review from Timer and styfle as code owners April 2, 2026 23:51
@styfle styfle changed the title Security: Predictable global cache directory in /tmp enables symlink/hijack risks fix(security): Predictable global cache directory in /tmp enables symlink/hijack risks Apr 3, 2026
const path = require("path");

const cacheBase = process.env.XDG_CACHE_HOME || path.join(os.homedir(), ".cache");
const projectKey = crypto.createHash("sha256").update(process.cwd()).digest("hex").slice(0, 12);
Copy link
Copy Markdown
Member

@styfle styfle Apr 3, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
const projectKey = crypto.createHash("sha256").update(process.cwd()).digest("hex").slice(0, 12);
const projectKey = crypto.createHash("sha1").update(process.cwd()).digest("hex");

No reason to truncate. Just use a smaller hashing function if you don't need the entropy.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants