Skip to content

Commit a4b65d0

Browse files
author
Andreas Molzer
authored
Add constructor of IoUring from raw FD (#288)
* Add constructor of IoUring from raw FD The user must communicate the parameters utilized with its construction out-of-band but can otherwise use an existing file descriptor. The library will then map the existing ring's queues. This permits using a pre-opened file descriptor such as one shared by a parent process, or one stashed away to be kept open in systemd's file descriptor store. Keeping a ring open can allow its operations to complete despite the writer's process dying unexpectedly. Additionally, another process might register a personality (IORING_REGISTER_PERSONALITY) to be used as means of effective access controls for operations that must avoid confused deputy scenarios. A ring opened by a parent might also have pre-existing trusted restrictions (IORING_REGISTER_RESTRICTIONS) applied to it. Note that this is _not_ an implementation of `IORING_SETUP_ATTACH_WQ` or of a multi-issuer submission queue. * Make parameters repr-transparent, add safety note
1 parent 02a27c9 commit a4b65d0

File tree

1 file changed

+20
-2
lines changed

1 file changed

+20
-2
lines changed

src/lib.rs

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,11 @@ where
6666
}
6767

6868
/// The parameters that were used to construct an [`IoUring`].
69+
///
70+
/// This type is a transparent wrapper over the system structure `io_uring_params`. A value can be
71+
/// (unsafely) created from any properly laid-out and initialized memory representation.
6972
#[derive(Clone)]
73+
#[repr(transparent)]
7074
pub struct Parameters(sys::io_uring_params);
7175

7276
unsafe impl<S: squeue::EntryMarker, C: cqueue::EntryMarker> Send for IoUring<S, C> {}
@@ -81,6 +85,17 @@ impl IoUring<squeue::Entry, cqueue::Entry> {
8185
pub fn new(entries: u32) -> io::Result<Self> {
8286
Self::builder().build(entries)
8387
}
88+
89+
/// Create an `IoUring` instance from a pre-opened file descriptor.
90+
///
91+
/// # Safety
92+
///
93+
/// The caller must uphold that the file descriptor is owned and refers to a uring. The
94+
/// `params` argument must be equivalent to the those previously filled in by the kernel when
95+
/// the provided ring was created.
96+
pub unsafe fn from_fd(fd: RawFd, params: Parameters) -> io::Result<Self> {
97+
Self::with_fd_and_params(OwnedFd::from_raw_fd(fd), params.0)
98+
}
8499
}
85100

86101
impl<S: squeue::EntryMarker, C: cqueue::EntryMarker> IoUring<S, C> {
@@ -103,6 +118,11 @@ impl<S: squeue::EntryMarker, C: cqueue::EntryMarker> IoUring<S, C> {
103118
}
104119

105120
fn with_params(entries: u32, mut p: sys::io_uring_params) -> io::Result<Self> {
121+
let fd: OwnedFd = unsafe { OwnedFd::from_raw_fd(sys::io_uring_setup(entries, &mut p)?) };
122+
unsafe { Self::with_fd_and_params(fd, p) }
123+
}
124+
125+
unsafe fn with_fd_and_params(fd: OwnedFd, p: sys::io_uring_params) -> io::Result<Self> {
106126
// NOTE: The `SubmissionQueue` and `CompletionQueue` are references,
107127
// and their lifetime can never exceed `MemoryMap`.
108128
//
@@ -149,8 +169,6 @@ impl<S: squeue::EntryMarker, C: cqueue::EntryMarker> IoUring<S, C> {
149169
}
150170
}
151171

152-
let fd: OwnedFd = unsafe { OwnedFd::from_raw_fd(sys::io_uring_setup(entries, &mut p)?) };
153-
154172
let (mm, sq, cq) = unsafe { setup_queue(&fd, &p)? };
155173

156174
Ok(IoUring {

0 commit comments

Comments
 (0)