mirror of
https://github.com/microsoft/onefuzz.git
synced 2025-06-23 06:38:50 +00:00
suspend process before killing it (#1444)
This commit is contained in:
2
src/agent/Cargo.lock
generated
2
src/agent/Cargo.lock
generated
@ -1717,6 +1717,7 @@ dependencies = [
|
||||
"env_logger 0.9.0",
|
||||
"futures",
|
||||
"log",
|
||||
"nix",
|
||||
"onefuzz",
|
||||
"onefuzz-telemetry",
|
||||
"reqwest",
|
||||
@ -1729,6 +1730,7 @@ dependencies = [
|
||||
"url",
|
||||
"users",
|
||||
"uuid",
|
||||
"winapi 0.3.9",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -29,3 +29,7 @@ backtrace = "0.3"
|
||||
|
||||
[target.'cfg(target_family = "unix")'.dependencies]
|
||||
users = "0.11"
|
||||
nix = "0.23"
|
||||
|
||||
[target.'cfg(target_family = "windows")'.dependencies]
|
||||
winapi = "0.3"
|
@ -239,6 +239,35 @@ impl IWorkerRunner for WorkerRunner {
|
||||
}
|
||||
}
|
||||
|
||||
trait SuspendableChild {
|
||||
fn suspend(&mut self) -> Result<()>;
|
||||
}
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
impl SuspendableChild for Child {
|
||||
fn suspend(&mut self) -> Result<()> {
|
||||
// DebugActiveProcess suspends all threads in the process.
|
||||
// https://docs.microsoft.com/en-us/windows/win32/api/debugapi/nf-debugapi-debugactiveprocess#remarks
|
||||
let result = unsafe { winapi::um::debugapi::DebugActiveProcess(self.id() as u32) };
|
||||
if result == 0 {
|
||||
bail!("unable to suspend child process");
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(any(target_os = "linux", target_os = "macos"))]
|
||||
impl SuspendableChild for Child {
|
||||
fn suspend(&mut self) -> Result<()> {
|
||||
use nix::sys::signal;
|
||||
signal::kill(
|
||||
nix::unistd::Pid::from_raw(self.id() as _),
|
||||
signal::Signal::SIGSTOP,
|
||||
)?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
/// Child process with redirected output streams, tailed by two worker threads.
|
||||
struct RedirectedChild {
|
||||
/// The child process.
|
||||
@ -358,6 +387,12 @@ impl IWorkerChild for RedirectedChild {
|
||||
fn kill(&mut self) -> Result<()> {
|
||||
use std::io::ErrorKind;
|
||||
|
||||
// Try to gracefully kill the child process to avoid spurious error telemetry;
|
||||
// we ignore the error here because the process will be killed anyway
|
||||
if let Err(suspend_error) = self.child.suspend() {
|
||||
log::info!("error while suspending process: {}", suspend_error);
|
||||
}
|
||||
|
||||
let killed = self.child.kill();
|
||||
|
||||
if let Err(err) = &killed {
|
||||
|
Reference in New Issue
Block a user