rust
use futures::future::BoxFuture;
use std::future::Future;
use std::sync::{Arc, Mutex};
use std::task::{Context};
use futures::task::{self, ArcWake};
use crossbeam::channel;
struct MiniTokio {
scheduled: channel::Receiver<Arc<Task>>,
sender: channel::Sender<Arc<Task>>,
}
impl MiniTokio {
fn new() -> MiniTokio {
let (sender, scheduled) = channel::unbounded();
MiniTokio { scheduled, sender }
}
fn spawn<F>(&self, future: F)
where
F: Future<Output=()> + Send + 'static,
{
Task::spawn(future, &self.sender);
}
fn run(&self) {
while let Ok(task) = self.scheduled.recv() {
task.poll();
}
}
}
struct Task {
// Pin<Box<dyn Future<Output = T> + Send + 'static>>
future: Mutex<BoxFuture<'static, ()>>,
executor: channel::Sender<Arc<Task>>,
}
impl Task {
fn spawn<F>(future: F, sender: &channel::Sender<Arc<Task>>)
where
F: Future<Output=()> + Send + 'static,
{
let task = Arc::new(Task {
future: Mutex::new(Box::pin(future)),
executor: sender.clone(),
});
let _ = sender.send(task);
}
fn poll(self: Arc<Self>) {
let waker = task::waker(self.clone());
let mut cx = Context::from_waker(&waker);
println!("{}", "创建waker");
let mut future = self.future.try_lock().unwrap();
let _ = future.as_mut().poll(&mut cx);
}
}
impl ArcWake for Task {
fn wake_by_ref(arc_self: &Arc<Self>) {
println!("arcWake");
let _ = arc_self.executor.send(arc_self.clone());
}
}
// 调用这个函数进行运行 ok?
pub fn yun_xin() {
let tokio = MiniTokio::new();
tokio.spawn(async { println!("hello,world!");() });
tokio.run();
}
粗略讲解