1 #![cfg(feature = "process")]
2 #![warn(rust_2018_idioms)]
3 // This test reveals a difference in behavior of kqueue on FreeBSD. When the
4 // reader disconnects, there does not seem to be an `EVFILT_WRITE` filter that
5 // is returned.
6 //
7 // It is expected that `EVFILT_WRITE` would be returned with either the
8 // `EV_EOF` or `EV_ERROR` flag set. If either flag is set a write would be
9 // attempted, but that does not seem to occur.
10 #![cfg(all(unix, not(target_os = "freebsd"), not(miri)))]
11 
12 use std::process::Stdio;
13 use std::time::Duration;
14 use tokio::io::AsyncWriteExt;
15 use tokio::process::Command;
16 use tokio::time;
17 use tokio_test::assert_err;
18 
19 #[tokio::test]
20 #[cfg_attr(panic = "abort", ignore)]
issue_2174()21 async fn issue_2174() {
22     let mut child = Command::new("sleep")
23         .arg("2")
24         .stdin(Stdio::piped())
25         .stdout(Stdio::null())
26         .spawn()
27         .unwrap();
28     let mut input = child.stdin.take().unwrap();
29 
30     // Writes will buffer up to 65_636. This *should* loop at least 8 times
31     // and then register interest.
32     let handle = tokio::spawn(async move {
33         let data = [0u8; 8192];
34         loop {
35             input.write_all(&data).await.unwrap();
36         }
37     });
38 
39     // Sleep enough time so that the child process's stdin's buffer fills.
40     time::sleep(Duration::from_secs(1)).await;
41 
42     // Kill the child process.
43     child.kill().await.unwrap();
44 
45     assert_err!(handle.await);
46 }
47