paperclipai/paperclip · error

Verified runtime executable path is invalid

Error message

Verified runtime executable path is invalid

What it means

On macOS there is no /proc fd-descriptor handoff, so verifiedRuntimeExecutable() requires the env value to equal the absolute, normalized process.execPath exactly: the Rust supervisor materializes the authenticated runtime as a private read-only executable launched from that exact pathname. Any deviation is rejected.

Source

Thrown at packages/paperclip-runner/src/drivers/acpx/verified-runtime-executable.ts:38

  platform: NodeJS.Platform = process.platform,
  _currentPid: number = process.pid,
  fallback: string = process.execPath,
): string {
  const configured = environment[VERIFIED_RUNTIME_EXECUTABLE_ENV];
  if (configured === undefined) return fallback;

  if (platform === "linux") {
    if (/^\/proc\/self\/fd\/[0-9]+$/.test(configured)) return configured;
    throw new Error("Verified runtime executable descriptor is invalid");
  }

  if (platform === "darwin") {
    if (
      !isAbsolute(fallback) ||
      resolve(fallback) !== fallback ||
      configured !== fallback
    ) {
      throw new Error("Verified runtime executable path is invalid");
    }
    // The Rust supervisor materializes the authenticated runtime as a private,
    // read-only executable and starts this process from that exact pathname.
    // Descendants may inherit the handoff variable, but they cannot nominate a
    // different absolute path and have it treated as verified.
    return fallback;
  }

  throw new Error(
    "Verified runtime executable is unsupported on this platform",
  );
}

/**
 * Project the current verified runtime into a chosen child descriptor. The
 * caller must place sourceFd at child targetFd in its stdio table.
 */
export function verifiedRuntimeExecutableHandoff(

View on GitHub (pinned to 01ad858492)

Solutions

  1. Launch the runner exactly as the supervisor does, from the materialized executable's canonical absolute path
  2. Unset PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE to fall back to process.execPath if no verified handoff applies
  3. Avoid symlinks/relative paths when starting the runner; use the resolved absolute path
  4. Do not manually export the env var on macOS; let the supervisor set it

Example fix

// before
env.PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE = "/opt/bin/runner"; // differs from execPath
// after
delete env.PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE; // fall back to process.execPath
Defensive patterns

Strategy: validation

Validate before calling

const v = process.env.PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE;
if (v !== undefined && process.platform === "darwin" &&
    (v !== process.execPath || path.resolve(process.execPath) !== process.execPath)) {
  delete process.env.PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE;
}

Type guard

function isValidDarwinHandoff(v, fallback) {
  return path.isAbsolute(fallback) && path.resolve(fallback) === fallback && v === fallback;
}

Try / catch

try {
  const exe = verifiedRuntimeExecutable();
} catch (err) {
  if (err.message === "Verified runtime executable path is invalid") {
    const { [VERIFIED_RUNTIME_EXECUTABLE_ENV]: _omit, ...clean } = process.env;
    return verifiedRuntimeExecutable(clean);
  }
  throw err;
}

Prevention

When it happens

Trigger: On darwin, calling verifiedRuntimeExecutable() when PAPERCLIP_VERIFIED_RUNTIME_EXECUTABLE differs from process.execPath, when execPath is not absolute, or when it contains non-normalized segments (resolve(execPath) !== execPath), e.g. after re-exec or a symlinked launch path.

Common situations: Launching the runner via a symlink or relative path so execPath differs from the supervisor's canonical path; manually setting the env var to a different binary; a tool re-execing node with a changed execPath.

Understand the failure class

Background: "is not a valid" / "Invalid ... value" environment variable errors: how libraries validate env vars and what to do when they reject yours — this error's family across 48 libraries.

Related errors


AI-assisted analysis of paperclipai/paperclip@01ad858492 (2026-09-10). Data as JSON: /api/errors/32050d335fa6749f. Report an issue: GitHub.