about summary refs log tree commit diff
path: root/tests/ui/process
diff options
context:
space:
mode:
Diffstat (limited to 'tests/ui/process')
-rw-r--r--tests/ui/process/core-run-destroy.rs5
-rw-r--r--tests/ui/process/env-args-reverse-iterator.rs3
-rw-r--r--tests/ui/process/fds-are-cloexec.rs5
-rw-r--r--tests/ui/process/inherit-env.rs3
-rw-r--r--tests/ui/process/issue-13304.rs6
-rw-r--r--tests/ui/process/issue-14456.rs6
-rw-r--r--tests/ui/process/issue-14940.rs3
-rw-r--r--tests/ui/process/issue-16272.rs3
-rw-r--r--tests/ui/process/issue-20091.rs6
-rw-r--r--tests/ui/process/issue-30490.rs3
-rw-r--r--tests/ui/process/multi-panic.rs3
-rw-r--r--tests/ui/process/no-stdio.rs3
-rw-r--r--tests/ui/process/println-with-broken-pipe.rs2
-rw-r--r--tests/ui/process/process-envs.rs3
-rw-r--r--tests/ui/process/process-exit.rs6
-rw-r--r--tests/ui/process/process-panic-after-fork.rs5
-rw-r--r--tests/ui/process/process-remove-from-env.rs3
-rw-r--r--tests/ui/process/process-sigpipe.rs2
-rw-r--r--tests/ui/process/process-spawn-nonexistent.rs3
-rw-r--r--tests/ui/process/process-spawn-with-unicode-params.rs3
-rw-r--r--tests/ui/process/process-status-inherits-stdin.rs3
-rw-r--r--tests/ui/process/signal-exit-status.rs5
-rw-r--r--tests/ui/process/sigpipe-should-be-ignored.rs7
-rw-r--r--tests/ui/process/tls-exit-status.rs2
-rw-r--r--tests/ui/process/try-wait.rs6
-rw-r--r--tests/ui/process/win-creation-flags.rs51
-rw-r--r--tests/ui/process/win-proc-thread-attributes.rs118
27 files changed, 202 insertions, 66 deletions
diff --git a/tests/ui/process/core-run-destroy.rs b/tests/ui/process/core-run-destroy.rs
index 3f2ea0e8441..b4815c9dfbb 100644
--- a/tests/ui/process/core-run-destroy.rs
+++ b/tests/ui/process/core-run-destroy.rs
@@ -1,12 +1,11 @@
 //@ run-pass
 
 #![allow(unused_must_use)]
-#![allow(stable_features)]
 #![allow(deprecated)]
 #![allow(unused_imports)]
+
 //@ compile-flags:--test
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-vxworks no 'cat' and 'sleep'
 //@ ignore-fuchsia no 'cat'
 
diff --git a/tests/ui/process/env-args-reverse-iterator.rs b/tests/ui/process/env-args-reverse-iterator.rs
index 830e9535466..f0afeeb22eb 100644
--- a/tests/ui/process/env-args-reverse-iterator.rs
+++ b/tests/ui/process/env-args-reverse-iterator.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env::args;
 use std::process::Command;
diff --git a/tests/ui/process/fds-are-cloexec.rs b/tests/ui/process/fds-are-cloexec.rs
index e7b000b2c49..f6678379dd6 100644
--- a/tests/ui/process/fds-are-cloexec.rs
+++ b/tests/ui/process/fds-are-cloexec.rs
@@ -1,9 +1,8 @@
 //@ run-pass
-//@ ignore-windows
+//@ only-unix
 //@ ignore-android
-//@ ignore-wasm32 no processes
+//@ needs-subprocess
 //@ ignore-haiku
-//@ ignore-sgx no processes
 
 #![feature(rustc_private)]
 
diff --git a/tests/ui/process/inherit-env.rs b/tests/ui/process/inherit-env.rs
index 0eb61fcdd53..09d5b76141e 100644
--- a/tests/ui/process/inherit-env.rs
+++ b/tests/ui/process/inherit-env.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no subprocess support
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
 use std::process::Command;
diff --git a/tests/ui/process/issue-13304.rs b/tests/ui/process/issue-13304.rs
index 6dbf0caaaec..621c54300d3 100644
--- a/tests/ui/process/issue-13304.rs
+++ b/tests/ui/process/issue-13304.rs
@@ -1,7 +1,5 @@
 //@ run-pass
