Description
Proposal
Problem statement
The current APIs for positioned reads
std::os::unix::fs::FileExt::read_at(&self, buf: &mut [u8], offset: u64)
std::os::unix::fs::FileExt::read_exact_at(&self, buf: &mut [u8], offset: u64)
std::os::windows::fs::FileExt::seek_read(&self, buf: &mut [u8], offset: u64)
take a &mut [u8]
output buffer that must be initialized even though it will be immediately overwritten. Initialization may add significant overhead.
Motivating examples or use cases
Positioned reads from fast storage or even in-memory files, avoiding memory maps for more control over error handling.
Solution sketch
RFC 2930 outlines a solution to this same problem for normal unpositioned reads, introducing BorrowedCursor<'_>
, an API for buffers to be incrementally filled and initialized.
Analogously to the proposed std::io::Read::read_buf
which is equivalent to read
, add trait methods:
// std::os::unix::fs
trait FileExt {
/// Equivalent to read_at()
fn read_buf_at(&self, buf: BorrowedCursor<'_>, offset: u64) -> io::Result<()>;
/// Equivalent to read_exact_at()
fn read_buf_exact_at(&self, buf: BorrowedCursor<'_>, offset: u64) -> io::Result<()>;
}
// std::os::windows::fs
trait FileExt {
// Equivalent to seek_read()
fn seek_read_buf(&self, buf: BorrowedCursor<'_>, offset: u64) -> io::Result<()>;
}
Alternatives
Alternative APIs for handling uninitialized buffers have been (and are still being) considered under the unstableread_buf
and core_io_borrowed_buf
features. However, in any case, positioned reads should likely use the same solution for consistency.