Messages in this thread | | | Date | Fri, 2 Jun 2023 09:39:25 +0000 | Subject | Re: [PATCH v2 8/8] rust: workqueue: add examples | From | Alice Ryhl <> |
| |
Gary Guo <gary@garyguo.net> writes: > On Thu, 1 Jun 2023 13:49:46 +0000 > Alice Ryhl <aliceryhl@google.com> wrote: >> This adds two examples of how to use the workqueue. The first example >> shows how to use it when you only have one `work_struct` field, and the >> second example shows how to use it when you have multiple `work_struct` >> fields. >> >> Signed-off-by: Alice Ryhl <aliceryhl@google.com> >> --- >> rust/kernel/workqueue.rs | 104 +++++++++++++++++++++++++++++++++++++++ >> 1 file changed, 104 insertions(+) >> >> diff --git a/rust/kernel/workqueue.rs b/rust/kernel/workqueue.rs >> index c302e8b8624b..cefcf43ff40e 100644 >> --- a/rust/kernel/workqueue.rs >> +++ b/rust/kernel/workqueue.rs >> @@ -26,6 +26,110 @@ >> //! * The `WorkItemPointer` trait is implemented for the pointer type that points at a something >> //! that implements `WorkItem`. >> //! >> +//! ## Example >> +//! >> +//! This example defines a struct that holds an integer and can be scheduled on the workqueue. When >> +//! the struct is executed, it will print the integer. Since there is only one `work_struct` field, >> +//! we do not need to specify ids for the fields. >> +//! >> +//! ``` >> +//! use kernel::prelude::*; >> +//! use kernel::sync::Arc; >> +//! use kernel::workqueue::{self, Work, WorkItem}; >> +//! >> +//! #[pin_data] >> +//! struct MyStruct { >> +//! value: i32, >> +//! #[pin] >> +//! work: Work<MyStruct>, >> +//! } >> +//! >> +//! impl_has_work! { >> +//! impl HasWork<Self> for MyStruct { self.work } >> +//! } >> +//! >> +//! impl MyStruct { >> +//! fn new(value: i32) -> Result<Arc<Self>> { >> +//! Arc::pin_init(pin_init!(MyStruct { >> +//! value, >> +//! work <- Work::new(), >> +//! })) >> +//! } >> +//! } >> +//! >> +//! impl WorkItem for MyStruct { >> +//! type Pointer = Arc<MyStruct>; >> +//! >> +//! fn run(this: Arc<MyStruct>) { >> +//! pr_info!("The value is: {}", this.value); >> +//! } >> +//! } >> +//! >> +//! /// This method will enqueue the struct for execution on the system workqueue, where its value >> +//! /// will be printed. >> +//! fn print_later(val: Arc<MyStruct>) { >> +//! let _ = workqueue::system().enqueue(val); >> +//! } >> +//! ``` >> +//! >> +//! The following example shows how multiple `work_struct` fields can be used: >> +//! >> +//! ``` >> +//! use kernel::prelude::*; >> +//! use kernel::sync::Arc; >> +//! use kernel::workqueue::{self, Work, WorkItem}; >> +//! >> +//! #[pin_data] >> +//! struct MyStruct { >> +//! value_1: i32, >> +//! value_2: i32, >> +//! #[pin] >> +//! work_1: Work<MyStruct, 1>, >> +//! #[pin] >> +//! work_2: Work<MyStruct, 2>, >> +//! } >> +//! >> +//! impl_has_work! { >> +//! impl HasWork<Self, 1> for MyStruct { self.work_1 } >> +//! impl HasWork<Self, 2> for MyStruct { self.work_2 } >> +//! } >> +//! >> +//! impl MyStruct { >> +//! fn new(value_1: i32, value_2: i32) -> Result<Arc<Self>> { >> +//! Arc::pin_init(pin_init!(MyStruct { >> +//! value_1, >> +//! value_2, >> +//! work_1 <- Work::new(), >> +//! work_2 <- Work::new(), >> +//! })) >> +//! } >> +//! } >> +//! >> +//! impl WorkItem<1> for MyStruct { >> +//! type Pointer = Arc<MyStruct>; >> +//! >> +//! fn run(this: Arc<MyStruct>) { >> +//! pr_info!("The value is: {}", this.value_1); >> +//! } >> +//! } >> +//! >> +//! impl WorkItem<2> for MyStruct { >> +//! type Pointer = Arc<MyStruct>; >> +//! >> +//! fn run(this: Arc<MyStruct>) { >> +//! pr_info!("The second value is: {}", this.value_2); >> +//! } >> +//! } >> +//! >> +//! fn print_1_later(val: Arc<MyStruct>) { >> +//! let _ = workqueue::system().enqueue::<Arc<MyStruct>, 1>(val); > > Nothing bad about explicit, but I just want to confirm that you could > write > > let _ = workqueue::system().enqueue::<_, 1>(val); > > here, right?
Yes, you can also do that.
| |