1 // SPDX-License-Identifier: GPL-2.0
3 //! Crate for all kernel procedural macros.
10 use proc_macro::TokenStream;
12 /// Declares a kernel module.
14 /// The `type` argument should be a type which implements the [`Module`]
15 /// trait. Also accepts various forms of kernel metadata.
17 /// C header: [`include/linux/moduleparam.h`](../../../include/linux/moduleparam.h)
19 /// [`Module`]: ../kernel/trait.Module.html
24 /// use kernel::prelude::*;
28 /// name: "my_kernel_module",
29 /// author: "Rust for Linux Contributors",
30 /// description: "My very own kernel module!",
35 /// permissions: 0o000,
36 /// description: "Example of i32",
38 /// writeable_i32: i32 {
40 /// permissions: 0o644,
41 /// description: "Example of i32",
48 /// impl kernel::Module for MyModule {
49 /// fn init() -> Result<Self> {
50 /// // If the parameter is writeable, then the kparam lock must be
51 /// // taken to read the parameter:
53 /// let lock = THIS_MODULE.kernel_param_lock();
54 /// pr_info!("i32 param is: {}\n", writeable_i32.read(&lock));
56 /// // If the parameter is read only, it can be read without locking
57 /// // the kernel parameters:
58 /// pr_info!("i32 param is: {}\n", my_i32.read());
64 /// # Supported argument types
65 /// - `type`: type which implements the [`Module`] trait (required).
66 /// - `name`: byte array of the name of the kernel module (required).
67 /// - `author`: byte array of the author of the kernel module.
68 /// - `description`: byte array of the description of the kernel module.
69 /// - `license`: byte array of the license of the kernel module (required).
70 /// - `alias`: byte array of alias name of the kernel module.
72 pub fn module(ts: TokenStream) -> TokenStream {
76 /// Declares or implements a vtable trait.
78 /// Linux's use of pure vtables is very close to Rust traits, but they differ
79 /// in how unimplemented functions are represented. In Rust, traits can provide
80 /// default implementation for all non-required methods (and the default
81 /// implementation could just return `Error::EINVAL`); Linux typically use C
82 /// `NULL` pointers to represent these functions.
84 /// This attribute is intended to close the gap. Traits can be declared and
85 /// implemented with the `#[vtable]` attribute, and a `HAS_*` associated constant
86 /// will be generated for each method in the trait, indicating if the implementor
87 /// has overridden a method.
89 /// This attribute is not needed if all methods are required.
94 /// use kernel::prelude::*;
96 /// // Declares a `#[vtable]` trait
98 /// pub trait Operations: Send + Sync + Sized {
99 /// fn foo(&self) -> Result<()> {
103 /// fn bar(&self) -> Result<()> {
110 /// // Implements the `#[vtable]` trait
112 /// impl Operations for Foo {
113 /// fn foo(&self) -> Result<()> {
119 /// assert_eq!(<Foo as Operations>::HAS_FOO, true);
120 /// assert_eq!(<Foo as Operations>::HAS_BAR, false);
122 #[proc_macro_attribute]
123 pub fn vtable(attr: TokenStream, ts: TokenStream) -> TokenStream {
124 vtable::vtable(attr, ts)
127 /// Concatenate two identifiers.
129 /// This is useful in macros that need to declare or reference items with names
130 /// starting with a fixed prefix and ending in a user specified name. The resulting
131 /// identifier has the span of the second argument.
136 /// use kernel::macro::concat_idents;
138 /// macro_rules! pub_no_prefix {
139 /// ($prefix:ident, $($newname:ident),+) => {
140 /// $(pub(crate) const $newname: u32 = kernel::macros::concat_idents!($prefix, $newname);)+
145 /// binder_driver_return_protocol_,
151 /// BR_TRANSACTION_COMPLETE,
159 /// BR_CLEAR_DEATH_NOTIFICATION_DONE,
163 /// assert_eq!(BR_OK, binder_driver_return_protocol_BR_OK);
166 pub fn concat_idents(ts: TokenStream) -> TokenStream {
167 concat_idents::concat_idents(ts)