diff --git a/Cargo.lock b/Cargo.lock index 1119162d..e4e64fa0 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -93,6 +93,7 @@ dependencies = [ "pinned-init-macro", "prettyplease", "rustc_version", + "test_dummy_only", "trybuild", ] @@ -220,6 +221,10 @@ dependencies = [ "winapi-util", ] +[[package]] +name = "test_dummy_only" +version = "0.0.1" + [[package]] name = "toml" version = "0.9.4" diff --git a/Cargo.toml b/Cargo.toml index cfe8c414..c3c1f25c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -32,6 +32,7 @@ trybuild = { version = "1.0", features = ["diff"] } macrotest = "1.0" # needed for macrotest, have to enable verbatim feature to be able to format `&raw` expressions. prettyplease = { version = "0.2", features = ["verbatim"] } +test_dummy_only = { path = "./test_dummy_only" } [lints.rust] non_ascii_idents = "deny" diff --git a/src/macros.rs b/src/macros.rs index a3eda1e4..210f6c30 100644 --- a/src/macros.rs +++ b/src/macros.rs @@ -779,8 +779,9 @@ macro_rules! __pin_data { @ty_generics($($ty_generics:tt)*), @decl_generics($($decl_generics:tt)*), @where($($whr:tt)*), - // Some other attribute, just put it into `$accum`. - @fields_munch(#[$($attr:tt)*] $($rest:tt)*), + // The #[cfg] attribute needs to be kept for our fields to make sense, + // so put it into `$accum`. + @fields_munch(#[cfg $($attr:tt)*] $($rest:tt)*), @pinned($($pinned:tt)*), @not_pinned($($not_pinned:tt)*), @fields($($fields:tt)*), @@ -800,7 +801,42 @@ macro_rules! __pin_data { @pinned($($pinned)*), @not_pinned($($not_pinned)*), @fields($($fields)*), - @accum($($accum)* #[$($attr)*]), + @accum($($accum)* #[cfg $($attr)*]), + @is_pinned($($is_pinned)?), + @pinned_drop($($pinned_drop)?), + ); + }; + (find_pinned_fields: + @struct_attrs($($struct_attrs:tt)*), + @vis($vis:vis), + @name($name:ident), + @impl_generics($($impl_generics:tt)*), + @ty_generics($($ty_generics:tt)*), + @decl_generics($($decl_generics:tt)*), + @where($($whr:tt)*), + // Some other attribute, we only need to keep it for the original + // struct, just put it into `$fields`. + @fields_munch(#[$($attr:tt)*] $($rest:tt)*), + @pinned($($pinned:tt)*), + @not_pinned($($not_pinned:tt)*), + @fields($($fields:tt)*), + @accum($($accum:tt)*), + @is_pinned($($is_pinned:ident)?), + @pinned_drop($($pinned_drop:ident)?), + ) => { + $crate::__pin_data!(find_pinned_fields: + @struct_attrs($($struct_attrs)*), + @vis($vis), + @name($name), + @impl_generics($($impl_generics)*), + @ty_generics($($ty_generics)*), + @decl_generics($($decl_generics)*), + @where($($whr)*), + @fields_munch($($rest)*), + @pinned($($pinned)*), + @not_pinned($($not_pinned)*), + @fields($($fields)* #[$($attr)*]), + @accum($($accum)*), @is_pinned($($is_pinned)?), @pinned_drop($($pinned_drop)?), ); diff --git a/test_dummy_only/Cargo.lock b/test_dummy_only/Cargo.lock new file mode 100644 index 00000000..fa62fcd5 --- /dev/null +++ b/test_dummy_only/Cargo.lock @@ -0,0 +1,7 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 4 + +[[package]] +name = "test_only" +version = "0.0.1" diff --git a/test_dummy_only/Cargo.toml b/test_dummy_only/Cargo.toml new file mode 100644 index 00000000..ada847fb --- /dev/null +++ b/test_dummy_only/Cargo.toml @@ -0,0 +1,13 @@ +[package] +name = "test_dummy_only" +version = "0.0.1" +edition = "2021" + +authors = ["y86-dev"] +license = "MIT OR Apache-2.0" +description = "Proc macro only for test reproduction." + +publish = false + +[lib] +proc-macro = true diff --git a/test_dummy_only/src/lib.rs b/test_dummy_only/src/lib.rs new file mode 100644 index 00000000..0ea09257 --- /dev/null +++ b/test_dummy_only/src/lib.rs @@ -0,0 +1,4 @@ +#[proc_macro_derive(Dummy, attributes(dummy_attr))] +pub fn derive_device(_: proc_macro::TokenStream) -> proc_macro::TokenStream { + proc_macro::TokenStream::new() +} diff --git a/tests/extra_attrs.rs b/tests/extra_attrs.rs new file mode 100644 index 00000000..46c88373 --- /dev/null +++ b/tests/extra_attrs.rs @@ -0,0 +1,23 @@ +#![cfg_attr(not(RUSTC_LINT_REASONS_IS_STABLE), feature(lint_reasons))] + +use pinned_init::*; +use test_dummy_only::Dummy; + +#[pin_data] +#[derive(Dummy)] +struct Pointless { + #[pin] + #[dummy_attr] + #[cfg(test)] + member: i8, + #[pin] + #[dummy_attr] + #[cfg(not(test))] + member: u8, +} + +#[test] +fn multiple_attributes() { + stack_pin_init!(let p = init!(Pointless { member: 0 })); + println!("{}", p.member); +}