//! Windows-specific extensions to primitives in the [`std::process`] module.
//!
//! [`std::process`]: crate::process

#![stable(feature = "process_extensions", since = "1.2.0")]

use crate::ffi::{OsStr, c_void};
use crate::mem::MaybeUninit;
use crate::os::windows::io::{
    AsHandle, AsRawHandle, BorrowedHandle, FromRawHandle, IntoRawHandle, OwnedHandle, RawHandle,
};
use crate::sys::{AsInner, AsInnerMut, FromInner, IntoInner};
use crate::{io, marker, process, ptr, sys};

#[stable(feature = "process_extensions", since = "1.2.0")]
impl FromRawHandle for process::Stdio {
    unsafe fn from_raw_handle(handle: RawHandle) -> process::Stdio {
        let handle = unsafe { sys::handle::Handle::from_raw_handle(handle as *mut _) };
        let io = sys::process::Stdio::Handle(handle);
        process::Stdio::from_inner(io)
    }
}

#[stable(feature = "io_safety", since = "1.63.0")]
impl From<OwnedHandle> for process::Stdio {
    /// Takes ownership of a handle and returns a [`Stdio`](process::Stdio)
    /// that can attach a stream to it.
    fn from(handle: OwnedHandle) -> process::Stdio {
        let handle = sys::handle::Handle::from_inner(handle);
        let io = sys::process::Stdio::Handle(handle);
        process::Stdio::from_inner(io)
    }
}

#[stable(feature = "process_extensions", since = "1.2.0")]
impl AsRawHandle for process::Child {
    #[inline]
    fn as_raw_handle(&self) -> RawHandle {
        self.as_inner().handle().as_raw_handle() as *mut _
    }
}

#[stable(feature = "io_safety", since = "1.63.0")]
impl AsHandle for process::Child {
    #[inline]
    fn as_handle(&self) -> BorrowedHandle<'_> {
        self.as_inner().handle().as_handle()
    }
}

#[stable(feature = "into_raw_os", since = "1.4.0")]
impl IntoRawHandle for process::Child {
    fn into_raw_handle(self) -> RawHandle {
        self.into_inner().into_handle().into_raw_handle() as *mut _
    }
}

#[stable(feature = "io_safety", since = "1.63.0")]
impl From<process::Child> for OwnedHandle {
    /// Takes ownership of a [`Child`](process::Child)'s process handle.
    fn from(child: process::Child) -> OwnedHandle {
        child.into_inner().into_handle().into_inner()
    }
}

#[stable(feature = "process_extensions", since = "1.2.0")]
impl AsRawHandle for process::ChildStdin {
    #[inline]
    fn as_raw_handle(&self) -> RawHandle {
        self.as_inner().handle().as_raw_handle() as *mut _
    }
}

#[stable(feature = "process_extensions", since = "1.2.0")]
impl AsRawHandle for process::ChildStdout {
    #[inline]
    fn as_raw_handle(&self) -> RawHandle {
        self.as_inner().handle().as_raw_handle() as *mut _
    }
}

#[stable(feature = "process_extensions", since = "1.2.0")]
impl AsRawHandle for process::ChildStderr {
    #[inline]
    fn as_raw_handle(&self) -> RawHandle {
        self.as_inner().handle().as_raw_handle() as *mut _
    }
}

#[stable(feature = "into_raw_os", since = "1.4.0")]
impl IntoRawHandle for process::ChildStdin {
    fn into_raw_handle(self) -> RawHandle {
        self.into_inner().into_handle().into_raw_handle() as *mut _
    }
}

#[stable(feature = "into_raw_os", since = "1.4.0")]
impl IntoRawHandle for process::ChildStdout {
    fn into_raw_handle(self) -> RawHandle {
        self.into_inner().into_handle().into_raw_handle() as *mut _
    }
}

#[stable(feature = "into_raw_os", since = "1.4.0")]
impl IntoRawHandle for process::ChildStderr {
    fn into_raw_handle(self) -> RawHandle {
        self.into_inner().into_handle().into_raw_handle() as *mut _
    }
}

