Rewrite the Windows Sandbox one-shot path onto an authenticated protocol (Phase 1)#577
Rewrite the Windows Sandbox one-shot path onto an authenticated protocol (Phase 1)#577MGudgin wants to merge 1 commit into
Conversation
dhoehna
left a comment
There was a problem hiding this comment.
Looked through the comments and code.
In addition to my comments I am concerned with the amount of in-code comments. Many comment blocks explain the code increasing the risk future developers will forget to update the comment and the code.
Because we need to get this out in a certain time frame I will not block the PR on comment length of quality. In the future please keep the length in mind.
b071f19 to
be48466
Compare
9d5d7e5 to
e3ccb02
Compare
60410fb to
e10515e
Compare
22cfc41 to
d140ea9
Compare
Comments heavily trimmed. |
d140ea9 to
daa4c4a
Compare
daa4c4a to
153e927
Compare
There was a problem hiding this comment.
Pull request overview
Reworks the Windows Sandbox one-shot execution path to use a new windows_sandbox_lifecycle crate with an authenticated host↔guest protocol, removing the legacy daemon-driven one-shot runner and aligning docs/tests with the “fresh VM per invocation” model.
Changes:
- Introduces
windows_sandbox_lifecycle(one-shotWindowsSandboxRunner+ VM lifecycle/policy/teardown primitives) and wiresmxc_enginedispatch to it. - Adds authenticated TCP channel setup (per-launch nonce + channel role) and a control-channel preamble; updates the guest agent accordingly (firewall + job-object cleanup).
- Updates Windows Sandbox docs and test runners/examples to reflect the new one-shot behavior and removes daemon pre-spawn assumptions.
Show a summary per file
| File | Description |
|---|---|
| tests/scripts/run_windows_sandbox_one_shot_tests.ps1 | Updates manual E2E runner for fresh-VM-per-test (but still has an elevated DISM preflight). |
| tests/scripts/README.md | Renames/clarifies Windows Sandbox script entry for one-shot suite. |
| tests/examples/10_windows_sandbox_network_isolated.json | Switches example command away from requiring host Python. |
| tests/examples/09_windows_sandbox_hello_world.json | Switches example command away from requiring host Python. |
| tests/configs/basic_windows_sandbox.json | Switches basic config away from requiring host Python. |
| src/testing/wxc_e2e_tests/tests/e2e_windows.rs | Removes daemon dependency from the Windows Sandbox E2E path. |
| src/core/wxc_common/src/models.rs | Marks WindowsSandboxConfig fields as legacy/ignored in one-shot. |
| src/core/mxc_engine/src/run.rs | Routes Windows Sandbox containment to windows_sandbox_lifecycle::WindowsSandboxRunner and warns on non-default legacy settings. |
| src/core/mxc_engine/Cargo.toml | Swaps Windows dependency from windows_sandbox_common to windows_sandbox_lifecycle. |
| src/Cargo.toml | Adds lifecycle crate to the workspace and removes the daemon member for this phase. |
| src/Cargo.lock | Updates dependency graph for new lifecycle crate and guest changes. |
| src/backends/windows_sandbox/lifecycle/Cargo.toml | Defines the new lifecycle crate and its dependencies. |
| src/backends/windows_sandbox/lifecycle/src/lib.rs | Exposes lifecycle modules and re-exports the one-shot runner on Windows. |
| src/backends/windows_sandbox/lifecycle/src/one_shot.rs | Implements the disposable one-shot ScriptRunner orchestration. |
| src/backends/windows_sandbox/lifecycle/src/policy.rs | Validates filesystem/network policy and maps to .wsb shares or rejects. |
| src/backends/windows_sandbox/lifecycle/src/vm.rs | Generates .wsb + bootstrap, launches Sandbox VM, captures ownership proof, and tears down. |
| src/backends/windows_sandbox/lifecycle/src/rendezvous.rs | Polls rendezvous file for guest ip:port and cleans up between runs. |
| src/backends/windows_sandbox/lifecycle/src/ipc_exec.rs | Adds framed exec protocol utilities (for upcoming state-aware daemon path). |
| src/backends/windows_sandbox/lifecycle/src/error.rs | Adds typed one-shot error mapping to ScriptResponse phases. |
| src/backends/windows_sandbox/lifecycle/src/control_plane/os.rs | Adds Win32 primitives for DACL, process identity, and named mutex locks. |
| src/backends/windows_sandbox/lifecycle/src/constants.rs | Centralizes daemon binary name constant (for Phase 2). |
| src/backends/windows_sandbox/lifecycle/src/bridge.rs | Implements authenticated 4-channel guest connection, preamble validation, and stdio/control relays. |
| src/backends/windows_sandbox/lifecycle/src/teardown.rs | Implements ownership-scoped teardown + marker-based crash recovery. |
| src/backends/windows_sandbox/guest/Cargo.toml | Adds Win32 windows dependency and tokio test-util for auth tests. |
| src/backends/windows_sandbox/guest/src/main.rs | Loads per-launch nonce and switches accepts/executor to authenticated protocol. |
| src/backends/windows_sandbox/guest/src/listener.rs | Accepts sockets by authenticated nonce + declared role (not accept order), with stall timeout handling. |
| src/backends/windows_sandbox/guest/src/executor.rs | Adds protocol preamble, avoids logging raw script text, improves process-tree cleanup and bounds stdio drain. |
| src/backends/windows_sandbox/guest/src/firewall.rs | Adds pre-authorization rule and tightens outbound rule to the established connection’s local port. |
| src/backends/windows_sandbox/guest/src/job.rs | Adds Job Object helper to terminate the full child process tree reliably. |
| src/backends/windows_sandbox/common/Cargo.toml | Adds tokio + getrandom for auth and async helpers. |
| src/backends/windows_sandbox/common/src/lib.rs | Exposes new auth module; removes the old one-shot runner export. |
| src/backends/windows_sandbox/common/src/auth.rs | Adds per-launch nonce + role handshake implementation. |
| src/backends/windows_sandbox/common/src/sandbox_protocol.rs | Adds control-channel preamble (magic + version) with validation. |
| src/backends/windows_sandbox/common/src/windows_sandbox_runner.rs | Deletes the legacy daemon-driven one-shot script runner. |
| docs/windows-sandbox/windows-sandbox.md | Updates high-level docs to reflect fresh-VM one-shot, auth protocol, and policy support/rejects. |
| docs/windows-sandbox/windows-sandbox-reference.md | Updates reference docs for new protocol/auth/preamble/teardown/markers model. |
| .github/copilot-instructions.md | Updates repo guidance to reflect new one-shot lifecycle implementation and test script name. |
Review details
Comments suppressed due to low confidence (1)
tests/scripts/run_windows_sandbox_one_shot_tests.ps1:52
- The script preflight uses
dism /get-featureinfo, which typically requires elevation and can reintroduce the non-elevated false-negative that this PR fixes (feature detection is now byWindowsSandbox.exepresence). Use a non-elevated file existence probe instead.
- Files reviewed: 37/38 changed files
- Comments generated: 1
- Review effort level: Low
5c49b06 to
11367a7
Compare
This PR rewrites the Windows Sandbox one-shot backend onto a fresh-VM lifecycle with an authenticated host-to-guest protocol and ownership-scoped teardown, and fixes non-elevated feature detection. Details * Adds `windows_sandbox_lifecycle` for policy validation, launch, rendezvous, execution, crash recovery, and guaranteed teardown of each disposable VM. * Authenticates every TCP channel with a per-launch nonce and channel role, and hardens guest process-tree cleanup and firewall isolation. * Routes the runner through `mxc_engine`, removes the host Python and warm-daemon dependencies, and warns only when non-default legacy daemon settings are ignored. * Rejects an existing Tokio runtime before host mutation or stdin-thread creation, avoiding a blocking thread leak on the error path. * Treats the state-aware daemon as optional in the Phase 1 SDK package; later stack phases build and require it. * Updates one-shot tests and documentation for the supported filesystem/network policy, protocol, security model, and debugging workflow. Tests * `cargo fmt --all -- --check` * `cargo check --workspace --all-targets` * `cargo clippy --workspace --all-targets -- -D warnings` * `cargo test --workspace --exclude wxc_host_prep` * `cargo check -p mxc_engine -p wxc --all-features` * `npm run build` (from `sdk`) Fixes #560 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> Copilot-Session: c03d0923-5577-4c56-b2df-a314428f5164 Generated-with: claude-opus-4.8 Generated-with: gpt-5.6-sol
11367a7 to
501432b
Compare
Phase 1 of the Windows Sandbox rewrite stack: rewrite the Windows Sandbox
one-shot backend onto a new
windows_sandbox_lifecyclecrate and anauthenticated host<->guest protocol, and fix the non-elevated feature-detection
false negative. The state-aware lifecycle + host daemon (Phase 2) and the SDK
(Phase 3) follow in stacked PRs.
Details
windows_sandbox_lifecyclecrate: the transient one-shotWindowsSandboxRunner(ScriptRunner) plus reusable VM lifecycle primitives(
vm,rendezvous,bridge,ipc_exec,policy,teardown,control_planehost-VM-lock/ownership + Win32osFFI).teardown on every exit path (normal/panic, Ctrl-C/shutdown handler,
next-run reconcile) -- no warm-VM reuse. The legacy
experimental.windows_sandbox.idleTimeoutMs/daemonPipeNamefields are stillparsed but ignored, with a stderr warning
(
WXC_WSB_ACK_ONESHOT_FRESH_VM=1silences the per-call notice).windows_sandbox_common::authadds a per-launch32-byte
Nonce+ 1-byteChannelRolehandshake on every TCP channel (boot +reconnect); the guest pairs accepted sockets by declared role, not accept
order, defeating cross-user accept-race hijack. Guest agent rewritten
(
listener/executor/job/firewall) onto the newsandbox_protocol+ auth.WindowsSandbox.exepresenceinstead of an elevated
dism /get-featureinfoquery, so a non-elevatedwxc-execno longer misreports "not enabled".windows_sandbox_common::windows_sandbox_runner; wxc one-shotdispatch constructs
WindowsSandboxRunner. The host daemon is dropped from theworkspace members for this phase (re-added with the state-aware lifecycle in
Phase 2); the dormant
control_planerecord/discovery functions arepubandcompile clean for Phase 2 to build on.
test_windows_sandboxand the renamedrun_windows_sandbox_one_shot_tests.ps1drop the daemon pre-spawn and exercisethe fresh-VM path. The full dual-mode backend-doc rewrites
(windows-sandbox.md/reference.md, schema.md, state-aware API) are deferred to
Phase 2, where they describe the end state; Phase 1 makes only minimal
P1-accurate touches to
copilot-instructions.md.Tests
cargo check --workspace --all-targets,cargo clippy --workspace --all-targets -- -D warnings, andcargo fmt --all -- --check: clean.cargo test: windows_sandbox_lifecycle 110, windows_sandbox_common 26, wxc 13,wxc_windows_sandbox_guest 8 -- all passed.
copy is
if exist-guarded) and that no source references the deleted runner.Fixes #560
Microsoft Reviewers: Open in CodeFlow