Skip to content

Add a query type which is always marked as red if it runs #57770

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 7 commits into from
Feb 10, 2019
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
89 changes: 54 additions & 35 deletions src/librustc/dep_graph/graph.rs
Original file line number Diff line number Diff line change
@@ -79,6 +79,16 @@ struct DepGraphData {
loaded_from_cache: Lock<FxHashMap<DepNodeIndex, bool>>,
}

pub fn hash_result<R>(hcx: &mut StableHashingContext<'_>, result: &R) -> Option<Fingerprint>
where
R: for<'a> HashStable<StableHashingContext<'a>>,
{
let mut stable_hasher = StableHasher::new();
result.hash_stable(hcx, &mut stable_hasher);

Some(stable_hasher.finish())
}

impl DepGraph {

pub fn new(prev_graph: PreviousDepGraph,
@@ -178,14 +188,16 @@ impl DepGraph {
/// `arg` parameter.
///
/// [rustc guide]: https://rust-lang.github.io/rustc-guide/incremental-compilation.html
pub fn with_task<'gcx, C, A, R>(&self,
key: DepNode,
cx: C,
arg: A,
task: fn(C, A) -> R)
-> (R, DepNodeIndex)
where C: DepGraphSafe + StableHashingContextProvider<'gcx>,
R: HashStable<StableHashingContext<'gcx>>,
pub fn with_task<'a, C, A, R>(
&self,
key: DepNode,
cx: C,
arg: A,
task: fn(C, A) -> R,
hash_result: impl FnOnce(&mut StableHashingContext<'_>, &R) -> Option<Fingerprint>,
) -> (R, DepNodeIndex)
where
C: DepGraphSafe + StableHashingContextProvider<'a>,
{
self.with_task_impl(key, cx, arg, false, task,
|_key| Some(TaskDeps {
@@ -196,17 +208,18 @@ impl DepGraph {
}),
|data, key, fingerprint, task| {
data.borrow_mut().complete_task(key, task.unwrap(), fingerprint)
})
},
hash_result)
}

/// Creates a new dep-graph input with value `input`
pub fn input_task<'gcx, C, R>(&self,
pub fn input_task<'a, C, R>(&self,
key: DepNode,
cx: C,
input: R)
-> (R, DepNodeIndex)
where C: DepGraphSafe + StableHashingContextProvider<'gcx>,
R: HashStable<StableHashingContext<'gcx>>,
where C: DepGraphSafe + StableHashingContextProvider<'a>,
R: for<'b> HashStable<StableHashingContext<'b>>,
{
fn identity_fn<C, A>(_: C, arg: A) -> A {
arg
@@ -216,10 +229,11 @@ impl DepGraph {
|_| None,
|data, key, fingerprint, _| {
data.borrow_mut().alloc_node(key, SmallVec::new(), fingerprint)
})
},
hash_result::<R>)
}

