summaryrefslogtreecommitdiffstats
path: root/tests/ui/stdio-is-blocking.rs
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-17 12:19:03 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-17 12:19:03 +0000
commit64d98f8ee037282c35007b64c2649055c56af1db (patch)
tree5492bcf97fce41ee1c0b1cc2add283f3e66cdab0 /tests/ui/stdio-is-blocking.rs
parentAdding debian version 1.67.1+dfsg1-1. (diff)
downloadrustc-64d98f8ee037282c35007b64c2649055c56af1db.tar.xz
rustc-64d98f8ee037282c35007b64c2649055c56af1db.zip
Merging upstream version 1.68.2+dfsg1.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'tests/ui/stdio-is-blocking.rs')
-rw-r--r--tests/ui/stdio-is-blocking.rs84
1 files changed, 84 insertions, 0 deletions
diff --git a/tests/ui/stdio-is-blocking.rs b/tests/ui/stdio-is-blocking.rs
new file mode 100644
index 000000000..4b67dbf79
--- /dev/null
+++ b/tests/ui/stdio-is-blocking.rs
@@ -0,0 +1,84 @@
+// run-pass
+// ignore-emscripten no processes
+// ignore-sgx no processes
+
+use std::env;
+use std::io::prelude::*;
+use std::process::Command;
+use std::thread;
+
+const THREADS: usize = 20;
+const WRITES: usize = 100;
+const WRITE_SIZE: usize = 1024 * 32;
+
+fn main() {
+ let args = env::args().collect::<Vec<_>>();
+ if args.len() == 1 {
+ parent();
+ } else {
+ child();
+ }
+}
+
+fn parent() {
+ let me = env::current_exe().unwrap();
+ let mut cmd = Command::new(me);
+ cmd.arg("run-the-test");
+ let output = cmd.output().unwrap();
+ assert!(output.status.success());
+ assert_eq!(output.stderr.len(), 0);
+ assert_eq!(output.stdout.len(), WRITES * THREADS * WRITE_SIZE);
+ for byte in output.stdout.iter() {
+ assert_eq!(*byte, b'a');
+ }
+}
+
+fn child() {
+ let threads = (0..THREADS).map(|_| {
+ thread::spawn(|| {
+ let buf = [b'a'; WRITE_SIZE];
+ for _ in 0..WRITES {
+ write_all(&buf);
+ }
+ })
+ }).collect::<Vec<_>>();
+
+ for thread in threads {
+ thread.join().unwrap();
+ }
+}
+
+#[cfg(unix)]
+fn write_all(buf: &[u8]) {
+ use std::fs::File;
+ use std::mem;
+ use std::os::unix::prelude::*;
+
+ let mut file = unsafe { File::from_raw_fd(1) };
+ let res = file.write_all(buf);
+ mem::forget(file);
+ res.unwrap();
+}
+
+#[cfg(windows)]
+fn write_all(buf: &[u8]) {
+ use std::fs::File;
+ use std::mem;
+ use std::os::windows::raw::*;
+ use std::os::windows::prelude::*;
+
+ const STD_OUTPUT_HANDLE: u32 = (-11i32) as u32;
+
+ extern "system" {
+ fn GetStdHandle(handle: u32) -> HANDLE;
+ }
+
+ let mut file = unsafe {
+ let handle = GetStdHandle(STD_OUTPUT_HANDLE);
+ assert!(!handle.is_null());
+ File::from_raw_handle(handle)
+ };
+ let res = file.write_all(buf);
+ mem::forget(file);
+ res.unwrap();
+}