Skip to content

Stablize anonymous pipe #137793

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Mar 17, 2025
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion library/std/src/io/mod.rs
Original file line number Diff line number Diff line change
@@ -310,7 +310,7 @@ pub use self::error::RawOsError;
pub use self::error::SimpleMessage;
#[unstable(feature = "io_const_error", issue = "133448")]
pub use self::error::const_error;
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
pub use self::pipe::{PipeReader, PipeWriter, pipe};
#[stable(feature = "is_terminal", since = "1.70.0")]
pub use self::stdio::IsTerminal;
46 changes: 34 additions & 12 deletions library/std/src/io/pipe.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use crate::io;
use crate::sys::anonymous_pipe::{AnonPipe, pipe as pipe_inner};
use crate::sys_common::{FromInner, IntoInner};

/// Create an anonymous pipe.
///
@@ -40,7 +41,6 @@ use crate::sys::anonymous_pipe::{AnonPipe, pipe as pipe_inner};
/// # Examples
///
/// ```no_run
/// #![feature(anonymous_pipe)]
/// # #[cfg(miri)] fn main() {}
/// # #[cfg(not(miri))]
/// # fn main() -> std::io::Result<()> {
@@ -67,29 +67,52 @@ use crate::sys::anonymous_pipe::{AnonPipe, pipe as pipe_inner};
/// ```
/// [changes]: io#platform-specific-behavior
/// [man page]: https://man7.org/linux/man-pages/man7/pipe.7.html
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
#[inline]
pub fn pipe() -> io::Result<(PipeReader, PipeWriter)> {
pipe_inner().map(|(reader, writer)| (PipeReader(reader), PipeWriter(writer)))
}

/// Read end of an anonymous pipe.
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
#[derive(Debug)]
pub struct PipeReader(pub(crate) AnonPipe);

/// Write end of an anonymous pipe.
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
#[derive(Debug)]
pub struct PipeWriter(pub(crate) AnonPipe);

impl FromInner<AnonPipe> for PipeReader {
fn from_inner(inner: AnonPipe) -> Self {
Self(inner)
}
}

impl IntoInner<AnonPipe> for PipeReader {
fn into_inner(self) -> AnonPipe {
self.0
}
}

impl FromInner<AnonPipe> for PipeWriter {
fn from_inner(inner: AnonPipe) -> Self {
Self(inner)
}
}

impl IntoInner<AnonPipe> for PipeWriter {
fn into_inner(self) -> AnonPipe {
self.0
}
}

