Skip to content

Commit

Permalink
fix: wait for spawned tasks to die before exiting (#2461)
Browse files Browse the repository at this point in the history
Fixes #2418
  • Loading branch information
jdx authored Aug 16, 2024
1 parent a316c80 commit 02f1423
Show file tree
Hide file tree
Showing 4 changed files with 38 additions and 22 deletions.
21 changes: 20 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,8 @@ xx = { version = "1.0.0", features = ["glob"] }
zip = { version = "2", default-features = false, features = ["deflate"] }

[target.'cfg(unix)'.dependencies]
exec = "0.3.1"
exec = "0.3"
nix = {version="0.29", features=["signal", "user"]}

[build-dependencies]
built = { version = "0.7", features = ["chrono", "git2"] }
Expand Down
31 changes: 12 additions & 19 deletions src/cli/run.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
use std::collections::{BTreeMap, HashSet};
use std::io::Write;
use std::iter::once;
#[cfg(unix)]
use std::os::unix::prelude::*;
use std::path::{Path, PathBuf};
use std::process::{exit, Stdio};
use std::sync::atomic::{AtomicUsize, Ordering};
Expand Down Expand Up @@ -186,6 +184,7 @@ impl Run {
let pool = rayon::ThreadPoolBuilder::new()
.num_threads(self.jobs() + 1)
.build()?;
let exit_status = Mutex::new(None);
pool.scope(|s| {
let run = |task: &Task| {
let t = task.clone();
Expand All @@ -194,7 +193,11 @@ impl Run {
trace!("running tasks: {task}");
if let Err(err) = self.run_task(config, &env, &task) {
error!("{err}");
exit(1);
if let Some(ScriptFailed(_, Some(status))) = err.downcast_ref::<Error>() {
*exit_status.lock().unwrap() = status.code();
} else {
*exit_status.lock().unwrap() = Some(1);
}
}
let mut tasks = tasks.lock().unwrap();
tasks.remove(&task);
Expand All @@ -211,6 +214,11 @@ impl Run {
info!("{}", style::edim(msg));
};

if let Some(status) = *exit_status.lock().unwrap() {
debug!("exiting with status: {status}");
exit(status);
}

Ok(())
}

Expand Down Expand Up @@ -340,22 +348,7 @@ impl Run {
if self.dry_run {
return Ok(());
}
if let Err(err) = cmd.execute() {
if let Some(ScriptFailed(_, Some(status))) = err.downcast_ref::<Error>() {
if let Some(code) = status.code() {
error!("{prefix} exited with code {code}");
exit(code);
} else {
#[cfg(unix)]
if let Some(signal) = status.signal() {
error!("{prefix} killed by signal {signal}");
exit(1);
}
}
}
error!("{err}");
exit(1);
}
cmd.execute()?;
trace!("{prefix} exited successfully");
Ok(())
}
Expand Down
5 changes: 4 additions & 1 deletion src/cmd.rs
Original file line number Diff line number Diff line change
Expand Up @@ -323,7 +323,10 @@ impl<'a> CmdLineRunner<'a> {
#[cfg(not(any(test, target_os = "windows")))]
ChildProcessOutput::Signal(sig) => {
if sig != SIGINT {
cmd!("kill", format!("-{sig}"), id.to_string()).run()?;
debug!("Received signal {}, {id}", sig);
let pid = nix::unistd::Pid::from_raw(id as i32);
let sig = nix::sys::signal::Signal::try_from(sig).unwrap();
nix::sys::signal::kill(pid, sig)?;
}
}
}
Expand Down

0 comments on commit 02f1423

Please sign in to comment.