Skip to content

Commit 1fbd7db

Browse files
committed
rust: simplify DeviceRemoval requirement.
Now we require `Driver::Data` to implement it, and we automatically implement it for `Ref<T>` and `Box<T>` if `T` implements it, and for `()` so that we can easily have empty data. This way we avoid having to repeat the bounds everywhere in the bus code. Signed-off-by: Wedson Almeida Filho <[email protected]>
1 parent 73bd4bb commit 1fbd7db

File tree

2 files changed

+29
-38
lines changed

2 files changed

+29
-38
lines changed

rust/kernel/amba.rs

Lines changed: 11 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ use crate::{
88
bindings, c_types, device, driver, error::from_kernel_result, io_mem::Resource, power,
99
str::CStr, to_result, types::PointerWrapper, Error, Result,
1010
};
11-
use core::{marker::PhantomData, ops::Deref};
1211

1312
/// A registration of an amba driver.
1413
pub type Registration<T> = driver::Registration<Adapter<T>>;
@@ -27,12 +26,9 @@ pub struct DeviceId<T = ()> {
2726
}
2827

2928
/// An amba driver.
30-
pub trait Driver
31-
where
32-
<Self::Data as Deref>::Target: driver::DeviceRemoval,
33-
{
29+
pub trait Driver {
3430
/// Data stored on device by driver.
35-
type Data: PointerWrapper + Send + Sync + Deref;
31+
type Data: PointerWrapper + Send + Sync + driver::DeviceRemoval = ();
3632

3733
/// The type that implements the power-management operations.
3834
///
@@ -56,14 +52,9 @@ where
5652
}
5753

5854
/// An adapter for the registration of Amba drivers.
59-
pub struct Adapter<T: Driver>(PhantomData<T>)
60-
where
61-
<T::Data as Deref>::Target: driver::DeviceRemoval;
55+
pub struct Adapter<T: Driver>(T);
6256

63-
impl<T: Driver> driver::DriverOps for Adapter<T>
64-
where
65-
<T::Data as Deref>::Target: driver::DeviceRemoval,
66-
{
57+
impl<T: Driver> driver::DriverOps for Adapter<T> {
6758
type RegType = bindings::amba_driver;
6859
type RawIdType = bindings::amba_id;
6960
type IdType = DeviceId<T::IdInfo>;
@@ -110,10 +101,7 @@ where
110101
unsafe extern "C" fn probe_callback<T: Driver>(
111102
adev: *mut bindings::amba_device,
112103
aid: *const bindings::amba_id,
113-
) -> c_types::c_int
114-
where
115-
<T::Data as Deref>::Target: driver::DeviceRemoval,
116-
{
104+
) -> c_types::c_int {
117105
from_kernel_result! {
118106
// SAFETY: `adev` is valid by the contract with the C code. `dev` is alive only for the
119107
// duration of this call, so it is guaranteed to remain alive for the lifetime of `dev`.
@@ -131,18 +119,15 @@ where
131119
}
132120
}
133121

134-
unsafe extern "C" fn remove_callback<T: Driver>(adev: *mut bindings::amba_device)
135-
where
136-
<T::Data as Deref>::Target: driver::DeviceRemoval,
137-
{
122+
unsafe extern "C" fn remove_callback<T: Driver>(adev: *mut bindings::amba_device) {
138123
// SAFETY: `adev` is valid by the contract with the C code.
139124
let ptr = unsafe { bindings::amba_get_drvdata(adev) };
140125
// SAFETY: The value returned by `amba_get_drvdata` was stored by a previous call to
141126
// `amba_set_drvdata` in `probe_callback` above; the value comes from a call to
142127
// `T::Data::into_pointer`.
143128
let data = unsafe { T::Data::from_pointer(ptr) };
144129
T::remove(&data);
145-
<<T::Data as Deref>::Target as driver::DeviceRemoval>::device_remove(data.deref());
130+
<T::Data as driver::DeviceRemoval>::device_remove(&data);
146131
}
147132

148133
/// An Amba device.
@@ -208,16 +193,11 @@ unsafe impl device::RawDevice for Device {
208193
/// # use kernel::prelude::*;
209194
/// # use kernel::{amba, declare_amba_id_table, module_amba_driver};
210195
/// #
211-
/// # struct State;
212-
/// # impl kernel::driver::DeviceRemoval for State {
213-
/// # fn device_remove(&self) {}
214-
/// # }
215196
/// struct MyDriver;
216197
/// impl amba::Driver for MyDriver {
217198
/// // [...]
218-
/// # type Data = kernel::sync::Ref<State>;
219-
/// # fn probe(dev: &mut amba::Device, id: &amba::DeviceId<Self::IdInfo>) -> Result<Self::Data> {
220-
/// # todo!()
199+
/// # fn probe(_dev: &mut amba::Device, _id: &amba::DeviceId<Self::IdInfo>) -> Result {
200+
/// # Ok(())
221201
/// # }
222202
/// # declare_amba_id_table! [
223203
/// # { id: 0x00041061, mask: 0x000fffff, data: () },
@@ -246,15 +226,10 @@ macro_rules! module_amba_driver {
246226
/// # use kernel::prelude::*;
247227
/// # use kernel::{amba, declare_amba_id_table};
248228
/// #
249-
/// # struct State;
250-
/// # impl kernel::driver::DeviceRemoval for State {
251-
/// # fn device_remove(&self) {}
252-
/// # }
253229
/// # struct Sample;
254230
/// # impl kernel::amba::Driver for Sample {
255-
/// # type Data = kernel::sync::Ref<State>;
256-
/// # fn probe(dev: &mut amba::Device, id: &amba::DeviceId<Self::IdInfo>) -> Result<Self::Data> {
257-
/// # todo!()
231+
/// # fn probe(_dev: &mut amba::Device, _id: &amba::DeviceId<Self::IdInfo>) -> Result {
232+
/// # Ok(())
258233
/// # }
259234
/// declare_amba_id_table! [
260235
/// { id: 0x00041061, mask: 0x000fffff, data: () },

rust/kernel/driver.rs

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@
55
//! Each bus/subsystem is expected to implement [`DriverOps`], which allows drivers to register
66
//! using the [`Registration`] class.
77
8-
use crate::{str::CStr, Error, KernelModule, Result, ScopeGuard, ThisModule};
8+
use crate::{str::CStr, sync::Ref, Error, KernelModule, Result, ScopeGuard, ThisModule};
99
use alloc::{boxed::Box, vec::Vec};
10-
use core::{cell::UnsafeCell, mem::MaybeUninit, pin::Pin};
10+
use core::{cell::UnsafeCell, mem::MaybeUninit, ops::Deref, pin::Pin};
1111

1212
/// A subsystem (e.g., PCI, Platform, Amba, etc.) that allows drivers to be written for it.
1313
pub trait DriverOps {
@@ -165,6 +165,22 @@ pub trait DeviceRemoval {
165165
fn device_remove(&self);
166166
}
167167

168+
impl DeviceRemoval for () {
169+
fn device_remove(&self) {}
170+
}
171+
172+
impl<T: DeviceRemoval> DeviceRemoval for Ref<T> {
173+
fn device_remove(&self) {
174+
self.deref().device_remove();
175+
}
176+
}
177+
178+
impl<T: DeviceRemoval> DeviceRemoval for Box<T> {
179+
fn device_remove(&self) {
180+
self.deref().device_remove();
181+
}
182+
}
183+
168184
/// A kernel module that only registers the given driver on init.
169185
///
170186
/// This is a helper struct to make it easier to define single-functionality modules, in this case,

0 commit comments

Comments
 (0)