Skip to content

Commit ed4ba22

Browse files
incr.comp.: Move result fingerprinting to DepGraph::with_task().
This makes sure that we don't introduce strange cases where we have nodes outside the query system that could break red/green tracking and it will allow to keep red/green neatly encapsulated within the DepGraph implementation.
1 parent 0cf6000 commit ed4ba22

File tree

9 files changed

+132
-39
lines changed

9 files changed

+132
-39
lines changed

src/librustc/dep_graph/graph.rs

+25-11
Original file line numberDiff line numberDiff line change
@@ -9,11 +9,15 @@
99
// except according to those terms.
1010

1111
use rustc_data_structures::fx::FxHashMap;
12+
use rustc_data_structures::stable_hasher::{HashStable, StableHasher,
13+
StableHashingContextProvider};
1214
use session::config::OutputType;
1315
use std::cell::{Ref, RefCell};
1416
use std::rc::Rc;
1517
use util::common::{ProfileQueriesMsg, profq_msg};
1618

19+
use ich::Fingerprint;
20+
1721
use super::dep_node::{DepNode, DepKind, WorkProductId};
1822
use super::query::DepGraphQuery;
1923
use super::raii;
@@ -71,10 +75,6 @@ impl DepGraph {
7175
self.data.as_ref().map(|data| raii::IgnoreTask::new(&data.edges))
7276
}
7377

