2019-03-14 08:53:40 +00:00
|
|
|
mod globs;
|
|
|
|
mod incremental;
|
2019-11-03 20:35:48 +00:00
|
|
|
mod macros;
|
2019-09-05 18:43:32 +00:00
|
|
|
mod mod_resolution;
|
2020-09-16 15:26:16 +00:00
|
|
|
mod diagnostics;
|
2019-11-03 20:35:48 +00:00
|
|
|
mod primitives;
|
2021-02-02 10:46:58 +00:00
|
|
|
mod block;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2019-03-13 13:04:28 +00:00
|
|
|
use std::sync::Arc;
|
|
|
|
|
2021-02-02 10:46:58 +00:00
|
|
|
use base_db::{fixture::WithFixture, FilePosition, SourceDatabase};
|
2020-08-21 11:19:31 +00:00
|
|
|
use expect_test::{expect, Expect};
|
2021-02-02 10:46:58 +00:00
|
|
|
use syntax::AstNode;
|
2020-05-20 10:59:20 +00:00
|
|
|
use test_utils::mark;
|
2019-03-13 13:04:28 +00:00
|
|
|
|
2021-02-02 10:46:58 +00:00
|
|
|
use crate::{db::DefDatabase, nameres::*, test_db::TestDB, Lookup};
|
2019-03-13 13:04:28 +00:00
|
|
|
|
2021-01-18 19:18:05 +00:00
|
|
|
fn compute_crate_def_map(ra_fixture: &str) -> Arc<DefMap> {
|
2020-12-19 00:12:41 +00:00
|
|
|
let db = TestDB::with_files(ra_fixture);
|
2019-10-31 15:45:10 +00:00
|
|
|
let krate = db.crate_graph().iter().next().unwrap();
|
2019-03-13 13:38:02 +00:00
|
|
|
db.crate_def_map(krate)
|
2019-03-13 13:04:28 +00:00
|
|
|
}
|
|
|
|
|
2021-02-02 10:46:58 +00:00
|
|
|
fn compute_block_def_map(ra_fixture: &str) -> Arc<DefMap> {
|
|
|
|
let (db, position) = TestDB::with_position(ra_fixture);
|
|
|
|
|
|
|
|
// FIXME: perhaps we should make this use body lowering tests instead?
|
|
|
|
|
|
|
|
let module = db.module_for_file(position.file_id);
|
|
|
|
let mut def_map = db.crate_def_map(module.krate);
|
|
|
|
while let Some(new_def_map) = descend_def_map_at_position(&db, position, def_map.clone()) {
|
|
|
|
def_map = new_def_map;
|
|
|
|
}
|
|
|
|
|
|
|
|
// FIXME: select the right module, not the root
|
|
|
|
|
|
|
|
def_map
|
|
|
|
}
|
|
|
|
|
|
|
|
fn descend_def_map_at_position(
|
|
|
|
db: &dyn DefDatabase,
|
|
|
|
position: FilePosition,
|
|
|
|
def_map: Arc<DefMap>,
|
|
|
|
) -> Option<Arc<DefMap>> {
|
|
|
|
for (local_id, module_data) in def_map.modules() {
|
|
|
|
let mod_def = module_data.origin.definition_source(db);
|
|
|
|
let ast_map = db.ast_id_map(mod_def.file_id);
|
|
|
|
let item_tree = db.item_tree(mod_def.file_id);
|
|
|
|
let root = db.parse_or_expand(mod_def.file_id).unwrap();
|
|
|
|
for item in module_data.scope.declarations() {
|
|
|
|
match item {
|
|
|
|
ModuleDefId::FunctionId(it) => {
|
|
|
|
// Technically blocks can be inside any type (due to arrays and const generics),
|
|
|
|
// and also in const/static initializers. For tests we only really care about
|
|
|
|
// functions though.
|
|
|
|
|
|
|
|
let ast = ast_map.get(item_tree[it.lookup(db).id.value].ast_id).to_node(&root);
|
|
|
|
|
|
|
|
if ast.syntax().text_range().contains(position.offset) {
|
|
|
|
// Cursor inside function, descend into its body's DefMap.
|
|
|
|
// Note that we don't handle block *expressions* inside function bodies.
|
|
|
|
let ast_map = db.ast_id_map(position.file_id.into());
|
|
|
|
let ast_id = ast_map.ast_id(&ast.body().unwrap());
|
|
|
|
let block = BlockLoc {
|
|
|
|
ast_id: InFile::new(position.file_id.into(), ast_id),
|
|
|
|
module: def_map.module_id(local_id),
|
|
|
|
};
|
|
|
|
let block_id = db.intern_block(block);
|
|
|
|
return Some(db.block_def_map(block_id));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
_ => continue,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
None
|
|
|
|
}
|
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
fn check(ra_fixture: &str, expect: Expect) {
|
2020-11-04 14:31:35 +00:00
|
|
|
let def_map = compute_crate_def_map(ra_fixture);
|
|
|
|
let actual = def_map.dump();
|
2020-07-17 12:37:51 +00:00
|
|
|
expect.assert_eq(&actual);
|
|
|
|
}
|
|
|
|
|
2021-02-02 10:46:58 +00:00
|
|
|
fn check_at(ra_fixture: &str, expect: Expect) {
|
|
|
|
let def_map = compute_block_def_map(ra_fixture);
|
|
|
|
let actual = def_map.dump();
|
|
|
|
expect.assert_eq(&actual);
|
|
|
|
}
|
|
|
|
|
2019-03-13 13:04:28 +00:00
|
|
|
#[test]
|
|
|
|
fn crate_def_map_smoke_test() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
struct S;
|
|
|
|
use crate::foo::bar::E;
|
|
|
|
use self::E::V;
|
2019-11-25 14:30:50 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/mod.rs
|
|
|
|
pub mod bar;
|
|
|
|
fn f() {}
|
2020-04-23 21:10:14 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/bar.rs
|
|
|
|
pub struct Baz;
|
|
|
|
|
|
|
|
union U { to_be: bool, not_to_be: u8 }
|
|
|
|
enum E { V }
|
|
|
|
|
|
|
|
extern {
|
2020-08-24 20:02:55 +00:00
|
|
|
type Ext;
|
2020-07-17 12:37:51 +00:00
|
|
|
static EXT: u8;
|
|
|
|
fn ext();
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
E: t
|
|
|
|
S: t v
|
|
|
|
V: t v
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
bar: t
|
|
|
|
f: v
|
|
|
|
|
|
|
|
crate::foo::bar
|
|
|
|
Baz: t v
|
|
|
|
E: t
|
|
|
|
EXT: v
|
2020-08-24 20:02:55 +00:00
|
|
|
Ext: t
|
2020-07-17 12:37:51 +00:00
|
|
|
U: t
|
|
|
|
ext: v
|
|
|
|
"#]],
|
2019-03-13 13:04:28 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2020-03-01 03:48:55 +00:00
|
|
|
#[test]
|
|
|
|
fn crate_def_map_super_super() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
mod a {
|
|
|
|
const A: usize = 0;
|
|
|
|
mod b {
|
|
|
|
const B: usize = 0;
|
|
|
|
mod c {
|
|
|
|
use super::super::*;
|
2020-03-01 03:48:55 +00:00
|
|
|
}
|
2020-07-17 12:37:51 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
a: t
|
|
|
|
|
|
|
|
crate::a
|
|
|
|
A: v
|
|
|
|
b: t
|
|
|
|
|
|
|
|
crate::a::b
|
|
|
|
B: v
|
|
|
|
c: t
|
|
|
|
|
|
|
|
crate::a::b::c
|
|
|
|
A: v
|
|
|
|
b: t
|
|
|
|
"#]],
|
2020-03-01 03:48:55 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2020-03-11 02:58:17 +00:00
|
|
|
#[test]
|
|
|
|
fn crate_def_map_fn_mod_same_name() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
mod m {
|
|
|
|
pub mod z {}
|
|
|
|
pub fn z() {}
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
m: t
|
|
|
|
|
|
|
|
crate::m
|
|
|
|
z: t v
|
|
|
|
|
|
|
|
crate::m::z
|
|
|
|
"#]],
|
2020-03-11 02:58:17 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2019-03-16 15:06:45 +00:00
|
|
|
#[test]
|
|
|
|
fn bogus_paths() {
|
2020-05-20 10:59:20 +00:00
|
|
|
mark::check!(bogus_paths);
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
struct S;
|
|
|
|
use self;
|
|
|
|
|
|
|
|
//- /foo/mod.rs
|
|
|
|
use super;
|
|
|
|
use crate;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
S: t v
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
"#]],
|
2019-03-16 15:06:45 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2019-03-13 13:04:28 +00:00
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn use_as() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
use crate::foo::Baz as Foo;
|
2019-03-13 13:04:28 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/mod.rs
|
|
|
|
pub struct Baz;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Foo: t v
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
2019-03-14 08:53:40 +00:00
|
|
|
);
|
2019-03-13 13:04:28 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn use_trees() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
use crate::foo::bar::{Baz, Quux};
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/mod.rs
|
|
|
|
pub mod bar;
|
2019-03-13 13:04:28 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/bar.rs
|
|
|
|
pub struct Baz;
|
|
|
|
pub enum Quux {};
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Baz: t v
|
|
|
|
Quux: t
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
bar: t
|
|
|
|
|
|
|
|
crate::foo::bar
|
|
|
|
Baz: t v
|
|
|
|
Quux: t
|
|
|
|
"#]],
|
2019-03-13 13:04:28 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn re_exports() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
use self::foo::Baz;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/mod.rs
|
|
|
|
pub mod bar;
|
|
|
|
pub use self::bar::Baz;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/bar.rs
|
|
|
|
pub struct Baz;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Baz: t v
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
Baz: t v
|
|
|
|
bar: t
|
|
|
|
|
|
|
|
crate::foo::bar
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
2019-03-13 13:04:28 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn std_prelude() {
|
2020-05-20 10:59:20 +00:00
|
|
|
mark::check!(std_prelude);
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:test_crate
|
|
|
|
use Foo::*;
|
|
|
|
|
|
|
|
//- /lib.rs crate:test_crate
|
|
|
|
mod prelude;
|
|
|
|
#[prelude_import]
|
|
|
|
use prelude::*;
|
|
|
|
|
|
|
|
//- /prelude.rs
|
|
|
|
pub enum Foo { Bar, Baz };
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Bar: t v
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
2019-03-13 13:04:28 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn can_import_enum_variant() {
|
2020-05-20 10:59:20 +00:00
|
|
|
mark::check!(can_import_enum_variant);
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
enum E { V }
|
|
|
|
use self::E::V;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
E: t
|
|
|
|
V: t v
|
|
|
|
"#]],
|
2019-03-14 08:53:40 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn edition_2015_imports() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:other_crate edition:2015
|
|
|
|
mod foo;
|
|
|
|
mod bar;
|
|
|
|
|
|
|
|
//- /bar.rs
|
|
|
|
struct Bar;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo.rs
|
|
|
|
use bar::Bar;
|
|
|
|
use other_crate::FromLib;
|
|
|
|
|
|
|
|
//- /lib.rs crate:other_crate edition:2018
|
|
|
|
struct FromLib;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
bar: t
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::bar
|
|
|
|
Bar: t v
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
Bar: t v
|
|
|
|
FromLib: t v
|
|
|
|
"#]],
|
|
|
|
);
|
2019-03-14 08:53:40 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn item_map_using_self() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /lib.rs
|
|
|
|
mod foo;
|
|
|
|
use crate::foo::bar::Baz::{self};
|
|
|
|
|
|
|
|
//- /foo/mod.rs
|
|
|
|
pub mod bar;
|
|
|
|
|
|
|
|
//- /foo/bar.rs
|
|
|
|
pub struct Baz;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Baz: t v
|
|
|
|
foo: t
|
|
|
|
|
|
|
|
crate::foo
|
|
|
|
bar: t
|
|
|
|
|
|
|
|
crate::foo::bar
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
2019-03-14 08:53:40 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn item_map_across_crates() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:test_crate
|
|
|
|
use test_crate::Baz;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /lib.rs crate:test_crate
|
|
|
|
pub struct Baz;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
|
|
|
);
|
2019-03-13 13:04:28 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn extern_crate_rename() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:alloc
|
|
|
|
extern crate alloc as alloc_crate;
|
|
|
|
mod alloc;
|
|
|
|
mod sync;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /sync.rs
|
|
|
|
use alloc_crate::Arc;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /lib.rs crate:alloc
|
|
|
|
struct Arc;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
alloc_crate: t
|
|
|
|
sync: t
|
|
|
|
|
|
|
|
crate::sync
|
|
|
|
Arc: t v
|
|
|
|
"#]],
|
2019-03-13 13:04:28 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
2019-03-14 08:53:40 +00:00
|
|
|
fn extern_crate_rename_2015_edition() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:alloc edition:2015
|
|
|
|
extern crate alloc as alloc_crate;
|
|
|
|
mod alloc;
|
|
|
|
mod sync;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /sync.rs
|
|
|
|
use alloc_crate::Arc;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /lib.rs crate:alloc
|
|
|
|
struct Arc;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
alloc_crate: t
|
|
|
|
sync: t
|
|
|
|
|
|
|
|
crate::sync
|
|
|
|
Arc: t v
|
|
|
|
"#]],
|
2019-03-14 08:53:40 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn reexport_across_crates() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:test_crate
|
|
|
|
use test_crate::Baz;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /lib.rs crate:test_crate
|
|
|
|
pub use foo::Baz;
|
|
|
|
mod foo;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo.rs
|
|
|
|
pub struct Baz;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Baz: t v
|
|
|
|
"#]],
|
2019-03-14 08:53:40 +00:00
|
|
|
);
|
2019-03-13 13:04:28 +00:00
|
|
|
}
|
2019-03-14 08:53:40 +00:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn values_dont_shadow_extern_crates() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:foo
|
|
|
|
fn foo() {}
|
|
|
|
use foo::Bar;
|
2019-03-14 08:53:40 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /foo/lib.rs crate:foo
|
|
|
|
pub struct Bar;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Bar: t v
|
|
|
|
foo: v
|
|
|
|
"#]],
|
|
|
|
);
|
2019-03-14 08:53:40 +00:00
|
|
|
}
|
2019-09-29 23:38:16 +00:00
|
|
|
|
2019-11-10 01:38:08 +00:00
|
|
|
#[test]
|
|
|
|
fn std_prelude_takes_precedence_above_core_prelude() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
2019-11-10 01:38:08 +00:00
|
|
|
r#"
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /main.rs crate:main deps:core,std
|
|
|
|
use {Foo, Bar};
|
|
|
|
|
|
|
|
//- /std.rs crate:std deps:core
|
|
|
|
#[prelude_import]
|
|
|
|
pub use self::prelude::*;
|
|
|
|
mod prelude {
|
|
|
|
pub struct Foo;
|
|
|
|
pub use core::prelude::Bar;
|
|
|
|
}
|
2019-11-10 01:38:08 +00:00
|
|
|
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /core.rs crate:core
|
|
|
|
#[prelude_import]
|
|
|
|
pub use self::prelude::*;
|
|
|
|
mod prelude {
|
|
|
|
pub struct Bar;
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Bar: t v
|
|
|
|
Foo: t v
|
|
|
|
"#]],
|
2019-11-10 01:38:08 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2019-09-29 23:38:16 +00:00
|
|
|
#[test]
|
|
|
|
fn cfg_not_test() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
2019-09-29 23:38:16 +00:00
|
|
|
r#"
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /main.rs crate:main deps:std
|
|
|
|
use {Foo, Bar, Baz};
|
|
|
|
|
|
|
|
//- /lib.rs crate:std
|
|
|
|
#[prelude_import]
|
|
|
|
pub use self::prelude::*;
|
|
|
|
mod prelude {
|
|
|
|
#[cfg(test)]
|
|
|
|
pub struct Foo;
|
|
|
|
#[cfg(not(test))]
|
|
|
|
pub struct Bar;
|
|
|
|
#[cfg(all(not(any()), feature = "foo", feature = "bar", opt = "42"))]
|
|
|
|
pub struct Baz;
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Bar: t v
|
|
|
|
Baz: _
|
|
|
|
Foo: _
|
|
|
|
"#]],
|
2019-09-29 23:38:16 +00:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn cfg_test() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
2019-09-29 23:38:16 +00:00
|
|
|
r#"
|
2020-07-17 12:37:51 +00:00
|
|
|
//- /main.rs crate:main deps:std
|
|
|
|
use {Foo, Bar, Baz};
|
|
|
|
|
|
|
|
//- /lib.rs crate:std cfg:test,feature=foo,feature=bar,opt=42
|
|
|
|
#[prelude_import]
|
|
|
|
pub use self::prelude::*;
|
|
|
|
mod prelude {
|
|
|
|
#[cfg(test)]
|
|
|
|
pub struct Foo;
|
|
|
|
#[cfg(not(test))]
|
|
|
|
pub struct Bar;
|
|
|
|
#[cfg(all(not(any()), feature = "foo", feature = "bar", opt = "42"))]
|
|
|
|
pub struct Baz;
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
Bar: _
|
|
|
|
Baz: t v
|
|
|
|
Foo: t v
|
|
|
|
"#]],
|
2019-09-29 23:38:16 +00:00
|
|
|
);
|
|
|
|
}
|
2019-12-03 11:33:48 +00:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn infer_multiple_namespace() {
|
2020-07-17 12:37:51 +00:00
|
|
|
check(
|
2019-12-03 11:33:48 +00:00
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
mod a {
|
|
|
|
pub type T = ();
|
|
|
|
pub use crate::b::*;
|
|
|
|
}
|
|
|
|
|
|
|
|
use crate::a::T;
|
|
|
|
|
|
|
|
mod b {
|
|
|
|
pub const T: () = ();
|
|
|
|
}
|
|
|
|
"#,
|
2020-07-17 12:37:51 +00:00
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
T: t v
|
|
|
|
a: t
|
|
|
|
b: t
|
|
|
|
|
|
|
|
crate::b
|
|
|
|
T: v
|
|
|
|
|
|
|
|
crate::a
|
|
|
|
T: t v
|
|
|
|
"#]],
|
2019-12-03 11:33:48 +00:00
|
|
|
);
|
|
|
|
}
|
2020-07-21 15:52:43 +00:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn underscore_import() {
|
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
use tr::Tr as _;
|
|
|
|
use tr::Tr2 as _;
|
|
|
|
|
|
|
|
mod tr {
|
|
|
|
pub trait Tr {}
|
|
|
|
pub trait Tr2 {}
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
_: t
|
|
|
|
_: t
|
|
|
|
tr: t
|
|
|
|
|
|
|
|
crate::tr
|
|
|
|
Tr: t
|
|
|
|
Tr2: t
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn underscore_reexport() {
|
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
mod tr {
|
|
|
|
pub trait PubTr {}
|
|
|
|
pub trait PrivTr {}
|
|
|
|
}
|
|
|
|
mod reex {
|
|
|
|
use crate::tr::PrivTr as _;
|
|
|
|
pub use crate::tr::PubTr as _;
|
|
|
|
}
|
|
|
|
use crate::reex::*;
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
_: t
|
|
|
|
reex: t
|
|
|
|
tr: t
|
|
|
|
|
|
|
|
crate::tr
|
|
|
|
PrivTr: t
|
|
|
|
PubTr: t
|
|
|
|
|
|
|
|
crate::reex
|
|
|
|
_: t
|
|
|
|
_: t
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn underscore_pub_crate_reexport() {
|
2020-07-22 12:01:50 +00:00
|
|
|
mark::check!(upgrade_underscore_visibility);
|
2020-07-21 15:52:43 +00:00
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs crate:main deps:lib
|
|
|
|
use lib::*;
|
|
|
|
|
|
|
|
//- /lib.rs crate:lib
|
|
|
|
use tr::Tr as _;
|
|
|
|
pub use tr::Tr as _;
|
|
|
|
|
|
|
|
mod tr {
|
2020-07-22 12:01:50 +00:00
|
|
|
pub trait Tr {}
|
2020-07-21 15:52:43 +00:00
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
_: t
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn underscore_nontrait() {
|
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
mod m {
|
|
|
|
pub struct Struct;
|
|
|
|
pub enum Enum {}
|
|
|
|
pub const CONST: () = ();
|
|
|
|
}
|
|
|
|
use crate::m::{Struct as _, Enum as _, CONST as _};
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
m: t
|
|
|
|
|
|
|
|
crate::m
|
|
|
|
CONST: v
|
|
|
|
Enum: t
|
|
|
|
Struct: t v
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn underscore_name_conflict() {
|
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
struct Tr;
|
|
|
|
|
|
|
|
use tr::Tr as _;
|
|
|
|
|
|
|
|
mod tr {
|
|
|
|
pub trait Tr {}
|
|
|
|
}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
_: t
|
|
|
|
Tr: t v
|
|
|
|
tr: t
|
|
|
|
|
|
|
|
crate::tr
|
|
|
|
Tr: t
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|
2020-10-26 15:04:08 +00:00
|
|
|
|
|
|
|
#[test]
|
|
|
|
fn cfg_the_entire_crate() {
|
|
|
|
check(
|
|
|
|
r#"
|
|
|
|
//- /main.rs
|
|
|
|
#![cfg(never)]
|
|
|
|
|
|
|
|
pub struct S;
|
|
|
|
pub enum E {}
|
|
|
|
pub fn f() {}
|
|
|
|
"#,
|
|
|
|
expect![[r#"
|
|
|
|
crate
|
|
|
|
"#]],
|
|
|
|
);
|
|
|
|
}
|