-#![allow(unused_mut)]
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
 use std::io::prelude::*;
@@ -32,7 +30,7 @@ fn parent() {
 }
 
 fn child() {
-    let mut stdin = io::stdin();
+    let stdin = io::stdin();
     for line in stdin.lock().lines() {
         println!("{}", line.unwrap());
     }
diff --git a/tests/ui/process/issue-14456.rs b/tests/ui/process/issue-14456.rs
index fd6da8a5fc4..e67a9d8bad5 100644
--- a/tests/ui/process/issue-14456.rs
+++ b/tests/ui/process/issue-14456.rs
@@ -1,7 +1,5 @@
 //@ run-pass
-#![allow(unused_mut)]
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
 use std::io::prelude::*;
@@ -20,7 +18,7 @@ fn main() {
 fn child() {
     writeln!(&mut io::stdout(), "foo").unwrap();
     writeln!(&mut io::stderr(), "bar").unwrap();
-    let mut stdin = io::stdin();
+    let stdin = io::stdin();
     let mut s = String::new();
     stdin.lock().read_line(&mut s).unwrap();
     assert_eq!(s.len(), 0);
diff --git a/tests/ui/process/issue-14940.rs b/tests/ui/process/issue-14940.rs
index 13fb18154a0..cfbc743250f 100644
--- a/tests/ui/process/issue-14940.rs
+++ b/tests/ui/process/issue-14940.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
 use std::process::Command;
diff --git a/tests/ui/process/issue-16272.rs b/tests/ui/process/issue-16272.rs
index bf26769d494..72708554753 100644
--- a/tests/ui/process/issue-16272.rs
+++ b/tests/ui/process/issue-16272.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::process::Command;
 use std::env;
diff --git a/tests/ui/process/issue-20091.rs b/tests/ui/process/issue-20091.rs
index b6d94661b75..72bf4c0e71e 100644
--- a/tests/ui/process/issue-20091.rs
+++ b/tests/ui/process/issue-20091.rs
@@ -1,9 +1,5 @@
 //@ run-pass
-#![allow(stable_features)]
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
-
-#![feature(os)]
+//@ needs-subprocess
 
 #[cfg(unix)]
 fn main() {
diff --git a/tests/ui/process/issue-30490.rs b/tests/ui/process/issue-30490.rs
index 0d918bc3dd5..75b36e7c20b 100644
--- a/tests/ui/process/issue-30490.rs
+++ b/tests/ui/process/issue-30490.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-emscripten no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-fuchsia Child I/O swaps not privileged
 
 // Previously libstd would set stdio descriptors of a child process
diff --git a/tests/ui/process/multi-panic.rs b/tests/ui/process/multi-panic.rs
index ad47925a149..481fe75c731 100644
--- a/tests/ui/process/multi-panic.rs
+++ b/tests/ui/process/multi-panic.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ needs-unwind
 
 fn check_for_no_backtrace(test: std::process::Output) {
diff --git a/tests/ui/process/no-stdio.rs b/tests/ui/process/no-stdio.rs
index 8eebf6dbc7d..5cc7cacbb22 100644
--- a/tests/ui/process/no-stdio.rs
+++ b/tests/ui/process/no-stdio.rs
@@ -1,7 +1,6 @@
 //@ run-pass
 //@ ignore-android
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 #![feature(rustc_private)]
 
diff --git a/tests/ui/process/println-with-broken-pipe.rs b/tests/ui/process/println-with-broken-pipe.rs
index d88c6dcc12b..fbac9b6cd95 100644
--- a/tests/ui/process/println-with-broken-pipe.rs
+++ b/tests/ui/process/println-with-broken-pipe.rs
@@ -1,7 +1,7 @@
 //@ run-pass
 //@ check-run-results
+//@ needs-subprocess
 //@ ignore-windows
-//@ ignore-wasm32
 //@ ignore-fuchsia
 //@ ignore-horizon
 //@ ignore-android
diff --git a/tests/ui/process/process-envs.rs b/tests/ui/process/process-envs.rs
index 15285960d16..98052f1d3a5 100644
--- a/tests/ui/process/process-envs.rs
+++ b/tests/ui/process/process-envs.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-vxworks no 'env'
 //@ ignore-fuchsia no 'env'
 
diff --git a/tests/ui/process/process-exit.rs b/tests/ui/process/process-exit.rs
index a75a7306cbc..a1ed243b62b 100644
--- a/tests/ui/process/process-exit.rs
+++ b/tests/ui/process/process-exit.rs
@@ -1,10 +1,8 @@
 //@ run-pass
-#![allow(unused_imports)]
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
-use std::process::{self, Command, Stdio};
+use std::process::{self, Command};
 
 fn main() {
     let args: Vec<String> = env::args().collect();
diff --git a/tests/ui/process/process-panic-after-fork.rs b/tests/ui/process/process-panic-after-fork.rs
index afb1b721182..6e0267e0a54 100644
--- a/tests/ui/process/process-panic-after-fork.rs
+++ b/tests/ui/process/process-panic-after-fork.rs
@@ -1,8 +1,7 @@
 //@ run-pass
 //@ no-prefer-dynamic
-//@ ignore-windows
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ only-unix
+//@ needs-subprocess
 //@ ignore-fuchsia no fork
 
 #![feature(rustc_private)]
diff --git a/tests/ui/process/process-remove-from-env.rs b/tests/ui/process/process-remove-from-env.rs
index 21fff4fd45d..c1a2b2daf5b 100644
--- a/tests/ui/process/process-remove-from-env.rs
+++ b/tests/ui/process/process-remove-from-env.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-vxworks no 'env'
 //@ ignore-fuchsia no 'env'
 
diff --git a/tests/ui/process/process-sigpipe.rs b/tests/ui/process/process-sigpipe.rs
index 9db130c26bd..453e53379fc 100644
--- a/tests/ui/process/process-sigpipe.rs
+++ b/tests/ui/process/process-sigpipe.rs
@@ -15,7 +15,7 @@
 
 //@ ignore-vxworks no 'sh'
 //@ ignore-fuchsia no 'sh'
-//@ ignore-emscripten No threads
+//@ needs-threads
 //@ only-unix SIGPIPE is a unix feature
 
 use std::process;
diff --git a/tests/ui/process/process-spawn-nonexistent.rs b/tests/ui/process/process-spawn-nonexistent.rs
index 1cd32866299..3db670624fb 100644
--- a/tests/ui/process/process-spawn-nonexistent.rs
+++ b/tests/ui/process/process-spawn-nonexistent.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-fuchsia ErrorKind not translated
 
 use std::io::ErrorKind;
diff --git a/tests/ui/process/process-spawn-with-unicode-params.rs b/tests/ui/process/process-spawn-with-unicode-params.rs
index 4d2ba49eeac..65f835c1345 100644
--- a/tests/ui/process/process-spawn-with-unicode-params.rs
+++ b/tests/ui/process/process-spawn-with-unicode-params.rs
@@ -7,8 +7,7 @@
 // non-ASCII characters.  The child process ensures all the strings are
 // intact.
 
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 //@ ignore-fuchsia Filesystem manipulation privileged
 
 use std::io::prelude::*;
diff --git a/tests/ui/process/process-status-inherits-stdin.rs b/tests/ui/process/process-status-inherits-stdin.rs
index 39eef34c5f8..d5dd0e55fa3 100644
--- a/tests/ui/process/process-status-inherits-stdin.rs
+++ b/tests/ui/process/process-status-inherits-stdin.rs
@@ -1,6 +1,5 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
+//@ needs-subprocess
 
 use std::env;
 use std::io;
diff --git a/tests/ui/process/signal-exit-status.rs b/tests/ui/process/signal-exit-status.rs
index a6acea47636..33aa83abfc3 100644
--- a/tests/ui/process/signal-exit-status.rs
+++ b/tests/ui/process/signal-exit-status.rs
@@ -1,7 +1,6 @@
 //@ run-pass
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
-//@ ignore-windows
+//@ needs-subprocess
+//@ only-unix (`code()` returns `None` if terminated by a signal on Unix)
 //@ ignore-fuchsia code returned as ZX_TASK_RETCODE_EXCEPTION_KILL, FIXME (#58590)
 
 #![feature(core_intrinsics)]
diff --git a/tests/ui/process/sigpipe-should-be-ignored.rs b/tests/ui/process/sigpipe-should-be-ignored.rs
index 44785bee7f8..3dcf0117ae9 100644
--- a/tests/ui/process/sigpipe-should-be-ignored.rs
+++ b/tests/ui/process/sigpipe-should-be-ignored.rs
@@ -1,12 +1,9 @@
 //@ run-pass
+//@ needs-subprocess
 
-#![allow(unused_must_use)]
 // Be sure that when a SIGPIPE would have been received that the entire process
 // doesn't die in a ball of fire, but rather it's gracefully handled.
 
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
-
 use std::env;
 use std::io::prelude::*;
 use std::io;
@@ -14,7 +11,7 @@ use std::process::{Command, Stdio};
 
 fn test() {
     let _ = io::stdin().read_line(&mut String::new());
-    io::stdout().write(&[1]);
+    io::stdout().write(&[1]).unwrap();
     assert!(io::stdout().flush().is_err());
 }
 
diff --git a/tests/ui/process/tls-exit-status.rs b/tests/ui/process/tls-exit-status.rs
index cddcf369da0..6dd0d71ef35 100644
--- a/tests/ui/process/tls-exit-status.rs
+++ b/tests/ui/process/tls-exit-status.rs
@@ -1,7 +1,7 @@
 //@ run-fail
 //@ error-pattern:nonzero
 //@ exec-env:RUST_NEWRT=1
-//@ ignore-wasm32 no processes
+//@ needs-subprocess
 
 use std::env;
 
diff --git a/tests/ui/process/try-wait.rs b/tests/ui/process/try-wait.rs
index b6d026d802f..dcef43ad348 100644
--- a/tests/ui/process/try-wait.rs
+++ b/tests/ui/process/try-wait.rs
@@ -1,9 +1,5 @@
 //@ run-pass
-
-#![allow(stable_features)]
-//@ ignore-wasm32 no processes
-//@ ignore-sgx no processes
-#![feature(process_try_wait)]
+//@ needs-subprocess
 
 use std::env;
 use std::process::Command;
diff --git a/tests/ui/process/win-creation-flags.rs b/tests/ui/process/win-creation-flags.rs
new file mode 100644
index 00000000000..0c7c6883d68
--- /dev/null
+++ b/tests/ui/process/win-creation-flags.rs
@@ -0,0 +1,51 @@
+// Test that windows `creation_flags` extension to `Command` works.
+
+//@ run-pass
+//@ only-windows
+//@ needs-subprocess
+
+use std::env;
+use std::os::windows::process::CommandExt;
+use std::process::{Command, exit};
+
+fn main() {
+    if env::args().skip(1).any(|s| s == "--child") {
+        child();
+    } else {
+        parent();
+    }
+}
+
+fn parent() {
+    let exe = env::current_exe().unwrap();
+
+    // Use the DETACH_PROCESS to create a subprocess that isn't attached to the console.
+    // The subprocess's exit status will be 0 if it's detached.
+    let status = Command::new(&exe)
+        .arg("--child")
+        .creation_flags(DETACH_PROCESS)
+        .spawn()
+        .unwrap()
+        .wait()
+        .unwrap();
+    assert_eq!(status.code(), Some(0));
+
+    // Try without DETACH_PROCESS to ensure this test works.
+    let status = Command::new(&exe).arg("--child").spawn().unwrap().wait().unwrap();
+    assert_eq!(status.code(), Some(1));
+}
+
+// exits with 1 if the console is attached or 0 otherwise
+fn child() {
+    // Get the attached console's code page.
+    // This will fail (return 0) if no console is attached.
+    let has_console = GetConsoleCP() != 0;
+    exit(has_console as i32);
+}
+
+// Windows API definitions.
+const DETACH_PROCESS: u32 = 0x00000008;
+#[link(name = "kernel32")]
+unsafe extern "system" {
+    safe fn GetConsoleCP() -> u32;
+}
diff --git a/tests/ui/process/win-proc-thread-attributes.rs b/tests/ui/process/win-proc-thread-attributes.rs
new file mode 100644
index 00000000000..91bb0b17e95
--- /dev/null
+++ b/tests/ui/process/win-proc-thread-attributes.rs
@@ -0,0 +1,118 @@
+// Tests proc thread attributes by spawning a process with a custom parent process,
+// then comparing the parent process ID with the expected parent process ID.
+
+//@ run-pass
+//@ only-windows
+//@ needs-subprocess
+//@ edition: 2021
+
+#![feature(windows_process_extensions_raw_attribute)]
+
+use std::os::windows::io::AsRawHandle;
+use std::os::windows::process::{CommandExt, ProcThreadAttributeList};
+use std::process::{Child, Command};
+use std::{env, mem, ptr, thread, time};
+
+// Make a best effort to ensure child processes always exit.
+struct ProcessDropGuard(Child);
+impl Drop for ProcessDropGuard {
+    fn drop(&mut self) {
+        let _ = self.0.kill();
+    }
+}
+
+fn main() {
+    if env::args().skip(1).any(|s| s == "--child") {
+        child();
+    } else {
+        parent();
+    }
+}
+
+fn parent() {
+    let exe = env::current_exe().unwrap();
+
+    let (fake_parent_id, child_parent_id) = {
+        // Create a process to be our fake parent process.
+        let fake_parent = Command::new(&exe).arg("--child").spawn().unwrap();
+        let fake_parent = ProcessDropGuard(fake_parent);
+        let parent_handle = fake_parent.0.as_raw_handle();
+
+        // Create another process with the parent process set to the fake.
+        let mut attribute_list = ProcThreadAttributeList::build()
+            .attribute(PROC_THREAD_ATTRIBUTE_PARENT_PROCESS, &parent_handle)
+            .finish()
+            .unwrap();
+        let child =
+            Command::new(&exe).arg("--child").spawn_with_attributes(&mut attribute_list).unwrap();
+        let child = ProcessDropGuard(child);
+
+        // Return the fake's process id and the child's parent's id.
+        (process_info(&fake_parent.0).process_id(), process_info(&child.0).parent_id())
+    };
+
+    assert_eq!(fake_parent_id, child_parent_id);
+}
+
+// A process that stays running until killed.
+fn child() {
+    // Don't wait forever if something goes wrong.
+    thread::sleep(time::Duration::from_secs(60));
+}
+
+fn process_info(child: &Child) -> PROCESS_BASIC_INFORMATION {
+    unsafe {
+        let mut info: PROCESS_BASIC_INFORMATION = mem::zeroed();
+        let result = NtQueryInformationProcess(
+            child.as_raw_handle(),
+            ProcessBasicInformation,
+            ptr::from_mut(&mut info).cast(),
+            mem::size_of_val(&info).try_into().unwrap(),
+            ptr::null_mut(),
+        );
+        assert_eq!(result, 0);
+        info
+    }
+}
+
+// Windows API
+mod winapi {
+    #![allow(nonstandard_style)]
+    use std::ffi::c_void;
+
+    pub type HANDLE = *mut c_void;
+    type NTSTATUS = i32;
+    type PROCESSINFOCLASS = i32;
+
+    pub const ProcessBasicInformation: i32 = 0;
+    pub const PROC_THREAD_ATTRIBUTE_PARENT_PROCESS: usize = 0x00020000;
+    #[repr(C)]
+    pub struct PROCESS_BASIC_INFORMATION {
+        pub ExitStatus: NTSTATUS,
+        pub PebBaseAddress: *mut (),
+        pub AffinityMask: usize,
+        pub BasePriority: i32,
+        pub UniqueProcessId: usize,
+        pub InheritedFromUniqueProcessId: usize,
+    }
+    impl PROCESS_BASIC_INFORMATION {
+        pub fn parent_id(&self) -> usize {
+            self.InheritedFromUniqueProcessId
+        }
+        pub fn process_id(&self) -> usize {
+            self.UniqueProcessId
+        }
+    }
+
+    #[link(name = "ntdll")]
+    extern "system" {
+        pub fn NtQueryInformationProcess(
+            ProcessHandle: HANDLE,
+            ProcessInformationClass: PROCESSINFOCLASS,
+            ProcessInformation: *mut c_void,
+            ProcessInformationLength: u32,
+            ReturnLength: *mut u32,
+        ) -> NTSTATUS;
+    }
+}
+use winapi::*;