/// Creates a `ChildStdin` from the provided `OwnedHandle`.
///
/// The provided handle must be asynchronous, as reading and
/// writing from and to it is implemented using asynchronous APIs.
#[stable(feature = "child_stream_from_fd", since = "1.74.0")]
impl From<OwnedHandle> for process::ChildStdin {
    fn from(handle: OwnedHandle) -> process::ChildStdin {
        let handle = sys::handle::Handle::from_inner(handle);
        let pipe = sys::process::ChildPipe::from_inner(handle);
        process::ChildStdin::from_inner(pipe)
    }
}

/// Creates a `ChildStdout` from the provided `OwnedHandle`.
///
/// The provided handle must be asynchronous, as reading and
/// writing from and to it is implemented using asynchronous APIs.
#[stable(feature = "child_stream_from_fd", since = "1.74.0")]
impl From<OwnedHandle> for process::ChildStdout {
    fn from(handle: OwnedHandle) -> process::ChildStdout {
        let handle = sys::handle::Handle::from_inner(handle);
        let pipe = sys::process::ChildPipe::from_inner(handle);
        process::ChildStdout::from_inner(pipe)
    }
}

/// Creates a `ChildStderr` from the provided `OwnedHandle`.
///
/// The provided handle must be asynchronous, as reading and
/// writing from and to it is implemented using asynchronous APIs.
#[stable(feature = "child_stream_from_fd", since = "1.74.0")]
impl From<OwnedHandle> for process::ChildStderr {
    fn from(handle: OwnedHandle) -> process::ChildStderr {
        let handle = sys::handle::Handle::from_inner(handle);
        let pipe = sys::process::ChildPipe::from_inner(handle);
        process::ChildStderr::from_inner(pipe)
    }
}

/// Windows-specific extensions to [`process::ExitStatus`].
#[stable(feature = "exit_status_from", since = "1.12.0")]
pub impl(self) trait ExitStatusExt {
    /// Creates a new `ExitStatus` from the raw underlying `u32` return value of
    /// a process.
    #[stable(feature = "exit_status_from", since = "1.12.0")]
    fn from_raw(raw: u32) -> Self;
}

#[stable(feature = "exit_status_from", since = "1.12.0")]
impl ExitStatusExt for process::ExitStatus {
    fn from_raw(raw: u32) -> Self {
        process::ExitStatus::from_inner(From::from(raw))
    }
}

/// Windows-specific extensions to the [`process::Command`] builder.
#[stable(feature = "windows_process_extensions", since = "1.16.0")]
pub impl(self) trait CommandExt {
    /// Sets the [process creation flags][1] to be passed to `CreateProcess`.
    ///
    /// These will always be ORed with `CREATE_UNICODE_ENVIRONMENT`.
    ///
    /// [1]: https://docs.microsoft.com/en-us/windows/win32/procthread/process-creation-flags
    #[stable(feature = "windows_process_extensions", since = "1.16.0")]
    fn creation_flags(&mut self, flags: u32) -> &mut process::Command;

    /// Sets the field `wShowWindow` of [STARTUPINFO][1] that is passed to `CreateProcess`.
    /// Allowed values are the ones listed in
    /// <https://learn.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-showwindow>
    ///
    /// [1]: <https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/ns-processthreadsapi-startupinfow>
    #[unstable(feature = "windows_process_extensions_show_window", issue = "127544")]
    fn show_window(&mut self, cmd_show: u16) -> &mut process::Command;

    /// Forces all arguments to be wrapped in quote (`"`) characters.
    ///
    /// This is useful for passing arguments to [MSYS2/Cygwin][1] based
    /// executables: these programs will expand unquoted arguments containing
    /// wildcard characters (`?` and `*`) by searching for any file paths
    /// matching the wildcard pattern.
    ///
    /// Adding quotes has no effect when passing arguments to programs
    /// that use [msvcrt][2]. This includes programs built with both
    /// MinGW and MSVC.
    ///
    /// [1]: <https://github.com/msys2/MSYS2-packages/issues/2176>
    /// [2]: <https://msdn.microsoft.com/en-us/library/17w5ykft.aspx>
    #[unstable(feature = "windows_process_extensions_force_quotes", issue = "82227")]
    fn force_quotes(&mut self, enabled: bool) -> &mut process::Command;

