1#![cfg_attr(not(feature = "std"), no_std)]
10
11use core::fmt::Display;
12
13use raw::RawExitCode;
14
15pub mod raw;
16pub mod unix;
17pub mod windows;
18
19#[allow(dead_code)]
21mod doc_tests {
22 #[doc = include_str!("../README.md")]
23 struct Readme;
24}
25
26#[derive(Clone, Copy, Debug, PartialEq, Eq)]
28#[non_exhaustive]
29pub enum Error {
30 Unix(unix::WaitStatus),
32
33 Windows(windows::ExitCode),
35}
36
37#[cfg(feature = "std")]
38impl Display for Error {
39 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
40 match self {
41 Error::Unix(status) => write!(f, "Unix exit status: {}", status.to_raw()),
42 Error::Windows(code) => write!(f, "Windows exit code: {}", code.to_raw()),
43 }
44 }
45}
46
47#[cfg(feature = "std")]
48impl std::error::Error for Error {}
49
50#[cfg(feature = "std")]
52pub type ProcResult<T> = std::result::Result<T, Error>;
53
54#[cfg(feature = "std")]
56pub trait ToProcResult<T> {
57 fn to_proc_result(&self) -> ProcResult<T>;
63}
64
65#[cfg(feature = "std")]
66impl ToProcResult<()> for std::process::ExitStatus {
67 #[allow(unreachable_code)]
68 fn to_proc_result(&self) -> ProcResult<()> {
69 if self.success() {
70 Ok(())
71 } else {
72 #[cfg(unix)]
73 {
74 let err: unix::WaitStatus = self.into();
75 return Err(Error::Unix(err));
76 }
77 #[cfg(windows)]
78 {
79 let err: windows::ExitCode = self.into();
80 return Err(Error::Windows(err));
81 }
82 panic!("Cannot convert exit status to error on this platform");
83 }
84 }
85}