fn with_task_impl<'gcx, C, A, R>(
fn with_task_impl<'a, C, A, R>(
&self,
key: DepNode,
cx: C,
@@ -230,11 +244,11 @@ impl DepGraph {
finish_task_and_alloc_depnode: fn(&Lock<CurrentDepGraph>,
DepNode,
Fingerprint,
Option<TaskDeps>) -> DepNodeIndex
Option<TaskDeps>) -> DepNodeIndex,
hash_result: impl FnOnce(&mut StableHashingContext<'_>, &R) -> Option<Fingerprint>,
) -> (R, DepNodeIndex)
where
C: DepGraphSafe + StableHashingContextProvider<'gcx>,
R: HashStable<StableHashingContext<'gcx>>,
C: DepGraphSafe + StableHashingContextProvider<'a>,
{
if let Some(ref data) = self.data {
let task_deps = create_task(key).map(|deps| Lock::new(deps));
@@ -269,31 +283,33 @@ impl DepGraph {
profq_msg(hcx.sess(), ProfileQueriesMsg::TaskEnd)
};

let mut stable_hasher = StableHasher::new();
result.hash_stable(&mut hcx, &mut stable_hasher);

let current_fingerprint = stable_hasher.finish();
let current_fingerprint = hash_result(&mut hcx, &result);

let dep_node_index = finish_task_and_alloc_depnode(
&data.current,
key,
current_fingerprint,
current_fingerprint.unwrap_or(Fingerprint::ZERO),
task_deps.map(|lock| lock.into_inner()),
);

// Determine the color of the new DepNode.
if let Some(prev_index) = data.previous.node_to_index_opt(&key) {
let prev_fingerprint = data.previous.fingerprint_by_index(prev_index);

let color = if current_fingerprint == prev_fingerprint {
DepNodeColor::Green(dep_node_index)
let color = if let Some(current_fingerprint) = current_fingerprint {
if current_fingerprint == prev_fingerprint {
DepNodeColor::Green(dep_node_index)
} else {
DepNodeColor::Red
}
} else {
// Mark the node as Red if we can't hash the result
DepNodeColor::Red
};

debug_assert!(data.colors.get(prev_index).is_none(),
"DepGraph::with_task() - Duplicate DepNodeColor \
insertion for {:?}", key);
"DepGraph::with_task() - Duplicate DepNodeColor \
insertion for {:?}", key);

data.colors.insert(prev_index, color);
}
@@ -342,14 +358,16 @@ impl DepGraph {

/// Execute something within an "eval-always" task which is a task
// that runs whenever anything changes.
pub fn with_eval_always_task<'gcx, C, A, R>(&self,
key: DepNode,
cx: C,
arg: A,
task: fn(C, A) -> R)
-> (R, DepNodeIndex)
where C: DepGraphSafe + StableHashingContextProvider<'gcx>,
R: HashStable<StableHashingContext<'gcx>>,
pub fn with_eval_always_task<'a, C, A, R>(
&self,
key: DepNode,
cx: C,
arg: A,
task: fn(C, A) -> R,
hash_result: impl FnOnce(&mut StableHashingContext<'_>, &R) -> Option<Fingerprint>,
) -> (R, DepNodeIndex)
where
C: DepGraphSafe + StableHashingContextProvider<'a>,
{
self.with_task_impl(key, cx, arg, false, task,
|_| None,
@@ -359,7 +377,8 @@ impl DepGraph {
&DepNode::new_no_params(DepKind::Krate)
];
current.alloc_node(key, smallvec![krate_idx], fingerprint)
})
},
hash_result)
}

#[inline]
2 changes: 1 addition & 1 deletion src/librustc/dep_graph/mod.rs
Original file line number Diff line number Diff line change
@@ -10,7 +10,7 @@ pub mod cgu_reuse_tracker;

pub use self::dep_tracking_map::{DepTrackingMap, DepTrackingMapConfig};
pub use self::dep_node::{DepNode, DepKind, DepConstructor, WorkProductId, label_strs};
pub use self::graph::{DepGraph, WorkProduct, DepNodeIndex, DepNodeColor, TaskDeps};
pub use self::graph::{DepGraph, WorkProduct, DepNodeIndex, DepNodeColor, TaskDeps, hash_result};
pub use self::graph::WorkProductFileKind;
pub use self::prev::PreviousDepGraph;
pub use self::query::DepGraphQuery;
14 changes: 7 additions & 7 deletions src/librustc/hir/map/collector.rs
Original file line number Diff line number Diff line change
@@ -48,14 +48,14 @@ pub(super) struct NodeCollector<'a, 'hir> {
hir_body_nodes: Vec<(DefPathHash, Fingerprint)>,
}

fn input_dep_node_and_hash<'a, I>(
fn input_dep_node_and_hash<I>(
dep_graph: &DepGraph,
hcx: &mut StableHashingContext<'a>,
hcx: &mut StableHashingContext<'_>,
dep_node: DepNode,
input: I,
) -> (DepNodeIndex, Fingerprint)
where
I: HashStable<StableHashingContext<'a>>,
I: for<'a> HashStable<StableHashingContext<'a>>,
{
let dep_node_index = dep_graph.input_task(dep_node, &mut *hcx, &input).1;

@@ -70,15 +70,15 @@ where
(dep_node_index, hash)
}

