diff --git a/rust/kernel/chrdev.rs b/rust/kernel/chrdev.rs index 631405920c29c7..33d3bb3c6763fb 100644 --- a/rust/kernel/chrdev.rs +++ b/rust/kernel/chrdev.rs @@ -8,10 +8,7 @@ //! //! Reference: -use alloc::boxed::Box; use core::convert::TryInto; -use core::marker::PhantomPinned; -use core::pin::Pin; use crate::bindings; use crate::c_types; @@ -80,12 +77,11 @@ struct RegistrationInner { dev: bindings::dev_t, used: usize, cdevs: [Option; N], - _pin: PhantomPinned, } /// Character device registration. /// -/// May contain up to a fixed number (`N`) of devices. Must be pinned. +/// May contain up to a fixed number (`N`) of devices. pub struct Registration { name: &'static CStr, minors_start: u16, @@ -97,12 +93,6 @@ impl Registration<{ N }> { /// Creates a [`Registration`] object for a character device. /// /// This does *not* register the device: see [`Self::register()`]. - /// - /// This associated function is intended to be used when you need to avoid - /// a memory allocation, e.g. when the [`Registration`] is a member of - /// a bigger structure inside your [`crate::KernelModule`] instance. If you - /// are going to pin the registration right away, call - /// [`Self::new_pinned()`] instead. pub fn new( name: &'static CStr, minors_start: u16, @@ -116,52 +106,34 @@ impl Registration<{ N }> { } } - /// Creates a pinned [`Registration`] object for a character device. - /// - /// This does *not* register the device: see [`Self::register()`]. - pub fn new_pinned( - name: &'static CStr, - minors_start: u16, - this_module: &'static crate::ThisModule, - ) -> Result>> { - Ok(Pin::from(Box::try_new(Self::new( - name, - minors_start, - this_module, - ))?)) - } - /// Registers a character device. /// /// You may call this once per device type, up to `N` times. - pub fn register>(self: Pin<&mut Self>) -> Result { - // SAFETY: We must ensure that we never move out of `this`. - let this = unsafe { self.get_unchecked_mut() }; - if this.inner.is_none() { + pub fn register>(&mut self) -> Result { + if self.inner.is_none() { let mut dev: bindings::dev_t = 0; // SAFETY: Calling unsafe function. `this.name` has `'static` // lifetime. let res = unsafe { bindings::alloc_chrdev_region( &mut dev, - this.minors_start.into(), + self.minors_start.into(), N.try_into()?, - this.name.as_char_ptr(), + self.name.as_char_ptr(), ) }; if res != 0 { return Err(Error::from_kernel_errno(res)); } const NONE: Option = None; - this.inner = Some(RegistrationInner { + self.inner = Some(RegistrationInner { dev, used: 0, cdevs: [NONE; N], - _pin: PhantomPinned, }); } - let mut inner = this.inner.as_mut().unwrap(); + let mut inner = self.inner.as_mut().unwrap(); if inner.used == N { return Err(Error::EINVAL); } @@ -169,7 +141,7 @@ impl Registration<{ N }> { // SAFETY: The adapter doesn't retrieve any state yet, so it's compatible with any // registration. let fops = unsafe { file_operations::FileOperationsVtable::::build() }; - let mut cdev = Cdev::alloc(fops, &this.this_module)?; + let mut cdev = Cdev::alloc(fops, &self.this_module)?; cdev.add(inner.dev + inner.used as bindings::dev_t, 1)?; inner.cdevs[inner.used].replace(cdev); inner.used += 1; diff --git a/samples/rust/rust_chrdev.rs b/samples/rust/rust_chrdev.rs index 0e8151dd783940..2e1e5276ecda69 100644 --- a/samples/rust/rust_chrdev.rs +++ b/samples/rust/rust_chrdev.rs @@ -5,8 +5,6 @@ #![no_std] #![feature(allocator_api, global_asm)] -use alloc::boxed::Box; -use core::pin::Pin; use kernel::prelude::*; use kernel::{c_str, chrdev, file_operations::FileOperations}; @@ -26,21 +24,20 @@ impl FileOperations for RustFile { } struct RustChrdev { - _dev: Pin>>, + _dev: chrdev::Registration<2>, } impl KernelModule for RustChrdev { fn init() -> Result { pr_info!("Rust character device sample (init)\n"); - let mut chrdev_reg = - chrdev::Registration::new_pinned(c_str!("rust_chrdev"), 0, &THIS_MODULE)?; + let mut chrdev_reg = chrdev::Registration::new(c_str!("rust_chrdev"), 0, &THIS_MODULE); // Register the same kind of device twice, we're just demonstrating // that you can use multiple minors. There are two minors in this case // because its type is `chrdev::Registration<2>` - chrdev_reg.as_mut().register::()?; - chrdev_reg.as_mut().register::()?; + chrdev_reg.register::()?; + chrdev_reg.register::()?; Ok(RustChrdev { _dev: chrdev_reg }) }