From: Mike Lothian <mike@fireburn.co.uk>
To: rust-for-linux@vger.kernel.org
Cc: "Mike Lothian" <mike@fireburn.co.uk>,
"Danilo Krummrich" <dakr@kernel.org>,
"Alice Ryhl" <aliceryhl@google.com>,
"Daniel Almeida" <daniel.almeida@collabora.com>,
"Miguel Ojeda" <ojeda@kernel.org>,
"Boqun Feng" <boqun@kernel.org>, "Gary Guo" <gary@garyguo.net>,
"Björn Roy Baron" <bjorn3_gh@protonmail.com>,
"Benno Lossin" <lossin@kernel.org>,
"Andreas Hindborg" <a.hindborg@kernel.org>,
"Trevor Gross" <tmgross@umich.edu>,
"Tamir Duberstein" <tamird@kernel.org>,
"Alexandre Courbot" <acourbot@nvidia.com>,
"Onur Özkan" <work@onurozkan.dev>,
driver-core@lists.linux.dev, linux-kernel@vger.kernel.org
Subject: [PATCH 6/9] rust: io: add checked offset copy helpers
Date: Wed, 26 Aug 2026 17:28:40 +0100 [thread overview]
Message-ID: <20260826162851.2497-7-mike@fireburn.co.uk> (raw)
In-Reply-To: <20260826162851.2497-1-mike@fireburn.co.uk>
I/O mappings often need to copy a bounded byte range rather than
the complete mapping. Add checked helpers that project the requested
range before using the backend copy operation. This keeps raw backend
pointers out of consumers and reports invalid ranges instead.
Assisted-by: Claude:claude-opus-5
Signed-off-by: Mike Lothian <mike@fireburn.co.uk>
---
rust/kernel/io.rs | 50 +++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 50 insertions(+)
diff --git a/rust/kernel/io.rs b/rust/kernel/io.rs
index 95f46bb75f9e..aea346b8b79e 100644
--- a/rust/kernel/io.rs
+++ b/rust/kernel/io.rs
@@ -225,6 +225,30 @@ fn io_view<'a, IO: Io<'a>, U>(
Ok(unsafe { IO::Backend::project_view(view, projected_ptr) })
}
+/// Returns a byte-slice view for a given range, performing runtime bounds checks.
+#[inline]
+fn io_byte_slice<'a, IO>(
+ this: IO,
+ offset: usize,
+ len: usize,
+) -> Result<<IO::Backend as IoBackend>::View<'a, [u8]>>
+where
+ IO: Io<'a, Target = [u8]>,
+{
+ let view = this.as_view();
+ let ptr = IO::Backend::as_ptr(view);
+ let end = offset.checked_add(len).ok_or(EINVAL)?;
+
+ if end > ptr.len() {
+ return Err(EINVAL);
+ }
+
+ let projected_ptr =
+ core::ptr::slice_from_raw_parts_mut(ptr.cast::<u8>().wrapping_add(offset), len);
+ // SAFETY: The bounds check above proves that `projected_ptr` is a sub-slice of `ptr`.
+ Ok(unsafe { IO::Backend::project_view(view, projected_ptr) })
+}
+
/// I/O backends.
///
/// This is an abstract representation to be implemented by arbitrary I/O
@@ -640,6 +664,32 @@ fn copy_to_slice(self, data: &mut [u8])
}
}
+ /// Copy bytes from `data` to a range of I/O memory.
+ ///
+ /// Returns [`EINVAL`] if `offset..offset + data.len()` is outside the I/O region.
+ #[inline]
+ fn try_copy_from_slice(self, offset: usize, data: &[u8]) -> Result
+ where
+ Self::Backend: IoCopyable,
+ Self: Io<'a, Target = [u8]>,
+ {
+ io_byte_slice(self, offset, data.len())?.copy_from_slice(data);
+ Ok(())
+ }
+
+ /// Copy a range of I/O memory to `data`.
+ ///
+ /// Returns [`EINVAL`] if `offset..offset + data.len()` is outside the I/O region.
+ #[inline]
+ fn try_copy_to_slice(self, offset: usize, data: &mut [u8]) -> Result
+ where
+ Self::Backend: IoCopyable,
+ Self: Io<'a, Target = [u8]>,
+ {
+ io_byte_slice(self, offset, data.len())?.copy_to_slice(data);
+ Ok(())
+ }
+
/// Fallible 8-bit read with runtime bounds check.
#[inline(always)]
fn try_read8(self, offset: usize) -> Result<u8>
parent reply other threads:[~2026-08-26 16:29 UTC|newest]
Thread overview: expand[flat|nested] mbox.gz Atom feed
[parent not found: <20260826162851.2497-1-mike@fireburn.co.uk>]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260826162851.2497-7-mike@fireburn.co.uk \
--to=mike@fireburn.co.uk \
--cc=a.hindborg@kernel.org \
--cc=acourbot@nvidia.com \
--cc=aliceryhl@google.com \
--cc=bjorn3_gh@protonmail.com \
--cc=boqun@kernel.org \
--cc=dakr@kernel.org \
--cc=daniel.almeida@collabora.com \
--cc=driver-core@lists.linux.dev \
--cc=gary@garyguo.net \
--cc=linux-kernel@vger.kernel.org \
--cc=lossin@kernel.org \
--cc=ojeda@kernel.org \
--cc=rust-for-linux@vger.kernel.org \
--cc=tamird@kernel.org \
--cc=tmgross@umich.edu \
--cc=work@onurozkan.dev \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox