From 6fba51c5fc05264abcbf971dcf28142746588d74 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sun, 3 Nov 2019 23:35:48 +0300 Subject: move crate_def_map tests to hir_def --- crates/ra_hir_def/src/nameres/tests/macros.rs | 602 ++++++++++++++++++++++++++ 1 file changed, 602 insertions(+) create mode 100644 crates/ra_hir_def/src/nameres/tests/macros.rs (limited to 'crates/ra_hir_def/src/nameres/tests/macros.rs') diff --git a/crates/ra_hir_def/src/nameres/tests/macros.rs b/crates/ra_hir_def/src/nameres/tests/macros.rs new file mode 100644 index 000000000..9bb3895ad --- /dev/null +++ b/crates/ra_hir_def/src/nameres/tests/macros.rs @@ -0,0 +1,602 @@ +use super::*; + +#[test] +fn macro_rules_are_globally_visible() { + let map = def_map( + " + //- /lib.rs + macro_rules! structs { + ($($i:ident),*) => { + $(struct $i { field: u32 } )* + } + } + structs!(Foo); + mod nested; + + //- /nested.rs + structs!(Bar, Baz); + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Foo: t v + ⋮nested: t + ⋮ + ⋮crate::nested + ⋮Bar: t v + ⋮Baz: t v + "###); +} + +#[test] +fn macro_rules_can_define_modules() { + let map = def_map( + " + //- /lib.rs + macro_rules! m { + ($name:ident) => { mod $name; } + } + m!(n1); + + mod m { + m!(n3) + } + + //- /n1.rs + m!(n2) + //- /n1/n2.rs + struct X; + //- /m/n3.rs + struct Y; + ", + ); + assert_snapshot!(map, @r###" + crate + m: t + n1: t + + crate::m + n3: t + + crate::m::n3 + Y: t v + + crate::n1 + n2: t + + crate::n1::n2 + X: t v + "###); +} + +#[test] +fn macro_rules_from_other_crates_are_visible() { + let map = def_map( + " + //- /main.rs crate:main deps:foo + foo::structs!(Foo, Bar) + mod bar; + + //- /bar.rs + use crate::*; + + //- /lib.rs crate:foo + #[macro_export] + macro_rules! structs { + ($($i:ident),*) => { + $(struct $i { field: u32 } )* + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Bar: t v + ⋮Foo: t v + ⋮bar: t + ⋮ + ⋮crate::bar + ⋮Bar: t v + ⋮Foo: t v + ⋮bar: t + "###); +} + +#[test] +fn macro_rules_export_with_local_inner_macros_are_visible() { + let map = def_map( + " + //- /main.rs crate:main deps:foo + foo::structs!(Foo, Bar) + mod bar; + + //- /bar.rs + use crate::*; + + //- /lib.rs crate:foo + #[macro_export(local_inner_macros)] + macro_rules! structs { + ($($i:ident),*) => { + $(struct $i { field: u32 } )* + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Bar: t v + ⋮Foo: t v + ⋮bar: t + ⋮ + ⋮crate::bar + ⋮Bar: t v + ⋮Foo: t v + ⋮bar: t + "###); +} + +#[test] +fn unexpanded_macro_should_expand_by_fixedpoint_loop() { + let map = def_map( + " + //- /main.rs crate:main deps:foo + macro_rules! baz { + () => { + use foo::bar; + } + } + + foo!(); + bar!(); + baz!(); + + //- /lib.rs crate:foo + #[macro_export] + macro_rules! foo { + () => { + struct Foo { field: u32 } + } + } + #[macro_export] + macro_rules! bar { + () => { + use foo::foo; + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Foo: t v + ⋮bar: m + ⋮foo: m + "###); +} + +#[test] +fn macro_rules_from_other_crates_are_visible_with_macro_use() { + // covers!(macro_rules_from_other_crates_are_visible_with_macro_use); + let map = def_map( + " + //- /main.rs crate:main deps:foo + structs!(Foo); + structs_priv!(Bar); + structs_not_exported!(MacroNotResolved1); + crate::structs!(MacroNotResolved2); + + mod bar; + + #[macro_use] + extern crate foo; + + //- /bar.rs + structs!(Baz); + crate::structs!(MacroNotResolved3); + + //- /lib.rs crate:foo + #[macro_export] + macro_rules! structs { + ($i:ident) => { struct $i; } + } + + macro_rules! structs_not_exported { + ($i:ident) => { struct $i; } + } + + mod priv_mod { + #[macro_export] + macro_rules! structs_priv { + ($i:ident) => { struct $i; } + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Bar: t v + ⋮Foo: t v + ⋮bar: t + ⋮foo: t + ⋮ + ⋮crate::bar + ⋮Baz: t v + "###); +} + +#[test] +fn prelude_is_macro_use() { + // covers!(prelude_is_macro_use); + let map = def_map( + " + //- /main.rs crate:main deps:foo + structs!(Foo); + structs_priv!(Bar); + structs_outside!(Out); + crate::structs!(MacroNotResolved2); + + mod bar; + + //- /bar.rs + structs!(Baz); + crate::structs!(MacroNotResolved3); + + //- /lib.rs crate:foo + #[prelude_import] + use self::prelude::*; + + mod prelude { + #[macro_export] + macro_rules! structs { + ($i:ident) => { struct $i; } + } + + mod priv_mod { + #[macro_export] + macro_rules! structs_priv { + ($i:ident) => { struct $i; } + } + } + } + + #[macro_export] + macro_rules! structs_outside { + ($i:ident) => { struct $i; } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Bar: t v + ⋮Foo: t v + ⋮Out: t v + ⋮bar: t + ⋮ + ⋮crate::bar + ⋮Baz: t v + "###); +} + +#[test] +fn prelude_cycle() { + let map = def_map( + " + //- /lib.rs + #[prelude_import] + use self::prelude::*; + + declare_mod!(); + + mod prelude { + macro_rules! declare_mod { + () => (mod foo {}) + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮prelude: t + ⋮ + ⋮crate::prelude + "###); +} + +#[test] +fn plain_macros_are_legacy_textual_scoped() { + let map = def_map( + r#" + //- /main.rs + mod m1; + bar!(NotFoundNotMacroUse); + + mod m2 { + foo!(NotFoundBeforeInside2); + } + + macro_rules! foo { + ($x:ident) => { struct $x; } + } + foo!(Ok); + + mod m3; + foo!(OkShadowStop); + bar!(NotFoundMacroUseStop); + + #[macro_use] + mod m5 { + #[macro_use] + mod m6 { + macro_rules! foo { + ($x:ident) => { fn $x() {} } + } + } + } + foo!(ok_double_macro_use_shadow); + + baz!(NotFoundBefore); + #[macro_use] + mod m7 { + macro_rules! baz { + ($x:ident) => { struct $x; } + } + } + baz!(OkAfter); + + //- /m1.rs + foo!(NotFoundBeforeInside1); + macro_rules! bar { + ($x:ident) => { struct $x; } + } + + //- /m3/mod.rs + foo!(OkAfterInside); + macro_rules! foo { + ($x:ident) => { fn $x() {} } + } + foo!(ok_shadow); + + #[macro_use] + mod m4; + bar!(OkMacroUse); + + //- /m3/m4.rs + foo!(ok_shadow_deep); + macro_rules! bar { + ($x:ident) => { struct $x; } + } + "#, + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Ok: t v + ⋮OkAfter: t v + ⋮OkShadowStop: t v + ⋮m1: t + ⋮m2: t + ⋮m3: t + ⋮m5: t + ⋮m7: t + ⋮ok_double_macro_use_shadow: v + ⋮ + ⋮crate::m7 + ⋮ + ⋮crate::m1 + ⋮ + ⋮crate::m5 + ⋮m6: t + ⋮ + ⋮crate::m5::m6 + ⋮ + ⋮crate::m2 + ⋮ + ⋮crate::m3 + ⋮OkAfterInside: t v + ⋮OkMacroUse: t v + ⋮m4: t + ⋮ok_shadow: v + ⋮ + ⋮crate::m3::m4 + ⋮ok_shadow_deep: v + "###); +} + +#[test] +fn type_value_macro_live_in_different_scopes() { + let map = def_map( + " + //- /main.rs + #[macro_export] + macro_rules! foo { + ($x:ident) => { type $x = (); } + } + + foo!(foo); + use foo as bar; + + use self::foo as baz; + fn baz() {} + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮bar: t m + ⋮baz: t v m + ⋮foo: t m + "###); +} + +#[test] +fn macro_use_can_be_aliased() { + let map = def_map( + " + //- /main.rs crate:main deps:foo + #[macro_use] + extern crate foo; + + foo!(Direct); + bar!(Alias); + + //- /lib.rs crate:foo + use crate::foo as bar; + + mod m { + #[macro_export] + macro_rules! foo { + ($x:ident) => { struct $x; } + } + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Alias: t v + ⋮Direct: t v + ⋮foo: t + "###); +} + +#[test] +fn path_qualified_macros() { + let map = def_map( + " + //- /main.rs + macro_rules! foo { + ($x:ident) => { struct $x; } + } + + crate::foo!(NotResolved); + + crate::bar!(OkCrate); + bar!(OkPlain); + alias1!(NotHere); + m::alias1!(OkAliasPlain); + m::alias2!(OkAliasSuper); + m::alias3!(OkAliasCrate); + not_found!(NotFound); + + mod m { + #[macro_export] + macro_rules! bar { + ($x:ident) => { struct $x; } + } + + pub use bar as alias1; + pub use super::bar as alias2; + pub use crate::bar as alias3; + pub use self::bar as not_found; + } + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮OkAliasCrate: t v + ⋮OkAliasPlain: t v + ⋮OkAliasSuper: t v + ⋮OkCrate: t v + ⋮OkPlain: t v + ⋮bar: m + ⋮m: t + ⋮ + ⋮crate::m + ⋮alias1: m + ⋮alias2: m + ⋮alias3: m + ⋮not_found: _ + "###); +} + +#[test] +fn macro_dollar_crate_is_correct_in_item() { + // covers!(macro_dollar_crate_self); + // covers!(macro_dollar_crate_other); + let map = def_map( + " + //- /main.rs crate:main deps:foo + #[macro_use] + extern crate foo; + + #[macro_use] + mod m { + macro_rules! current { + () => { + use $crate::Foo as FooSelf; + } + } + } + + struct Foo; + + current!(); + not_current1!(); + foo::not_current2!(); + + //- /lib.rs crate:foo + mod m { + #[macro_export] + macro_rules! not_current1 { + () => { + use $crate::Bar; + } + } + } + + #[macro_export] + macro_rules! not_current2 { + () => { + use $crate::Baz; + } + } + + struct Bar; + struct Baz; + ", + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮Bar: t v + ⋮Baz: t v + ⋮Foo: t v + ⋮FooSelf: t v + ⋮foo: t + ⋮m: t + ⋮ + ⋮crate::m + "###); +} + +#[test] +fn macro_dollar_crate_is_correct_in_indirect_deps() { + // covers!(macro_dollar_crate_other); + // From std + let map = def_map( + r#" + //- /main.rs crate:main deps:std + foo!(); + + //- /std.rs crate:std deps:core + #[prelude_import] + use self::prelude::*; + + pub use core::foo; + + mod prelude {} + + #[macro_use] + mod std_macros; + + //- /core.rs crate:core + #[macro_export] + macro_rules! foo { + () => { + use $crate::bar; + } + } + + pub struct bar; + "#, + ); + assert_snapshot!(map, @r###" + ⋮crate + ⋮bar: t v + "###); +} -- cgit v1.2.3 From 73fcf9a2d6ae14afa4e822370c0a46bf1d336081 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sun, 3 Nov 2019 23:44:23 +0300 Subject: Restore crate_def_map marks --- crates/ra_hir_def/src/nameres/tests/macros.rs | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'crates/ra_hir_def/src/nameres/tests/macros.rs') diff --git a/crates/ra_hir_def/src/nameres/tests/macros.rs b/crates/ra_hir_def/src/nameres/tests/macros.rs index 9bb3895ad..704065633 100644 --- a/crates/ra_hir_def/src/nameres/tests/macros.rs +++ b/crates/ra_hir_def/src/nameres/tests/macros.rs @@ -175,7 +175,7 @@ fn unexpanded_macro_should_expand_by_fixedpoint_loop() { #[test] fn macro_rules_from_other_crates_are_visible_with_macro_use() { - // covers!(macro_rules_from_other_crates_are_visible_with_macro_use); + covers!(macro_rules_from_other_crates_are_visible_with_macro_use); let map = def_map( " //- /main.rs crate:main deps:foo @@ -225,7 +225,7 @@ fn macro_rules_from_other_crates_are_visible_with_macro_use() { #[test] fn prelude_is_macro_use() { - // covers!(prelude_is_macro_use); + covers!(prelude_is_macro_use); let map = def_map( " //- /main.rs crate:main deps:foo @@ -507,8 +507,8 @@ fn path_qualified_macros() { #[test] fn macro_dollar_crate_is_correct_in_item() { - // covers!(macro_dollar_crate_self); - // covers!(macro_dollar_crate_other); + covers!(macro_dollar_crate_self); + covers!(macro_dollar_crate_other); let map = def_map( " //- /main.rs crate:main deps:foo @@ -566,7 +566,7 @@ fn macro_dollar_crate_is_correct_in_item() { #[test] fn macro_dollar_crate_is_correct_in_indirect_deps() { - // covers!(macro_dollar_crate_other); + covers!(macro_dollar_crate_other); // From std let map = def_map( r#" -- cgit v1.2.3