On Tue, 13 Jan 2026 at 01:11, Gary Guo <[email protected]> wrote: > > From: Gary Guo <[email protected]> > > With `quote` crate now vendored in the kernel, we can remove our custom > `quote!` macro implementation and just rely on that crate instead. > > The `quote` crate uses types from the `proc-macro2` library so we also > update to use that, and perform conversion in the top-level lib.rs. > > Clippy complains about unnecessary `.to_string()` as `proc-macro2` > provides additional `PartialEq` impl, so they are removed. > > Reviewed-by: Tamir Duberstein <[email protected]> > Reviewed-by: Benno Lossin <[email protected]> > Signed-off-by: Gary Guo <[email protected]> > ---
Acked-by: David Gow <[email protected]> # for kunit Cheers, -- David -- David > rust/macros/concat_idents.rs | 2 +- > rust/macros/export.rs | 4 +- > rust/macros/fmt.rs | 4 +- > rust/macros/helpers.rs | 4 +- > rust/macros/kunit.rs | 5 +- > rust/macros/lib.rs | 21 ++-- > rust/macros/module.rs | 6 +- > rust/macros/paste.rs | 2 +- > rust/macros/quote.rs | 182 ----------------------------------- > rust/macros/vtable.rs | 7 +- > 10 files changed, 32 insertions(+), 205 deletions(-) > delete mode 100644 rust/macros/quote.rs > > diff --git a/rust/macros/concat_idents.rs b/rust/macros/concat_idents.rs > index 7e4b450f3a507..12cb231c3d715 100644 > --- a/rust/macros/concat_idents.rs > +++ b/rust/macros/concat_idents.rs > @@ -1,6 +1,6 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use proc_macro::{token_stream, Ident, TokenStream, TokenTree}; > +use proc_macro2::{token_stream, Ident, TokenStream, TokenTree}; > > use crate::helpers::expect_punct; > > diff --git a/rust/macros/export.rs b/rust/macros/export.rs > index a08f6337d5c8d..92d9b30971929 100644 > --- a/rust/macros/export.rs > +++ b/rust/macros/export.rs > @@ -1,7 +1,9 @@ > // SPDX-License-Identifier: GPL-2.0 > > +use proc_macro2::TokenStream; > +use quote::quote; > + > use crate::helpers::function_name; > -use proc_macro::TokenStream; > > /// Please see [`crate::export`] for documentation. > pub(crate) fn export(_attr: TokenStream, ts: TokenStream) -> TokenStream { > diff --git a/rust/macros/fmt.rs b/rust/macros/fmt.rs > index 2f4b9f6e22110..19f709262552b 100644 > --- a/rust/macros/fmt.rs > +++ b/rust/macros/fmt.rs > @@ -1,8 +1,10 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use proc_macro::{Ident, TokenStream, TokenTree}; > use std::collections::BTreeSet; > > +use proc_macro2::{Ident, TokenStream, TokenTree}; > +use quote::quote_spanned; > + > /// Please see [`crate::fmt`] for documentation. > pub(crate) fn fmt(input: TokenStream) -> TokenStream { > let mut input = input.into_iter(); > diff --git a/rust/macros/helpers.rs b/rust/macros/helpers.rs > index 365d7eb499c08..13fafaba12261 100644 > --- a/rust/macros/helpers.rs > +++ b/rust/macros/helpers.rs > @@ -1,6 +1,6 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use proc_macro::{token_stream, Group, Ident, TokenStream, TokenTree}; > +use proc_macro2::{token_stream, Group, Ident, TokenStream, TokenTree}; > > pub(crate) fn try_ident(it: &mut token_stream::IntoIter) -> Option<String> { > if let Some(TokenTree::Ident(ident)) = it.next() { > @@ -86,7 +86,7 @@ pub(crate) fn function_name(input: TokenStream) -> > Option<Ident> { > let mut input = input.into_iter(); > while let Some(token) = input.next() { > match token { > - TokenTree::Ident(i) if i.to_string() == "fn" => { > + TokenTree::Ident(i) if i == "fn" => { > if let Some(TokenTree::Ident(i)) = input.next() { > return Some(i); > } > diff --git a/rust/macros/kunit.rs b/rust/macros/kunit.rs > index b395bb0536959..5cd6aa5eef07d 100644 > --- a/rust/macros/kunit.rs > +++ b/rust/macros/kunit.rs > @@ -4,10 +4,11 @@ > //! > //! Copyright (c) 2023 José Expósito <[email protected]> > > -use proc_macro::{Delimiter, Group, TokenStream, TokenTree}; > use std::collections::HashMap; > use std::fmt::Write; > > +use proc_macro2::{Delimiter, Group, TokenStream, TokenTree}; > + > pub(crate) fn kunit_tests(attr: TokenStream, ts: TokenStream) -> TokenStream > { > let attr = attr.to_string(); > > @@ -59,7 +60,7 @@ pub(crate) fn kunit_tests(attr: TokenStream, ts: > TokenStream) -> TokenStream { > } > _ => (), > }, > - TokenTree::Ident(i) if i.to_string() == "fn" && > attributes.contains_key("test") => { > + TokenTree::Ident(i) if i == "fn" && > attributes.contains_key("test") => { > if let Some(TokenTree::Ident(test_name)) = body_it.next() { > tests.push((test_name, > attributes.remove("cfg").unwrap_or_default())) > } > diff --git a/rust/macros/lib.rs b/rust/macros/lib.rs > index b38002151871a..945982c21f703 100644 > --- a/rust/macros/lib.rs > +++ b/rust/macros/lib.rs > @@ -11,8 +11,6 @@ > // to avoid depending on the full `proc_macro_span` on Rust >= 1.88.0. > #![cfg_attr(not(CONFIG_RUSTC_HAS_SPAN_FILE), feature(proc_macro_span))] > > -#[macro_use] > -mod quote; > mod concat_idents; > mod export; > mod fmt; > @@ -132,7 +130,7 @@ > /// the kernel module. > #[proc_macro] > pub fn module(ts: TokenStream) -> TokenStream { > - module::module(ts) > + module::module(ts.into()).into() > } > > /// Declares or implements a vtable trait. > @@ -207,7 +205,7 @@ pub fn module(ts: TokenStream) -> TokenStream { > /// [`kernel::error::VTABLE_DEFAULT_ERROR`]: > ../kernel/error/constant.VTABLE_DEFAULT_ERROR.html > #[proc_macro_attribute] > pub fn vtable(attr: TokenStream, ts: TokenStream) -> TokenStream { > - vtable::vtable(attr, ts) > + vtable::vtable(attr.into(), ts.into()).into() > } > > /// Export a function so that C code can call it via a header file. > @@ -230,7 +228,7 @@ pub fn vtable(attr: TokenStream, ts: TokenStream) -> > TokenStream { > /// automatically exported with `EXPORT_SYMBOL_GPL`. > #[proc_macro_attribute] > pub fn export(attr: TokenStream, ts: TokenStream) -> TokenStream { > - export::export(attr, ts) > + export::export(attr.into(), ts.into()).into() > } > > /// Like [`core::format_args!`], but automatically wraps arguments in > [`kernel::fmt::Adapter`]. > @@ -248,7 +246,7 @@ pub fn export(attr: TokenStream, ts: TokenStream) -> > TokenStream { > /// [`pr_info!`]: ../kernel/macro.pr_info.html > #[proc_macro] > pub fn fmt(input: TokenStream) -> TokenStream { > - fmt::fmt(input) > + fmt::fmt(input.into()).into() > } > > /// Concatenate two identifiers. > @@ -306,7 +304,7 @@ pub fn fmt(input: TokenStream) -> TokenStream { > /// ``` > #[proc_macro] > pub fn concat_idents(ts: TokenStream) -> TokenStream { > - concat_idents::concat_idents(ts) > + concat_idents::concat_idents(ts.into()).into() > } > > /// Paste identifiers together. > @@ -444,9 +442,12 @@ pub fn concat_idents(ts: TokenStream) -> TokenStream { > /// [`paste`]: https://docs.rs/paste/ > #[proc_macro] > pub fn paste(input: TokenStream) -> TokenStream { > - let mut tokens = input.into_iter().collect(); > + let mut tokens = > proc_macro2::TokenStream::from(input).into_iter().collect(); > paste::expand(&mut tokens); > - tokens.into_iter().collect() > + tokens > + .into_iter() > + .collect::<proc_macro2::TokenStream>() > + .into() > } > > /// Registers a KUnit test suite and its test cases using a user-space like > syntax. > @@ -473,5 +474,5 @@ pub fn paste(input: TokenStream) -> TokenStream { > /// ``` > #[proc_macro_attribute] > pub fn kunit_tests(attr: TokenStream, ts: TokenStream) -> TokenStream { > - kunit::kunit_tests(attr, ts) > + kunit::kunit_tests(attr.into(), ts.into()).into() > } > diff --git a/rust/macros/module.rs b/rust/macros/module.rs > index 80cb9b16f5aaf..b855a2b586e18 100644 > --- a/rust/macros/module.rs > +++ b/rust/macros/module.rs > @@ -1,9 +1,11 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use crate::helpers::*; > -use proc_macro::{token_stream, Delimiter, Literal, TokenStream, TokenTree}; > use std::fmt::Write; > > +use proc_macro2::{token_stream, Delimiter, Literal, TokenStream, TokenTree}; > + > +use crate::helpers::*; > + > fn expect_string_array(it: &mut token_stream::IntoIter) -> Vec<String> { > let group = expect_group(it); > assert_eq!(group.delimiter(), Delimiter::Bracket); > diff --git a/rust/macros/paste.rs b/rust/macros/paste.rs > index cce712d19855b..2181e312a7d32 100644 > --- a/rust/macros/paste.rs > +++ b/rust/macros/paste.rs > @@ -1,6 +1,6 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use proc_macro::{Delimiter, Group, Ident, Spacing, Span, TokenTree}; > +use proc_macro2::{Delimiter, Group, Ident, Spacing, Span, TokenTree}; > > fn concat_helper(tokens: &[TokenTree]) -> Vec<(String, Span)> { > let mut tokens = tokens.iter(); > diff --git a/rust/macros/quote.rs b/rust/macros/quote.rs > deleted file mode 100644 > index ddfc21577539c..0000000000000 > --- a/rust/macros/quote.rs > +++ /dev/null > @@ -1,182 +0,0 @@ > -// SPDX-License-Identifier: Apache-2.0 OR MIT > - > -use proc_macro::{TokenStream, TokenTree}; > - > -pub(crate) trait ToTokens { > - fn to_tokens(&self, tokens: &mut TokenStream); > -} > - > -impl<T: ToTokens> ToTokens for Option<T> { > - fn to_tokens(&self, tokens: &mut TokenStream) { > - if let Some(v) = self { > - v.to_tokens(tokens); > - } > - } > -} > - > -impl ToTokens for proc_macro::Group { > - fn to_tokens(&self, tokens: &mut TokenStream) { > - tokens.extend([TokenTree::from(self.clone())]); > - } > -} > - > -impl ToTokens for proc_macro::Ident { > - fn to_tokens(&self, tokens: &mut TokenStream) { > - tokens.extend([TokenTree::from(self.clone())]); > - } > -} > - > -impl ToTokens for TokenTree { > - fn to_tokens(&self, tokens: &mut TokenStream) { > - tokens.extend([self.clone()]); > - } > -} > - > -impl ToTokens for TokenStream { > - fn to_tokens(&self, tokens: &mut TokenStream) { > - tokens.extend(self.clone()); > - } > -} > - > -/// Converts tokens into [`proc_macro::TokenStream`] and performs variable > interpolations with > -/// the given span. > -/// > -/// This is a similar to the > -/// > [`quote_spanned!`](https://docs.rs/quote/latest/quote/macro.quote_spanned.html) > macro from the > -/// `quote` crate but provides only just enough functionality needed by the > current `macros` crate. > -macro_rules! quote_spanned { > - ($span:expr => $($tt:tt)*) => {{ > - let mut tokens = ::proc_macro::TokenStream::new(); > - { > - #[allow(unused_variables)] > - let span = $span; > - quote_spanned!(@proc tokens span $($tt)*); > - } > - tokens > - }}; > - (@proc $v:ident $span:ident) => {}; > - (@proc $v:ident $span:ident #$id:ident $($tt:tt)*) => { > - $crate::quote::ToTokens::to_tokens(&$id, &mut $v); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident #(#$id:ident)* $($tt:tt)*) => { > - for token in $id { > - $crate::quote::ToTokens::to_tokens(&token, &mut $v); > - } > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident ( $($inner:tt)* ) $($tt:tt)*) => { > - #[allow(unused_mut)] > - let mut tokens = ::proc_macro::TokenStream::new(); > - quote_spanned!(@proc tokens $span $($inner)*); > - $v.extend([::proc_macro::TokenTree::Group(::proc_macro::Group::new( > - ::proc_macro::Delimiter::Parenthesis, > - tokens, > - ))]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident [ $($inner:tt)* ] $($tt:tt)*) => { > - let mut tokens = ::proc_macro::TokenStream::new(); > - quote_spanned!(@proc tokens $span $($inner)*); > - $v.extend([::proc_macro::TokenTree::Group(::proc_macro::Group::new( > - ::proc_macro::Delimiter::Bracket, > - tokens, > - ))]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident { $($inner:tt)* } $($tt:tt)*) => { > - let mut tokens = ::proc_macro::TokenStream::new(); > - quote_spanned!(@proc tokens $span $($inner)*); > - $v.extend([::proc_macro::TokenTree::Group(::proc_macro::Group::new( > - ::proc_macro::Delimiter::Brace, > - tokens, > - ))]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident :: $($tt:tt)*) => { > - $v.extend([::proc_macro::Spacing::Joint, > ::proc_macro::Spacing::Alone].map(|spacing| { > - ::proc_macro::TokenTree::Punct(::proc_macro::Punct::new(':', > spacing)) > - })); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident : $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new(':', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident , $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new(',', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident @ $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('@', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident ! $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('!', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident ; $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new(';', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident + $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('+', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident = $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('=', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident # $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('#', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident & $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Punct( > - ::proc_macro::Punct::new('&', ::proc_macro::Spacing::Alone), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident _ $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Ident( > - ::proc_macro::Ident::new("_", $span), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > - (@proc $v:ident $span:ident $id:ident $($tt:tt)*) => { > - $v.extend([::proc_macro::TokenTree::Ident( > - ::proc_macro::Ident::new(stringify!($id), $span), > - )]); > - quote_spanned!(@proc $v $span $($tt)*); > - }; > -} > - > -/// Converts tokens into [`proc_macro::TokenStream`] and performs variable > interpolations with > -/// mixed site span ([`Span::mixed_site()`]). > -/// > -/// This is a similar to the > [`quote!`](https://docs.rs/quote/latest/quote/macro.quote.html) macro > -/// from the `quote` crate but provides only just enough functionality > needed by the current > -/// `macros` crate. > -/// > -/// [`Span::mixed_site()`]: > https://doc.rust-lang.org/proc_macro/struct.Span.html#method.mixed_site > -macro_rules! quote { > - ($($tt:tt)*) => { > - quote_spanned!(::proc_macro::Span::mixed_site() => $($tt)*) > - } > -} > diff --git a/rust/macros/vtable.rs b/rust/macros/vtable.rs > index ee06044fcd4f3..a67d1cc81a2d3 100644 > --- a/rust/macros/vtable.rs > +++ b/rust/macros/vtable.rs > @@ -1,9 +1,10 @@ > // SPDX-License-Identifier: GPL-2.0 > > -use proc_macro::{Delimiter, Group, TokenStream, TokenTree}; > use std::collections::HashSet; > use std::fmt::Write; > > +use proc_macro2::{Delimiter, Group, TokenStream, TokenTree}; > + > pub(crate) fn vtable(_attr: TokenStream, ts: TokenStream) -> TokenStream { > let mut tokens: Vec<_> = ts.into_iter().collect(); > > @@ -31,7 +32,7 @@ pub(crate) fn vtable(_attr: TokenStream, ts: TokenStream) > -> TokenStream { > let mut consts = HashSet::new(); > while let Some(token) = body_it.next() { > match token { > - TokenTree::Ident(ident) if ident.to_string() == "fn" => { > + TokenTree::Ident(ident) if ident == "fn" => { > let fn_name = match body_it.next() { > Some(TokenTree::Ident(ident)) => ident.to_string(), > // Possibly we've encountered a fn pointer type instead. > @@ -39,7 +40,7 @@ pub(crate) fn vtable(_attr: TokenStream, ts: TokenStream) > -> TokenStream { > }; > functions.push(fn_name); > } > - TokenTree::Ident(ident) if ident.to_string() == "const" => { > + TokenTree::Ident(ident) if ident == "const" => { > let const_name = match body_it.next() { > Some(TokenTree::Ident(ident)) => ident.to_string(), > // Possibly we've encountered an inline const block > instead. > -- > 2.51.2 >
smime.p7s
Description: S/MIME Cryptographic Signature

