Skip to content

Commit 8f29406

Browse files
committed
Optimize incremental_verify_ich
1 parent 8be3c2b commit 8f29406

File tree

5 files changed

+74
-49
lines changed

5 files changed

+74
-49
lines changed

compiler/rustc_middle/src/dep_graph/mod.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,13 +71,19 @@ impl rustc_query_system::dep_graph::DepKind for DepKind {
7171
}
7272

7373
impl<'tcx> DepContext for TyCtxt<'tcx> {
74+
type Implicit<'a> = TyCtxt<'a>;
7475
type DepKind = DepKind;
7576

7677
#[inline]
7778
fn with_stable_hashing_context<R>(self, f: impl FnOnce(StableHashingContext<'_>) -> R) -> R {
7879
TyCtxt::with_stable_hashing_context(self, f)
7980
}
8081

82+
#[inline]
83+
fn with_context<R>(f: impl FnOnce(TyCtxt<'_>) -> R) -> R {
84+
ty::tls::with(|tcx| f(tcx))
85+
}
86+
8187
#[inline]
8288
fn dep_graph(&self) -> &DepGraph {
8389
&self.dep_graph

compiler/rustc_query_system/src/dep_graph/graph.rs

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -535,13 +535,14 @@ impl<K: DepKind> DepGraph<K> {
535535
// value to an existing node.
536536
//
537537
// For sanity, we still check that the loaded stable hash and the new one match.
538-
if let Some(dep_node_index) = data.dep_node_index_of_opt(&node) {
539-
let _current_fingerprint =
540-
crate::query::incremental_verify_ich(cx, data, result, &node, hash_result);
538+
if let Some(prev_index) = data.previous.node_to_index_opt(&node)
539+
&& let Some(dep_node_index) = { data.current.prev_index_to_index.lock()[prev_index] }
540+
{
541+
crate::query::incremental_verify_ich(cx, data, result, prev_index, hash_result);
541542

542543
#[cfg(debug_assertions)]
543544
if hash_result.is_some() {
544-
data.current.record_edge(dep_node_index, node, _current_fingerprint);
545+
data.current.record_edge(dep_node_index, node, data.prev_fingerprint_of(prev_index));
545546
}
546547

547548
return dep_node_index;
@@ -626,13 +627,19 @@ impl<K: DepKind> DepGraphData<K> {
626627

627628
/// Returns true if the given node has been marked as green during the
628629
/// current compilation session. Used in various assertions
629-
pub fn is_green(&self, dep_node: &DepNode<K>) -> bool {
630-
self.node_color(dep_node).map_or(false, |c| c.is_green())
630+
#[inline]
631+
pub fn is_index_green(&self, prev_index: SerializedDepNodeIndex) -> bool {
632+
self.colors.get(prev_index).map_or(false, |c| c.is_green())
633+
}
634+
635+
#[inline]
636+
pub fn prev_fingerprint_of(&self, prev_index: SerializedDepNodeIndex) -> Fingerprint {
637+
self.previous.fingerprint_by_index(prev_index)
631638
}
632639

633640
#[inline]
634-
pub fn prev_fingerprint_of(&self, dep_node: &DepNode<K>) -> Option<Fingerprint> {
635-
self.previous.fingerprint_of(dep_node)
641+
pub fn prev_node_of(&self, prev_index: SerializedDepNodeIndex) -> DepNode<K> {
642+
self.previous.index_to_node(prev_index)
636643
}
637644

638645
pub fn mark_debug_loaded_from_disk(&self, dep_node: DepNode<K>) {
@@ -643,7 +650,7 @@ impl<K: DepKind> DepGraphData<K> {
643650
impl<K: DepKind> DepGraph<K> {
644651
#[inline]
645652
pub fn dep_node_exists(&self, dep_node: &DepNode<K>) -> bool {
646-
self.data.as_ref().and_then(|data| data.dep_node_index_of_opt(dep_node)).is_some()
653+
self.data.as_ref().map_or(false, |data| data.dep_node_exists(dep_node))
647654
}
648655

649656
/// Checks whether a previous work product exists for `v` and, if

compiler/rustc_query_system/src/dep_graph/mod.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,11 +23,15 @@ use std::{fmt, panic};
2323
use self::graph::{print_markframe_trace, MarkFrame};
2424

2525
pub trait DepContext: Copy {
26+
type Implicit<'a>: DepContext;
2627
type DepKind: self::DepKind;
2728

2829
/// Create a hashing context for hashing new results.
2930
fn with_stable_hashing_context<R>(self, f: impl FnOnce(StableHashingContext<'_>) -> R) -> R;
3031

32+
/// Access the implicit context.
33+
fn with_context<R>(f: impl FnOnce(Self::Implicit<'_>) -> R) -> R;
34+
3135
/// Access the DepGraph.
3236
fn dep_graph(&self) -> &DepGraph<Self::DepKind>;
3337

compiler/rustc_query_system/src/dep_graph/serialized.rs

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -79,11 +79,6 @@ impl<K: DepKind> SerializedDepGraph<K> {
7979
self.index.get(dep_node).cloned()
8080
}
8181

82-
#[inline]
83-
pub fn fingerprint_of(&self, dep_node: &DepNode<K>) -> Option<Fingerprint> {
84-
self.index.get(dep_node).map(|&node_index| self.fingerprints[node_index])
85-
}
86-
8782
#[inline]
8883
pub fn fingerprint_by_index(&self, dep_node_index: SerializedDepNodeIndex) -> Fingerprint {
8984
self.fingerprints[dep_node_index]

compiler/rustc_query_system/src/query/plumbing.rs

Lines changed: 48 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ use crate::dep_graph::{DepGraphData, HasDepContext};
77
use crate::ich::StableHashingContext;
88
use crate::query::caches::QueryCache;
99
use crate::query::job::{report_cycle, QueryInfo, QueryJob, QueryJobId, QueryJobInfo};
10+
use crate::query::SerializedDepNodeIndex;
1011
use crate::query::{QueryContext, QueryMap, QuerySideEffects, QueryStackFrame};
1112
use crate::values::Value;
1213
use crate::HandleCycleError;
@@ -19,7 +20,6 @@ use rustc_data_structures::sharded::Sharded;
1920
use rustc_data_structures::stack::ensure_sufficient_stack;
2021
use rustc_data_structures::sync::{Lock, LockGuard};
2122
use rustc_errors::{DiagnosticBuilder, ErrorGuaranteed, FatalError};
22-
use rustc_session::Session;
2323
use rustc_span::{Span, DUMMY_SP};
2424
use std::cell::Cell;
2525
use std::collections::hash_map::Entry;
@@ -537,7 +537,7 @@ where
537537

538538
let (prev_dep_node_index, dep_node_index) = dep_graph_data.try_mark_green(qcx, &dep_node)?;
539539

540-
debug_assert!(dep_graph_data.is_green(dep_node));
540+
debug_assert!(dep_graph_data.is_index_green(prev_dep_node_index));
541541

542542
// First we try to load the result from the on-disk cache.
543543
// Some things are never cached on disk.
@@ -561,8 +561,7 @@ where
561561
dep_graph_data.mark_debug_loaded_from_disk(*dep_node)
562562
}
563563

564-
let prev_fingerprint =
565-
dep_graph_data.prev_fingerprint_of(dep_node).unwrap_or(Fingerprint::ZERO);
564+
let prev_fingerprint = dep_graph_data.prev_fingerprint_of(prev_dep_node_index);
566565
// If `-Zincremental-verify-ich` is specified, re-hash results from
567566
// the cache and make sure that they have the expected fingerprint.
568567
//
@@ -578,7 +577,7 @@ where
578577
*qcx.dep_context(),
579578
dep_graph_data,
580579
&result,
581-
dep_node,
580+
prev_dep_node_index,
582581
query.hash_result(),
583582
);
584583
}
@@ -623,7 +622,7 @@ where
623622
*qcx.dep_context(),
624623
dep_graph_data,
625624
&result,
626-
dep_node,
625+
prev_dep_node_index,
627626
query.hash_result(),
628627
);
629628

@@ -636,32 +635,38 @@ pub(crate) fn incremental_verify_ich<Tcx, V: Debug>(
636635
tcx: Tcx,
637636
dep_graph_data: &DepGraphData<Tcx::DepKind>,
638637
result: &V,
639-
dep_node: &DepNode<Tcx::DepKind>,
638+
prev_index: SerializedDepNodeIndex,
640639
hash_result: Option<fn(&mut StableHashingContext<'_>, &V) -> Fingerprint>,
641-
) -> Fingerprint
642-
where
640+
) where
643641
Tcx: DepContext,
644642
{
645-
assert!(
646-
dep_graph_data.is_green(dep_node),
647-
"fingerprint for green query instance not loaded from cache: {dep_node:?}",
648-
);
643+
if !dep_graph_data.is_index_green(prev_index) {
644+
incremental_verify_ich_not_green::<Tcx>(prev_index)
645+
}
649646

650647
let new_hash = hash_result.map_or(Fingerprint::ZERO, |f| {
651648
tcx.with_stable_hashing_context(|mut hcx| f(&mut hcx, result))
652649
});
653650

654-
let old_hash = dep_graph_data.prev_fingerprint_of(dep_node);
651+
let old_hash = dep_graph_data.prev_fingerprint_of(prev_index);
655652

656-
if Some(new_hash) != old_hash {
657-
incremental_verify_ich_failed(
658-
tcx.sess(),
659-
DebugArg::from(&dep_node),
660-
DebugArg::from(&result),
661-
);
653+
if new_hash != old_hash {
654+
incremental_verify_ich_failed::<Tcx>(prev_index, DebugArg::from(&result));
662655
}
656+
}
663657

664-
new_hash
658+
#[cold]
659+
#[inline(never)]
660+
fn incremental_verify_ich_not_green<Tcx>(prev_index: SerializedDepNodeIndex)
661+
where
662+
Tcx: DepContext,
663+
{
664+
Tcx::with_context(|tcx| {
665+
panic!(
666+
"fingerprint for green query instance not loaded from cache: {:?}",
667+
tcx.dep_graph().data().unwrap().prev_node_of(prev_index)
668+
)
669+
})
665670
}
666671

667672
// This DebugArg business is largely a mirror of std::fmt::ArgumentV1, which is
@@ -706,7 +711,11 @@ impl std::fmt::Debug for DebugArg<'_> {
706711
// different implementations for LLVM to chew on (and filling up the final
707712
// binary, too).
708713
#[cold]
709-
fn incremental_verify_ich_failed(sess: &Session, dep_node: DebugArg<'_>, result: DebugArg<'_>) {
714+
#[inline(never)]
715+
fn incremental_verify_ich_failed<Tcx>(prev_index: SerializedDepNodeIndex, result: DebugArg<'_>)
716+
where
717+
Tcx: DepContext,
718+
{
710719
// When we emit an error message and panic, we try to debug-print the `DepNode`
711720
// and query result. Unfortunately, this can cause us to run additional queries,
712721
// which may result in another fingerprint mismatch while we're in the middle
@@ -719,21 +728,25 @@ fn incremental_verify_ich_failed(sess: &Session, dep_node: DebugArg<'_>, result:
719728

720729
let old_in_panic = INSIDE_VERIFY_PANIC.with(|in_panic| in_panic.replace(true));
721730

722-
if old_in_panic {
723-
sess.emit_err(crate::error::Reentrant);
724-
} else {
725-
let run_cmd = if let Some(crate_name) = &sess.opts.crate_name {
726-
format!("`cargo clean -p {crate_name}` or `cargo clean`")
731+
Tcx::with_context(|tcx| {
732+
if old_in_panic {
733+
tcx.sess().emit_err(crate::error::Reentrant);
727734
} else {
728-
"`cargo clean`".to_string()
729-
};
735+
let run_cmd = if let Some(crate_name) = &tcx.sess().opts.crate_name {
736+
format!("`cargo clean -p {crate_name}` or `cargo clean`")
737+
} else {
738+
"`cargo clean`".to_string()
739+
};
730740

731-
sess.emit_err(crate::error::IncrementCompilation {
732-
run_cmd,
733-
dep_node: format!("{dep_node:?}"),
734-
});
735-
panic!("Found unstable fingerprints for {dep_node:?}: {result:?}");
736-
}
741+
let dep_node = tcx.dep_graph().data().unwrap().prev_node_of(prev_index);
742+
743+
let dep_node = tcx.sess().emit_err(crate::error::IncrementCompilation {
744+
run_cmd,
745+
dep_node: format!("{dep_node:?}"),
746+
});
747+
panic!("Found unstable fingerprints for {dep_node:?}: {result:?}");
748+
}
749+
});
737750

738751
INSIDE_VERIFY_PANIC.with(|in_panic| in_panic.set(old_in_panic));
739752
}

0 commit comments

Comments
 (0)