    /// Append literal text to the command line without any quoting or escaping.
    ///
    /// This is useful for passing arguments to applications that don't follow
    /// the standard C run-time escaping rules, such as `cmd.exe /c`.
    ///
    /// # Batch files
    ///
    /// Note the `cmd /c` command line has slightly different escaping rules than batch files
    /// themselves. If possible, it may be better to write complex arguments to a temporary
    /// `.bat` file, with appropriate escaping, and simply run that using:
    ///
    /// ```no_run
    /// # use std::process::Command;
    /// # let temp_bat_file = "";
    /// # #[allow(unused)]
    /// let output = Command::new("cmd").args(["/c", &format!("\"{temp_bat_file}\"")]).output();
    /// ```
    ///
    /// # Example
    ///
    /// Run a batch script using both trusted and untrusted arguments.
    ///
    /// ```no_run
    /// #[cfg(windows)]
    /// // `my_script_path` is a path to known bat file.
    /// // `user_name` is an untrusted name given by the user.
    /// fn run_script(
    ///     my_script_path: &str,
    ///     user_name: &str,
    /// ) -> Result<std::process::Output, std::io::Error> {
    ///     use std::io::{Error, ErrorKind};
    ///     use std::os::windows::process::CommandExt;
    ///     use std::process::Command;
    ///
    ///     // Create the command line, making sure to quote the script path.
    ///     // This assumes the fixed arguments have been tested to work with the script we're using.
    ///     let mut cmd_args = format!(r#""{my_script_path}" "--features=[a,b,c]""#);
    ///
    ///     // Make sure the user name is safe. In particular we need to be
    ///     // cautious of ascii symbols that cmd may interpret specially.
    ///     // Here we only allow alphanumeric characters.
    ///     if !user_name.chars().all(|c| c.is_alphanumeric()) {
    ///         return Err(Error::new(ErrorKind::InvalidInput, "invalid user name"));
    ///     }
    ///
    ///     // now we have validated the user name, let's add that too.
    ///     cmd_args.push_str(" --user ");
    ///     cmd_args.push_str(user_name);
    ///
    ///     // call cmd.exe and return the output
    ///     Command::new("cmd.exe")
    ///         .arg("/c")
    ///         // surround the entire command in an extra pair of quotes, as required by cmd.exe.
    ///         .raw_arg(&format!("\"{cmd_args}\""))
    ///         .output()
    /// }
    /// ````
    #[stable(feature = "windows_process_extensions_raw_arg", since = "1.62.0")]
    fn raw_arg<S: AsRef<OsStr>>(&mut self, text_to_append_as_is: S) -> &mut process::Command;

    /// When [`process::Command`] creates pipes, request that our side is always async.
    ///
    /// By default [`process::Command`] may choose to use pipes where both ends
    /// are opened for synchronous read or write operations. By using
    /// `async_pipes(true)`, this behavior is overridden so that our side is
    /// always async.
    ///
    /// This is important because if doing async I/O a pipe or a file has to be
    /// opened for async access.
    ///
    /// The end of the pipe sent to the child process will always be synchronous
    /// regardless of this option.
    ///
    /// # Example
    ///
    /// ```
    /// #![feature(windows_process_extensions_async_pipes)]
    /// use std::os::windows::process::CommandExt;
    /// use std::process::{Command, Stdio};
    ///
    /// # let program = "";
    ///
    /// Command::new(program)
    ///     .async_pipes(true)
    ///     .stdin(Stdio::piped())
    ///     .stdout(Stdio::piped())
    ///     .stderr(Stdio::piped());
    /// ```
    #[unstable(feature = "windows_process_extensions_async_pipes", issue = "98289")]
    fn async_pipes(&mut self, always_async: bool) -> &mut process::Command;

