alnyan/yggdrasil: better fd inheritance in spawn

This commit is contained in:
Mark Poliakov 2025-01-03 15:28:51 +02:00
parent 7e037c9d4e
commit 8099ae1760
3 changed files with 28 additions and 18 deletions

View File

@ -3,3 +3,11 @@ mod raw;
pub use owned::*;
pub use raw::*;
use crate::io;
use crate::sys::cvt_io;
#[unstable(feature = "yggdrasil_os", issue = "none")]
pub fn clone_fd(src: RawFd) -> io::Result<RawFd> {
cvt_io(unsafe { yggdrasil_rt::sys::clone_fd(src, None) })
}

View File

@ -1,6 +1,6 @@
#![stable(feature = "os_fd", since = "1.66.0")]
use crate::sys_common::{AsInner, FromInner};
use crate::sys_common::{AsInner, FromInner, IntoInner};
#[stable(feature = "rust1", since = "1.0.0")]
pub type RawFd = yggdrasil_rt::io::RawFd;
@ -89,3 +89,10 @@ impl FromRawFd for crate::fs::File {
crate::fs::File::from_inner(inner)
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl IntoRawFd for crate::fs::File {
fn into_raw_fd(self) -> RawFd {
self.into_inner().into_raw_fd()
}
}

View File

@ -10,7 +10,7 @@ pub use crate::ffi::OsString as EnvKey;
use crate::fmt;
use crate::io::{self, Stderr, Stdout};
use crate::num::NonZeroI32;
use crate::os::fd::{AsRawFd, FromRawFd, OwnedFd};
use crate::os::fd::{AsRawFd, FromRawFd, IntoRawFd};
use crate::os::yggdrasil::io::pipe as os_pipe;
use crate::path::Path;
use crate::sys::cvt_io;
@ -42,7 +42,6 @@ pub enum ChildStdio {
Inherit,
Null,
RawFd(RawFd),
OwnedFd(OwnedFd),
}
#[derive(Debug)]
@ -51,8 +50,6 @@ pub enum Stdio {
Null,
MakePipe,
RawFd(RawFd),
#[allow(dead_code)]
OwnedFd(FileDesc),
}
pub struct Process {
@ -109,13 +106,12 @@ impl Stdio {
if readable {
let write = AnonPipe::from_inner(write);
Ok((ChildStdio::OwnedFd(read), Some(write)))
Ok((ChildStdio::RawFd(read.into_raw_fd()), Some(write)))
} else {
let read = AnonPipe::from_inner(read);
Ok((ChildStdio::OwnedFd(write), Some(read)))
Ok((ChildStdio::RawFd(write.into_raw_fd()), Some(read)))
}
}
Stdio::OwnedFd(fd) => Ok((ChildStdio::RawFd(fd.as_raw_fd()), None)),
Stdio::RawFd(fd) => Ok((ChildStdio::RawFd(*fd), None)),
}
}
@ -146,12 +142,11 @@ impl From<Stderr> for Stdio {
}
impl ChildStdio {
fn as_raw_fd_or_default(&self, default: RawFd) -> Option<RawFd> {
fn as_inherit_option(&self, child: RawFd) -> Option<SpawnOption> {
match self {
Self::Inherit => Some(SpawnOption::CopyFile { source: child, child }),
&Self::RawFd(fd) => Some(SpawnOption::MoveFile { source: fd, child }),
Self::Null => None,
Self::Inherit => Some(default),
Self::OwnedFd(fd) => Some(fd.as_raw_fd()),
Self::RawFd(fd) => Some(*fd),
}
}
}
@ -345,14 +340,14 @@ impl Command {
fn do_spawn(&mut self, pipes: &ChildPipes) -> io::Result<Process> {
let mut optional = Vec::new();
if let Some(fd) = pipes.stdin.as_raw_fd_or_default(RawFd::STDIN) {
optional.push(SpawnOption::InheritFile { source: fd, child: RawFd::STDIN });
if let Some(stdin) = pipes.stdin.as_inherit_option(RawFd::STDIN) {
optional.push(stdin);
}
if let Some(fd) = pipes.stdout.as_raw_fd_or_default(RawFd::STDOUT) {
optional.push(SpawnOption::InheritFile { source: fd, child: RawFd::STDOUT });
if let Some(stdout) = pipes.stdout.as_inherit_option(RawFd::STDOUT) {
optional.push(stdout);
}
if let Some(fd) = pipes.stderr.as_raw_fd_or_default(RawFd::STDERR) {
optional.push(SpawnOption::InheritFile { source: fd, child: RawFd::STDERR });
if let Some(stderr) = pipes.stderr.as_inherit_option(RawFd::STDERR) {
optional.push(stderr);
}
if let Some(pgroup) = self.pgroup {