Skip to content

fix(subprocess): resolve executables against PATH not cwd on Windows; reject %VAR% paths - #1905

Draft
iankhou wants to merge 2 commits into
mainfrom
iankhou-windows-exec-resolution
Draft

fix(subprocess): resolve executables against PATH not cwd on Windows; reject %VAR% paths#1905
iankhou wants to merge 2 commits into
mainfrom
iankhou-windows-exec-resolution

Conversation

@iankhou

@iankhou iankhou commented Aug 26, 2026

Copy link
Copy Markdown
Contributor

Requires windows integ test verification

Follow-up to #1763 / #1849. Two Windows-specific hardening fixes to the shared subprocess module, plus a test that exercises the .cmd path.

Summary

  1. resolveExecutable() — on Windows a bare program name spawned without a shell is searched for in the working directory before PATH, so a file planted in a handed-over cloud assembly (e.g. docker.bat) could shadow the real binary. run()/runSync() now resolve the executable to an absolute PATH hit up front and refuse a name that is not on PATH rather than let the cwd satisfy it. POSIX is unchanged (execvp already searches PATH only); an explicit path (absolute or containing a separator) is honored verbatim.

  2. quoteShellPart() (toolkit-lib) — cmd.exe expands %VAR% even inside double quotes, and a cmd /c command line cannot reliably escape a percent (doubling only works in batch files). A discovered path carrying a %...% reference is now refused loudly instead of being silently rewritten (an env var spliced into the path).

  3. A Windows-only test that runs a .cmd shim with hostile arguments — the one path where cross-spawn's cmd.exe escaping is exercised (a plain .exe, as in every existing test, never is).

Testing

  • Unit tests for resolveExecutable
  • [pending] The .cmd hostile-args test that will be run with the Windows integ workflow.
  • %VAR% detection was verified in isolation; environment.test.ts runs in CI's Linux jest.

Checklist

  • Unit tests added/updated
  • Integration tests — Windows integ run required (pending)
  • No manual edits to generated files

By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license.

@github-actions

Copy link
Copy Markdown
Contributor

Dependency Review

✅ No vulnerabilities or license issues or OpenSSF Scorecard issues found.

Scanned Files

None

…s; reject %VAR% paths

Two Windows-specific hardening fixes to the shared subprocess module, plus a
test that actually exercises the .cmd path.

1. resolveExecutable(): on Windows a bare program name spawned without a shell
   is searched for in the cwd *before* PATH, so a file planted in a handed-over
   cloud assembly (e.g. docker.bat) could shadow the real binary. run()/runSync()
   now resolve the executable to an absolute PATH hit up front and refuse a name
   that is not on PATH rather than let the cwd satisfy it. POSIX is unchanged
   (execvp already searches PATH only); explicit paths are honored verbatim.

2. quoteShellPart() (toolkit-lib): cmd.exe expands %VAR% even inside double
   quotes and a `cmd /c` line cannot reliably escape a percent, so a discovered
   path carrying a %...% reference is now refused loudly instead of being
   silently rewritten.

3. Adds a Windows-only test that runs a real .cmd shim with hostile arguments —
   the one path where cross-spawn's cmd.exe escaping is exercised (a plain .exe
   never is).

NOTE: items 1 and 3 change Windows spawn behavior and must be validated by the
Windows integ tests; the resolveExecutable logic is unit-tested cross-platform
via a `platform` parameter.
@iankhou
iankhou force-pushed the iankhou-windows-exec-resolution branch from b334c08 to 9f440cb Compare August 26, 2026 20:27
@iankhou
iankhou deployed to no-approval August 26, 2026 20:28 — with GitHub Actions Active
@iankhou
iankhou deployed to no-approval August 26, 2026 20:50 — with GitHub Actions Active
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants