From 472658d0143ac6599b02408674e6720726de7e43 Mon Sep 17 00:00:00 2001 From: kshitijk4poor <82637225+kshitijk4poor@users.noreply.github.com> Date: Wed, 29 Jul 2026 16:28:53 +0500 Subject: [PATCH] fix(desktop): pass shell to serve probe; bound Windows discovery probes Two residual gaps from the #72707/#72632 probe-hardening series: - backendSupportsServe never forwarded backend.shell to the serve --help probe. A .cmd/.bat shim backend (which carries shell: true in its step-4 descriptor) makes execFileSync throw EINVAL on modern Node; the bare catch then caches supported=false for the process lifetime, permanently routing that backend through the legacy dashboard form. Forward the flag. - The Windows python-discovery probes ran with no timeout at all: reg query (registry read) and py.exe -c 'import sys;...' (bare interpreter startup) are both synchronous execs on the boot path; a wedged reg.exe or python.exe would hang the resolver forever. Bound reg query at 5s and the py.exe probe at the shared PROBE_TIMEOUT_MS budget. --- apps/desktop/electron/main.ts | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/apps/desktop/electron/main.ts b/apps/desktop/electron/main.ts index 4efb9c98620..344b149d0d1 100644 --- a/apps/desktop/electron/main.ts +++ b/apps/desktop/electron/main.ts @@ -1903,6 +1903,11 @@ function backendSupportsServe(backend) { env: { ...process.env, HERMES_HOME, ...(backend.env || {}) }, timeout: PROBE_TIMEOUT_MS, stdio: 'ignore', + // `.cmd`/`.bat` shim backends carry shell: true in their descriptor + // (see resolveHermesBackend step 4); execFileSync of a .cmd without + // shell throws EINVAL on modern Node, which the catch below would + // mis-cache as "serve unsupported" for the process lifetime. + shell: Boolean(backend.shell), windowsHide: true }) supported = true @@ -2059,7 +2064,10 @@ function findSystemPython() { const out = execFileSync( 'reg', ['query', `${hive}\\SOFTWARE\\Python\\PythonCore\\${version}\\InstallPath`, '/ve', '/reg:64'], - hiddenWindowsChildOptions({ encoding: 'utf8', stdio: ['ignore', 'pipe', 'ignore'] }) + // Registry reads are near-instant; the bound only exists so a + // pathologically wedged reg.exe can't hang the synchronous boot + // resolver forever (this ran unbounded before). + hiddenWindowsChildOptions({ encoding: 'utf8', stdio: ['ignore', 'pipe', 'ignore'], timeout: 5_000 }) ) // Output format: " (Default) REG_SZ C:\Path\To\Python\" @@ -2114,7 +2122,12 @@ function findSystemPython() { [`-${version}`, '-c', 'import sys; print(sys.executable)'], hiddenWindowsChildOptions({ encoding: 'utf8', - stdio: ['ignore', 'pipe', 'ignore'] + stdio: ['ignore', 'pipe', 'ignore'], + // Bare interpreter startup — much lighter than the hermes-import + // probes, but still python.exe under cold cache / AV scan, so + // share the probe budget rather than running unbounded (this + // synchronous exec previously had no timeout at all). + timeout: PROBE_TIMEOUT_MS }) )