compio-runtime 0.9.1

High-level runtime for compio
use std::{
    future::Future,
    pin::Pin,
    task::{Context, Poll},
};

use compio_buf::BufResult;
use compio_driver::{Key, OpCode, PushEntry};

use crate::runtime::Runtime;

#[derive(Debug)]
pub struct OpFuture<T: OpCode> {
    key: Option<Key<T>>,
}

impl<T: OpCode> OpFuture<T> {
    pub fn new(key: Key<T>) -> Self {
        Self { key: Some(key) }
    }
}

impl<T: OpCode> Future for OpFuture<T> {
    type Output = (BufResult<usize, T>, u32);

    fn poll(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
        let res = Runtime::with_current(|r| r.poll_task(cx, self.key.take().unwrap()));
        match res {
            PushEntry::Pending(key) => {
                self.key = Some(key);
                Poll::Pending
            }
            PushEntry::Ready(res) => Poll::Ready(res),
        }
    }
}

impl<T: OpCode> Drop for OpFuture<T> {
    fn drop(&mut self) {
        if let Some(key) = self.key.take() {
            Runtime::with_current(|r| r.cancel_op(key));
        }
    }
}