@@ -33,7 +33,7 @@ use rustc_span::def_id::LOCAL_CRATE;
3333use crate :: error:: { QueryOverflow , QueryOverflowNote } ;
3434use crate :: execution:: { all_inactive, force_query} ;
3535use crate :: job:: find_dep_kind_root;
36- use crate :: { GetQueryVTable , collect_active_jobs_from_all_queries} ;
36+ use crate :: { GetQueryVTable , collect_active_jobs_from_all_queries, for_each_query_vtable } ;
3737
3838fn depth_limit_error < ' tcx > ( tcx : TyCtxt < ' tcx > , job : QueryJobId ) {
3939 let job_map =
@@ -146,7 +146,21 @@ where
146146 QueryStackFrame :: new ( info, kind, def_id, def_id_for_ty_in_cycle)
147147}
148148
149- pub ( crate ) fn encode_query_results < ' a , ' tcx , C , V > (
149+ pub ( crate ) fn encode_all_query_results < ' tcx > (
150+ tcx : TyCtxt < ' tcx > ,
151+ encoder : & mut CacheEncoder < ' _ , ' tcx > ,
152+ query_result_index : & mut EncodedDepNodeIndex ,
153+ ) {
154+ for_each_query_vtable ! (
155+ encode_query_results,
156+ tcx,
157+ CACHE_ON_DISK_QUERIES ,
158+ encoder,
159+ query_result_index,
160+ ) ;
161+ }
162+
163+ fn encode_query_results < ' a , ' tcx , C , V > (
150164 tcx : TyCtxt < ' tcx > ,
151165 query : & ' tcx QueryVTable < ' tcx , C > ,
152166 encoder : & mut CacheEncoder < ' a , ' tcx > ,
@@ -172,9 +186,17 @@ pub(crate) fn encode_query_results<'a, 'tcx, C, V>(
172186 } ) ;
173187}
174188
175- pub ( crate ) fn query_key_hash_verify < ' tcx , C : QueryCache > (
176- query : & ' tcx QueryVTable < ' tcx , C > ,
189+ pub ( crate ) fn query_key_hash_verify_all < ' tcx > ( tcx : TyCtxt < ' tcx > ) {
190+ if tcx. sess . opts . unstable_opts . incremental_verify_ich || cfg ! ( debug_assertions) {
191+ tcx. sess . time ( "query_key_hash_verify_all" , || {
192+ for_each_query_vtable ! ( query_key_hash_verify, tcx, ALL_QUERIES )
193+ } ) ;
194+ }
195+ }
196+
197+ fn query_key_hash_verify < ' tcx , C : QueryCache > (
177198 tcx : TyCtxt < ' tcx > ,
199+ query : & ' tcx QueryVTable < ' tcx , C > ,
178200) {
179201 let _timer = tcx. prof . generic_activity_with_arg ( "query_key_hash_verify_for" , query. name ) ;
180202
@@ -512,95 +534,55 @@ macro_rules! define_queries {
512534 }
513535 }
514536
515- /// Returns a map of currently active query jobs, collected from all queries.
537+ /// Given a function name, a `tcx`, and a filter condition
538+ /// (e.g. `ALL_QUERIES` or `CACHE_ON_DISK_QUERIES`),
539+ /// this macro calls that function with each query vtable that satisfies
540+ /// the filter condition.
516541 ///
517- /// If `require_complete` is `true`, this function locks all shards of the
518- /// query results to produce a complete map, which always returns `Ok`.
519- /// Otherwise, it may return an incomplete map as an error if any shard
520- /// lock cannot be acquired.
542+ /// The arguments passed to each function call are:
543+ /// - `tcx`
544+ /// - A query vtable that satisfies the filter condition
545+ /// - All other arguments given after the filter condition
521546 ///
522- /// Prefer passing `false` to `require_complete` to avoid potential deadlocks,
523- /// especially when called from within a deadlock handler, unless a
524- /// complete map is needed and no deadlock is possible at this call site.
525- pub fn collect_active_jobs_from_all_queries<' tcx>(
526- tcx: TyCtxt <' tcx>,
527- require_complete: bool ,
528- ) -> Result <QueryJobMap <' tcx>, QueryJobMap <' tcx>> {
529- let mut job_map_out = QueryJobMap :: default ( ) ;
530- let mut complete = true ;
531-
532- $(
533- let res = crate :: execution:: gather_active_jobs(
534- & tcx. query_system. query_vtables. $name,
535- tcx,
536- require_complete,
537- & mut job_map_out,
538- ) ;
539- if res. is_none( ) {
540- complete = false ;
541- }
542- ) *
543-
544- if complete { Ok ( job_map_out) } else { Err ( job_map_out) }
545- }
546-
547- /// All self-profiling events generated by the query engine use
548- /// virtual `StringId`s for their `event_id`. This method makes all
549- /// those virtual `StringId`s point to actual strings.
547+ /// This needs to be a macro, because the vtables can have different
548+ /// key/value/cache types for different queries.
550549 ///
551- /// If we are recording only summary data, the ids will point to
552- /// just the query names. If we are recording query keys too, we
553- /// allocate the corresponding strings here.
554- pub fn alloc_self_profile_query_strings( tcx: TyCtxt <' _>) {
555- if !tcx. prof. enabled( ) {
556- return ;
557- }
558-
559- let _prof_timer = tcx. sess. prof. generic_activity( "self_profile_alloc_query_strings" ) ;
560-
561- let mut string_cache = QueryKeyStringCache :: new( ) ;
562-
563- $(
564- $crate:: profiling_support:: alloc_self_profile_query_strings_for_query_cache(
565- tcx,
566- stringify!( $name) ,
567- & tcx. query_system. query_vtables. $name. cache,
568- & mut string_cache,
569- ) ;
570- ) *
571-
572- tcx. sess. prof. store_query_cache_hits( ) ;
573- }
574-
575- fn encode_all_query_results<' tcx>(
576- tcx: TyCtxt <' tcx>,
577- encoder: & mut CacheEncoder <' _, ' tcx>,
578- query_result_index: & mut EncodedDepNodeIndex ,
579- ) {
580- $(
581- #[ cfg( $cache_on_disk) ]
582- {
583- $crate:: plumbing:: encode_query_results(
550+ /// This macro's argument syntax is specifically intended to look like
551+ /// plain Rust code, so that `for_each_query_vtable!(..)` calls will be
552+ /// formatted by rustfmt.
553+ ///
554+ /// To avoid too much nested-macro complication, filter conditions are
555+ /// implemented by hand as needed.
556+ macro_rules! for_each_query_vtable {
557+ // Call with all queries.
558+ ( $inner_fn: expr, $tcx: expr, ALL_QUERIES $$( , $args: expr) * $$( , ) ?) => { {
559+ let tcx: rustc_middle:: ty:: TyCtxt <' _> = $tcx;
560+ $(
561+ $inner_fn(
584562 tcx,
585563 & tcx. query_system. query_vtables. $name,
586- encoder,
587- query_result_index,
588- )
589- }
590- ) *
564+ $$( $args) ,*
565+ ) ;
566+ ) *
567+ } } ;
568+
569+ // Only call with queries that can potentially cache to disk.
570+ //
571+ // This allows the use of trait bounds that only need to be satisfied
572+ // by the subset of queries that actually cache to disk.
573+ ( $inner_fn: expr, $tcx: expr, CACHE_ON_DISK_QUERIES $$( , $args: expr) * $$( , ) ?) => { {
574+ let tcx: rustc_middle:: ty:: TyCtxt <' _> = $tcx;
575+ $(
576+ #[ cfg( $cache_on_disk) ]
577+ $inner_fn(
578+ tcx,
579+ & tcx. query_system. query_vtables. $name,
580+ $$( $args) ,*
581+ ) ;
582+ ) *
583+ } } ;
591584 }
592585
593- pub fn query_key_hash_verify_all<' tcx>( tcx: TyCtxt <' tcx>) {
594- if tcx. sess. opts. unstable_opts. incremental_verify_ich || cfg!( debug_assertions) {
595- tcx. sess. time( "query_key_hash_verify_all" , || {
596- $(
597- $crate:: plumbing:: query_key_hash_verify(
598- & tcx. query_system. query_vtables. $name,
599- tcx
600- ) ;
601- ) *
602- } )
603- }
604- }
586+ pub ( crate ) use for_each_query_vtable;
605587 }
606588}
0 commit comments