    /// Executes the command as a child process with the given
    /// [`ProcThreadAttributeList`], returning a handle to it.
    ///
    /// This method enables the customization of attributes for the spawned
    /// child process on Windows systems.
    /// Attributes offer extended configurability for process creation,
    /// but their usage can be intricate and potentially unsafe.
    ///
    /// # Note
    ///
    /// By default, stdin, stdout, and stderr are inherited from the parent
    /// process.
    ///
    /// # Example
    ///
    /// ```
    /// #![feature(windows_process_extensions_raw_attribute)]
    /// use std::os::windows::io::AsRawHandle;
    /// use std::os::windows::process::{CommandExt, ProcThreadAttributeList};
    /// use std::process::Command;
    ///
    /// # struct ProcessDropGuard(std::process::Child);
    /// # impl Drop for ProcessDropGuard {
    /// #     fn drop(&mut self) {
    /// #         let _ = self.0.kill();
    /// #     }
    /// # }
    /// #
    /// let parent = Command::new("cmd").spawn()?;
    /// let parent_process_handle = parent.as_raw_handle();
    /// # let parent = ProcessDropGuard(parent);
    ///
    /// const PROC_THREAD_ATTRIBUTE_PARENT_PROCESS: usize = 0x00020000;
    /// let mut attribute_list = ProcThreadAttributeList::build()
    ///     .attribute(PROC_THREAD_ATTRIBUTE_PARENT_PROCESS, &parent_process_handle)
    ///     .finish()
    ///     .unwrap();
    ///
    /// let mut child = Command::new("cmd").spawn_with_attributes(&attribute_list)?;
    /// #
    /// # child.kill()?;
    /// # Ok::<(), std::io::Error>(())
    /// ```
    #[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
    fn spawn_with_attributes(
        &mut self,
        attribute_list: &ProcThreadAttributeList<'_>,
    ) -> io::Result<process::Child>;

    /// When true, sets the `STARTF_RUNFULLSCREEN` flag on the [STARTUPINFO][1] struct before passing it to `CreateProcess`.
    ///
    /// [1]: https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/ns-processthreadsapi-startupinfoa
    #[unstable(feature = "windows_process_extensions_startupinfo", issue = "141010")]
    fn startupinfo_fullscreen(&mut self, enabled: bool) -> &mut process::Command;

    /// When true, sets the `STARTF_UNTRUSTEDSOURCE` flag on the [STARTUPINFO][1] struct before passing it to `CreateProcess`.
    ///
    /// [1]: https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/ns-processthreadsapi-startupinfoa
    #[unstable(feature = "windows_process_extensions_startupinfo", issue = "141010")]
    fn startupinfo_untrusted_source(&mut self, enabled: bool) -> &mut process::Command;

    /// When specified, sets the following flags on the [STARTUPINFO][1] struct before passing it to `CreateProcess`:
    /// - If `Some(true)`, sets `STARTF_FORCEONFEEDBACK`
    /// - If `Some(false)`, sets `STARTF_FORCEOFFFEEDBACK`
    /// - If `None`, does not set any flags
    ///
    /// [1]: https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/ns-processthreadsapi-startupinfoa
    #[unstable(feature = "windows_process_extensions_startupinfo", issue = "141010")]
    fn startupinfo_force_feedback(&mut self, enabled: Option<bool>) -> &mut process::Command;

    /// If this flag is set to `true`, each inheritable handle in the calling
    /// process is inherited by the new process. If the flag is `false`, the
    /// handles are not inherited.
    ///
    /// The default value for this flag is `true`.
    ///
    /// **Note** that inherited handles have the same value and access rights
    /// as the original handles. For additional discussion of inheritable handles,
    /// see the [Remarks][1] section of the `CreateProcessW` documentation.
    ///
    /// [1]: https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-createprocessw#remarks
    #[unstable(feature = "windows_process_extensions_inherit_handles", issue = "146407")]
    fn inherit_handles(&mut self, inherit_handles: bool) -> &mut process::Command;
}

#[stable(feature = "windows_process_extensions", since = "1.16.0")]
impl CommandExt for process::Command {
    fn creation_flags(&mut self, flags: u32) -> &mut process::Command {
        self.as_inner_mut().creation_flags(flags);
        self
    }

    fn show_window(&mut self, cmd_show: u16) -> &mut process::Command {
        self.as_inner_mut().show_window(Some(cmd_show));
        self
    }

