xref: /linux/rust/macros/lib.rs (revision f4cdf7ca9a1fdcca413157df19753f388a5a224e)
1 // SPDX-License-Identifier: GPL-2.0
2 
3 //! Crate for all kernel procedural macros.
4 
5 // When fixdep scans this, it will find this string `CONFIG_RUSTC_VERSION_TEXT`
6 // and thus add a dependency on `include/config/RUSTC_VERSION_TEXT`, which is
7 // touched by Kconfig when the version string from the compiler changes.
8 
9 // Stable since Rust 1.87.0.
10 #![feature(extract_if)]
11 //
12 // Stable since Rust 1.88.0 under a different name, `proc_macro_span_file`,
13 // which was added in Rust 1.88.0. This is why `cfg_attr` is used here, i.e.
14 // to avoid depending on the full `proc_macro_span` on Rust >= 1.88.0.
15 #![cfg_attr(not(CONFIG_RUSTC_HAS_SPAN_FILE), feature(proc_macro_span))]
16 
17 mod concat_idents;
18 mod export;
19 mod fmt;
20 mod for_lt;
21 mod helpers;
22 mod kunit;
23 mod module;
24 mod paste;
25 mod vtable;
26 
27 use proc_macro::TokenStream;
28 
29 use syn::parse_macro_input;
30 
31 /// Declares a kernel module.
32 ///
33 /// The `type` argument should be a type which implements the [`Module`]
34 /// trait. Also accepts various forms of kernel metadata.
35 ///
36 /// The `params` field describe module parameters. Each entry has the form
37 ///
38 /// ```ignore
39 /// parameter_name: type {
40 ///     default: default_value,
41 ///     description: "Description",
42 /// }
43 /// ```
44 ///
45 /// `type` may be one of
46 ///
47 /// - [`i8`]
48 /// - [`u8`]
49 /// - [`i8`]
50 /// - [`u8`]
51 /// - [`i16`]
52 /// - [`u16`]
53 /// - [`i32`]
54 /// - [`u32`]
55 /// - [`i64`]
56 /// - [`u64`]
57 /// - [`isize`]
58 /// - [`usize`]
59 ///
60 /// C header: [`include/linux/moduleparam.h`](srctree/include/linux/moduleparam.h)
61 ///
62 /// [`Module`]: ../kernel/trait.Module.html
63 ///
64 /// # Examples
65 ///
66 /// ```ignore
67 /// use kernel::prelude::*;
68 ///
69 /// module!{
70 ///     type: MyModule,
71 ///     name: "my_kernel_module",
72 ///     authors: ["Rust for Linux Contributors"],
73 ///     description: "My very own kernel module!",
74 ///     license: "GPL",
75 ///     alias: ["alternate_module_name"],
76 ///     params: {
77 ///         my_parameter: i64 {
78 ///             default: 1,
79 ///             description: "This parameter has a default of 1",
80 ///         },
81 ///     },
82 /// }
83 ///
84 /// struct MyModule(i32);
85 ///
86 /// impl kernel::Module for MyModule {
87 ///     fn init(_module: &'static ThisModule) -> Result<Self> {
88 ///         let foo: i32 = 42;
89 ///         pr_info!("I contain:  {}\n", foo);
90 ///         pr_info!("i32 param is:  {}\n", module_parameters::my_parameter.read());
91 ///         Ok(Self(foo))
92 ///     }
93 /// }
94 /// # fn main() {}
95 /// ```
96 ///
97 /// ## Firmware
98 ///
99 /// The following example shows how to declare a kernel module that needs
100 /// to load binary firmware files. You need to specify the file names of
101 /// the firmware in the `firmware` field. The information is embedded
102 /// in the `modinfo` section of the kernel module. For example, a tool to
103 /// build an initramfs uses this information to put the firmware files into
104 /// the initramfs image.
105 ///
106 /// ```
107 /// use kernel::prelude::*;
108 ///
109 /// module!{
110 ///     type: MyDeviceDriverModule,
111 ///     name: "my_device_driver_module",
112 ///     authors: ["Rust for Linux Contributors"],
113 ///     description: "My device driver requires firmware",
114 ///     license: "GPL",
115 ///     firmware: ["my_device_firmware1.bin", "my_device_firmware2.bin"],
116 /// }
117 ///
118 /// struct MyDeviceDriverModule;
119 ///
120 /// impl kernel::Module for MyDeviceDriverModule {
121 ///     fn init(_module: &'static ThisModule) -> Result<Self> {
122 ///         Ok(Self)
123 ///     }
124 /// }
125 /// # fn main() {}
126 /// ```
127 ///
128 /// # Supported argument types
129 ///   - `type`: type which implements the [`Module`] trait (required).
130 ///   - `name`: ASCII string literal of the name of the kernel module (required).
131 ///   - `authors`: array of ASCII string literals of the authors of the kernel module.
132 ///   - `description`: string literal of the description of the kernel module.
133 ///   - `license`: ASCII string literal of the license of the kernel module (required).
134 ///   - `alias`: array of ASCII string literals of the alias names of the kernel module.
135 ///   - `firmware`: array of ASCII string literals of the firmware files of
136 ///     the kernel module.
137 #[proc_macro]
138 pub fn module(input: TokenStream) -> TokenStream {
139     module::module(parse_macro_input!(input))
140         .unwrap_or_else(|e| e.into_compile_error())
141         .into()
142 }
143 
144 /// Declares or implements a vtable trait.
145 ///
146 /// Linux's use of pure vtables is very close to Rust traits, but they differ
147 /// in how unimplemented functions are represented. In Rust, traits can provide
148 /// default implementation for all non-required methods (and the default
149 /// implementation could just return `Error::EINVAL`); Linux typically use C
150 /// `NULL` pointers to represent these functions.
151 ///
152 /// This attribute closes that gap. A trait can be annotated with the
153 /// `#[vtable]` attribute. Implementers of the trait will then also have to
154 /// annotate the trait with `#[vtable]`. This attribute generates a `HAS_*`
155 /// associated constant bool for each method in the trait that is set to true if
156 /// the implementer has overridden the associated method.
157 ///
158 /// For a trait method to be optional, it must have a default implementation.
159 /// This is also the case for traits annotated with `#[vtable]`, but in this
160 /// case the default implementation will never be executed. The reason for this
161 /// is that the functions will be called through function pointers installed in
162 /// C side vtables. When an optional method is not implemented on a `#[vtable]`
163 /// trait, a `NULL` entry is installed in the vtable. Thus the default
164 /// implementation is never called. Since these traits are not designed to be
165 /// used on the Rust side, it should not be possible to call the default
166 /// implementation. This is done to ensure that we call the vtable methods
167 /// through the C vtable, and not through the Rust vtable. Therefore, the
168 /// default implementation should call `build_error!`, which prevents
169 /// calls to this function at compile time:
170 ///
171 /// ```compile_fail
172 /// # // Intentionally missing `use`s to simplify `rusttest`.
173 /// build_error!(VTABLE_DEFAULT_ERROR)
174 /// ```
175 ///
176 /// Note that you might need to import [`kernel::error::VTABLE_DEFAULT_ERROR`].
177 ///
178 /// This macro should not be used when all functions are required.
179 ///
180 /// Additionally, this macro automatically handles the `OwnerModule`
181 /// associated type: on the trait side, `type OwnerModule: ModuleMetadata;`
182 /// is added as a required associated type if not already defined; on the
183 /// impl side, `type OwnerModule = LocalModule;` is automatically inserted
184 /// if not explicitly defined.
185 ///
186 /// # Examples
187 ///
188 /// ```
189 /// use kernel::error::VTABLE_DEFAULT_ERROR;
190 /// use kernel::prelude::*;
191 ///
192 /// # struct LocalModule;
193 /// # impl kernel::ModuleMetadata for LocalModule {
194 /// #     const NAME: &'static kernel::str::CStr = c"vtable_doctest";
195 /// #
196 /// #     // SAFETY: This doctest runs on the host: there is no `THIS_MODULE`.
197 /// #     const THIS_MODULE: kernel::ThisModule = unsafe {
198 /// #         kernel::ThisModule::from_ptr(core::ptr::null_mut())
199 /// #     };
200 /// # }
201 /// #
202 /// # fn main() {
203 /// // Declares a `#[vtable]` trait
204 /// #[vtable]
205 /// pub trait Operations: Send + Sync + Sized {
206 ///     fn foo(&self) -> Result<()> {
207 ///         build_error!(VTABLE_DEFAULT_ERROR)
208 ///     }
209 ///
210 ///     fn bar(&self) -> Result<()> {
211 ///         build_error!(VTABLE_DEFAULT_ERROR)
212 ///     }
213 /// }
214 ///
215 /// struct Foo;
216 ///
217 /// // Implements the `#[vtable]` trait
218 /// #[vtable]
219 /// impl Operations for Foo {
220 ///     fn foo(&self) -> Result<()> {
221 /// #        Err(EINVAL)
222 ///         // ...
223 ///     }
224 /// }
225 ///
226 /// assert_eq!(<Foo as Operations>::HAS_FOO, true);
227 /// assert_eq!(<Foo as Operations>::HAS_BAR, false);
228 /// # }
229 /// ```
230 ///
231 /// [`kernel::error::VTABLE_DEFAULT_ERROR`]: ../kernel/error/constant.VTABLE_DEFAULT_ERROR.html
232 #[proc_macro_attribute]
233 pub fn vtable(attr: TokenStream, input: TokenStream) -> TokenStream {
234     parse_macro_input!(attr as syn::parse::Nothing);
235     vtable::vtable(parse_macro_input!(input))
236         .unwrap_or_else(|e| e.into_compile_error())
237         .into()
238 }
239 
240 /// Export a function so that C code can call it via a header file.
241 ///
242 /// Functions exported using this macro can be called from C code using the declaration in the
243 /// appropriate header file. It should only be used in cases where C calls the function through a
244 /// header file; cases where C calls into Rust via a function pointer in a vtable (such as
245 /// `file_operations`) should not use this macro.
246 ///
247 /// This macro has the following effect:
248 ///
249 /// * Disables name mangling for this function.
250 /// * Verifies at compile-time that the function signature matches the declaration in the header
251 ///   file.
252 ///
253 /// You must declare the signature of the Rust function in a header file that is included by
254 /// `rust/bindings/bindings_helper.h`.
255 ///
256 /// This macro is *not* the same as the C macros `EXPORT_SYMBOL_*`. All Rust symbols are currently
257 /// automatically exported with `EXPORT_SYMBOL_GPL`.
258 #[proc_macro_attribute]
259 pub fn export(attr: TokenStream, input: TokenStream) -> TokenStream {
260     parse_macro_input!(attr as syn::parse::Nothing);
261     export::export(parse_macro_input!(input)).into()
262 }
263 
264 /// Like [`core::format_args!`], but automatically wraps arguments in [`kernel::fmt::Adapter`].
265 ///
266 /// This macro allows generating `fmt::Arguments` while ensuring that each argument is wrapped with
267 /// `::kernel::fmt::Adapter`, which customizes formatting behavior for kernel logging.
268 ///
269 /// Named arguments used in the format string (e.g. `{foo}`) are detected and resolved from local
270 /// bindings. All positional and named arguments are automatically wrapped.
271 ///
272 /// This macro is an implementation detail of other kernel logging macros like [`pr_info!`] and
273 /// should not typically be used directly.
274 ///
275 /// [`kernel::fmt::Adapter`]: ../kernel/fmt/struct.Adapter.html
276 /// [`pr_info!`]: ../kernel/macro.pr_info.html
277 #[proc_macro]
278 pub fn fmt(input: TokenStream) -> TokenStream {
279     fmt::fmt(input.into()).into()
280 }
281 
282 /// Concatenate two identifiers.
283 ///
284 /// This is useful in macros that need to declare or reference items with names
285 /// starting with a fixed prefix and ending in a user specified name. The resulting
286 /// identifier has the span of the second argument.
287 ///
288 /// # Examples
289 ///
290 /// ```
291 /// # const binder_driver_return_protocol_BR_OK: u32 = 0;
292 /// # const binder_driver_return_protocol_BR_ERROR: u32 = 1;
293 /// # const binder_driver_return_protocol_BR_TRANSACTION: u32 = 2;
294 /// # const binder_driver_return_protocol_BR_REPLY: u32 = 3;
295 /// # const binder_driver_return_protocol_BR_DEAD_REPLY: u32 = 4;
296 /// # const binder_driver_return_protocol_BR_TRANSACTION_COMPLETE: u32 = 5;
297 /// # const binder_driver_return_protocol_BR_INCREFS: u32 = 6;
298 /// # const binder_driver_return_protocol_BR_ACQUIRE: u32 = 7;
299 /// # const binder_driver_return_protocol_BR_RELEASE: u32 = 8;
300 /// # const binder_driver_return_protocol_BR_DECREFS: u32 = 9;
301 /// # const binder_driver_return_protocol_BR_NOOP: u32 = 10;
302 /// # const binder_driver_return_protocol_BR_SPAWN_LOOPER: u32 = 11;
303 /// # const binder_driver_return_protocol_BR_DEAD_BINDER: u32 = 12;
304 /// # const binder_driver_return_protocol_BR_CLEAR_DEATH_NOTIFICATION_DONE: u32 = 13;
305 /// # const binder_driver_return_protocol_BR_FAILED_REPLY: u32 = 14;
306 /// use kernel::macros::concat_idents;
307 ///
308 /// macro_rules! pub_no_prefix {
309 ///     ($prefix:ident, $($newname:ident),+) => {
310 ///         $(pub(crate) const $newname: u32 = concat_idents!($prefix, $newname);)+
311 ///     };
312 /// }
313 ///
314 /// pub_no_prefix!(
315 ///     binder_driver_return_protocol_,
316 ///     BR_OK,
317 ///     BR_ERROR,
318 ///     BR_TRANSACTION,
319 ///     BR_REPLY,
320 ///     BR_DEAD_REPLY,
321 ///     BR_TRANSACTION_COMPLETE,
322 ///     BR_INCREFS,
323 ///     BR_ACQUIRE,
324 ///     BR_RELEASE,
325 ///     BR_DECREFS,
326 ///     BR_NOOP,
327 ///     BR_SPAWN_LOOPER,
328 ///     BR_DEAD_BINDER,
329 ///     BR_CLEAR_DEATH_NOTIFICATION_DONE,
330 ///     BR_FAILED_REPLY
331 /// );
332 ///
333 /// assert_eq!(BR_OK, binder_driver_return_protocol_BR_OK);
334 /// ```
335 #[proc_macro]
336 pub fn concat_idents(input: TokenStream) -> TokenStream {
337     concat_idents::concat_idents(parse_macro_input!(input)).into()
338 }
339 
340 /// Paste identifiers together.
341 ///
342 /// Within the `paste!` macro, identifiers inside `[<` and `>]` are concatenated together to form a
343 /// single identifier.
344 ///
345 /// This is similar to the [`paste`] crate, but with pasting feature limited to identifiers and
346 /// literals (lifetimes and documentation strings are not supported). There is a difference in
347 /// supported modifiers as well.
348 ///
349 /// # Examples
350 ///
351 /// ```
352 /// # const binder_driver_return_protocol_BR_OK: u32 = 0;
353 /// # const binder_driver_return_protocol_BR_ERROR: u32 = 1;
354 /// # const binder_driver_return_protocol_BR_TRANSACTION: u32 = 2;
355 /// # const binder_driver_return_protocol_BR_REPLY: u32 = 3;
356 /// # const binder_driver_return_protocol_BR_DEAD_REPLY: u32 = 4;
357 /// # const binder_driver_return_protocol_BR_TRANSACTION_COMPLETE: u32 = 5;
358 /// # const binder_driver_return_protocol_BR_INCREFS: u32 = 6;
359 /// # const binder_driver_return_protocol_BR_ACQUIRE: u32 = 7;
360 /// # const binder_driver_return_protocol_BR_RELEASE: u32 = 8;
361 /// # const binder_driver_return_protocol_BR_DECREFS: u32 = 9;
362 /// # const binder_driver_return_protocol_BR_NOOP: u32 = 10;
363 /// # const binder_driver_return_protocol_BR_SPAWN_LOOPER: u32 = 11;
364 /// # const binder_driver_return_protocol_BR_DEAD_BINDER: u32 = 12;
365 /// # const binder_driver_return_protocol_BR_CLEAR_DEATH_NOTIFICATION_DONE: u32 = 13;
366 /// # const binder_driver_return_protocol_BR_FAILED_REPLY: u32 = 14;
367 /// macro_rules! pub_no_prefix {
368 ///     ($prefix:ident, $($newname:ident),+) => {
369 ///         ::kernel::macros::paste! {
370 ///             $(pub(crate) const $newname: u32 = [<$prefix $newname>];)+
371 ///         }
372 ///     };
373 /// }
374 ///
375 /// pub_no_prefix!(
376 ///     binder_driver_return_protocol_,
377 ///     BR_OK,
378 ///     BR_ERROR,
379 ///     BR_TRANSACTION,
380 ///     BR_REPLY,
381 ///     BR_DEAD_REPLY,
382 ///     BR_TRANSACTION_COMPLETE,
383 ///     BR_INCREFS,
384 ///     BR_ACQUIRE,
385 ///     BR_RELEASE,
386 ///     BR_DECREFS,
387 ///     BR_NOOP,
388 ///     BR_SPAWN_LOOPER,
389 ///     BR_DEAD_BINDER,
390 ///     BR_CLEAR_DEATH_NOTIFICATION_DONE,
391 ///     BR_FAILED_REPLY
392 /// );
393 ///
394 /// assert_eq!(BR_OK, binder_driver_return_protocol_BR_OK);
395 /// ```
396 ///
397 /// # Modifiers
398 ///
399 /// For each identifier, it is possible to attach one or multiple modifiers to
400 /// it.
401 ///
402 /// Currently supported modifiers are:
403 /// * `span`: change the span of concatenated identifier to the span of the specified token. By
404 ///   default the span of the `[< >]` group is used.
405 /// * `lower`: change the identifier to lower case.
406 /// * `upper`: change the identifier to upper case.
407 ///
408 /// ```
409 /// # const binder_driver_return_protocol_BR_OK: u32 = 0;
410 /// # const binder_driver_return_protocol_BR_ERROR: u32 = 1;
411 /// # const binder_driver_return_protocol_BR_TRANSACTION: u32 = 2;
412 /// # const binder_driver_return_protocol_BR_REPLY: u32 = 3;
413 /// # const binder_driver_return_protocol_BR_DEAD_REPLY: u32 = 4;
414 /// # const binder_driver_return_protocol_BR_TRANSACTION_COMPLETE: u32 = 5;
415 /// # const binder_driver_return_protocol_BR_INCREFS: u32 = 6;
416 /// # const binder_driver_return_protocol_BR_ACQUIRE: u32 = 7;
417 /// # const binder_driver_return_protocol_BR_RELEASE: u32 = 8;
418 /// # const binder_driver_return_protocol_BR_DECREFS: u32 = 9;
419 /// # const binder_driver_return_protocol_BR_NOOP: u32 = 10;
420 /// # const binder_driver_return_protocol_BR_SPAWN_LOOPER: u32 = 11;
421 /// # const binder_driver_return_protocol_BR_DEAD_BINDER: u32 = 12;
422 /// # const binder_driver_return_protocol_BR_CLEAR_DEATH_NOTIFICATION_DONE: u32 = 13;
423 /// # const binder_driver_return_protocol_BR_FAILED_REPLY: u32 = 14;
424 /// macro_rules! pub_no_prefix {
425 ///     ($prefix:ident, $($newname:ident),+) => {
426 ///         ::kernel::macros::paste! {
427 ///             $(pub(crate) const fn [<$newname:lower:span>]() -> u32 { [<$prefix $newname:span>] })+
428 ///         }
429 ///     };
430 /// }
431 ///
432 /// pub_no_prefix!(
433 ///     binder_driver_return_protocol_,
434 ///     BR_OK,
435 ///     BR_ERROR,
436 ///     BR_TRANSACTION,
437 ///     BR_REPLY,
438 ///     BR_DEAD_REPLY,
439 ///     BR_TRANSACTION_COMPLETE,
440 ///     BR_INCREFS,
441 ///     BR_ACQUIRE,
442 ///     BR_RELEASE,
443 ///     BR_DECREFS,
444 ///     BR_NOOP,
445 ///     BR_SPAWN_LOOPER,
446 ///     BR_DEAD_BINDER,
447 ///     BR_CLEAR_DEATH_NOTIFICATION_DONE,
448 ///     BR_FAILED_REPLY
449 /// );
450 ///
451 /// assert_eq!(br_ok(), binder_driver_return_protocol_BR_OK);
452 /// ```
453 ///
454 /// # Literals
455 ///
456 /// Literals can also be concatenated with other identifiers:
457 ///
458 /// ```
459 /// macro_rules! create_numbered_fn {
460 ///     ($name:literal, $val:literal) => {
461 ///         ::kernel::macros::paste! {
462 ///             fn [<some_ $name _fn $val>]() -> u32 { $val }
463 ///         }
464 ///     };
465 /// }
466 ///
467 /// create_numbered_fn!("foo", 100);
468 ///
469 /// assert_eq!(some_foo_fn100(), 100)
470 /// ```
471 ///
472 /// [`paste`]: https://docs.rs/paste/
473 #[proc_macro]
474 pub fn paste(input: TokenStream) -> TokenStream {
475     let mut tokens = proc_macro2::TokenStream::from(input).into_iter().collect();
476     paste::expand(&mut tokens);
477     tokens
478         .into_iter()
479         .collect::<proc_macro2::TokenStream>()
480         .into()
481 }
482 
483 /// Registers a KUnit test suite and its test cases using a user-space like syntax.
484 ///
485 /// This macro should be used on modules. If `CONFIG_KUNIT` (in `.config`) is `n`, the target module
486 /// is ignored.
487 ///
488 /// # Examples
489 ///
490 /// ```ignore
491 /// # use kernel::prelude::*;
492 /// #[kunit_tests(kunit_test_suit_name)]
493 /// mod tests {
494 ///     #[test]
495 ///     fn foo() {
496 ///         assert_eq!(1, 1);
497 ///     }
498 ///
499 ///     #[test]
500 ///     fn bar() {
501 ///         assert_eq!(2, 2);
502 ///     }
503 /// }
504 /// ```
505 #[proc_macro_attribute]
506 pub fn kunit_tests(attr: TokenStream, input: TokenStream) -> TokenStream {
507     kunit::kunit_tests(parse_macro_input!(attr), parse_macro_input!(input))
508         .unwrap_or_else(|e| e.into_compile_error())
509         .into()
510 }
511 
512 /// Obtain a type that implements [`ForLt`] for the given higher-ranked type.
513 ///
514 /// Please refer to the documentation of the [`ForLt`] trait.
515 ///
516 /// [`ForLt`]: trait.ForLt.html
517 #[proc_macro]
518 // The macro shares the name with the trait.
519 #[allow(non_snake_case)]
520 pub fn ForLt(input: TokenStream) -> TokenStream {
521     for_lt::for_lt(parse_macro_input!(input)).into()
522 }
523