Skip to content

Conversation

mox692
Copy link
Member

@mox692 mox692 commented Sep 1, 2025

Add io-uring version of fs::write. I think the change itself is mostly straightforward. This PR might need to coordinate with #7547 regarding the usage of cfg.

Related issue: #7266

@mox692 mox692 added A-tokio Area: The main tokio crate M-fs Module: tokio/fs labels Sep 1, 2025
@mox692
Copy link
Member Author

mox692 commented Sep 4, 2025

I made some changes in da5b9e1:

  1. Fixed to rely on an owned buffer.
  2. Made the Write struct own resources: EDIT: this is removed
    - Introduced & updated some ref-counted owned utility types such as SharedFd and OwnedBuf.

I think (2) is not strictly required (it's more of a coding style change), but makes it clear that an operation owns the resources when reading the code IMO.

while offset < total {
// There is a cap on how many bytes we can write in a single uring write operation.
// ref: https://github.com/axboe/liburing/discussions/497
let len = std::cmp::min(total - offset, u32::MAX as usize) as u32;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could also make sense to move this logic inside Op::write_at and have it accept usize. After all, it's indistinguishable to the caller from any other situation that writes the bytes partially. That way it's more natural for the caller as the caller expects usize for both input and output length.

Suggested change
let len = std::cmp::min(total - offset, u32::MAX as usize) as u32;
let len = u32::try_from(total - offset).unwrap_or(u32::MAX);

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you mean having a dedicated variable for file_offset here? I did so in c2ed659.

Comment on lines 59 to 61
let total: usize = buf.len();
let mut offset: usize = 0;
while offset < total {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since write_at accepts u64 for file positions, let's use that here too.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moved that logic into write_at function in c2ed659.

Copy link
Contributor

@Darksonn Darksonn left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me!

Comment on lines +60 to +62
let mut buf_offset: usize = 0;
let mut file_offset: u64 = 0;
while buf_offset < total {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These variables are always equal.

Comment on lines +39 to +43
// There is a cap on how many bytes we can write in a single uring write operation.
// ref: https://github.com/axboe/liburing/discussions/497
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();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a super-nit, but I like this:

Suggested change
// There is a cap on how many bytes we can write in a single uring write operation.
// ref: https://github.com/axboe/liburing/discussions/497
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 buf = owned_buf.as_ref();
// There is a cap on how many bytes we can write in a single uring write operation.
// ref: https://github.com/axboe/liburing/discussions/497
let len = u32::try_from(buf.len() - buf_offset).unwrap_or(u32::MAX);
let ptr = buf[buf_offset..buf_offset + len as usize].as_ptr();

use std::task::Waker;
use std::{io, mem};

// This field isn't accessed directly, but it holds cancellation data,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// This field isn't accessed directly, but it holds cancellation data,
// These fields aren't accessed directly, but they hold cancellation data,

@mox692 mox692 enabled auto-merge (squash) October 2, 2025 10:43
@mox692 mox692 merged commit 3698a6f into master Oct 2, 2025
89 checks passed
@mox692 mox692 deleted the mox692/add_uring_write branch October 2, 2025 11:01
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-tokio Area: The main tokio crate M-fs Module: tokio/fs
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants