@@ -6,6 +6,7 @@ use std::collections::hash_map::Entry;
6
6
use base_db:: CrateId ;
7
7
use hir_expand:: { attrs:: AttrId , db:: ExpandDatabase , name:: Name , AstId , MacroCallId } ;
8
8
use itertools:: Itertools ;
9
+ use la_arena:: Idx ;
9
10
use once_cell:: sync:: Lazy ;
10
11
use profile:: Count ;
11
12
use rustc_hash:: { FxHashMap , FxHashSet } ;
@@ -32,15 +33,50 @@ pub struct PerNsGlobImports {
32
33
macros : FxHashSet < ( LocalModuleId , Name ) > ,
33
34
}
34
35
36
+ #[ derive( Debug , Copy , Clone , PartialEq , Eq , Hash ) ]
37
+ pub enum ImportOrExternCrate {
38
+ Import ( ImportId ) ,
39
+ Glob ( UseId ) ,
40
+ ExternCrate ( ExternCrateId ) ,
41
+ }
42
+
43
+ impl ImportOrExternCrate {
44
+ pub fn into_import ( self ) -> Option < ImportId > {
45
+ match self {
46
+ ImportOrExternCrate :: Import ( it) => Some ( it) ,
47
+ _ => None ,
48
+ }
49
+ }
50
+
51
+ pub fn into_glob ( self ) -> Option < UseId > {
52
+ match self {
53
+ ImportOrExternCrate :: Glob ( it) => Some ( it) ,
54
+ _ => None ,
55
+ }
56
+ }
57
+ }
58
+
59
+ #[ derive( Debug , Copy , Clone , PartialEq , Eq , Hash ) ]
60
+ pub enum ImportOrDef {
61
+ Import ( ImportId ) ,
62
+ ExternCrate ( ExternCrateId ) ,
63
+ Def ( ModuleDefId ) ,
64
+ }
65
+ #[ derive( Debug , Copy , Clone , PartialEq , Eq , Hash ) ]
66
+ pub struct ImportId {
67
+ pub import : UseId ,
68
+ pub idx : Idx < ast:: UseTree > ,
69
+ }
70
+
35
71
#[ derive( Debug , Default , PartialEq , Eq ) ]
36
72
pub struct ItemScope {
37
73
_c : Count < Self > ,
38
74
39
75
/// Defs visible in this scope. This includes `declarations`, but also
40
76
/// imports.
41
- types : FxHashMap < Name , ( ModuleDefId , Visibility ) > ,
42
- values : FxHashMap < Name , ( ModuleDefId , Visibility ) > ,
43
- macros : FxHashMap < Name , ( MacroId , Visibility ) > ,
77
+ types : FxHashMap < Name , ( ModuleDefId , Visibility , Option < ImportOrExternCrate > ) > ,
78
+ values : FxHashMap < Name , ( ModuleDefId , Visibility , Option < ImportId > ) > ,
79
+ macros : FxHashMap < Name , ( MacroId , Visibility , Option < ImportId > ) > ,
44
80
unresolved : FxHashSet < Name > ,
45
81
46
82
/// The defs declared in this scope. Each def has a single scope where it is
@@ -50,7 +86,14 @@ pub struct ItemScope {
50
86
impls : Vec < ImplId > ,
51
87
unnamed_consts : Vec < ConstId > ,
52
88
/// Traits imported via `use Trait as _;`.
53
- unnamed_trait_imports : FxHashMap < TraitId , Visibility > ,
89
+ unnamed_trait_imports : FxHashMap < TraitId , ( Visibility , Option < ImportId > ) > ,
90
+
91
+ // the resolutions of the imports of this scope
92
+ use_imports_types : FxHashMap < UseId , ImportOrDef > ,
93
+ use_imports_values : FxHashMap < UseId , ImportOrDef > ,
94
+ use_imports_macros : FxHashMap < UseId , ImportOrDef > ,
95
+
96
+ use_decls : Vec < UseId > ,
54
97
extern_crate_decls : Vec < ExternCrateId > ,
55
98
/// Macros visible in current module in legacy textual scope
56
99
///
@@ -121,8 +164,7 @@ impl ItemScope {
121
164
}
122
165
123
166
pub fn use_decls ( & self ) -> impl Iterator < Item = UseId > + ExactSizeIterator + ' _ {
124
- // FIXME: to be implemented
125
- std:: iter:: empty ( )
167
+ self . use_decls . iter ( ) . copied ( )
126
168
}
127
169
128
170
pub fn impls ( & self ) -> impl Iterator < Item = ImplId > + ExactSizeIterator + ' _ {
@@ -132,13 +174,13 @@ impl ItemScope {
132
174
pub fn values (
133
175
& self ,
134
176
) -> impl Iterator < Item = ( ModuleDefId , Visibility ) > + ExactSizeIterator + ' _ {
135
- self . values . values ( ) . copied ( )
177
+ self . values . values ( ) . copied ( ) . map ( | ( a , b , _ ) | ( a , b ) )
136
178
}
137
179
138
- pub fn types (
180
+ pub ( crate ) fn types (
139
181
& self ,
140
182
) -> impl Iterator < Item = ( ModuleDefId , Visibility ) > + ExactSizeIterator + ' _ {
141
- self . types . values ( ) . copied ( )
183
+ self . types . values ( ) . copied ( ) . map ( | ( def , vis , _ ) | ( def , vis ) )
142
184
}
143
185
144
186
pub fn unnamed_consts ( & self ) -> impl Iterator < Item = ConstId > + ' _ {
@@ -165,33 +207,48 @@ impl ItemScope {
165
207
}
166
208
167
209
pub ( crate ) fn type_ ( & self , name : & Name ) -> Option < ( ModuleDefId , Visibility ) > {
168
- self . types . get ( name) . copied ( )
210
+ self . types . get ( name) . copied ( ) . map ( | ( a , b , _ ) | ( a , b ) )
169
211
}
170
212
171
213
/// XXX: this is O(N) rather than O(1), try to not introduce new usages.
172
214
pub ( crate ) fn name_of ( & self , item : ItemInNs ) -> Option < ( & Name , Visibility ) > {
173
- let ( def, mut iter) = match item {
174
- ItemInNs :: Macros ( def) => {
175
- return self . macros . iter ( ) . find_map ( |( name, & ( other_def, vis) ) | {
176
- ( other_def == def) . then_some ( ( name, vis) )
177
- } ) ;
178
- }
179
- ItemInNs :: Types ( def) => ( def, self . types . iter ( ) ) ,
180
- ItemInNs :: Values ( def) => ( def, self . values . iter ( ) ) ,
181
- } ;
182
- iter. find_map ( |( name, & ( other_def, vis) ) | ( other_def == def) . then_some ( ( name, vis) ) )
215
+ match item {
216
+ ItemInNs :: Macros ( def) => self
217
+ . macros
218
+ . iter ( )
219
+ . find_map ( |( name, & ( other_def, vis, _) ) | ( other_def == def) . then_some ( ( name, vis) ) ) ,
220
+ ItemInNs :: Types ( def) => self
221
+ . types
222
+ . iter ( )
223
+ . find_map ( |( name, & ( other_def, vis, _) ) | ( other_def == def) . then_some ( ( name, vis) ) ) ,
224
+
225
+ ItemInNs :: Values ( def) => self
226
+ . values
227
+ . iter ( )
228
+ . find_map ( |( name, & ( other_def, vis, _) ) | ( other_def == def) . then_some ( ( name, vis) ) ) ,
229
+ }
183
230
}
184
231
185
232
pub ( crate ) fn traits ( & self ) -> impl Iterator < Item = TraitId > + ' _ {
186
233
self . types
187
234
. values ( )
188
- . filter_map ( |& ( def, _) | match def {
235
+ . filter_map ( |& ( def, _, _ ) | match def {
189
236
ModuleDefId :: TraitId ( t) => Some ( t) ,
190
237
_ => None ,
191
238
} )
192
239
. chain ( self . unnamed_trait_imports . keys ( ) . copied ( ) )
193
240
}
194
241
242
+ pub ( crate ) fn resolutions ( & self ) -> impl Iterator < Item = ( Option < Name > , PerNs ) > + ' _ {
243
+ self . entries ( ) . map ( |( name, res) | ( Some ( name. clone ( ) ) , res) ) . chain (
244
+ self . unnamed_trait_imports
245
+ . iter ( )
246
+ . map ( |( tr, ( vis, _) ) | ( None , PerNs :: types ( ModuleDefId :: TraitId ( * tr) , * vis) ) ) ,
247
+ )
248
+ }
249
+ }
250
+
251
+ impl ItemScope {
195
252
pub ( crate ) fn declare ( & mut self , def : ModuleDefId ) {
196
253
self . declarations . push ( def)
197
254
}
@@ -278,11 +335,11 @@ impl ItemScope {
278
335
}
279
336
280
337
pub ( crate ) fn unnamed_trait_vis ( & self , tr : TraitId ) -> Option < Visibility > {
281
- self . unnamed_trait_imports . get ( & tr) . copied ( )
338
+ self . unnamed_trait_imports . get ( & tr) . copied ( ) . map ( | ( a , _ ) | a )
282
339
}
283
340
284
341
pub ( crate ) fn push_unnamed_trait ( & mut self , tr : TraitId , vis : Visibility ) {
285
- self . unnamed_trait_imports . insert ( tr, vis) ;
342
+ self . unnamed_trait_imports . insert ( tr, ( vis, None ) ) ;
286
343
}
287
344
288
345
pub ( crate ) fn push_res_with_import (
@@ -343,27 +400,18 @@ impl ItemScope {
343
400
changed
344
401
}
345
402
346
- pub ( crate ) fn resolutions ( & self ) -> impl Iterator < Item = ( Option < Name > , PerNs ) > + ' _ {
347
- self . entries ( ) . map ( |( name, res) | ( Some ( name. clone ( ) ) , res) ) . chain (
348
- self . unnamed_trait_imports
349
- . iter ( )
350
- . map ( |( tr, vis) | ( None , PerNs :: types ( ModuleDefId :: TraitId ( * tr) , * vis) ) ) ,
351
- )
352
- }
353
-
354
403
/// Marks everything that is not a procedural macro as private to `this_module`.
355
404
pub ( crate ) fn censor_non_proc_macros ( & mut self , this_module : ModuleId ) {
356
405
self . types
357
406
. values_mut ( )
358
- . chain ( self . values . values_mut ( ) )
407
+ . map ( |( def, vis, _) | ( def, vis) )
408
+ . chain ( self . values . values_mut ( ) . map ( |( def, vis, _) | ( def, vis) ) )
359
409
. map ( |( _, v) | v)
360
- . chain ( self . unnamed_trait_imports . values_mut ( ) )
410
+ . chain ( self . unnamed_trait_imports . values_mut ( ) . map ( | ( vis , _ ) | vis ) )
361
411
. for_each ( |vis| * vis = Visibility :: Module ( this_module) ) ;
362
412
363
- for ( mac, vis) in self . macros . values_mut ( ) {
364
- if let MacroId :: ProcMacroId ( _) = mac {
365
- // FIXME: Technically this is insufficient since reexports of proc macros are also
366
- // forbidden. Practically nobody does that.
413
+ for ( mac, vis, import) in self . macros . values_mut ( ) {
414
+ if matches ! ( mac, MacroId :: ProcMacroId ( _) if import. is_none( ) ) {
367
415
continue ;
368
416
}
369
417
@@ -415,10 +463,17 @@ impl ItemScope {
415
463
attr_macros,
416
464
derive_macros,
417
465
extern_crate_decls,
466
+ use_decls,
467
+ use_imports_values,
468
+ use_imports_types,
469
+ use_imports_macros,
418
470
} = self ;
419
471
types. shrink_to_fit ( ) ;
420
472
values. shrink_to_fit ( ) ;
421
473
macros. shrink_to_fit ( ) ;
474
+ use_imports_types. shrink_to_fit ( ) ;
475
+ use_imports_values. shrink_to_fit ( ) ;
476
+ use_imports_macros. shrink_to_fit ( ) ;
422
477
unresolved. shrink_to_fit ( ) ;
423
478
declarations. shrink_to_fit ( ) ;
424
479
impls. shrink_to_fit ( ) ;
@@ -428,6 +483,7 @@ impl ItemScope {
428
483
attr_macros. shrink_to_fit ( ) ;
429
484
derive_macros. shrink_to_fit ( ) ;
430
485
extern_crate_decls. shrink_to_fit ( ) ;
486
+ use_decls. shrink_to_fit ( ) ;
431
487
}
432
488
}
433
489
0 commit comments