Skip to content

Commit 3aaf469

Browse files
committed
refactor: linearize platform-specific stop process flow
1 parent 9015c20 commit 3aaf469

1 file changed

Lines changed: 62 additions & 38 deletions

File tree

src-tauri/src/main.rs

Lines changed: 62 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -2385,75 +2385,99 @@ fn wait_for_child_exit(child: &mut Child, timeout: Duration) -> bool {
23852385
}
23862386
}
23872387

2388+
fn run_stop_command(pid: u32, label: &str, program: &str, args: &[&str]) -> io::Result<ExitStatus> {
2389+
let status = Command::new(program)
2390+
.args(args)
2391+
.stdout(Stdio::null())
2392+
.stderr(Stdio::null())
2393+
.stdin(Stdio::null())
2394+
.status();
2395+
2396+
match &status {
2397+
Ok(exit_status) if exit_status.success() => {}
2398+
Ok(exit_status) => append_desktop_log(&format!(
2399+
"{label} returned non-zero: pid={pid}, status={exit_status:?}"
2400+
)),
2401+
Err(error) => append_desktop_log(&format!(
2402+
"{label} failed to start: pid={pid}, error={error}"
2403+
)),
2404+
}
2405+
2406+
status
2407+
}
2408+
2409+
fn compute_followup_wait(timeout: Duration, max_extra_wait: Duration) -> Duration {
2410+
if timeout.is_zero() {
2411+
Duration::ZERO
2412+
} else {
2413+
(timeout / 4)
2414+
.max(Duration::from_millis(FORCE_STOP_WAIT_MIN_MS))
2415+
.min(max_extra_wait)
2416+
}
2417+
}
2418+
23882419
/// Attempt to stop a child process gracefully within `timeout`.
23892420
///
23902421
/// On the force-kill path, a follow-up wait is derived from `timeout` (`timeout / 4`)
23912422
/// and capped per-platform:
23922423
/// - Windows: up to 2200ms.
23932424
/// - Non-Windows: up to 1500ms.
2425+
#[cfg(target_os = "windows")]
23942426
fn stop_child_process_gracefully(child: &mut Child, timeout: Duration) -> bool {
23952427
let pid = child.id();
23962428
let pid_arg = pid.to_string();
23972429

2398-
let run_stop_command = |label: &str, program: &str, args: &[&str]| -> io::Result<ExitStatus> {
2399-
let status = Command::new(program)
2400-
.args(args)
2401-
.stdout(Stdio::null())
2402-
.stderr(Stdio::null())
2403-
.stdin(Stdio::null())
2404-
.status();
2405-
2406-
match &status {
2407-
Ok(exit_status) if exit_status.success() => {}
2408-
Ok(exit_status) => append_desktop_log(&format!(
2409-
"{label} returned non-zero: pid={pid}, status={exit_status:?}"
2410-
)),
2411-
Err(error) => append_desktop_log(&format!(
2412-
"{label} failed to start: pid={pid}, error={error}"
2413-
)),
2414-
}
2415-
2416-
status
2417-
};
2418-
2419-
#[cfg(target_os = "windows")]
24202430
let graceful_status = run_stop_command(
2431+
pid,
24212432
"taskkill graceful stop",
24222433
"taskkill",
24232434
&["/pid", &pid_arg, "/t"],
24242435
);
2425-
#[cfg(not(target_os = "windows"))]
2426-
let graceful_status = run_stop_command("kill -TERM", "kill", &["-TERM", &pid_arg]);
24272436

24282437
if wait_for_child_exit(child, timeout) {
24292438
return true;
24302439
}
24312440

2432-
#[cfg(target_os = "windows")]
24332441
let force_status = run_stop_command(
2442+
pid,
24342443
"taskkill force stop",
24352444
"taskkill",
24362445
&["/pid", &pid_arg, "/t", "/f"],
24372446
);
2438-
#[cfg(not(target_os = "windows"))]
2439-
let force_status = run_stop_command("kill -KILL", "kill", &["-KILL", &pid_arg]);
24402447

2441-
#[cfg(target_os = "windows")]
2442-
let max_extra_wait = Duration::from_millis(FORCE_STOP_WAIT_MAX_WINDOWS_MS);
2443-
#[cfg(not(target_os = "windows"))]
2444-
let max_extra_wait = Duration::from_millis(FORCE_STOP_WAIT_MAX_NON_WINDOWS_MS);
2448+
let followup_wait = compute_followup_wait(
2449+
timeout,
2450+
Duration::from_millis(FORCE_STOP_WAIT_MAX_WINDOWS_MS),
2451+
);
2452+
append_desktop_log(&format!(
2453+
"child graceful stop timed out, force-kill issued: pid={pid}, graceful={graceful_status:?}, force={force_status:?}, followup_wait_ms={}",
2454+
followup_wait.as_millis(),
2455+
));
2456+
wait_for_child_exit(child, followup_wait)
2457+
}
24452458

2446-
let followup_wait = if timeout.is_zero() {
2447-
Duration::ZERO
2448-
} else {
2449-
(timeout / 4)
2450-
.max(Duration::from_millis(FORCE_STOP_WAIT_MIN_MS))
2451-
.min(max_extra_wait)
2452-
};
2459+
#[cfg(not(target_os = "windows"))]
2460+
fn stop_child_process_gracefully(child: &mut Child, timeout: Duration) -> bool {
2461+
let pid = child.id();
2462+
let pid_arg = pid.to_string();
2463+
2464+
let graceful_status = run_stop_command(pid, "kill -TERM", "kill", &["-TERM", &pid_arg]);
2465+
2466+
if wait_for_child_exit(child, timeout) {
2467+
return true;
2468+
}
2469+
2470+
let force_status = run_stop_command(pid, "kill -KILL", "kill", &["-KILL", &pid_arg]);
2471+
2472+
let followup_wait = compute_followup_wait(
2473+
timeout,
2474+
Duration::from_millis(FORCE_STOP_WAIT_MAX_NON_WINDOWS_MS),
2475+
);
24532476
append_desktop_log(&format!(
24542477
"child graceful stop timed out, force-kill issued: pid={pid}, graceful={graceful_status:?}, force={force_status:?}, followup_wait_ms={}",
24552478
followup_wait.as_millis(),
24562479
));
2480+
24572481
wait_for_child_exit(child, followup_wait)
24582482
}
24592483

0 commit comments

Comments
 (0)