From d163d731be3e5541320a6a029109bb145ab1644f Mon Sep 17 00:00:00 2001 From: marksverdhei Date: Thu, 4 Jun 2026 18:58:13 +0200 Subject: [PATCH] fix(server): portable exit-code read on subprocess-alive=false path MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `tools/server/server-models.cpp:923` used `child_proc->return_status`, which is a POSIX-only field of `subprocess_s` — the Windows variant of the struct has `hProcess` instead, so this fails to compile on every Windows CI runner. Replace the direct field access with a portable `subprocess_join(child_proc.get(), &child_exit)` call (same pattern already used at line 908 of the same file). `subprocess_alive()` has already reaped the zombie on POSIX, so `subprocess_join()` returns immediately with the cached status. --- tools/server/server-models.cpp | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/tools/server/server-models.cpp b/tools/server/server-models.cpp index c7a1f0d9902..d50913a751b 100644 --- a/tools/server/server-models.cpp +++ b/tools/server/server-models.cpp @@ -920,7 +920,15 @@ void server_models::load(const std::string & name) { // but that cleanup can stall on log_thread.join() if the stdout pipe isn't // EOFing (e.g. another process inherited the write end). Setting status here // breaks the "500 forever" loop even when the management thread is stuck. - this->update_status(name, SERVER_MODEL_STATUS_UNLOADED, child_proc->return_status); + // + // subprocess_join() is the portable way to read the exit code — + // subprocess_s::return_status exists only on POSIX (the Windows variant uses + // hProcess + GetExitCodeProcess via subprocess_join). subprocess_alive() + // already reaped the zombie on POSIX, so subprocess_join() returns + // immediately with the cached status. + int child_exit = 0; + subprocess_join(child_proc.get(), &child_exit); + this->update_status(name, SERVER_MODEL_STATUS_UNLOADED, child_exit); // Force the stdout pipe read end closed so log_thread's fgets() returns and // the outer thread can proceed past log_thread.join(). if (child_proc->stdout_file) {