need Any on WasiFile to upcast for AsRawFd

This commit is contained in:
Pat Hickey
2021-01-14 13:39:01 -08:00
parent ea94d6f79d
commit 5c8efe868e
7 changed files with 87 additions and 19 deletions

View File

@@ -1,11 +1,13 @@
use crate::Error; use crate::Error;
use bitflags::bitflags; use bitflags::bitflags;
use fs_set_times::SetTimes; use fs_set_times::SetTimes;
use std::any::Any;
use std::cell::Ref; use std::cell::Ref;
use std::ops::Deref; use std::ops::Deref;
use system_interface::fs::FileIoExt; use system_interface::fs::FileIoExt;
pub trait WasiFile: FileIoExt + SetTimes { pub trait WasiFile: FileIoExt + SetTimes {
fn as_any(&self) -> &dyn Any;
fn datasync(&self) -> Result<(), Error>; fn datasync(&self) -> Result<(), Error>;
fn sync(&self) -> Result<(), Error>; fn sync(&self) -> Result<(), Error>;
fn get_filetype(&self) -> Result<FileType, Error>; fn get_filetype(&self) -> Result<FileType, Error>;
@@ -165,6 +167,9 @@ pub struct FdStat {
} }
impl WasiFile for cap_std::fs::File { impl WasiFile for cap_std::fs::File {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
self.sync_data()?; self.sync_data()?;
Ok(()) Ok(())

View File

@@ -5,32 +5,23 @@ use cap_std::time::{Duration, SystemTime};
use std::cell::Ref; use std::cell::Ref;
pub mod subscription; pub mod subscription;
mod sync;
pub use sync::SyncSched;
use subscription::{RwSubscription, Subscription, SubscriptionResult, SystemTimerSubscription}; use subscription::{RwSubscription, Subscription, SubscriptionResult, SystemTimerSubscription};
pub trait WasiSched { pub trait WasiSched {
fn poll_oneoff<'a>(&self, poll: &mut Poll<'a>) -> Result<(), Error>; fn poll_oneoff(&self, poll: &Poll) -> Result<(), Error>;
fn sched_yield(&self) -> Result<(), Error>; fn sched_yield(&self) -> Result<(), Error>;
} }
#[derive(Default)]
pub struct SyncSched {}
impl WasiSched for SyncSched {
fn poll_oneoff<'a>(&self, poll: &mut Poll<'a>) -> Result<(), Error> {
todo!()
}
fn sched_yield(&self) -> Result<(), Error> {
std::thread::yield_now();
Ok(())
}
}
pub struct Userdata(u64); pub struct Userdata(u64);
impl From<u64> for Userdata { impl From<u64> for Userdata {
fn from(u: u64) -> Userdata { fn from(u: u64) -> Userdata {
Userdata(u) Userdata(u)
} }
} }
impl From<Userdata> for u64 { impl From<Userdata> for u64 {
fn from(u: Userdata) -> u64 { fn from(u: Userdata) -> u64 {
u.0 u.0
@@ -75,7 +66,7 @@ impl<'a> Poll<'a> {
.filter_map(|(s, ud)| SubscriptionResult::from_subscription(s).map(|r| (r, ud))) .filter_map(|(s, ud)| SubscriptionResult::from_subscription(s).map(|r| (r, ud)))
.collect() .collect()
} }
pub fn subscriptions(&'a mut self) -> impl Iterator<Item = &Subscription<'a>> { pub fn subscriptions(&'a self) -> impl Iterator<Item = &Subscription<'a>> {
self.subs.iter().map(|(s, _ud)| s) self.subs.iter().map(|(s, _ud)| s)
} }
} }

View File

@@ -12,7 +12,7 @@ bitflags! {
} }
pub struct RwSubscription<'a> { pub struct RwSubscription<'a> {
file: Ref<'a, dyn WasiFile>, pub file: Ref<'a, dyn WasiFile>,
status: Cell<Option<Result<(u64, RwEventFlags), Error>>>, status: Cell<Option<Result<(u64, RwEventFlags), Error>>>,
} }

View File

@@ -0,0 +1,55 @@
use crate::file::WasiFile;
use crate::sched::subscription::{RwSubscription, Subscription, SystemTimerSubscription};
use crate::sched::{Poll, WasiSched};
use crate::Error;
use std::any::Any;
use std::ops::Deref;
#[cfg(unix)]
use std::os::unix::io::{AsRawFd, RawFd};
#[derive(Default)]
pub struct SyncSched {}
impl WasiSched for SyncSched {
fn poll_oneoff(&self, poll: &Poll) -> Result<(), Error> {
for s in poll.subscriptions() {
match s {
Subscription::Read(f) | Subscription::Write(f) => {
let raw_fd = wasi_file_raw_fd(f.file.deref()).ok_or(Error::Inval)?;
todo!()
}
Subscription::SystemTimer(t) => {
todo!()
}
}
}
Ok(())
}
fn sched_yield(&self) -> Result<(), Error> {
std::thread::yield_now();
Ok(())
}
}
fn wasi_file_raw_fd(f: &dyn WasiFile) -> Option<RawFd> {
let a = f.as_any();
if a.is::<cap_std::fs::File>() {
Some(a.downcast_ref::<cap_std::fs::File>().unwrap().as_raw_fd())
} else if a.is::<crate::stdio::Stdin>() {
Some(a.downcast_ref::<crate::stdio::Stdin>().unwrap().as_raw_fd())
} else if a.is::<crate::stdio::Stdout>() {
Some(
a.downcast_ref::<crate::stdio::Stdout>()
.unwrap()
.as_raw_fd(),
)
} else if a.is::<crate::stdio::Stderr>() {
Some(
a.downcast_ref::<crate::stdio::Stderr>()
.unwrap()
.as_raw_fd(),
)
} else {
None
}
}

View File

@@ -939,7 +939,7 @@ impl<'a> wasi_snapshot_preview1::WasiSnapshotPreview1 for WasiCtx {
} }
} }
self.sched.poll_oneoff(&mut poll)?; self.sched.poll_oneoff(&poll)?;
let results = poll.results(); let results = poll.results();
let num_results = results.len(); let num_results = results.len();

