@@ -15,7 +15,7 @@ use crate::dep_graph::{DepKind, DepNodeIndex, SerializedDepNodeIndex};
1515use crate :: ich:: StableHashingContext ;
1616use crate :: queries:: { ExternProviders , Providers , QueryArenas , QueryVTables } ;
1717use crate :: query:: on_disk_cache:: OnDiskCache ;
18- use crate :: query:: stack:: { QueryStackDeferred , QueryStackFrame , QueryStackFrameExtra } ;
18+ use crate :: query:: stack:: QueryStackFrame ;
1919use crate :: query:: { QueryCache , QueryInfo , QueryJob } ;
2020use crate :: ty:: TyCtxt ;
2121
@@ -62,19 +62,10 @@ pub enum CycleErrorHandling {
6262}
6363
6464#[ derive( Clone , Debug ) ]
65- pub struct CycleError < I = QueryStackFrameExtra > {
65+ pub struct CycleError < ' tcx > {
6666 /// The query and related span that uses the cycle.
67- pub usage : Option < ( Span , QueryStackFrame < I > ) > ,
68- pub cycle : Vec < QueryInfo < I > > ,
69- }
70-
71- impl < ' tcx > CycleError < QueryStackDeferred < ' tcx > > {
72- pub fn lift ( & self ) -> CycleError < QueryStackFrameExtra > {
73- CycleError {
74- usage : self . usage . as_ref ( ) . map ( |( span, frame) | ( * span, frame. lift ( ) ) ) ,
75- cycle : self . cycle . iter ( ) . map ( |info| info. lift ( ) ) . collect ( ) ,
76- }
77- }
67+ pub usage : Option < ( Span , QueryStackFrame < ' tcx > ) > ,
68+ pub cycle : Vec < QueryInfo < ' tcx > > ,
7869}
7970
8071#[ derive( Debug ) ]
@@ -146,15 +137,9 @@ pub struct QueryVTable<'tcx, C: QueryCache> {
146137 pub hash_value_fn : Option < fn ( & mut StableHashingContext < ' _ > , & C :: Value ) -> Fingerprint > ,
147138
148139 pub value_from_cycle_error :
149- fn ( tcx : TyCtxt < ' tcx > , cycle_error : CycleError , guar : ErrorGuaranteed ) -> C :: Value ,
140+ fn ( tcx : TyCtxt < ' tcx > , cycle_error : CycleError < ' tcx > , guar : ErrorGuaranteed ) -> C :: Value ,
150141 pub format_value : fn ( & C :: Value ) -> String ,
151142
152- /// Formats a human-readable description of this query and its key, as
153- /// specified by the `desc` query modifier.
154- ///
155- /// Used when reporting query cycle errors and similar problems.
156- pub description_fn : fn ( TyCtxt < ' tcx > , C :: Key ) -> String ,
157-
158143 /// Function pointer that is called by the query methods on [`TyCtxt`] and
159144 /// friends[^1], after they have checked the in-memory cache and found no
160145 /// existing value for this key.
@@ -516,6 +501,67 @@ macro_rules! define_callbacks {
516501 }
517502 ) *
518503
504+ /// Identifies a query by kind and key. This is in contrast to `QueryId` which is just a number.
505+ #[ allow( non_camel_case_types) ]
506+ #[ derive( Clone , Debug ) ]
507+ pub enum QueryKeyId <' tcx> {
508+ $(
509+ $name( $name:: Key <' tcx>) ,
510+ ) *
511+ }
512+
513+ impl <' tcx> QueryKeyId <' tcx> {
514+ /// Formats a human-readable description of this query and its key, as
515+ /// specified by the `desc` query modifier.
516+ ///
517+ /// Used when reporting query cycle errors and similar problems.
518+ pub fn description( & self , tcx: TyCtxt <' tcx>) -> String {
519+ let ( name, description) = ty:: print:: with_no_queries!( match self {
520+ $(
521+ QueryKeyId :: $name( key) => ( stringify!( $name) , _description_fns:: $name( tcx, * key) ) ,
522+ ) *
523+ } ) ;
524+ if tcx. sess. verbose_internals( ) {
525+ format!( "{description} [{name:?}]" )
526+ } else {
527+ description
528+ }
529+ }
530+
531+ /// Returns the default span for this query if `span` is a dummy span.
532+ pub fn default_span( & self , tcx: TyCtxt <' tcx>, span: Span ) -> Span {
533+ if !span. is_dummy( ) {
534+ return span
535+ }
536+ if let QueryKeyId :: def_span( ..) = self {
537+ // The `def_span` query is used to calculate `default_span`,
538+ // so exit to avoid infinite recursion.
539+ return DUMMY_SP
540+ }
541+ match self {
542+ $(
543+ QueryKeyId :: $name( key) => crate :: query:: QueryKey :: default_span( key, tcx) ,
544+ ) *
545+ }
546+ }
547+
548+ pub fn def_kind( & self , tcx: TyCtxt <' tcx>) -> Option <DefKind > {
549+ fn inner<' tcx>( key: & impl crate :: query:: QueryKey , tcx: TyCtxt <' tcx>) -> Option <DefKind > {
550+ key. key_as_def_id( ) . and_then( |def_id| def_id. as_local( ) ) . map( |def_id| tcx. def_kind( def_id) )
551+ }
552+
553+ if let QueryKeyId :: def_kind( ..) = self {
554+ // Try to avoid infinite recursion.
555+ return None
556+ }
557+ match self {
558+ $(
559+ QueryKeyId :: $name( key) => inner( key, tcx) ,
560+ ) *
561+ }
562+ }
563+ }
564+
519565 /// Holds a `QueryVTable` for each query.
520566 pub struct QueryVTables <' tcx> {
521567 $(
0 commit comments