Upstream creates the module's console here, not at the daemon's own launch.
Two independent reasons this window exists, and only one of them was mine:
-
Upstream gap. spawn_child_in_slot (crates/subc-daemon/src/supervise.rs:5620-5650)
builds the module Command with piped stdout/stderr and stdin(null), but no
creation_flags on Windows. A console-subsystem child launched without
CREATE_NO_WINDOW gets a fresh console, so every supervised module (ck-aft,
the Synapse module) opens one. Closing that window sends CTRL_C_EVENT, which
the child reports as 0xC000013A STATUS_CONTROL_C_EXIT — so a user who just
wants to tidy their desktop kills a healthy module and the supervisor restarts
it. This is why CREATE_NO_WINDOW exists in setup/uninstall.rs upstream but
never in supervise.rs.
-
My own regression, in the job-object work. set_suspended_creation_flags
called command.creation_flags(CREATE_SUSPENDED_FLAG), and
std::process::Command::creation_flags replaces the whole mask rather than
OR-ing into it. So a second CREATE_NO_WINDOW call added later would have
silently dropped CREATE_SUSPENDED — leaving the child both uncontained and
unresumable. Both flags now go in as one OR'd mask
(CONTAINMENT_CREATION_FLAGS, crates/subc-jobobject/src/sys.rs).
The fix is one flag at the module spawn site, not at the daemon's own launch
site — the daemon is already launched hidden by the OMP extension
(windowsHide: true), and CREATE_NO_WINDOW is inert for the daemon itself.
The doc comment on SupervisedChild::job already names the remaining
non-Unix gap in this area (drain-then-exit on Windows), which is the separate
follow-up in #111.
Upstream creates the module's console here, not at the daemon's own launch.
Two independent reasons this window exists, and only one of them was mine:
Upstream gap.
spawn_child_in_slot(crates/subc-daemon/src/supervise.rs:5620-5650)builds the module
Commandwith piped stdout/stderr andstdin(null), but nocreation_flagson Windows. A console-subsystem child launched withoutCREATE_NO_WINDOWgets a fresh console, so every supervised module (ck-aft,the Synapse module) opens one. Closing that window sends
CTRL_C_EVENT, whichthe child reports as
0xC000013A STATUS_CONTROL_C_EXIT— so a user who justwants to tidy their desktop kills a healthy module and the supervisor restarts
it. This is why
CREATE_NO_WINDOWexists insetup/uninstall.rsupstream butnever in
supervise.rs.My own regression, in the job-object work.
set_suspended_creation_flagscalled
command.creation_flags(CREATE_SUSPENDED_FLAG), andstd::process::Command::creation_flagsreplaces the whole mask rather thanOR-ing into it. So a second
CREATE_NO_WINDOWcall added later would havesilently dropped
CREATE_SUSPENDED— leaving the child both uncontained andunresumable. Both flags now go in as one OR'd mask
(
CONTAINMENT_CREATION_FLAGS,crates/subc-jobobject/src/sys.rs).The fix is one flag at the module spawn site, not at the daemon's own launch
site — the daemon is already launched hidden by the OMP extension
(
windowsHide: true), andCREATE_NO_WINDOWis inert for the daemon itself.The doc comment on
SupervisedChild::jobalready names the remainingnon-Unix gap in this area (drain-then-exit on Windows), which is the separate
follow-up in #111.