Skip to content

Commit 88528a1

Browse files
committed
Introduce io::ErrorKind::SubprocessFailed and add a From impl
We add this to the existing feature gate exit_status_error, since we will probably want to stabilise this trait impl along with the new type - or not at all. Signed-off-by: Ian Jackson <ijackson@chiark.greenend.org.uk>
1 parent 7b5c0ec commit 88528a1

File tree

2 files changed

+47
-0
lines changed

2 files changed

+47
-0
lines changed

library/std/src/io/error.rs

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -284,6 +284,45 @@ pub enum ErrorKind {
284284
#[stable(feature = "out_of_memory_error", since = "1.54.0")]
285285
OutOfMemory,
286286

287+
/// Subprocess failed.
288+
///
289+
/// A subprocess (eg, run by a
290+
/// [`Command`](care::process::Command)) failed.
291+
///
292+
/// Often wraps an
293+
/// [`ExitStatusError`](crate::process::ExitStatusError),
294+
/// (perhaps via `?` and `Into`), in which case
295+
/// [`io::Error::get_ref`](crate::io::error::get_ref) or
296+
/// [`std::error::Error::source`](crate::error::Error::source)
297+
/// is the `ExitStatusError`,
298+
/// allowing the subprocess's exit status to be obtained.
299+
///
300+
/// (The exit code, exit status, or wait status is generally *not*
301+
/// available via
302+
/// [`io::Error::raw_os_error`](crate::io::Error::raw_os_error),
303+
/// since process exit codes are not generally the same as OS
304+
/// error codes..)
305+
///
306+
/// # Example
307+
/// ```
308+
/// #![feature(exit_status_error)]
309+
/// use std::process::{Command, ExitStatusError};
310+
///
311+
/// fn system(shellcmd: &str) -> Result<(), std::io::Error> {
312+
/// Command::new("sh").args(&["-c",shellcmd]).status()?.exit_ok()?;
313+
/// Ok(())
314+
/// }
315+
///
316+
/// # if cfg!(unix) {
317+
/// let err = system("exit 23").unwrap_err();
318+
/// let exit_error: &ExitStatusError = err.get_ref().unwrap().downcast_ref().unwrap();
319+
/// assert_eq!(err.to_string(), "process exited unsuccessfully: exit status: 23");
320+
/// assert_eq!(exit_error.code(), Some(23));
321+
/// # }
322+
/// ```
323+
#[unstable(feature = "exit_status_error", issue = "84908")]
324+
SubprocessFailed,
325+
287326
// "Unusual" error kinds which do not correspond simply to (sets
288327
// of) OS error codes, should be added just above this comment.
289328
// `Other` and `Uncategorised` should remain at the end:
@@ -350,6 +389,7 @@ impl ErrorKind {
350389
ResourceBusy => "resource busy",
351390
StaleNetworkFileHandle => "stale network file handle",
352391
StorageFull => "no storage space",
392+
SubprocessFailed => "subprocess failed",
353393
TimedOut => "timed out",
354394
TooManyLinks => "too many links",
355395
Uncategorized => "uncategorized error",

library/std/src/process.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1636,6 +1636,13 @@ impl fmt::Display for ExitStatusError {
16361636
#[unstable(feature = "exit_status_error", issue = "84908")]
16371637
impl crate::error::Error for ExitStatusError {}
16381638

1639+
#[unstable(feature = "exit_status_error", issue = "84908")]
1640+
impl From<ExitStatusError> for io::Error {
1641+
fn from(ese: ExitStatusError) -> io::Error {
1642+
io::Error::new(io::ErrorKind::SubprocessFailed, ese)
1643+
}
1644+
}
1645+
16391646
/// This type represents the status code a process can return to its
16401647
/// parent under normal termination.
16411648
///

0 commit comments

Comments
 (0)