| extern crate wait_timeout; |
| |
| use std::env; |
| use std::process::{Command, Child, Stdio}; |
| use std::time::{Duration, Instant}; |
| |
| use wait_timeout::ChildExt; |
| |
| macro_rules! t { |
| ($e:expr) => (match $e { |
| Ok(e) => e, |
| Err(e) => panic!("{} failed with {}", stringify!($e), e), |
| }) |
| } |
| |
| fn sleeper(ms: u32) -> Child { |
| let mut me = env::current_exe().unwrap(); |
| me.pop(); |
| if me.ends_with("deps") { |
| me.pop(); |
| } |
| me.push("sleep"); |
| t!(Command::new(me).arg(ms.to_string()).spawn()) |
| } |
| |
| fn exit(code: u32) -> Child { |
| let mut me = env::current_exe().unwrap(); |
| me.pop(); |
| if me.ends_with("deps") { |
| me.pop(); |
| } |
| me.push("exit"); |
| t!(Command::new(me).arg(code.to_string()).spawn()) |
| } |
| |
| fn reader() -> Child { |
| let mut me = env::current_exe().unwrap(); |
| me.pop(); |
| if me.ends_with("deps") { |
| me.pop(); |
| } |
| me.push("reader"); |
| t!(Command::new(me).stdin(Stdio::piped()).spawn()) |
| } |
| |
| #[test] |
| fn smoke_insta_timeout() { |
| let mut child = sleeper(1_000); |
| assert_eq!(t!(child.wait_timeout_ms(0)), None); |
| |
| t!(child.kill()); |
| let status = t!(child.wait()); |
| assert!(!status.success()); |
| } |
| |
| #[test] |
| fn smoke_success() { |
| let start = Instant::now(); |
| let mut child = sleeper(0); |
| let status = t!(child.wait_timeout_ms(1_000)).expect("should have succeeded"); |
| assert!(status.success()); |
| |
| assert!(start.elapsed() < Duration::from_millis(500)); |
| } |
| |
| #[test] |
| fn smoke_timeout() { |
| let mut child = sleeper(1_000_000); |
| let start = Instant::now(); |
| assert_eq!(t!(child.wait_timeout_ms(100)), None); |
| assert!(start.elapsed() > Duration::from_millis(80)); |
| |
| t!(child.kill()); |
| let status = t!(child.wait()); |
| assert!(!status.success()); |
| } |
| |
| #[test] |
| fn smoke_reader() { |
| let mut child = reader(); |
| let dur = Duration::from_millis(100); |
| let status = t!(child.wait_timeout(dur)).unwrap(); |
| assert!(status.success()); |
| } |
| |
| #[test] |
| fn exit_codes() { |
| let mut child = exit(0); |
| let status = t!(child.wait_timeout_ms(1_000)).unwrap(); |
| assert_eq!(status.code(), Some(0)); |
| |
| let mut child = exit(1); |
| let status = t!(child.wait_timeout_ms(1_000)).unwrap(); |
| assert_eq!(status.code(), Some(1)); |
| |
| // check STILL_ACTIVE on windows, on unix this ends up just getting |
| // truncated so don't bother with it. |
| if cfg!(windows) { |
| let mut child = exit(259); |
| let status = t!(child.wait_timeout_ms(1_000)).unwrap(); |
| assert_eq!(status.code(), Some(259)); |
| } |
| } |