impl PipeReader {
/// Create a new [`PipeReader`] instance that shares the same underlying file description.
///
/// # Examples
///
/// ```no_run
/// #![feature(anonymous_pipe)]
/// # #[cfg(miri)] fn main() {}
/// # #[cfg(not(miri))]
/// # fn main() -> std::io::Result<()> {
@@ -137,7 +160,7 @@ impl PipeReader {
/// # Ok(())
/// # }
/// ```
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
pub fn try_clone(&self) -> io::Result<Self> {
self.0.try_clone().map(Self)
}
@@ -149,7 +172,6 @@ impl PipeWriter {
/// # Examples
///
/// ```no_run
/// #![feature(anonymous_pipe)]
/// # #[cfg(miri)] fn main() {}
/// # #[cfg(not(miri))]
/// # fn main() -> std::io::Result<()> {
@@ -177,13 +199,13 @@ impl PipeWriter {
/// # Ok(())
/// # }
/// ```
#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
pub fn try_clone(&self) -> io::Result<Self> {
self.0.try_clone().map(Self)
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl io::Read for &PipeReader {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
self.0.read(buf)
@@ -203,7 +225,7 @@ impl io::Read for &PipeReader {
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl io::Read for PipeReader {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
self.0.read(buf)
@@ -223,7 +245,7 @@ impl io::Read for PipeReader {
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl io::Write for &PipeWriter {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
self.0.write(buf)
@@ -241,7 +263,7 @@ impl io::Write for &PipeWriter {
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl io::Write for PipeWriter {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
self.0.write(buf)
45 changes: 44 additions & 1 deletion library/std/src/os/fd/owned.rs
Original file line number Diff line number Diff line change
@@ -15,8 +15,9 @@ use crate::mem::ManuallyDrop;
target_os = "trusty"
)))]
use crate::sys::cvt;
use crate::sys_common::FromInner;
#[cfg(not(target_os = "trusty"))]
use crate::sys_common::{AsInner, FromInner, IntoInner};
use crate::sys_common::{AsInner, IntoInner};
use crate::{fmt, io};

type ValidRawFd = core::num::niche_types::NotAllOnes<RawFd>;
@@ -504,3 +505,45 @@ impl<'a> AsFd for io::StderrLock<'a> {
unsafe { BorrowedFd::borrow_raw(2) }
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsFd for io::PipeReader {
fn as_fd(&self) -> BorrowedFd<'_> {
self.0.as_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeReader> for OwnedFd {
fn from(pipe: io::PipeReader) -> Self {
pipe.0.into_inner()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsFd for io::PipeWriter {
fn as_fd(&self) -> BorrowedFd<'_> {
self.0.as_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeWriter> for OwnedFd {
fn from(pipe: io::PipeWriter) -> Self {
pipe.0.into_inner()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<OwnedFd> for io::PipeReader {
fn from(owned_fd: OwnedFd) -> Self {
Self(FromInner::from_inner(owned_fd))
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<OwnedFd> for io::PipeWriter {
fn from(owned_fd: OwnedFd) -> Self {
Self(FromInner::from_inner(owned_fd))
}
}
43 changes: 43 additions & 0 deletions library/std/src/os/fd/raw.rs
Original file line number Diff line number Diff line change
@@ -18,6 +18,7 @@ use crate::os::unix::io::AsFd;
use crate::os::unix::io::OwnedFd;
#[cfg(target_os = "wasi")]
use crate::os::wasi::io::OwnedFd;
use crate::sys_common::FromInner;
#[cfg(not(target_os = "trusty"))]
use crate::sys_common::{AsInner, IntoInner};

@@ -284,3 +285,45 @@ impl<T: AsRawFd> AsRawFd for Box<T> {
(**self).as_raw_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsRawFd for io::PipeReader {
fn as_raw_fd(&self) -> RawFd {
self.0.as_raw_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl FromRawFd for io::PipeReader {
unsafe fn from_raw_fd(raw_fd: RawFd) -> Self {
Self::from_inner(unsafe { FromRawFd::from_raw_fd(raw_fd) })
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl IntoRawFd for io::PipeReader {
fn into_raw_fd(self) -> RawFd {
self.0.into_raw_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsRawFd for io::PipeWriter {
fn as_raw_fd(&self) -> RawFd {
self.0.as_raw_fd()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl FromRawFd for io::PipeWriter {
unsafe fn from_raw_fd(raw_fd: RawFd) -> Self {
Self::from_inner(unsafe { FromRawFd::from_raw_fd(raw_fd) })
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl IntoRawFd for io::PipeWriter {
fn into_raw_fd(self) -> RawFd {
self.0.into_raw_fd()
}
}
42 changes: 42 additions & 0 deletions library/std/src/os/windows/io/handle.rs
Original file line number Diff line number Diff line change
@@ -660,3 +660,45 @@ impl<T> From<crate::thread::JoinHandle<T>> for OwnedHandle {
join_handle.into_inner().into_handle().into_inner()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsHandle for io::PipeReader {
fn as_handle(&self) -> BorrowedHandle<'_> {
self.0.as_handle()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeReader> for OwnedHandle {
fn from(pipe: io::PipeReader) -> Self {
pipe.into_inner().into_inner()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsHandle for io::PipeWriter {
fn as_handle(&self) -> BorrowedHandle<'_> {
self.0.as_handle()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeWriter> for OwnedHandle {
fn from(pipe: io::PipeWriter) -> Self {
pipe.into_inner().into_inner()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<OwnedHandle> for io::PipeReader {
fn from(owned_handle: OwnedHandle) -> Self {
Self::from_inner(FromInner::from_inner(owned_handle))
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<OwnedHandle> for io::PipeWriter {
fn from(owned_handle: OwnedHandle) -> Self {
Self::from_inner(FromInner::from_inner(owned_handle))
}
}
42 changes: 42 additions & 0 deletions library/std/src/os/windows/io/raw.rs
Original file line number Diff line number Diff line change
@@ -310,3 +310,45 @@ impl IntoRawSocket for net::UdpSocket {
self.into_inner().into_socket().into_inner().into_raw_socket()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsRawHandle for io::PipeReader {
fn as_raw_handle(&self) -> RawHandle {
self.0.as_raw_handle()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl FromRawHandle for io::PipeReader {
unsafe fn from_raw_handle(raw_handle: RawHandle) -> Self {
unsafe { Self::from_inner(FromRawHandle::from_raw_handle(raw_handle)) }
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl IntoRawHandle for io::PipeReader {
fn into_raw_handle(self) -> RawHandle {
self.0.into_raw_handle()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl AsRawHandle for io::PipeWriter {
fn as_raw_handle(&self) -> RawHandle {
self.0.as_raw_handle()
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl FromRawHandle for io::PipeWriter {
unsafe fn from_raw_handle(raw_handle: RawHandle) -> Self {
unsafe { Self::from_inner(FromRawHandle::from_raw_handle(raw_handle)) }
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl IntoRawHandle for io::PipeWriter {
fn into_raw_handle(self) -> RawHandle {
self.0.into_raw_handle()
}
}
14 changes: 14 additions & 0 deletions library/std/src/process.rs
Original file line number Diff line number Diff line change
@@ -1659,6 +1659,20 @@ impl From<io::Stderr> for Stdio {
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeWriter> for Stdio {
fn from(pipe: io::PipeWriter) -> Self {
Stdio::from_inner(pipe.into_inner().into())
}
}

#[stable(feature = "anonymous_pipe", since = "CURRENT_RUSTC_VERSION")]
impl From<io::PipeReader> for Stdio {
fn from(pipe: io::PipeReader) -> Self {
Stdio::from_inner(pipe.into_inner().into())
}
}

/// Describes the result of a process after it has terminated.
///
/// This `struct` is used to represent the exit status or other termination of a child process.
94 changes: 2 additions & 92 deletions library/std/src/sys/anonymous_pipe/unix.rs
Original file line number Diff line number Diff line change
@@ -1,101 +1,11 @@
use crate::io::{self, PipeReader, PipeWriter};
use crate::os::fd::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, OwnedFd, RawFd};
use crate::process::Stdio;
use crate::io;
use crate::sys::fd::FileDesc;
use crate::sys::pipe::anon_pipe;
use crate::sys_common::{FromInner, IntoInner};
use crate::sys_common::IntoInner;

pub type AnonPipe = FileDesc;

#[inline]
pub fn pipe() -> io::Result<(AnonPipe, AnonPipe)> {
anon_pipe().map(|(rx, wx)| (rx.into_inner(), wx.into_inner()))
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsFd for PipeReader {
fn as_fd(&self) -> BorrowedFd<'_> {
self.0.as_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsRawFd for PipeReader {
fn as_raw_fd(&self) -> RawFd {
self.0.as_raw_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeReader> for OwnedFd {
fn from(pipe: PipeReader) -> Self {
FileDesc::into_inner(pipe.0)
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl FromRawFd for PipeReader {
unsafe fn from_raw_fd(raw_fd: RawFd) -> Self {
unsafe { Self(FileDesc::from_raw_fd(raw_fd)) }
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl IntoRawFd for PipeReader {
fn into_raw_fd(self) -> RawFd {
self.0.into_raw_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeReader> for Stdio {
fn from(pipe: PipeReader) -> Self {
Self::from(OwnedFd::from(pipe))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsFd for PipeWriter {
fn as_fd(&self) -> BorrowedFd<'_> {
self.0.as_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsRawFd for PipeWriter {
fn as_raw_fd(&self) -> RawFd {
self.0.as_raw_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeWriter> for OwnedFd {
fn from(pipe: PipeWriter) -> Self {
FileDesc::into_inner(pipe.0)
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl FromRawFd for PipeWriter {
unsafe fn from_raw_fd(raw_fd: RawFd) -> Self {
unsafe { Self(FileDesc::from_raw_fd(raw_fd)) }
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl IntoRawFd for PipeWriter {
fn into_raw_fd(self) -> RawFd {
self.0.into_raw_fd()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeWriter> for Stdio {
fn from(pipe: PipeWriter) -> Self {
Self::from(OwnedFd::from(pipe))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<OwnedFd> for PipeReader {
fn from(owned_fd: OwnedFd) -> Self {
Self(FileDesc::from_inner(owned_fd))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<OwnedFd> for PipeWriter {
fn from(owned_fd: OwnedFd) -> Self {
Self(FileDesc::from_inner(owned_fd))
}
}
17 changes: 1 addition & 16 deletions library/std/src/sys/anonymous_pipe/unsupported.rs
Original file line number Diff line number Diff line change
@@ -1,22 +1,7 @@
use crate::io::{self, PipeReader, PipeWriter};
use crate::process::Stdio;
use crate::io;
pub use crate::sys::pipe::AnonPipe;

#[inline]
pub fn pipe() -> io::Result<(AnonPipe, AnonPipe)> {
Err(io::Error::UNSUPPORTED_PLATFORM)
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeReader> for Stdio {
fn from(pipe: PipeReader) -> Self {
pipe.0.diverge()
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeWriter> for Stdio {
fn from(pipe: PipeWriter) -> Self {
pipe.0.diverge()
}
}
101 changes: 2 additions & 99 deletions library/std/src/sys/anonymous_pipe/windows.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,7 @@
use crate::io::{self, PipeReader, PipeWriter};
use crate::os::windows::io::{
AsHandle, AsRawHandle, BorrowedHandle, FromRawHandle, IntoRawHandle, OwnedHandle, RawHandle,
};
use crate::process::Stdio;
use crate::ptr;
use crate::os::windows::io::FromRawHandle;
use crate::sys::c;
use crate::sys::handle::Handle;
use crate::sys_common::{FromInner, IntoInner};
use crate::{io, ptr};

pub type AnonPipe = Handle;

@@ -22,95 +17,3 @@ pub fn pipe() -> io::Result<(AnonPipe, AnonPipe)> {
unsafe { Ok((Handle::from_raw_handle(read_pipe), Handle::from_raw_handle(write_pipe))) }
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsHandle for PipeReader {
fn as_handle(&self) -> BorrowedHandle<'_> {
self.0.as_handle()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsRawHandle for PipeReader {
fn as_raw_handle(&self) -> RawHandle {
self.0.as_raw_handle()
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl FromRawHandle for PipeReader {
unsafe fn from_raw_handle(raw_handle: RawHandle) -> Self {
unsafe { Self(Handle::from_raw_handle(raw_handle)) }
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl IntoRawHandle for PipeReader {
fn into_raw_handle(self) -> RawHandle {
self.0.into_raw_handle()
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeReader> for OwnedHandle {
fn from(pipe: PipeReader) -> Self {
Handle::into_inner(pipe.0)
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeReader> for Stdio {
fn from(pipe: PipeReader) -> Self {
Self::from(OwnedHandle::from(pipe))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsHandle for PipeWriter {
fn as_handle(&self) -> BorrowedHandle<'_> {
self.0.as_handle()
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl AsRawHandle for PipeWriter {
fn as_raw_handle(&self) -> RawHandle {
self.0.as_raw_handle()
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl FromRawHandle for PipeWriter {
unsafe fn from_raw_handle(raw_handle: RawHandle) -> Self {
unsafe { Self(Handle::from_raw_handle(raw_handle)) }
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl IntoRawHandle for PipeWriter {
fn into_raw_handle(self) -> RawHandle {
self.0.into_raw_handle()
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeWriter> for OwnedHandle {
fn from(pipe: PipeWriter) -> Self {
Handle::into_inner(pipe.0)
}
}
#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<PipeWriter> for Stdio {
fn from(pipe: PipeWriter) -> Self {
Self::from(OwnedHandle::from(pipe))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<OwnedHandle> for PipeReader {
fn from(owned_handle: OwnedHandle) -> Self {
Self(Handle::from_inner(owned_handle))
}
}

#[unstable(feature = "anonymous_pipe", issue = "127154")]
impl From<OwnedHandle> for PipeWriter {
fn from(owned_handle: OwnedHandle) -> Self {
Self(Handle::from_inner(owned_handle))
}
}
6 changes: 6 additions & 0 deletions library/std/src/sys/pal/unix/process/process_common.rs
Original file line number Diff line number Diff line change
@@ -491,6 +491,12 @@ impl From<AnonPipe> for Stdio {
}
}

impl From<FileDesc> for Stdio {
fn from(fd: FileDesc) -> Stdio {
Stdio::Fd(fd)
}
}

impl From<File> for Stdio {
fn from(file: File) -> Stdio {
Stdio::Fd(file.into_inner())
51 changes: 51 additions & 0 deletions library/std/src/sys/pal/unsupported/pipe.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use crate::fmt;
use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
use crate::sys_common::{FromInner, IntoInner};

pub struct AnonPipe(!);

@@ -54,3 +55,53 @@ impl AnonPipe {
pub fn read2(p1: AnonPipe, _v1: &mut Vec<u8>, _p2: AnonPipe, _v2: &mut Vec<u8>) -> io::Result<()> {
match p1.0 {}
}

impl FromInner<!> for AnonPipe {
fn from_inner(inner: !) -> Self {
inner
}
}

impl IntoInner<!> for AnonPipe {
fn into_inner(self) -> ! {
self.0
}
}

#[cfg(any(unix, target_os = "hermit", target_os = "wasi"))]
mod unix_traits {
use super::AnonPipe;
use crate::os::fd::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, OwnedFd, RawFd};
use crate::sys_common::FromInner;

impl AsRawFd for AnonPipe {
#[inline]
fn as_raw_fd(&self) -> RawFd {
self.0
}
}

impl AsFd for AnonPipe {
fn as_fd(&self) -> BorrowedFd<'_> {
self.0
}
}

impl IntoRawFd for AnonPipe {
fn into_raw_fd(self) -> RawFd {
self.0
}
}

impl FromRawFd for AnonPipe {
unsafe fn from_raw_fd(_: RawFd) -> Self {
panic!("creating pipe on this platform is unsupported!")
}
}

impl FromInner<OwnedFd> for AnonPipe {
fn from_inner(_: OwnedFd) -> Self {
panic!("creating pipe on this platform is unsupported!")
}
}
}
6 changes: 6 additions & 0 deletions library/std/src/sys/pal/windows/process.rs
Original file line number Diff line number Diff line change
@@ -621,6 +621,12 @@ impl From<AnonPipe> for Stdio {
}
}

impl From<Handle> for Stdio {
fn from(pipe: Handle) -> Stdio {
Stdio::Handle(pipe)
}
}

impl From<File> for Stdio {
fn from(file: File) -> Stdio {
Stdio::Handle(file.into_inner())
2 changes: 0 additions & 2 deletions library/std/tests/pipe_subprocess.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
#![feature(anonymous_pipe)]

fn main() {
#[cfg(all(not(miri), any(unix, windows), not(target_os = "emscripten")))]
{
2 changes: 0 additions & 2 deletions src/tools/miri/tests/pass/shims/pipe.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
//@ignore-target: windows

#![feature(anonymous_pipe)]

use std::io::{Read, Write, pipe};

fn main() {