@@ -3,8 +3,8 @@ use std::{any::TypeId, mem, str::FromStr, sync};
3
3
4
4
use base_db:: {
5
5
Crate , CrateDisplayName , CrateGraphBuilder , CrateName , CrateOrigin , CrateWorkspaceData ,
6
- DependencyBuilder , Env , FileChange , FileSet , LangCrateOrigin , SourceDatabase , SourceRoot ,
7
- Version , VfsPath , salsa,
6
+ DependencyBuilder , Env , FileChange , FileSet , FxIndexMap , LangCrateOrigin , SourceDatabase ,
7
+ SourceRoot , Version , VfsPath , salsa,
8
8
} ;
9
9
use cfg:: CfgOptions ;
10
10
use hir_expand:: {
@@ -20,7 +20,6 @@ use hir_expand::{
20
20
} ;
21
21
use intern:: { Symbol , sym} ;
22
22
use paths:: AbsPathBuf ;
23
- use rustc_hash:: FxHashMap ;
24
23
use span:: { Edition , FileId , Span } ;
25
24
use stdx:: itertools:: Itertools ;
26
25
use test_utils:: {
@@ -147,7 +146,7 @@ impl ChangeFixture {
147
146
148
147
let mut files = Vec :: new ( ) ;
149
148
let mut crate_graph = CrateGraphBuilder :: default ( ) ;
150
- let mut crates = FxHashMap :: default ( ) ;
149
+ let mut crates = FxIndexMap :: default ( ) ;
151
150
let mut crate_deps = Vec :: new ( ) ;
152
151
let mut default_crate_root: Option < FileId > = None ;
153
152
let mut default_edition = Edition :: CURRENT ;
@@ -249,37 +248,7 @@ impl ChangeFixture {
249
248
file_id = FileId :: from_raw ( file_id. index ( ) + 1 ) ;
250
249
}
251
250
252
- if crates. is_empty ( ) {
253
- let crate_root = default_crate_root
254
- . expect ( "missing default crate root, specify a main.rs or lib.rs" ) ;
255
- crate_graph. add_crate_root (
256
- crate_root,
257
- default_edition,
258
- Some ( CrateName :: new ( "ra_test_fixture" ) . unwrap ( ) . into ( ) ) ,
259
- None ,
260
- default_cfg. clone ( ) ,
261
- Some ( default_cfg) ,
262
- default_env,
263
- CrateOrigin :: Local { repo : None , name : None } ,
264
- false ,
265
- proc_macro_cwd. clone ( ) ,
266
- crate_ws_data. clone ( ) ,
267
- ) ;
268
- } else {
269
- for ( from, to, prelude) in crate_deps {
270
- let from_id = crates[ & from] ;
271
- let to_id = crates[ & to] ;
272
- let sysroot = crate_graph[ to_id] . basic . origin . is_lang ( ) ;
273
- crate_graph
274
- . add_dep (
275
- from_id,
276
- DependencyBuilder :: with_prelude ( to. clone ( ) , to_id, prelude, sysroot) ,
277
- )
278
- . unwrap ( ) ;
279
- }
280
- }
281
-
282
- if let Some ( mini_core) = mini_core {
251
+ let mini_core = mini_core. map ( |mini_core| {
283
252
let core_file = file_id;
284
253
file_id = FileId :: from_raw ( file_id. index ( ) + 1 ) ;
285
254
@@ -289,8 +258,6 @@ impl ChangeFixture {
289
258
290
259
source_change. change_file ( core_file, Some ( mini_core. source_code ( ) ) ) ;
291
260
292
- let all_crates = crate_graph. iter ( ) . collect :: < Vec < _ > > ( ) ;
293
-
294
261
let core_crate = crate_graph. add_crate_root (
295
262
core_file,
296
263
Edition :: CURRENT ,
@@ -308,16 +275,58 @@ impl ChangeFixture {
308
275
crate_ws_data. clone ( ) ,
309
276
) ;
310
277
311
- for krate in all_crates {
278
+ (
279
+ move || {
280
+ DependencyBuilder :: with_prelude (
281
+ CrateName :: new ( "core" ) . unwrap ( ) ,
282
+ core_crate,
283
+ true ,
284
+ true ,
285
+ )
286
+ } ,
287
+ core_crate,
288
+ )
289
+ } ) ;
290
+
291
+ if crates. is_empty ( ) {
292
+ let crate_root = default_crate_root
293
+ . expect ( "missing default crate root, specify a main.rs or lib.rs" ) ;
294
+ let root = crate_graph. add_crate_root (
295
+ crate_root,
296
+ default_edition,
297
+ Some ( CrateName :: new ( "ra_test_fixture" ) . unwrap ( ) . into ( ) ) ,
298
+ None ,
299
+ default_cfg. clone ( ) ,
300
+ Some ( default_cfg) ,
301
+ default_env,
302
+ CrateOrigin :: Local { repo : None , name : None } ,
303
+ false ,
304
+ proc_macro_cwd. clone ( ) ,
305
+ crate_ws_data. clone ( ) ,
306
+ ) ;
307
+ if let Some ( ( mini_core, _) ) = mini_core {
308
+ crate_graph. add_dep ( root, mini_core ( ) ) . unwrap ( ) ;
309
+ }
310
+ } else {
311
+ // Insert minicore first to match with `project-model::workspace`
312
+ if let Some ( ( mini_core, core_crate) ) = mini_core {
313
+ let all_crates = crate_graph. iter ( ) . collect :: < Vec < _ > > ( ) ;
314
+ for krate in all_crates {
315
+ if krate == core_crate {
316
+ continue ;
317
+ }
318
+ crate_graph. add_dep ( krate, mini_core ( ) ) . unwrap ( ) ;
319
+ }
320
+ }
321
+
322
+ for ( from, to, prelude) in crate_deps {
323
+ let from_id = crates[ & from] ;
324
+ let to_id = crates[ & to] ;
325
+ let sysroot = crate_graph[ to_id] . basic . origin . is_lang ( ) ;
312
326
crate_graph
313
327
. add_dep (
314
- krate,
315
- DependencyBuilder :: with_prelude (
316
- CrateName :: new ( "core" ) . unwrap ( ) ,
317
- core_crate,
318
- true ,
319
- true ,
320
- ) ,
328
+ from_id,
329
+ DependencyBuilder :: with_prelude ( to. clone ( ) , to_id, prelude, sysroot) ,
321
330
)
322
331
. unwrap ( ) ;
323
332
}
@@ -627,11 +636,23 @@ impl FileMeta {
627
636
}
628
637
}
629
638
639
+ #[ derive( Debug , Clone , Copy , PartialEq , Eq ) ]
640
+ enum ForceNoneLangOrigin {
641
+ Yes ,
642
+ No ,
643
+ }
644
+
630
645
fn parse_crate (
631
646
crate_str : String ,
632
647
current_source_root_kind : SourceRootKind ,
633
648
explicit_non_workspace_member : bool ,
634
649
) -> ( String , CrateOrigin , Option < String > ) {
650
+ let ( crate_str, force_non_lang_origin) = if let Some ( s) = crate_str. strip_prefix ( "r#" ) {
651
+ ( s. to_owned ( ) , ForceNoneLangOrigin :: Yes )
652
+ } else {
653
+ ( crate_str, ForceNoneLangOrigin :: No )
654
+ } ;
655
+
635
656
// syntax:
636
657
// "my_awesome_crate"
637
658
// "[email protected] ,http://example.com"
@@ -646,16 +667,25 @@ fn parse_crate(
646
667
let non_workspace_member = explicit_non_workspace_member
647
668
|| matches ! ( current_source_root_kind, SourceRootKind :: Library ) ;
648
669
649
- let origin = match LangCrateOrigin :: from ( & * name) {
650
- LangCrateOrigin :: Other => {
651
- let name = Symbol :: intern ( & name) ;
652
- if non_workspace_member {
653
- CrateOrigin :: Library { repo, name }
654
- } else {
655
- CrateOrigin :: Local { repo, name : Some ( name) }
670
+ let origin = if force_non_lang_origin == ForceNoneLangOrigin :: Yes {
671
+ let name = Symbol :: intern ( & name) ;
672
+ if non_workspace_member {
673
+ CrateOrigin :: Library { repo, name }
674
+ } else {
675
+ CrateOrigin :: Local { repo, name : Some ( name) }
676
+ }
677
+ } else {
678
+ match LangCrateOrigin :: from ( & * name) {
679
+ LangCrateOrigin :: Other => {
680
+ let name = Symbol :: intern ( & name) ;
681
+ if non_workspace_member {
682
+ CrateOrigin :: Library { repo, name }
683
+ } else {
684
+ CrateOrigin :: Local { repo, name : Some ( name) }
685
+ }
656
686
}
687
+ origin => CrateOrigin :: Lang ( origin) ,
657
688
}
658
- origin => CrateOrigin :: Lang ( origin) ,
659
689
} ;
660
690
661
691
( name, origin, version)
0 commit comments