    fn force_quotes(&mut self, enabled: bool) -> &mut process::Command {
        self.as_inner_mut().force_quotes(enabled);
        self
    }

    fn raw_arg<S: AsRef<OsStr>>(&mut self, raw_text: S) -> &mut process::Command {
        self.as_inner_mut().raw_arg(raw_text.as_ref());
        self
    }

    fn async_pipes(&mut self, always_async: bool) -> &mut process::Command {
        // FIXME: This currently has an intentional no-op implementation.
        // For the time being our side of the pipes will always be async.
        // Once the ecosystem has adjusted, we may then be able to start making
        // use of synchronous pipes within the standard library.
        let _ = always_async;
        self
    }

    fn spawn_with_attributes(
        &mut self,
        attribute_list: &ProcThreadAttributeList<'_>,
    ) -> io::Result<process::Child> {
        self.as_inner_mut()
            .spawn_with_attributes(sys::process::Stdio::Inherit, true, Some(attribute_list))
            .map(process::Child::from_inner)
    }

    fn startupinfo_fullscreen(&mut self, enabled: bool) -> &mut process::Command {
        self.as_inner_mut().startupinfo_fullscreen(enabled);
        self
    }

    fn startupinfo_untrusted_source(&mut self, enabled: bool) -> &mut process::Command {
        self.as_inner_mut().startupinfo_untrusted_source(enabled);
        self
    }

    fn startupinfo_force_feedback(&mut self, enabled: Option<bool>) -> &mut process::Command {
        self.as_inner_mut().startupinfo_force_feedback(enabled);
        self
    }

    fn inherit_handles(&mut self, inherit_handles: bool) -> &mut process::Command {
        self.as_inner_mut().inherit_handles(inherit_handles);
        self
    }
}

#[unstable(feature = "windows_process_extensions_main_thread_handle", issue = "96723")]
pub impl(self) trait ChildExt {
    /// Extracts the main thread raw handle, without taking ownership
    #[unstable(feature = "windows_process_extensions_main_thread_handle", issue = "96723")]
    fn main_thread_handle(&self) -> BorrowedHandle<'_>;
}

#[unstable(feature = "windows_process_extensions_main_thread_handle", issue = "96723")]
impl ChildExt for process::Child {
    fn main_thread_handle(&self) -> BorrowedHandle<'_> {
        self.handle.main_thread_handle()
    }
}

/// Windows-specific extensions to [`process::ExitCode`].
#[unstable(feature = "windows_process_exit_code_from", issue = "111688")]
pub impl(self) trait ExitCodeExt {
    /// Creates a new `ExitCode` from the raw underlying `u32` return value of
    /// a process.
    ///
    /// The exit code should not be 259, as this conflicts with the `STILL_ACTIVE`
    /// macro returned from the `GetExitCodeProcess` function to signal that the
    /// process has yet to run to completion.
    #[unstable(feature = "windows_process_exit_code_from", issue = "111688")]
    fn from_raw(raw: u32) -> Self;
}

#[unstable(feature = "windows_process_exit_code_from", issue = "111688")]
impl ExitCodeExt for process::ExitCode {
    fn from_raw(raw: u32) -> Self {
        process::ExitCode::from_inner(From::from(raw))
    }
}

/// A wrapper around windows [`ProcThreadAttributeList`][1].
///
/// [1]: <https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-initializeprocthreadattributelist>
#[derive(Debug)]
#[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
pub struct ProcThreadAttributeList<'a> {
    attribute_list: Box<[MaybeUninit<u8>]>,
    _lifetime_marker: marker::PhantomData<&'a ()>,
}

#[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
impl<'a> ProcThreadAttributeList<'a> {
    /// Creates a new builder for constructing a [`ProcThreadAttributeList`].
    pub fn build() -> ProcThreadAttributeListBuilder<'a> {
        ProcThreadAttributeListBuilder::new()
    }

    /// Returns a pointer to the underling attribute list.
    #[doc(hidden)]
    pub fn as_ptr(&self) -> *const MaybeUninit<u8> {
        self.attribute_list.as_ptr()
    }
}

