Skip to content

Commit cb62f59

Browse files
committed
refactor(driver): require Default for Control
1 parent 50470ef commit cb62f59

19 files changed

Lines changed: 525 additions & 499 deletions

File tree

compio-driver/src/control.rs

Lines changed: 29 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,5 @@
11
#![allow(dead_code)]
22

3-
use std::{
4-
mem::{ManuallyDrop, MaybeUninit},
5-
ptr,
6-
};
7-
83
use compio_buf::IntoInner;
94

105
use crate::{DriverType, OpCode};
@@ -52,36 +47,33 @@ impl<T: OpCode> ControlInner<T> {
5247
///
5348
/// [`ErasedKey`]: crate::key::ErasedKey
5449
pub(crate) struct Carrier<T: OpCode + ?Sized> {
55-
control: MaybeUninit<ControlInner<T>>,
50+
control: ControlInner<T>,
51+
driver_ty: DriverType,
5652
op: T,
5753
}
5854

5955
impl<T: OpCode> IntoInner for Carrier<T> {
6056
type Inner = T;
6157

6258
fn into_inner(self) -> Self::Inner {
63-
let mut this = ManuallyDrop::new(self);
64-
unsafe {
65-
// SAFETY: `new_uninit` ensures that the type is initialized
66-
MaybeUninit::assume_init_drop(&mut this.control);
67-
// SAFETY: `self` is warpped in ManuallyDrop and is not used after here
68-
ptr::read(&this.op)
69-
}
59+
self.op
7060
}
7161
}
7262

7363
impl<T: OpCode> Carrier<T> {
74-
/// Create a new Carrier with given OpCode.
75-
///
76-
/// # Safety
77-
///
78-
/// Returned [`Carrier`] must be [`initialized`] before converting to `dyn
79-
/// Carry` or calling any of the `as_` getters.
80-
///
81-
/// [`initialized`]: Self::init
82-
pub unsafe fn new_uninit(op: T) -> Self {
64+
/// Create a new Carrier with given OpCode and driver type.
65+
pub fn new(op: T, driver_ty: DriverType) -> Self {
66+
#[cfg(fusion)]
67+
let control = match driver_ty {
68+
DriverType::IoUring => ControlInner::IoUring(Default::default()),
69+
DriverType::Poll => ControlInner::Poll(Default::default()),
70+
_ => unreachable!("Cannot be IOCP"),
71+
};
72+
#[cfg(not(fusion))]
73+
let control = T::Control::default();
8374
Self {
84-
control: MaybeUninit::uninit(),
75+
control,
76+
driver_ty,
8577
op,
8678
}
8779
}
@@ -92,77 +84,45 @@ impl<T: OpCode> Carrier<T> {
9284
///
9385
/// `self` must have stable address until control is no longer used, include
9486
/// all function calls via `dyn Carry` and `as_` getters.
95-
pub unsafe fn init(&mut self, driver_ty: DriverType) {
87+
pub unsafe fn init(&mut self) {
9688
#[cfg(fusion)]
97-
{
98-
let control = match driver_ty {
99-
DriverType::Poll => ControlInner::Poll(unsafe { PollOpCode::init(&mut self.op) }),
100-
DriverType::IoUring => {
101-
ControlInner::IoUring(unsafe { IourOpCode::init(&mut self.op) })
102-
}
103-
DriverType::IOCP => unreachable!("Cannot be windows"),
89+
unsafe {
90+
match self.driver_ty {
91+
DriverType::Poll => PollOpCode::init(&mut self.op, self.control.poll()),
92+
DriverType::IoUring => IourOpCode::init(&mut self.op, self.control.iour()),
93+
_ => unreachable!("Cannot be IOCP"),
10494
};
105-
106-
self.control.write(control);
10795
}
10896

10997
#[cfg(not(fusion))]
110-
{
111-
_ = driver_ty;
112-
113-
let control = unsafe { OpCode::init(&mut self.op) };
114-
self.control.write(control);
98+
unsafe {
99+
OpCode::init(&mut self.op, &mut self.control)
115100
}
116101
}
117102

118103
#[cfg(io_uring)]
119104
pub fn as_iour(&mut self) -> (&mut T, &mut <T as IourOpCode>::Control) {
120-
// SAFETY: `new_uninit` ensures that the type is initialized
121-
let control = unsafe { self.control.assume_init_mut() };
122105
#[cfg(fusion)]
123-
{
124-
(&mut self.op, control.iour())
125-
}
106+
return (&mut self.op, self.control.iour());
126107
#[cfg(not(fusion))]
127-
{
128-
(&mut self.op, control)
129-
}
108+
(&mut self.op, &mut self.control)
130109
}
131110

132111
#[cfg(polling)]
133112
pub fn as_poll(&mut self) -> (&mut T, &mut <T as PollOpCode>::Control) {
134-
// SAFETY: `new_uninit` ensures that the type is initialized
135-
let control = unsafe { self.control.assume_init_mut() };
136113
#[cfg(fusion)]
137-
{
138-
(&mut self.op, control.poll())
139-
}
114+
return (&mut self.op, self.control.poll());
140115
#[cfg(not(fusion))]
141-
{
142-
(&mut self.op, control)
143-
}
116+
(&mut self.op, &mut self.control)
144117
}
145118

146119
#[cfg(windows)]
147120
pub fn as_iocp(&self) -> (&T, &<T as OpCode>::Control) {
148-
// SAFETY: `new_uninit` ensures that the type is initialized
149-
let control = unsafe { self.control.assume_init_ref() };
150-
151-
(&self.op, control)
121+
(&self.op, &self.control)
152122
}
153123

154124
#[cfg(windows)]
155125
pub fn as_iocp_mut(&mut self) -> (&mut T, &mut <T as OpCode>::Control) {
156-
// SAFETY: `new_uninit` ensures that the type is initialized
157-
let control = unsafe { self.control.assume_init_mut() };
158-
159-
(&mut self.op, control)
160-
}
161-
}
162-
163-
impl<T: OpCode + ?Sized> Drop for Carrier<T> {
164-
fn drop(&mut self) {
165-
// SAFETY: `new_uninit` ensures that the type is initialized
166-
unsafe { MaybeUninit::assume_init_drop(&mut self.control) };
126+
(&mut self.op, &mut self.control)
167127
}
168128
}

compio-driver/src/key.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -200,15 +200,14 @@ impl ErasedKey {
200200
extra,
201201
cancelled: false,
202202
result: PushEntry::Pending(None),
203-
// SAFETY: carrier is initialized below
204-
carrier: unsafe { Carrier::new_uninit(op) },
203+
carrier: Carrier::new(op, driver_ty),
205204
};
206205
let mut inner = ThinCell::new(raw_op);
207206
// SAFETY:
208207
// - ThinCell is just created, there will be no shared owner or borrower
209208
// - Carrier is being pinned by ThinCell, it will have a stable address until
210209
// move out
211-
unsafe { inner.borrow_unchecked().carrier.init(driver_ty) };
210+
unsafe { inner.borrow_unchecked().carrier.init() };
212211
Self {
213212
inner: unsafe { inner.unsize(|p| p as *const Inner<RawOp<dyn Carry>>) },
214213
}

compio-driver/src/sys/fusion/op.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -81,8 +81,8 @@ macro_rules! op {
8181
unsafe impl<$($ty: $trait),*> poll::OpCode for $name<$($ty),*> {
8282
type Control = <poll::$name<$($ty),*> as poll::OpCode>::Control;
8383

84-
unsafe fn init(&mut self) -> Self::Control {
85-
unsafe { poll::OpCode::init(self.inner.poll()) }
84+
unsafe fn init(&mut self, ctrl: &mut Self::Control) {
85+
unsafe { poll::OpCode::init(self.inner.poll(), ctrl) }
8686
}
8787

8888
fn pre_submit(&mut self, control: &mut Self::Control) -> std::io::Result<crate::Decision> {
@@ -103,8 +103,8 @@ macro_rules! op {
103103
unsafe impl<$($ty: $trait),*> iour::OpCode for $name<$($ty),*> {
104104
type Control = <iour::$name<$($ty),*> as iour::OpCode>::Control;
105105

106-
unsafe fn init(&mut self) -> Self::Control {
107-
unsafe { self.inner.iour().init() }
106+
unsafe fn init(&mut self, ctrl: &mut Self::Control) {
107+
unsafe { self.inner.iour().init(ctrl) }
108108
}
109109

110110
fn create_entry(&mut self, control: &mut Self::Control) -> OpEntry {
@@ -214,8 +214,8 @@ macro_rules! mop {
214214
unsafe impl<$($ty: $trait),*> poll::OpCode for $name<$($ty),*> {
215215
type Control = <crate::op::managed::$name<$($ty),*> as poll::OpCode>::Control;
216216

217-
unsafe fn init(&mut self) -> Self::Control {
218-
unsafe { self.inner.poll().init() }
217+
unsafe fn init(&mut self, ctrl: &mut Self::Control) {
218+
unsafe { self.inner.poll().init(ctrl) }
219219
}
220220

221221
fn pre_submit(&mut self, control: &mut Self::Control) -> std::io::Result<crate::Decision> {
@@ -236,8 +236,8 @@ macro_rules! mop {
236236
unsafe impl<$($ty: $trait),*> iour::OpCode for $name<$($ty),*> {
237237
type Control = <iour::$name<$($ty),*> as iour::OpCode>::Control;
238238

239-
unsafe fn init(&mut self) -> Self::Control {
240-
unsafe { self.inner.iour().init() }
239+
unsafe fn init(&mut self, ctrl: &mut Self::Control) {
240+
unsafe { self.inner.iour().init(ctrl) }
241241
}
242242

243243
fn create_entry(&mut self, control: &mut Self::Control) -> OpEntry {

compio-driver/src/sys/iocp/mod.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -294,15 +294,15 @@ pub enum OpType {
294294
pub unsafe trait OpCode {
295295
/// Type that contains self-references and other needed info during the
296296
/// operation
297-
type Control;
297+
type Control: Default;
298298

299299
/// Constructs a `Control`
300300
///
301301
/// # Safety
302302
///
303303
/// Caller must guarantee that during the lifetime of the returned
304304
/// `Control`, `Self` must be unmoved and valid.
305-
unsafe fn init(&mut self) -> Self::Control;
305+
unsafe fn init(&mut self, ctrl: &mut Self::Control);
306306

307307
/// Determines that the operation is really overlapped defined by Windows
308308
/// API. If not, the driver will try to operate it in another thread.

0 commit comments

Comments
 (0)