fn alloc_hir_dep_nodes<'a, I>(
fn alloc_hir_dep_nodes<I>(
dep_graph: &DepGraph,
hcx: &mut StableHashingContext<'a>,
hcx: &mut StableHashingContext<'_>,
def_path_hash: DefPathHash,
item_like: I,
hir_body_nodes: &mut Vec<(DefPathHash, Fingerprint)>,
) -> (DepNodeIndex, DepNodeIndex)
where
I: HashStable<StableHashingContext<'a>>,
I: for<'a> HashStable<StableHashingContext<'a>>,
{
let sig = dep_graph.input_task(
def_path_hash.to_dep_node(DepKind::Hir),
@@ -286,7 +286,7 @@ impl<'a, 'hir> NodeCollector<'a, 'hir> {
self.parent_node = parent_node;
}

fn with_dep_node_owner<T: HashStable<StableHashingContext<'a>>,
fn with_dep_node_owner<T: for<'b> HashStable<StableHashingContext<'b>>,
F: FnOnce(&mut Self)>(&mut self,
dep_node_owner: DefIndex,
item_like: &T,
5 changes: 3 additions & 2 deletions src/librustc/ty/context.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
//! type context book-keeping

use crate::dep_graph::DepGraph;
use crate::dep_graph::{DepNode, DepConstructor};
use crate::dep_graph::{self, DepNode, DepConstructor};
use crate::errors::DiagnosticBuilder;
use crate::session::Session;
use crate::session::config::{BorrowckMode, OutputFilenames};
@@ -1435,7 +1435,8 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
self.dep_graph.with_task(dep_node,
self,
crate_hash,
|_, x| x // No transformation needed
|_, x| x, // No transformation needed
dep_graph::hash_result,
);
}
}
9 changes: 7 additions & 2 deletions src/librustc/ty/query/config.rs
Original file line number Diff line number Diff line change
@@ -20,7 +20,7 @@ use std::hash::Hash;
use std::fmt::Debug;
use syntax_pos::symbol::InternedString;
use rustc_data_structures::sync::Lock;
use rustc_data_structures::stable_hasher::HashStable;
use rustc_data_structures::fingerprint::Fingerprint;
use crate::ich::StableHashingContext;

// Query configuration and description traits.
@@ -30,7 +30,7 @@ pub trait QueryConfig<'tcx> {
const CATEGORY: ProfileCategory;

type Key: Eq + Hash + Clone + Debug;
type Value: Clone + for<'a> HashStable<StableHashingContext<'a>>;
type Value: Clone;
}

