Skip to content

fix(windows): document MotW unblock, surface config errors, fix taskkill quoting#702

Open
ShauryaaSharma wants to merge 2 commits into
DeusData:mainfrom
ShauryaaSharma:fix/windows-installer-697
Open

fix(windows): document MotW unblock, surface config errors, fix taskkill quoting#702
ShauryaaSharma wants to merge 2 commits into
DeusData:mainfrom
ShauryaaSharma:fix/windows-installer-697

Conversation

@ShauryaaSharma

Copy link
Copy Markdown
Contributor

Fixes #697

What does this PR do?

Addresses all three root causes reported in #697, where install.ps1 reports success but leaves the MCP server unconfigured on Windows.

1. Mark-of-the-Web (README)
Invoke-WebRequest stamps downloaded files with a Zone Identifier that causes PowerShell to refuse execution. The README Windows install steps now include an explicit Unblock-File .\install.ps1 step (both the quick-install
block and the manual-install block), with a note on -ExecutionPolicy Bypass as a fallback.

2. Swallowed config errors (install.ps1)
The try/catch around & $Dest install -y does not catch non-terminating exits. A non-zero exit code was silently swallowed and the script printed "Done!" regardless. The block now checks $LASTEXITCODE after the call and, if non-zero, prints a red error message and exits 1 so the failure is visible.

3. taskkill /FI quoting (compat_fs.c)
cbm_exec_no_shell on Windows used _spawnvp, whose MinGW CRT implementation does not quote arguments that contain spaces when building the CreateProcess command line. The filter value "IMAGENAME eq codebase-memory-mcp.exe" was passed as three bare tokens, causing taskkill to print ERROR: Invalid argument/option - 'eq' on every invocation.

cbm_exec_no_shell now uses CreateProcess directly with a new cbm_build_cmdline helper that produces a properly-quoted command line following the MSVC/Windows CRT convention (arguments with spaces, tabs, or embedded double-quotes are wrapped in "…", with backslashes before a closing quote doubled). The POSIX path (fork/execvp) is unchanged.

CreateProcess replaces _spawnvp at the same call site with the same security surface, no new subprocess capability is introduced, and no update to scripts/security-allowlist.txt is required.

Checklist

  • Every commit is signed off (git commit -s) — required, CI rejects unsigned commits (DCO, see CONTRIBUTING.md)
  • Tests pass locally (make -f Makefile.cbm test), full suite requires ASan + 64-bit toolchain unavailable in this environment; the cbm_build_cmdline quoting logic and cbm_exec_no_shell live-exec paths were verified with a targeted harness compiled under MinGW GCC 6.3 (7 quoting cases + 3 live CreateProcess exec cases, all passing)
  • Lint passes (make -f Makefile.cbm lint-ci) — clang-tidy unavailable in this environment; please run in CI
  • New behavior is covered by a test (reproduce-first for bug fixes) no test added to tests/; the fix is in the installer script and a Windows-only code path not currently covered by the test suite.

@ShauryaaSharma ShauryaaSharma requested a review from DeusData as a code owner June 29, 2026 18:17
@ShauryaaSharma ShauryaaSharma force-pushed the fix/windows-installer-697 branch 2 times, most recently from 32af727 to 471bb4d Compare June 29, 2026 18:20
@ShauryaaSharma ShauryaaSharma force-pushed the fix/windows-installer-697 branch from ad18db5 to be0c1c8 Compare June 29, 2026 19:20
@DeusData DeusData added bug Something isn't working windows Windows-specific issues editor/integration Editor compatibility and CLI integration ux/behavior Display bugs, docs, adoption UX priority/high Needs near-term maintainer attention; high-impact bug, regression, safety issue, or release blocker. labels Jun 29, 2026
@DeusData

DeusData commented Jul 1, 2026

Copy link
Copy Markdown
Owner

Huge thanks for opening this PR and for the work you put into it.

The maintainer shop is currently full, so this may sit for a bit before it gets a proper review. We will come back to this as soon as possible with real feedback; I wanted to make sure it did not sit unacknowledged in the meantime.

@DeusData

DeusData commented Jul 1, 2026

Copy link
Copy Markdown
Owner

Thanks for the clear Windows fix. Before this can move forward, could you add a regression guard for the Windows quoting/config failure, or explain why it cannot live in the suite? This touches install.ps1 and Windows process spawning, so we’ll also need CI/maintainer verification around those paths.

@ShauryaaSharma ShauryaaSharma force-pushed the fix/windows-installer-697 branch 2 times, most recently from 2ad6b24 to 8a72685 Compare July 2, 2026 05:26
@ShauryaaSharma

