@@ -27,6 +27,7 @@ use rustc_middle::thir;
27
27
use rustc_middle:: traits:: specialization_graph;
28
28
use rustc_middle:: ty:: codec:: TyEncoder ;
29
29
use rustc_middle:: ty:: fast_reject:: { self , SimplifyParams , StripReferences } ;
30
+ use rustc_middle:: ty:: query:: Providers ;
30
31
use rustc_middle:: ty:: { self , SymbolName , Ty , TyCtxt } ;
31
32
use rustc_serialize:: { opaque, Encodable , Encoder } ;
32
33
use rustc_session:: config:: CrateType ;
@@ -612,10 +613,15 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
612
613
self . encode_def_path_table ( ) ;
613
614
let def_path_table_bytes = self . position ( ) - i;
614
615
616
+ // Encode the def IDs of traits, for rustdoc and diagnostics.
617
+ i = self . position ( ) ;
618
+ let traits = self . encode_traits ( ) ;
619
+ let traits_bytes = self . position ( ) - i;
620
+
615
621
// Encode the def IDs of impls, for coherence checking.
616
622
i = self . position ( ) ;
617
- let ( traits , impls) = self . encode_traits_and_impls ( ) ;
618
- let traits_and_impls_bytes = self . position ( ) - i;
623
+ let impls = self . encode_impls ( ) ;
624
+ let impls_bytes = self . position ( ) - i;
619
625
620
626
let tcx = self . tcx ;
621
627
@@ -726,8 +732,8 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
726
732
native_libraries,
727
733
foreign_modules,
728
734
source_map,
729
- impls,
730
735
traits,
736
+ impls,
731
737
exported_symbols,
732
738
interpret_alloc_index,
733
739
tables,
@@ -754,7 +760,8 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
754
760
eprintln ! ( " diagnostic item bytes: {}" , diagnostic_item_bytes) ;
755
761
eprintln ! ( " native bytes: {}" , native_lib_bytes) ;
756
762
eprintln ! ( " source_map bytes: {}" , source_map_bytes) ;
757
- eprintln ! ( "traits and impls bytes: {}" , traits_and_impls_bytes) ;
763
+ eprintln ! ( " traits bytes: {}" , traits_bytes) ;
764
+ eprintln ! ( " impls bytes: {}" , impls_bytes) ;
758
765
eprintln ! ( " exp. symbols bytes: {}" , exported_symbols_bytes) ;
759
766
eprintln ! ( " def-path table bytes: {}" , def_path_table_bytes) ;
760
767
eprintln ! ( " def-path hashes bytes: {}" , def_path_hash_map_bytes) ;
@@ -1791,24 +1798,22 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
1791
1798
self . lazy ( & tcx. lang_items ( ) . missing )
1792
1799
}
1793
1800
1801
+ fn encode_traits ( & mut self ) -> Lazy < [ DefIndex ] > {
1802
+ empty_proc_macro ! ( self ) ;
1803
+ self . lazy ( self . tcx . traits_in_crate ( LOCAL_CRATE ) . iter ( ) . map ( |def_id| def_id. index ) )
1804
+ }
1805
+
1794
1806
/// Encodes an index, mapping each trait to its (local) implementations.
1795
- fn encode_traits_and_impls ( & mut self ) -> ( Lazy < [ DefIndex ] > , Lazy < [ TraitImpls ] > ) {
1796
- if self . is_proc_macro {
1797
- return ( Lazy :: empty ( ) , Lazy :: empty ( ) ) ;
1798
- }
1807
+ fn encode_impls ( & mut self ) -> Lazy < [ TraitImpls ] > {
1799
1808
debug ! ( "EncodeContext::encode_traits_and_impls()" ) ;
1809
+ empty_proc_macro ! ( self ) ;
1800
1810
let tcx = self . tcx ;
1801
- let mut visitor =
1802
- TraitsAndImplsVisitor { tcx, impls : FxHashMap :: default ( ) , traits : Default :: default ( ) } ;
1811
+ let mut visitor = ImplsVisitor { tcx, impls : FxHashMap :: default ( ) } ;
1803
1812
tcx. hir ( ) . visit_all_item_likes ( & mut visitor) ;
1804
1813
1805
- let mut all_traits = visitor. traits ;
1806
1814
let mut all_impls: Vec < _ > = visitor. impls . into_iter ( ) . collect ( ) ;
1807
1815
1808
1816
// Bring everything into deterministic order for hashing
1809
- all_traits. sort_by_cached_key ( |& local_def_index| {
1810
- tcx. hir ( ) . def_path_hash ( LocalDefId { local_def_index } )
1811
- } ) ;
1812
1817
all_impls. sort_by_cached_key ( |& ( trait_def_id, _) | tcx. def_path_hash ( trait_def_id) ) ;
1813
1818
1814
1819
let all_impls: Vec < _ > = all_impls
@@ -1826,7 +1831,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
1826
1831
} )
1827
1832
. collect ( ) ;
1828
1833
1829
- ( self . lazy ( & all_traits ) , self . lazy ( & all_impls) )
1834
+ self . lazy ( & all_impls)
1830
1835
}
1831
1836
1832
1837
// Encodes all symbols exported from this crate into the metadata.
@@ -2048,18 +2053,14 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
2048
2053
}
2049
2054
}
2050
2055
2051
- struct TraitsAndImplsVisitor < ' tcx > {
2056
+ struct ImplsVisitor < ' tcx > {
2052
2057
tcx : TyCtxt < ' tcx > ,
2053
- traits : Vec < DefIndex > ,
2054
2058
impls : FxHashMap < DefId , Vec < ( DefIndex , Option < fast_reject:: SimplifiedType > ) > > ,
2055
2059
}
2056
2060
2057
- impl < ' tcx , ' v > ItemLikeVisitor < ' v > for TraitsAndImplsVisitor < ' tcx > {
2061
+ impl < ' tcx , ' v > ItemLikeVisitor < ' v > for ImplsVisitor < ' tcx > {
2058
2062
fn visit_item ( & mut self , item : & hir:: Item < ' _ > ) {
2059
2063
match item. kind {
2060
- hir:: ItemKind :: Trait ( ..) | hir:: ItemKind :: TraitAlias ( ..) => {
2061
- self . traits . push ( item. def_id . local_def_index ) ;
2062
- }
2063
2064
hir:: ItemKind :: Impl ( ..) => {
2064
2065
if let Some ( trait_ref) = self . tcx . impl_trait_ref ( item. def_id . to_def_id ( ) ) {
2065
2066
let simplified_self_ty = fast_reject:: simplify_type (
@@ -2224,3 +2225,34 @@ fn encode_metadata_impl(tcx: TyCtxt<'_>) -> EncodedMetadata {
2224
2225
2225
2226
EncodedMetadata { raw_data : result }
2226
2227
}
2228
+
2229
+ pub fn provide ( providers : & mut Providers ) {
2230
+ * providers = Providers {
2231
+ traits_in_crate : |tcx, cnum| {
2232
+ assert_eq ! ( cnum, LOCAL_CRATE ) ;
2233
+
2234
+ #[ derive( Default ) ]
2235
+ struct TraitsVisitor {
2236
+ traits : Vec < DefId > ,
2237
+ }
2238
+ impl ItemLikeVisitor < ' _ > for TraitsVisitor {
2239
+ fn visit_item ( & mut self , item : & hir:: Item < ' _ > ) {
2240
+ if let hir:: ItemKind :: Trait ( ..) | hir:: ItemKind :: TraitAlias ( ..) = item. kind {
2241
+ self . traits . push ( item. def_id . to_def_id ( ) ) ;
2242
+ }
2243
+ }
2244
+ fn visit_trait_item ( & mut self , _trait_item : & hir:: TraitItem < ' _ > ) { }
2245
+ fn visit_impl_item ( & mut self , _impl_item : & hir:: ImplItem < ' _ > ) { }
2246
+ fn visit_foreign_item ( & mut self , _foreign_item : & hir:: ForeignItem < ' _ > ) { }
2247
+ }
2248
+
2249
+ let mut visitor = TraitsVisitor :: default ( ) ;
2250
+ tcx. hir ( ) . visit_all_item_likes ( & mut visitor) ;
2251
+ // Bring everything into deterministic order.
2252
+ visitor. traits . sort_by_cached_key ( |& def_id| tcx. def_path_hash ( def_id) ) ;
2253
+ tcx. arena . alloc_slice ( & visitor. traits )
2254
+ } ,
2255
+
2256
+ ..* providers
2257
+ } ;
2258
+ }
0 commit comments