pub(super) trait QueryAccessors<'tcx>: QueryConfig<'tcx> {
@@ -44,6 +44,11 @@ pub(super) trait QueryAccessors<'tcx>: QueryConfig<'tcx> {
// Don't use this method to compute query results, instead use the methods on TyCtxt
fn compute(tcx: TyCtxt<'_, 'tcx, '_>, key: Self::Key) -> Self::Value;

fn hash_result(
hcx: &mut StableHashingContext<'_>,
result: &Self::Value
) -> Option<Fingerprint>;

fn handle_cycle_error(tcx: TyCtxt<'_, 'tcx, '_>) -> Self::Value;
}

7 changes: 4 additions & 3 deletions src/librustc/ty/query/mod.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use crate::dep_graph::{DepConstructor, DepNode};
use crate::dep_graph::{self, DepConstructor, DepNode};
use crate::errors::DiagnosticBuilder;
use crate::hir::def_id::{CrateNum, DefId, DefIndex};
use crate::hir::def::{Def, Export};
@@ -49,6 +49,7 @@ use rustc_data_structures::indexed_vec::IndexVec;
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
use rustc_data_structures::stable_hasher::StableVec;
use rustc_data_structures::sync::Lrc;
use rustc_data_structures::fingerprint::Fingerprint;
use rustc_target::spec::PanicStrategy;

use std::borrow::Cow;
@@ -233,9 +234,9 @@ define_queries! { <'tcx>
/// ready for const evaluation.
///
/// See the README for the `mir` module for details.
[] fn mir_const: MirConst(DefId) -> &'tcx Steal<mir::Mir<'tcx>>,
[no_hash] fn mir_const: MirConst(DefId) -> &'tcx Steal<mir::Mir<'tcx>>,

[] fn mir_validated: MirValidated(DefId) -> &'tcx Steal<mir::Mir<'tcx>>,
[no_hash] fn mir_validated: MirValidated(DefId) -> &'tcx Steal<mir::Mir<'tcx>>,

/// MIR after our optimization passes have run. This is MIR that is ready
/// for codegen. This is also the only query that can fetch non-local MIR, at present.
31 changes: 24 additions & 7 deletions src/librustc/ty/query/plumbing.rs
Original file line number Diff line number Diff line change
@@ -499,7 +499,6 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
dep_node: &DepNode,
dep_node_index: DepNodeIndex,
) {
use rustc_data_structures::stable_hasher::{StableHasher, HashStable};
use crate::ich::Fingerprint;

assert!(Some(self.dep_graph.fingerprint_of(dep_node_index)) ==
@@ -509,11 +508,8 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {

debug!("BEGIN verify_ich({:?})", dep_node);
let mut hcx = self.create_stable_hashing_context();
let mut hasher = StableHasher::new();

result.hash_stable(&mut hcx, &mut hasher);

let new_hash: Fingerprint = hasher.finish();
let new_hash = Q::hash_result(&mut hcx, result).unwrap_or(Fingerprint::ZERO);
debug!("END verify_ich({:?})", dep_node);

let old_hash = self.dep_graph.fingerprint_of(dep_node_index);
@@ -549,12 +545,14 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
tcx.dep_graph.with_eval_always_task(dep_node,
tcx,
key,
Q::compute)
Q::compute,
Q::hash_result)
} else {
tcx.dep_graph.with_task(dep_node,
tcx,
key,
Q::compute)
Q::compute,
Q::hash_result)
}
})
});
@@ -679,6 +677,18 @@ macro_rules! handle_cycle_error {
};
}

macro_rules! hash_result {
([][$hcx:expr, $result:expr]) => {{
dep_graph::hash_result($hcx, &$result)
}};
([no_hash$(, $modifiers:ident)*][$hcx:expr, $result:expr]) => {{
None
}};
([$other:ident$(, $modifiers:ident)*][$($args:tt)*]) => {
hash_result!([$($modifiers),*][$($args)*])
};
}

macro_rules! define_queries {
(<$tcx:tt> $($category:tt {
$($(#[$attr:meta])* [$($modifiers:tt)*] fn $name:ident: $node:ident($K:ty) -> $V:ty,)*
@@ -966,6 +976,13 @@ macro_rules! define_queries_inner {
})
}

fn hash_result(
_hcx: &mut StableHashingContext<'_>,
_result: &Self::Value
) -> Option<Fingerprint> {
hash_result!([$($modifiers)*][_hcx, _result])
}

fn handle_cycle_error(tcx: TyCtxt<'_, 'tcx, '_>) -> Self::Value {
handle_cycle_error!([$($modifiers)*][tcx])
}
4 changes: 3 additions & 1 deletion src/librustc_codegen_llvm/base.rs
Original file line number Diff line number Diff line change
@@ -20,6 +20,7 @@ use super::LlvmCodegenBackend;

use llvm;
use metadata;
use rustc::dep_graph;
use rustc::mir::mono::{Linkage, Visibility, Stats};
use rustc::middle::cstore::{EncodedMetadata};
use rustc::ty::TyCtxt;
@@ -145,7 +146,8 @@ pub fn compile_codegen_unit<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
let ((stats, module), _) = tcx.dep_graph.with_task(dep_node,
tcx,
cgu_name,
module_codegen);
module_codegen,
dep_graph::hash_result);
let time_to_codegen = start_time.elapsed();

// We assume that the cost to run LLVM on a CGU is proportional to
Loading