74-
pub fn in_task<'graph>(&'graph self, key: DepNode) -> Option<raii::DepTask<'graph>> {
75-
self.data.as_ref().map(|data| raii::DepTask::new(&data.edges, key))
76-
}
77-
7878
pub fn with_ignore<OP,R>(&self, op: OP) -> R
7979
where OP: FnOnce() -> R
8080
{
@@ -109,24 +109,38 @@ impl DepGraph {
109109
/// `arg` parameter.
110110
///
111111
/// [README]: README.md
112-
pub fn with_task<C, A, R>(&self,
113-
key: DepNode,
114-
cx: C,
115-
arg: A,
116-
task: fn(C, A) -> R)
117-
-> (R, DepNodeIndex)
118-
where C: DepGraphSafe
112+
pub fn with_task<C, A, R, HCX>(&self,
113+
key: DepNode,
114+
cx: C,
115+
arg: A,
116+
task: fn(C, A) -> R)
117+
-> (R, DepNodeIndex)
118+
where C: DepGraphSafe + StableHashingContextProvider<ContextType=HCX>,
119+
R: HashStable<HCX>,
119120
{
120121
if let Some(ref data) = self.data {
121122
data.edges.borrow_mut().push_task(key);
122123
if cfg!(debug_assertions) {
123124
profq_msg(ProfileQueriesMsg::TaskBegin(key.clone()))
124125
};
126+
127+
// In incremental mode, hash the result of the task. We don't
128+
// do anything with the hash yet, but we are computing it
129+
// anyway so that
130+
// - we make sure that the infrastructure works and
131+
// - we can get an idea of the runtime cost.
132+
let mut hcx = cx.create_stable_hashing_context();
133+
125134
let result = task(cx, arg);
126135
if cfg!(debug_assertions) {
127136
profq_msg(ProfileQueriesMsg::TaskEnd)
128137
};
129138
let dep_node_index = data.edges.borrow_mut().pop_task(key);
139+
140+
let mut stable_hasher = StableHasher::new();
141+
result.hash_stable(&mut hcx, &mut stable_hasher);
142+
let _: Fingerprint = stable_hasher.finish();
143+
130144
(result, dep_node_index)
131145
} else {
132146
(task(cx, arg), DepNodeIndex::INVALID)

src/librustc/dep_graph/safe.rs

+7
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,13 @@ impl<'a, A> DepGraphSafe for &'a A
5858
{
5959
}
6060

61+
/// Mut ref to dep-graph-safe stuff should still be dep-graph-safe.
62+
impl<'a, A> DepGraphSafe for &'a mut A
63+
where A: DepGraphSafe,
64+
{
65+
}
66+
67+
6168
/// No data here! :)
6269
impl DepGraphSafe for () {
6370
}

src/librustc/ich/hcx.rs

+8-2
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@ use syntax::ext::hygiene::SyntaxContext;
2626
use syntax::symbol::Symbol;
2727
use syntax_pos::Span;
2828

29-
use rustc_data_structures::stable_hasher::{HashStable, StableHasher,
30-
StableHasherResult};
29+
use rustc_data_structures::stable_hasher::{HashStable, StableHashingContextProvider,
30+
StableHasher, StableHasherResult};
3131
use rustc_data_structures::accumulate_vec::AccumulateVec;
3232

3333
/// This is the context state available during incr. comp. hashing. It contains
@@ -196,6 +196,12 @@ impl<'a, 'gcx, 'tcx> StableHashingContext<'a, 'gcx, 'tcx> {
196196
}
197197
}
198198

199+
impl<'a, 'gcx, 'lcx> StableHashingContextProvider for ty::TyCtxt<'a, 'gcx, 'lcx> {
200+
type ContextType = StableHashingContext<'a, 'gcx, 'lcx>;
201+
fn create_stable_hashing_context(&self) -> Self::ContextType {
202+
StableHashingContext::new(*self)
203+
}
204+
}
199205

200206
impl<'a, 'gcx, 'tcx> HashStable<StableHashingContext<'a, 'gcx, 'tcx>> for ast::NodeId {
201207
fn hash_stable<W: StableHasherResult>(&self,

src/librustc/ty/maps.rs

+1-16
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@ use errors::{Diagnostic, DiagnosticBuilder};
1313
use hir::def_id::{CrateNum, DefId, LOCAL_CRATE};
1414
use hir::def::{Def, Export};
1515
use hir::{self, TraitCandidate, HirId};
16-
use ich::{Fingerprint, StableHashingContext};
1716
use lint;
1817
use middle::const_val;
1918
use middle::cstore::{ExternCrate, LinkagePreference};
@@ -37,7 +36,7 @@ use rustc_data_structures::indexed_set::IdxSetBuf;
3736
use rustc_data_structures::indexed_vec::IndexVec;
3837
use rustc_data_structures::fx::FxHashMap;
3938
use std::cell::{RefCell, RefMut, Cell};
40-
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
39+
4140
use std::fmt::Debug;
4241
use std::hash::Hash;
4342
use std::marker::PhantomData;
@@ -732,20 +731,6 @@ macro_rules! define_maps {
732731

733732
tcx.dep_graph.read_index(dep_node_index);
734733

735-
// In incremental mode, hash the result of the query. We don't
736-
// do anything with the hash yet, but we are computing it
737-
// anyway so that
738-
// - we make sure that the infrastructure works and
739-
// - we can get an idea of the runtime cost.
740-
if !dep_node.kind.is_anon() && tcx.sess.opts.incremental.is_some() {
741-
let mut hcx = StableHashingContext::new(tcx);
742-
let mut hasher = StableHasher::new();
743-
744-
result.hash_stable(&mut hcx, &mut hasher);
745-
746-
let _: Fingerprint = hasher.finish();
747-
}
748-
749734
let value = QueryValue {
750735
value: result,
751736
index: dep_node_index,

src/librustc/ty/mod.rs

+4
Original file line numberDiff line numberDiff line change
@@ -2597,6 +2597,10 @@ pub struct SymbolName {
25972597
pub name: InternedString
25982598
}
25992599

2600+
impl_stable_hash_for!(struct self::SymbolName {
2601+
name
2602+
});
2603+
26002604
impl Deref for SymbolName {
26012605
type Target = str;
26022606

src/librustc_data_structures/stable_hasher.rs

+25-3
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,28 @@ impl<W> Hasher for StableHasher<W> {
192192
}
193193

194194

195+
/// Something that can provide a stable hashing context.
196+
pub trait StableHashingContextProvider {
197+
type ContextType;
198+
fn create_stable_hashing_context(&self) -> Self::ContextType;
199+
}
200+
201+
impl<'a, T: StableHashingContextProvider> StableHashingContextProvider for &'a T {
202+
type ContextType = T::ContextType;
203+
204+
fn create_stable_hashing_context(&self) -> Self::ContextType {
205+
(**self).create_stable_hashing_context()
206+
}
207+
}
208+
209+
impl<'a, T: StableHashingContextProvider> StableHashingContextProvider for &'a mut T {
210+
type ContextType = T::ContextType;
211+
212+
fn create_stable_hashing_context(&self) -> Self::ContextType {
213+
(**self).create_stable_hashing_context()
214+
}
215+
}
216+
195217
/// Something that implements `HashStable<CTX>` can be hashed in a way that is
196218
/// stable across multiple compilation sessions.
197219
pub trait HashStable<CTX> {
@@ -292,7 +314,7 @@ impl<T: HashStable<CTX>, CTX> HashStable<CTX> for Vec<T> {
292314
}
293315
}
294316

295-
impl<T: HashStable<CTX>, CTX> HashStable<CTX> for Box<T> {
317+
impl<T: ?Sized + HashStable<CTX>, CTX> HashStable<CTX> for Box<T> {
296318
#[inline]
297319
fn hash_stable<W: StableHasherResult>(&self,
298320
ctx: &mut CTX,
@@ -301,7 +323,7 @@ impl<T: HashStable<CTX>, CTX> HashStable<CTX> for Box<T> {
301323
}
302324
}
303325

304-
impl<T: HashStable<CTX>, CTX> HashStable<CTX> for ::std::rc::Rc<T> {
326+
impl<T: ?Sized + HashStable<CTX>, CTX> HashStable<CTX> for ::std::rc::Rc<T> {
305327
#[inline]
306328
fn hash_stable<W: StableHasherResult>(&self,
307329
ctx: &mut CTX,
@@ -310,7 +332,7 @@ impl<T: HashStable<CTX>, CTX> HashStable<CTX> for ::std::rc::Rc<T> {
310332
}
311333
}
312334

313-
impl<T: HashStable<CTX>, CTX> HashStable<CTX> for ::std::sync::Arc<T> {
335+
impl<T: ?Sized + HashStable<CTX>, CTX> HashStable<CTX> for ::std::sync::Arc<T> {
314336
#[inline]
315337
fn hash_stable<W: StableHasherResult>(&self,
316338
ctx: &mut CTX,

src/librustc_trans/base.rs

+33-3
Original file line numberDiff line numberDiff line change
@@ -1116,7 +1116,7 @@ pub fn trans_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
11161116
let dep_node = cgu.work_product_dep_node();
11171117
let ((stats, module), _) =
11181118
tcx.dep_graph.with_task(dep_node,
1119-
AssertDepGraphSafe(&shared_ccx),
1119+
&shared_ccx,
11201120
AssertDepGraphSafe((cgu,
11211121
translation_items.clone(),
11221122
exported_symbols.clone())),
@@ -1159,14 +1159,13 @@ pub fn trans_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
11591159
}
11601160

11611161
fn module_translation<'a, 'tcx>(
1162-
scx: AssertDepGraphSafe<&SharedCrateContext<'a, 'tcx>>,
1162+
scx: &SharedCrateContext<'a, 'tcx>,
11631163
args: AssertDepGraphSafe<(CodegenUnit<'tcx>,
11641164
Arc<FxHashSet<TransItem<'tcx>>>,
11651165
Arc<ExportedSymbols>)>)
11661166
-> (Stats, ModuleTranslation)
11671167
{
11681168
// FIXME(#40304): We ought to be using the id as a key and some queries, I think.
1169-
let AssertDepGraphSafe(scx) = scx;
11701169
let AssertDepGraphSafe((cgu, crate_trans_items, exported_symbols)) = args;
11711170

11721171
let cgu_name = String::from(cgu.name());
@@ -1502,3 +1501,34 @@ fn collect_and_partition_translation_items<'a, 'tcx>(scx: &SharedCrateContext<'a
15021501

15031502
(translation_items, codegen_units)
15041503
}
1504+
1505+
// FIXME(mw): Anything that is produced via DepGraph::with_task() must implement
1506+
// the HashStable trait. Normally DepGraph::with_task() calls are
1507+
// hidden behind queries, but CGU creation is a special case in two
1508+
// ways: (1) it's not a query and (2) CGU are output nodes, so their
1509+
// Fingerprints are not actually needed. It remains to be clarified
1510+
// how exactly this case will be handled in the red/green system but
1511+
// for now we content ourselves with providing a no-op HashStable
1512+
// implementation for CGUs.
1513+
mod temp_stable_hash_impls {
1514+
use rustc_data_structures::stable_hasher::{StableHasherResult, StableHasher,
1515+
HashStable};
1516+
use context::Stats;
1517+
use ModuleTranslation;
1518+
1519+
impl<HCX> HashStable<HCX> for Stats {
1520+
fn hash_stable<W: StableHasherResult>(&self,
1521+
_: &mut HCX,
1522+
_: &mut StableHasher<W>) {
1523+
// do nothing
1524+
}
1525+
}
1526+
1527+
impl<HCX> HashStable<HCX> for ModuleTranslation {
1528+
fn hash_stable<W: StableHasherResult>(&self,
1529+
_: &mut HCX,
1530+
_: &mut StableHasher<W>) {
1531+
// do nothing
1532+
}
1533+
}
1534+
}

src/librustc_trans/context.rs

+13
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ use llvm::{ContextRef, ModuleRef, ValueRef};
1313
use rustc::dep_graph::{DepGraph, DepGraphSafe};
1414
use rustc::hir;
1515
use rustc::hir::def_id::DefId;
16+
use rustc::ich::StableHashingContext;
1617
use rustc::traits;
1718
use debuginfo;
1819
use callee;
@@ -25,6 +26,7 @@ use partitioning::CodegenUnit;
2526
use trans_item::TransItem;
2627
use type_::Type;
2728
use rustc_data_structures::base_n;
29+
use rustc_data_structures::stable_hasher::StableHashingContextProvider;
2830
use rustc::session::config::{self, NoDebugInfo, OutputFilenames};
2931
use rustc::session::Session;
3032
use rustc::ty::{self, Ty, TyCtxt};
@@ -174,6 +176,17 @@ impl<'a, 'tcx> CrateContext<'a, 'tcx> {
174176
impl<'a, 'tcx> DepGraphSafe for CrateContext<'a, 'tcx> {
175177
}
176178

179+
impl<'a, 'tcx> DepGraphSafe for SharedCrateContext<'a, 'tcx> {
180+
}
181+
182+
impl<'a, 'tcx> StableHashingContextProvider for SharedCrateContext<'a, 'tcx> {
183+
type ContextType = StableHashingContext<'a, 'tcx, 'tcx>;
184+
185+
fn create_stable_hashing_context(&self) -> Self::ContextType {
186+
StableHashingContext::new(self.tcx)
187+
}
188+
}
189+
177190
pub fn get_reloc_model(sess: &Session) -> llvm::RelocMode {
178191
let reloc_model_arg = match sess.opts.cg.relocation_model {
179192
Some(ref s) => &s[..],

src/librustc_typeck/variance/constraints.rs

+16-4
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,16 @@
1414
//! We walk the set of items and, for each member, generate new constraints.
1515
1616
use hir::def_id::DefId;
17-
use rustc::dep_graph::{AssertDepGraphSafe, DepKind};
17+
use rustc::dep_graph::{DepGraphSafe, DepKind};
18+
use rustc::ich::StableHashingContext;
1819
use rustc::ty::subst::Substs;
1920
use rustc::ty::{self, Ty, TyCtxt};
2021
use syntax::ast;
2122
use rustc::hir;
2223
use rustc::hir::itemlikevisit::ItemLikeVisitor;
2324

2425
use rustc_data_structures::transitive_relation::TransitiveRelation;
26+
use rustc_data_structures::stable_hasher::StableHashingContextProvider;
2527

2628
use super::terms::*;
2729
use super::terms::VarianceTerm::*;
@@ -138,6 +140,16 @@ impl<'a, 'tcx, 'v> ItemLikeVisitor<'v> for ConstraintContext<'a, 'tcx> {
138140
}
139141
}
140142

143+
impl<'a, 'tcx> StableHashingContextProvider for ConstraintContext<'a, 'tcx> {
144+
type ContextType = StableHashingContext<'a, 'tcx, 'tcx>;
145+
146+
fn create_stable_hashing_context(&self) -> Self::ContextType {
147+
StableHashingContext::new(self.terms_cx.tcx)
148+
}
149+
}
150+
151+
impl<'a, 'tcx> DepGraphSafe for ConstraintContext<'a, 'tcx> {}
152+
141153
impl<'a, 'tcx> ConstraintContext<'a, 'tcx> {
142154
fn visit_node_helper(&mut self, id: ast::NodeId) {
143155
let tcx = self.terms_cx.tcx;
@@ -151,14 +163,14 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> {
151163
// on dep-graph management.
152164
let dep_node = def_id.to_dep_node(tcx, DepKind::ItemVarianceConstraints);
153165
tcx.dep_graph.with_task(dep_node,
154-
AssertDepGraphSafe(self),
166+
self,
155167
def_id,
156168
visit_item_task);
157169

158-
fn visit_item_task<'a, 'tcx>(ccx: AssertDepGraphSafe<&mut ConstraintContext<'a, 'tcx>>,
170+
fn visit_item_task<'a, 'tcx>(ccx: &mut ConstraintContext<'a, 'tcx>,
159171
def_id: DefId)
160172
{
161-
ccx.0.build_constraints_for_item(def_id);
173+
ccx.build_constraints_for_item(def_id);
162174
}
163175
}
164176

0 commit comments

Comments
 (0)