View File

@@ -1,5 +1,6 @@
use crate::file::{FdFlags, FileType, Filestat, WasiFile}; use crate::file::{FdFlags, FileType, Filestat, WasiFile};
use crate::Error; use crate::Error;
use std::any::Any;
#[cfg(unix)] #[cfg(unix)]
use std::os::unix::io::{AsRawFd, RawFd}; use std::os::unix::io::{AsRawFd, RawFd};
@@ -17,6 +18,9 @@ impl AsRawFd for Stdin {
} }
impl WasiFile for Stdin { impl WasiFile for Stdin {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
Ok(()) Ok(())
} }
@@ -54,6 +58,9 @@ impl AsRawFd for Stdout {
} }
impl WasiFile for Stdout { impl WasiFile for Stdout {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
Ok(()) Ok(())
} }
@@ -91,6 +98,9 @@ impl AsRawFd for Stderr {
} }
impl WasiFile for Stderr { impl WasiFile for Stderr {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
Ok(()) Ok(())
} }

View File

@@ -11,6 +11,7 @@
//! //!
use crate::file::{FdFlags, FileType, Filestat, WasiFile}; use crate::file::{FdFlags, FileType, Filestat, WasiFile};
use crate::Error; use crate::Error;
use std::any::Any;
use std::io::{self, Read, Write}; use std::io::{self, Read, Write};
use std::sync::{Arc, RwLock}; use std::sync::{Arc, RwLock};
use system_interface::fs::{Advice, FileIoExt}; use system_interface::fs::{Advice, FileIoExt};
@@ -167,7 +168,10 @@ impl<R: Read> fs_set_times::SetTimes for ReadPipe<R> {
todo!() todo!()
} }
} }
impl<R: Read> WasiFile for ReadPipe<R> { impl<R: Read + Any> WasiFile for ReadPipe<R> {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
Ok(()) // trivial: no implementation needed Ok(()) // trivial: no implementation needed
} }
@@ -339,7 +343,10 @@ impl<W: Write> fs_set_times::SetTimes for WritePipe<W> {
} }
} }
impl<W: Write> WasiFile for WritePipe<W> { impl<W: Write + Any> WasiFile for WritePipe<W> {
fn as_any(&self) -> &dyn Any {
self
}
fn datasync(&self) -> Result<(), Error> { fn datasync(&self) -> Result<(), Error> {
Ok(()) Ok(())
} }