#[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
impl<'a> Drop for ProcThreadAttributeList<'a> {
    /// Deletes the attribute list.
    ///
    /// This method calls [`DeleteProcThreadAttributeList`][1] to delete the
    /// underlying attribute list.
    ///
    /// [1]: <https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-deleteprocthreadattributelist>
    fn drop(&mut self) {
        let lp_attribute_list = self.attribute_list.as_mut_ptr().cast::<c_void>();
        unsafe { sys::c::DeleteProcThreadAttributeList(lp_attribute_list) }
    }
}

/// Builder for constructing a [`ProcThreadAttributeList`].
#[derive(Clone, Debug)]
#[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
pub struct ProcThreadAttributeListBuilder<'a> {
    attributes: alloc::collections::BTreeMap<usize, ProcThreadAttributeValue>,
    _lifetime_marker: marker::PhantomData<&'a ()>,
}

#[unstable(feature = "windows_process_extensions_raw_attribute", issue = "114854")]
impl<'a> ProcThreadAttributeListBuilder<'a> {
    fn new() -> Self {
        ProcThreadAttributeListBuilder {
            attributes: alloc::collections::BTreeMap::new(),
            _lifetime_marker: marker::PhantomData,
        }
    }

    /// Sets an attribute on the attribute list.
    ///
    /// The `attribute` parameter specifies the raw attribute to be set, while
    /// the `value` parameter holds the value associated with that attribute.
    /// Please refer to the [Windows documentation][1] for a list of valid attributes.
    ///
    /// # Note
    ///
    /// The maximum number of attributes is the value of [`u32::MAX`]. If this
    /// limit is exceeded, the call to [`Self::finish`] will return an `Error`
    /// indicating that the maximum number of attributes has been exceeded.
    ///
    /// # Safety Note
    ///
    /// Remember that improper use of attributes can lead to undefined behavior
    /// or security vulnerabilities. Always consult the documentation and ensure
    /// proper attribute values are used.
    ///
    /// [1]: <https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-updateprocthreadattribute#parameters>
    pub fn attribute<T>(self, attribute: usize, value: &'a T) -> Self {
        unsafe {
            self.raw_attribute(attribute, ptr::addr_of!(*value).cast::<c_void>(), size_of::<T>())
        }
    }

    /// Sets a raw attribute on the attribute list.
    ///
    /// This function is useful for setting attributes with pointers or sizes
    /// that cannot be derived directly from their values.
    ///
    /// # Safety
    ///
    /// This function is marked as `unsafe` because it deals with raw pointers
    /// and sizes. It is the responsibility of the caller to ensure the value
    /// lives longer than the resulting [`ProcThreadAttributeList`] as well as
    /// the validity of the size parameter.
    ///
    /// # Example
    ///
    #[cfg_attr(target_vendor = "win7", doc = "```no_run")]
    #[cfg_attr(not(target_vendor = "win7"), doc = "```")]
    /// #![feature(windows_process_extensions_raw_attribute)]
    /// use std::ffi::c_void;
    /// use std::os::windows::process::{CommandExt, ProcThreadAttributeList};
    /// use std::os::windows::raw::HANDLE;
    /// use std::process::Command;
    ///
    /// #[repr(C)]
    /// pub struct COORD {
    ///     pub X: i16,
    ///     pub Y: i16,
    /// }
    ///
    /// unsafe extern "system" {
    ///     fn CreatePipe(
    ///         hreadpipe: *mut HANDLE,
    ///         hwritepipe: *mut HANDLE,
    ///         lppipeattributes: *const c_void,
    ///         nsize: u32,
    ///     ) -> i32;
    ///     fn CreatePseudoConsole(
    ///         size: COORD,
    ///         hinput: HANDLE,
    ///         houtput: HANDLE,
    ///         dwflags: u32,
    ///         phpc: *mut isize,
    ///     ) -> i32;
    ///     fn CloseHandle(hobject: HANDLE) -> i32;
    /// }
    ///
    /// let [mut input_read_side, mut output_write_side, mut output_read_side, mut input_write_side] =
    ///     [unsafe { std::mem::zeroed::<HANDLE>() }; 4];
    ///
    /// unsafe {
    ///     CreatePipe(&mut input_read_side, &mut input_write_side, std::ptr::null(), 0);
    ///     CreatePipe(&mut output_read_side, &mut output_write_side, std::ptr::null(), 0);
    /// }
    ///
    /// let size = COORD { X: 60, Y: 40 };
    /// let mut h_pc = unsafe { std::mem::zeroed() };
    /// unsafe { CreatePseudoConsole(size, input_read_side, output_write_side, 0, &mut h_pc) };
    ///
    /// unsafe { CloseHandle(input_read_side) };
    /// unsafe { CloseHandle(output_write_side) };
    ///
    /// const PROC_THREAD_ATTRIBUTE_PSEUDOCONSOLE: usize = 131094;
    ///
    /// let attribute_list = unsafe {
    ///     ProcThreadAttributeList::build()
    ///         .raw_attribute(
    ///             PROC_THREAD_ATTRIBUTE_PSEUDOCONSOLE,
    ///             h_pc as *const c_void,
    ///             size_of::<isize>(),
    ///         )
    ///         .finish()?
    /// };
    ///
    /// let mut child = Command::new("cmd").spawn_with_attributes(&attribute_list)?;
    /// #
    /// # child.kill()?;
    /// # Ok::<(), std::io::Error>(())
    /// ```
    pub unsafe fn raw_attribute<T>(
        mut self,
        attribute: usize,
        value_ptr: *const T,
        value_size: usize,
    ) -> Self {
        self.attributes.insert(
            attribute,
            ProcThreadAttributeValue { ptr: value_ptr.cast::<c_void>(), size: value_size },
        );
        self
    }

