use crate::runtime::driver::op::{CancelData, Cancellable, Completable, CqeResult, Op};
use crate::util::as_ref::OwnedBuf;
use io_uring::{opcode, types};
use std::io::{self, Error};
use std::os::fd::{AsRawFd, OwnedFd};
#[derive(Debug)]
pub(crate) struct Write {
buf: OwnedBuf,
fd: OwnedFd,
}
impl Completable for Write {
type Output = (io::Result<u32>, OwnedBuf, OwnedFd);
fn complete(self, cqe: CqeResult) -> Self::Output {
(cqe.result, self.buf, self.fd)
}
fn complete_with_error(self, err: Error) -> Self::Output {
(Err(err), self.buf, self.fd)
}
}
impl Cancellable for Write {
fn cancel(self) -> CancelData {
CancelData::Write(self)
}
}
impl Op<Write> {
pub(crate) fn write_at(
fd: OwnedFd,
buf: OwnedBuf,
buf_offset: usize,
file_offset: u64,
) -> io::Result<Self> {
let len = u32::try_from(buf.as_ref().len() - buf_offset).unwrap_or(u32::MAX);
let ptr = buf.as_ref()[buf_offset..buf_offset + len as usize].as_ptr();
let sqe = opcode::Write::new(types::Fd(fd.as_raw_fd()), ptr, len)
.offset(file_offset)
.build();
let op = unsafe { Op::new(sqe, Write { buf, fd }) };
Ok(op)
}
}