alnyan/yggdrasil: File open/read/write

This commit is contained in:
2023-07-18 17:43:04 +03:00
parent 8b39059da8
commit 0a15cff03f
7 changed files with 529 additions and 479 deletions
+3 -3
View File
@@ -151,8 +151,6 @@ pub mod owned {
impl FromRawFd for OwnedFd {
unsafe fn from_raw_fd(fd: RawFd) -> Self {
assert_ne!(fd, u32::MAX as RawFd);
Self { fd }
}
}
@@ -165,7 +163,9 @@ pub mod owned {
impl Drop for OwnedFd {
fn drop(&mut self) {
todo!()
unsafe {
yggdrasil_rt::sys::close(self.fd).ok();
}
}
}
-432
View File
@@ -1,432 +0,0 @@
#![allow(dead_code)]
use crate::ffi::{CStr, OsString};
use crate::fmt;
use crate::hash::{Hash, Hasher};
use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut, SeekFrom};
use crate::os::yggdrasil::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, RawFd};
use crate::path::{Path, PathBuf};
use crate::sys::fd::FileDesc;
use crate::sys::time::SystemTime;
use crate::sys_common::{AsInner, AsInnerMut, FromInner, IntoInner};
#[derive(Debug)]
pub struct File(FileDesc);
pub struct FileAttr(!);
pub struct FilePermissions(!);
pub struct FileType(!);
#[derive(Copy, Clone, Debug, Default)]
pub struct FileTimes {}
#[derive(Clone, Copy, Debug)]
pub struct OpenOptions {
read: bool,
write: bool,
append: bool,
truncate: bool,
create: bool,
create_new: bool,
mode: i32,
}
pub struct DirEntry(!);
pub struct ReadDir(!);
#[derive(Debug)]
pub struct DirBuilder {}
impl OpenOptions {
pub fn new() -> Self {
todo!()
}
pub fn read(&mut self, _read: bool) {
todo!()
}
pub fn write(&mut self, _write: bool) {
todo!()
}
pub fn append(&mut self, _append: bool) {
todo!()
}
pub fn truncate(&mut self, _truncate: bool) {
todo!()
}
pub fn create(&mut self, _create: bool) {
todo!()
}
pub fn create_new(&mut self, _create_new: bool) {
todo!()
}
}
impl FileAttr {
pub fn size(&self) -> u64 {
todo!()
}
pub fn perm(&self) -> FilePermissions {
todo!()
}
pub fn file_type(&self) -> FileType {
todo!()
}
pub fn modified(&self) -> io::Result<SystemTime> {
todo!()
}
pub fn accessed(&self) -> io::Result<SystemTime> {
todo!()
}
pub fn created(&self) -> io::Result<SystemTime> {
todo!()
}
}
impl Clone for FileAttr {
fn clone(&self) -> Self {
todo!()
}
}
impl FilePermissions {
pub fn readonly(&self) -> bool {
todo!()
}
pub fn set_readonly(&mut self, _readonly: bool) {
todo!()
}
}
impl Clone for FilePermissions {
fn clone(&self) -> Self {
todo!()
}
}
impl PartialEq for FilePermissions {
fn eq(&self, _other: &Self) -> bool {
todo!()
}
}
impl Eq for FilePermissions {}
impl fmt::Debug for FilePermissions {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl FileType {
pub fn is_dir(&self) -> bool {
todo!()
}
pub fn is_file(&self) -> bool {
todo!()
}
pub fn is_symlink(&self) -> bool {
todo!()
}
}
impl Clone for FileType {
fn clone(&self) -> Self {
todo!()
}
}
impl Copy for FileType {}
impl PartialEq for FileType {
fn eq(&self, _other: &Self) -> bool {
todo!()
}
}
impl Eq for FileType {}
impl Hash for FileType {
fn hash<H: Hasher>(&self, _h: &mut H) {
todo!()
}
}
impl fmt::Debug for FileType {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl FileTimes {
pub fn set_accessed(&mut self, _t: SystemTime) {
todo!()
}
pub fn set_modified(&mut self, _t: SystemTime) {
todo!()
}
}
impl File {
pub fn open(_path: &Path, _opts: &OpenOptions) -> io::Result<File> {
todo!()
// run_path_with_cstr(path, |path| File::open_c(&path, opts))
}
pub fn open_c(_path: &CStr, _opts: &OpenOptions) -> io::Result<File> {
todo!()
// let mut flags = opts.get_access_mode()?;
// flags = flags | opts.get_creation_mode()?;
// let mode;
// if flags & O_CREAT == O_CREAT {
// mode = opts.mode;
// } else {
// mode = 0;
// }
// let fd = unsafe { cvt(abi::open(path.as_ptr(), flags, mode))? };
// Ok(File(unsafe { FileDesc::from_raw_fd(fd as i32) }))
}
pub fn file_attr(&self) -> io::Result<FileAttr> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn fsync(&self) -> io::Result<()> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn datasync(&self) -> io::Result<()> {
todo!()
// self.fsync()
}
pub fn truncate(&self, _size: u64) -> io::Result<()> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn read(&self, _buf: &mut [u8]) -> io::Result<usize> {
todo!()
// self.0.read(buf)
}
pub fn read_vectored(&self, _bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
todo!()
// crate::io::default_read_vectored(|buf| self.read(buf), bufs)
}
#[inline]
pub fn is_read_vectored(&self) -> bool {
todo!()
// false
}
pub fn read_buf(&self, _cursor: BorrowedCursor<'_>) -> io::Result<()> {
todo!()
// crate::io::default_read_buf(|buf| self.read(buf), cursor)
}
pub fn write(&self, _buf: &[u8]) -> io::Result<usize> {
todo!()
// self.0.write(buf)
}
pub fn write_vectored(&self, _bufs: &[IoSlice<'_>]) -> io::Result<usize> {
todo!()
// crate::io::default_write_vectored(|buf| self.write(buf), bufs)
}
#[inline]
pub fn is_write_vectored(&self) -> bool {
todo!()
// false
}
pub fn flush(&self) -> io::Result<()> {
todo!()
// Ok(())
}
pub fn seek(&self, _pos: SeekFrom) -> io::Result<u64> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn duplicate(&self) -> io::Result<File> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn set_permissions(&self, _perm: FilePermissions) -> io::Result<()> {
todo!()
// Err(Error::from_raw_os_error(22))
}
pub fn set_times(&self, _times: FileTimes) -> io::Result<()> {
todo!();
// Err(Error::from_raw_os_error(22))
}
}
impl Iterator for ReadDir {
type Item = io::Result<DirEntry>;
fn next(&mut self) -> Option<io::Result<DirEntry>> {
todo!()
}
}
impl fmt::Debug for ReadDir {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl DirEntry {
pub fn path(&self) -> PathBuf {
todo!()
}
pub fn file_name(&self) -> OsString {
todo!()
}
pub fn metadata(&self) -> io::Result<FileAttr> {
todo!()
}
pub fn file_type(&self) -> io::Result<FileType> {
todo!()
}
}
impl DirBuilder {
pub fn new() -> DirBuilder {
todo!()
}
pub fn mkdir(&self, _p: &Path) -> io::Result<()> {
todo!()
}
}
impl AsInner<FileDesc> for File {
fn as_inner(&self) -> &FileDesc {
todo!()
}
}
impl IntoInner<FileDesc> for File {
fn into_inner(self) -> FileDesc {
todo!()
}
}
impl AsInnerMut<FileDesc> for File {
fn as_inner_mut(&mut self) -> &mut FileDesc {
todo!()
}
}
impl FromInner<FileDesc> for File {
fn from_inner(_file_desc: FileDesc) -> Self {
todo!()
}
}
impl AsFd for File {
fn as_fd(&self) -> BorrowedFd<'_> {
todo!()
}
}
impl AsRawFd for File {
fn as_raw_fd(&self) -> RawFd {
todo!()
}
}
impl IntoRawFd for File {
fn into_raw_fd(self) -> RawFd {
todo!()
}
}
impl FromRawFd for File {
unsafe fn from_raw_fd(_raw_fd: RawFd) -> Self {
todo!()
}
}
pub fn readdir(_p: &Path) -> io::Result<ReadDir> {
todo!()
}
pub fn unlink(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn rename(_old: &Path, _new: &Path) -> io::Result<()> {
todo!()
}
pub fn set_perm(_p: &Path, _perm: FilePermissions) -> io::Result<()> {
todo!()
}
pub fn remove_dir_all(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn readlink(_p: &Path) -> io::Result<PathBuf> {
todo!()
}
pub fn symlink(_original: &Path, _link: &Path) -> io::Result<()> {
todo!()
}
pub fn link(_original: &Path, _link: &Path) -> io::Result<()> {
todo!()
}
pub fn stat(_p: &Path) -> io::Result<FileAttr> {
todo!()
}
pub fn lstat(_p: &Path) -> io::Result<FileAttr> {
todo!()
}
pub fn canonicalize(_p: &Path) -> io::Result<PathBuf> {
todo!()
}
pub fn rmdir(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn copy(_from: &Path, _to: &Path) -> io::Result<u64> {
todo!()
}
pub fn try_exists(_path: &Path) -> io::Result<bool> {
todo!()
}
+190
View File
@@ -0,0 +1,190 @@
use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut, SeekFrom};
use crate::os::yggdrasil::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, RawFd};
use crate::path::Path;
use crate::sys::cvt_io;
use crate::sys::fd::FileDesc;
use crate::sys_common::{AsInner, AsInnerMut, FromInner, IntoInner};
use super::{FileAttr, FilePermissions, FileTimes};
#[derive(Debug)]
pub struct File(FileDesc);
#[allow(dead_code)]
#[derive(Clone, Copy, Debug, Default)]
pub struct OpenOptions {
read: bool,
write: bool,
append: bool,
truncate: bool,
create: bool,
create_new: bool,
mode: i32,
}
impl OpenOptions {
pub fn new() -> Self {
Self { mode: 0o700, ..Default::default() }
}
pub fn read(&mut self, read: bool) {
self.read = read;
}
pub fn write(&mut self, write: bool) {
self.write = write;
}
pub fn append(&mut self, _append: bool) {
todo!()
}
pub fn truncate(&mut self, _truncate: bool) {
todo!()
}
pub fn create(&mut self, _create: bool) {
todo!()
}
pub fn create_new(&mut self, _create_new: bool) {
todo!()
}
}
impl Into<yggdrasil_rt::OpenFlags> for OpenOptions {
fn into(self) -> yggdrasil_rt::OpenFlags {
let mut res = yggdrasil_rt::OpenFlags::new();
if self.read {
res = res.read();
}
if self.write {
res = res.write();
}
res
}
}
impl File {
pub fn open(path: &Path, opts: &OpenOptions) -> io::Result<File> {
let path = path.as_os_str();
unsafe {
cvt_io(yggdrasil_rt::sys::open(path.to_str().unwrap(), (*opts).into()))
.map(|fd| File::from_raw_fd(fd))
}
}
pub fn file_attr(&self) -> io::Result<FileAttr> {
todo!()
}
pub fn fsync(&self) -> io::Result<()> {
todo!()
}
pub fn datasync(&self) -> io::Result<()> {
todo!()
}
pub fn truncate(&self, _size: u64) -> io::Result<()> {
todo!()
}
pub fn read(&self, buf: &mut [u8]) -> io::Result<usize> {
unsafe { cvt_io(yggdrasil_rt::sys::read(self.as_raw_fd(), buf)) }
}
pub fn read_vectored(&self, _bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
todo!()
}
#[inline]
pub fn is_read_vectored(&self) -> bool {
false
}
pub fn read_buf(&self, _cursor: BorrowedCursor<'_>) -> io::Result<()> {
todo!()
}
pub fn write(&self, buf: &[u8]) -> io::Result<usize> {
unsafe { cvt_io(yggdrasil_rt::sys::write(self.as_raw_fd(), buf)) }
}
pub fn write_vectored(&self, _bufs: &[IoSlice<'_>]) -> io::Result<usize> {
todo!()
}
#[inline]
pub fn is_write_vectored(&self) -> bool {
false
}
pub fn flush(&self) -> io::Result<()> {
todo!()
}
pub fn seek(&self, _pos: SeekFrom) -> io::Result<u64> {
todo!()
}
pub fn duplicate(&self) -> io::Result<File> {
todo!()
}
pub fn set_permissions(&self, _perm: FilePermissions) -> io::Result<()> {
todo!()
}
pub fn set_times(&self, _times: FileTimes) -> io::Result<()> {
todo!();
}
}
impl AsInner<FileDesc> for File {
fn as_inner(&self) -> &FileDesc {
todo!()
}
}
impl IntoInner<FileDesc> for File {
fn into_inner(self) -> FileDesc {
todo!()
}
}
impl AsInnerMut<FileDesc> for File {
fn as_inner_mut(&mut self) -> &mut FileDesc {
todo!()
}
}
impl FromInner<FileDesc> for File {
fn from_inner(_file_desc: FileDesc) -> Self {
todo!()
}
}
impl AsFd for File {
fn as_fd(&self) -> BorrowedFd<'_> {
todo!()
}
}
impl AsRawFd for File {
fn as_raw_fd(&self) -> RawFd {
self.0.as_raw_fd()
}
}
impl IntoRawFd for File {
fn into_raw_fd(self) -> RawFd {
todo!()
}
}
impl FromRawFd for File {
unsafe fn from_raw_fd(raw_fd: RawFd) -> Self {
Self(FromRawFd::from_raw_fd(raw_fd))
}
}
+234
View File
@@ -0,0 +1,234 @@
use crate::ffi::OsString;
use crate::fmt;
use crate::hash::{Hash, Hasher};
use crate::io;
use crate::path::{Path, PathBuf};
use crate::sys::time::SystemTime;
mod file;
pub use file::{File, OpenOptions};
pub struct FileAttr(!);
pub struct FilePermissions(!);
pub struct FileType(!);
#[derive(Copy, Clone, Debug, Default)]
pub struct FileTimes {}
pub struct DirEntry(!);
pub struct ReadDir(!);
#[derive(Debug)]
pub struct DirBuilder {}
impl FileAttr {
pub fn size(&self) -> u64 {
todo!()
}
pub fn perm(&self) -> FilePermissions {
todo!()
}
pub fn file_type(&self) -> FileType {
todo!()
}
pub fn modified(&self) -> io::Result<SystemTime> {
todo!()
}
pub fn accessed(&self) -> io::Result<SystemTime> {
todo!()
}
pub fn created(&self) -> io::Result<SystemTime> {
todo!()
}
}
impl Clone for FileAttr {
fn clone(&self) -> Self {
todo!()
}
}
impl FilePermissions {
pub fn readonly(&self) -> bool {
todo!()
}
pub fn set_readonly(&mut self, _readonly: bool) {
todo!()
}
}
impl Clone for FilePermissions {
fn clone(&self) -> Self {
todo!()
}
}
impl PartialEq for FilePermissions {
fn eq(&self, _other: &Self) -> bool {
todo!()
}
}
impl Eq for FilePermissions {}
impl fmt::Debug for FilePermissions {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl FileType {
pub fn is_dir(&self) -> bool {
todo!()
}
pub fn is_file(&self) -> bool {
todo!()
}
pub fn is_symlink(&self) -> bool {
todo!()
}
}
impl Clone for FileType {
fn clone(&self) -> Self {
todo!()
}
}
impl Copy for FileType {}
impl PartialEq for FileType {
fn eq(&self, _other: &Self) -> bool {
todo!()
}
}
impl Eq for FileType {}
impl Hash for FileType {
fn hash<H: Hasher>(&self, _h: &mut H) {
todo!()
}
}
impl fmt::Debug for FileType {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl FileTimes {
pub fn set_accessed(&mut self, _t: SystemTime) {
todo!()
}
pub fn set_modified(&mut self, _t: SystemTime) {
todo!()
}
}
impl Iterator for ReadDir {
type Item = io::Result<DirEntry>;
fn next(&mut self) -> Option<io::Result<DirEntry>> {
todo!()
}
}
impl fmt::Debug for ReadDir {
fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result {
todo!()
}
}
impl DirEntry {
pub fn path(&self) -> PathBuf {
todo!()
}
pub fn file_name(&self) -> OsString {
todo!()
}
pub fn metadata(&self) -> io::Result<FileAttr> {
todo!()
}
pub fn file_type(&self) -> io::Result<FileType> {
todo!()
}
}
impl DirBuilder {
pub fn new() -> DirBuilder {
todo!()
}
pub fn mkdir(&self, _p: &Path) -> io::Result<()> {
todo!()
}
}
pub fn readdir(_p: &Path) -> io::Result<ReadDir> {
todo!()
}
pub fn unlink(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn rename(_old: &Path, _new: &Path) -> io::Result<()> {
todo!()
}
pub fn set_perm(_p: &Path, _perm: FilePermissions) -> io::Result<()> {
todo!()
}
pub fn remove_dir_all(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn readlink(_p: &Path) -> io::Result<PathBuf> {
todo!()
}
pub fn symlink(_original: &Path, _link: &Path) -> io::Result<()> {
todo!()
}
pub fn link(_original: &Path, _link: &Path) -> io::Result<()> {
todo!()
}
pub fn stat(_p: &Path) -> io::Result<FileAttr> {
todo!()
}
pub fn lstat(_p: &Path) -> io::Result<FileAttr> {
todo!()
}
pub fn canonicalize(_p: &Path) -> io::Result<PathBuf> {
todo!()
}
pub fn rmdir(_p: &Path) -> io::Result<()> {
todo!()
}
pub fn copy(_from: &Path, _to: &Path) -> io::Result<u64> {
todo!()
}
pub fn try_exists(_path: &Path) -> io::Result<bool> {
todo!()
}
+53 -2
View File
@@ -6,8 +6,6 @@ use crate::io::ErrorKind;
pub mod cmath;
#[path = "../unix/os_str.rs"]
pub mod os_str;
#[path = "../unix/path.rs"]
pub mod path;
#[path = "../unsupported/pipe.rs"]
pub mod pipe;
#[path = "../unsupported/process.rs"]
@@ -24,6 +22,7 @@ pub mod memchr;
pub mod net;
pub mod once;
pub mod os;
pub mod path;
pub mod stdio;
pub mod thread;
pub mod thread_local_key;
@@ -31,6 +30,8 @@ pub mod time;
pub(self) use yggdrasil_rt;
use yggdrasil_rt::Error as OsError;
#[doc(hidden)]
pub trait IsNegative {
fn is_negative(&self) -> bool;
@@ -61,7 +62,44 @@ impl IsNegative for i32 {
impl_is_negative! { i8 i16 i64 isize }
fn cvt_io_err(e: OsError) -> crate::io::Error {
match e {
OsError::DoesNotExist => {
crate::io::const_io_error!(ErrorKind::NotFound, "does not exist")
}
OsError::InvalidFile => {
crate::io::const_io_error!(ErrorKind::Other, "invalid file descriptor")
}
OsError::OutOfMemory => {
crate::io::const_io_error!(ErrorKind::OutOfMemory, "out of memory")
}
OsError::InvalidMemoryOperation => {
crate::io::const_io_error!(ErrorKind::InvalidData, "invalid memory operation")
}
OsError::AlreadyExists => {
crate::io::const_io_error!(ErrorKind::AlreadyExists, "already exists")
}
OsError::TimedOut => {
crate::io::const_io_error!(ErrorKind::TimedOut, "operation timed out")
}
OsError::IsADirectory => {
crate::io::const_io_error!(ErrorKind::IsADirectory, "is a directory")
}
OsError::InvalidArgument => {
crate::io::const_io_error!(ErrorKind::InvalidInput, "invalid argument")
}
}
}
pub fn cvt_io<T>(t: Result<T, OsError>) -> crate::io::Result<T> {
match t {
Ok(t) => Ok(t),
Err(e) => Err(cvt_io_err(e)),
}
}
pub fn cvt<T: IsNegative>(_t: T) -> crate::io::Result<T> {
println!("cvt!");
loop {}
}
@@ -70,14 +108,21 @@ where
T: IsNegative,
F: FnMut() -> T,
{
println!("cvt_r!");
loop {}
}
pub fn hashmap_random_keys() -> (u64, u64) {
unsafe {
yggdrasil_rt::sys::debug_trace("sys::yggdrasil::hashmap_random_keys()");
}
loop {}
}
pub fn abort_internal() -> ! {
unsafe {
yggdrasil_rt::sys::debug_trace("sys::yggdrasil::abort_internal()");
}
loop {}
}
@@ -90,10 +135,16 @@ pub unsafe fn cleanup() {
}
pub fn decode_error_kind(_errno: i32) -> ErrorKind {
unsafe {
yggdrasil_rt::sys::debug_trace("sys::yggdrasil::decode_error_kind()");
}
loop {}
}
pub fn unsupported() -> ! {
unsafe {
yggdrasil_rt::sys::debug_trace("sys::yggrdasil::unsupported()");
}
loop {}
}
+46
View File
@@ -0,0 +1,46 @@
use crate::env;
use crate::ffi::OsStr;
use crate::io;
use crate::path::{Path, PathBuf, Prefix};
use yggdrasil_rt::path as rt_path;
#[inline]
pub fn is_sep_byte(b: u8) -> bool {
b == (rt_path::SEPARATOR as u8)
}
#[inline]
pub fn is_verbatim_sep(b: u8) -> bool {
b == (rt_path::SEPARATOR as u8)
}
#[inline]
pub fn parse_prefix(_: &OsStr) -> Option<Prefix<'_>> {
None
}
pub const MAIN_SEP_STR: &str = rt_path::SEPARATOR_STR;
pub const MAIN_SEP: char = rt_path::SEPARATOR;
pub(crate) fn absolute(path: &Path) -> io::Result<PathBuf> {
let mut components = path.strip_prefix(".").unwrap_or(path).components();
let path_os = path.as_os_str().bytes();
let mut normalized = if path.is_absolute() {
if path_os.starts_with(b"//") && !path_os.starts_with(b"///") {
components.next();
PathBuf::from("//")
} else {
PathBuf::new()
}
} else {
env::current_dir()?
};
normalized.extend(components);
if path_os.ends_with(b"/") {
normalized.push("");
}
Ok(normalized)
}
+3 -42
View File
@@ -1,9 +1,8 @@
use crate::io;
use crate::io::{IoSlice, IoSliceMut};
use yggdrasil_rt::RawFd;
// const FILENO_STDIN: i32 = 0;
const FILENO_STDOUT: i32 = 1;
const FILENO_STDERR: i32 = 2;
pub struct Stdin;
pub struct Stdout;
@@ -47,76 +46,38 @@ impl io::Read for Stdin {
impl io::Write for Stdout {
fn write(&mut self, data: &[u8]) -> io::Result<usize> {
match unsafe { yggdrasil_rt::sys::write(FILENO_STDOUT, data) } {
match unsafe { yggdrasil_rt::sys::write(RawFd::STDOUT, data) } {
Ok(len) => Ok(len),
Err(_) => Err(io::const_io_error!(
io::ErrorKind::Uncategorized,
"Stdout is not able to print"
)),
}
// let len;
// unsafe { len = abi::write(1, data.as_ptr() as *const u8, data.len()) }
// if len < 0 {
// Err(io::const_io_error!(
// io::ErrorKind::Uncategorized,
// "Stdout is not able to print"
// ))
// } else {
// Ok(len as usize)
// }
}
fn write_vectored(&mut self, _data: &[IoSlice<'_>]) -> io::Result<usize> {
todo!();
// let len;
// unsafe { len = abi::write(1, data.as_ptr() as *const u8, data.len()) }
// if len < 0 {
// Err(io::const_io_error!(
// io::ErrorKind::Uncategorized,
// "Stdout is not able to print"
// ))
// } else {
// Ok(len as usize)
// }
}
#[inline]
fn is_write_vectored(&self) -> bool {
false
// true
}
fn flush(&mut self) -> io::Result<()> {
Ok(())
// Ok(())
}
}
impl io::Write for Stderr {
fn write(&mut self, data: &[u8]) -> io::Result<usize> {
match unsafe { yggdrasil_rt::sys::write(FILENO_STDERR, data) } {
match unsafe { yggdrasil_rt::sys::write(RawFd::STDERR, data) } {
Ok(len) => Ok(len),
Err(_) => Err(io::const_io_error!(
io::ErrorKind::Uncategorized,
"Stderr is not able to print"
)),
}
// let len;
// unsafe { len = abi::write(1, data.as_ptr() as *const u8, data.len()) }
// if len < 0 {
// Err(io::const_io_error!(
// io::ErrorKind::Uncategorized,
// "Stdout is not able to print"
// ))
// } else {
// Ok(len as usize)
// }
}
fn write_vectored(&mut self, _data: &[IoSlice<'_>]) -> io::Result<usize> {