Copy link
Copy Markdown
Contributor Author

Hey, Thanks for the steer!

So, you were right to call out my "can't really test this" note. I was wrong, I'd figured the bug only really shows itself once taskkill actually chokes on the args, which would've meant spinning up a live Windows process to catch it. But when I went back and actually looked, the real reason is just the command-line building in cbm_build_cmdline, and that thing is pure string logic, no OS calls, totally deterministic. So there was nothing stopping me from testing it directly. Sorry about that.

Pushed an update just now, rebased onto main first (went through clean), then added the guard.

@ShauryaaSharma

Copy link
Copy Markdown
Contributor Author

The one thing I didn't write a test for is the install.ps1 config-error fix.

There's no Pester setup anywhere in the repo and install.ps1 never actually runs in CI (it just gets zipped for release), so testing it properly would mean a whole new CI job plus reworking the installer so the config step can be driven in isolation.

I'm glad to pick it up as a follow-up if you'd like. I did check the exit 1 behavior on the config failure by hand for now.

Let me know what you think!

@ShauryaaSharma

Copy link
Copy Markdown
Contributor Author

Rest, here is what i have done as of now.

I exposed the command-line builder (cbm_build_cmdline) through a new compat_fs_internal.h, the same trick system_info_internal.h already uses to make internal helpers reachable from tests, and dropped a few tests into test_security.c. The main test nails the exact #697 case:

{"taskkill","/FI","IMAGENAME eq codebase-memory-mcp.exe"}
  ->  taskkill /FI "IMAGENAME eq codebase-memory-mcp.exe"

so that the IMAGENAME filter has to survive as one quoted token instead of the three bare words that had taskkill tripping over eq. I threw in the fiddly quoting cases too (empty args, embedded quotes, trailing backslashes). And while I was in test_security.c I noticed the cbm_exec_no_shell tests were all behind #ifndef _WIN32, so the Windows spawn path had no coverage at all, I filled that gap with a couple of live CreateProcessW runs. All of these tests ride on the windows-latest job that's already in _test.yml, so there's nothing new needed on the CI side.

…uoting

- README: document Unblock-File step for Mark-of-the-Web restriction
  that prevents install.ps1 from running after Invoke-WebRequest
- install.ps1: check $LASTEXITCODE after `install -y` and exit 1 with
  a visible error when zero agents are configured, instead of silently
  printing "Done!"
- compat_fs.c: replace _spawnvp with CreateProcess in cbm_exec_no_shell
  on Windows; add cbm_build_cmdline that properly quotes argv arguments
  containing spaces (MSVC convention), fixing the taskkill /FI filter
  that was splitting "IMAGENAME eq codebase-memory-mcp.exe" into three
  bare tokens and printing an invalid-argument error

Fixes DeusData#697

Signed-off-by: ShauryaaSharma <shauryasofficial27@gmail.com>
Expose cbm_build_cmdline via compat_fs_internal.h (following the
system_info_internal.h "exposed for testing" pattern) and add
Windows-only tests in test_security.c that pin the MSVC command-line
quoting convention:

  - the exact DeusData#697 case: {"taskkill","/FI","IMAGENAME eq ...exe"} must
    become taskkill /FI "IMAGENAME eq ...exe" (one quoted token, not
    three bare words that made taskkill print "Invalid argument - eq")
  - unquoted simple args, empty-arg -> "", embedded-quote escaping,
    trailing-backslash doubling before the closing quote

Also fills in the previously-empty Windows side of the
cbm_exec_no_shell suite with live CreateProcessW exec tests
(cmd /c exit N). These run in CI on the existing windows-latest test
job, so the Windows spawn path is now covered rather than
#ifndef _WIN32-excluded.

The quoting logic is pure and deterministic; the seven cmdline cases
were validated against the production algorithm under MinGW GCC 6.3.

Signed-off-by: ShauryaaSharma <shauryasofficial27@gmail.com>
@ShauryaaSharma ShauryaaSharma force-pushed the fix/windows-installer-697 branch from 8a72685 to ec80e7d Compare July 2, 2026 17:17
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working editor/integration Editor compatibility and CLI integration priority/high Needs near-term maintainer attention; high-impact bug, regression, safety issue, or release blocker. ux/behavior Display bugs, docs, adoption UX windows Windows-specific issues

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Windows: install.ps1 reports success but leaves MCP server unregistered (MotW + swallowed config errors + malformed taskkill)

2 participants