    /// Finalizes the construction of the `ProcThreadAttributeList`.
    ///
    /// # Errors
    ///
    /// Returns an error if the maximum number of attributes is exceeded
    /// or if there is an I/O error during initialization.
    pub fn finish(&self) -> io::Result<ProcThreadAttributeList<'a>> {
        // To initialize our ProcThreadAttributeList, we need to determine
        // how many bytes to allocate for it. The Windows API simplifies this
        // process by allowing us to call `InitializeProcThreadAttributeList`
        // with a null pointer to retrieve the required size.
        let mut required_size = 0;
        let Ok(attribute_count) = self.attributes.len().try_into() else {
            return Err(io::const_error!(
                io::ErrorKind::InvalidInput,
                "maximum number of ProcThreadAttributes exceeded",
            ));
        };
        unsafe {
            sys::c::InitializeProcThreadAttributeList(
                ptr::null_mut(),
                attribute_count,
                0,
                &mut required_size,
            )
        };

        let mut attribute_list = vec![MaybeUninit::uninit(); required_size].into_boxed_slice();

        // Once we've allocated the necessary memory, it's safe to invoke
        // `InitializeProcThreadAttributeList` to properly initialize the list.
        sys::cvt(unsafe {
            sys::c::InitializeProcThreadAttributeList(
                attribute_list.as_mut_ptr().cast::<c_void>(),
                attribute_count,
                0,
                &mut required_size,
            )
        })?;

        // # Add our attributes to the buffer.
        // It's theoretically possible for the attribute count to exceed a u32
        // value. Therefore, we ensure that we don't add more attributes than
        // the buffer was initialized for.
        for (&attribute, value) in self.attributes.iter().take(attribute_count as usize) {
            sys::cvt(unsafe {
                sys::c::UpdateProcThreadAttribute(
                    attribute_list.as_mut_ptr().cast::<c_void>(),
                    0,
                    attribute,
                    value.ptr,
                    value.size,
                    ptr::null_mut(),
                    ptr::null_mut(),
                )
            })?;
        }

        Ok(ProcThreadAttributeList { attribute_list, _lifetime_marker: marker::PhantomData })
    }
}

/// Wrapper around the value data to be used as a Process Thread Attribute.
#[derive(Clone, Debug)]
struct ProcThreadAttributeValue {
    ptr: *const c_void,
    size: usize,
}
