Skip to content

Commit 9da25d9

Browse files
authored
Rollup merge of #67761 - cjgillot:split_graph, r=Zoxc
Move the dep_graph construction to a dedicated crate. The interface for librustc consists in two traits: `DepKind` and `DepContext`. The `DepKind` is the main interface. It allows to probe properties of the dependency. As before, `DepNode` is the pair of a `DepKind` object and a hash fingerprint. The `DepContext` takes the place of the `TyCtxt`, and handles communication with the query engine. The use of the `ImplicitCtxt` through `ty::tls` is done through the `DepKind` trait. This may not be the best choice, but it seemed like the simplest.
2 parents 1edd389 + 0f918cb commit 9da25d9

File tree

21 files changed

+763
-431
lines changed

21 files changed

+763
-431
lines changed

Cargo.lock

+17
Original file line numberDiff line numberDiff line change
@@ -3116,6 +3116,7 @@ dependencies = [
31163116
"rustc_hir",
31173117
"rustc_index",
31183118
"rustc_macros",
3119+
"rustc_query_system",
31193120
"rustc_session",
31203121
"rustc_span",
31213122
"rustc_target",
@@ -4021,6 +4022,22 @@ dependencies = [
40214022
"rustc_typeck",
40224023
]
40234024

4025+
[[package]]
4026+
name = "rustc_query_system"
4027+
version = "0.0.0"
4028+
dependencies = [
4029+
"log",
4030+
"parking_lot 0.9.0",
4031+
"rustc_ast",
4032+
"rustc_data_structures",
4033+
"rustc_errors",
4034+
"rustc_hir",
4035+
"rustc_index",
4036+
"rustc_macros",
4037+
"serialize",
4038+
"smallvec 1.0.0",
4039+
]
4040+
40244041
[[package]]
40254042
name = "rustc_resolve"
40264043
version = "0.0.0"

src/librustc/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ rustc_hir = { path = "../librustc_hir" }
2525
rustc_target = { path = "../librustc_target" }
2626
rustc_macros = { path = "../librustc_macros" }
2727
rustc_data_structures = { path = "../librustc_data_structures" }
28+
rustc_query_system = { path = "../librustc_query_system" }
2829
rustc_errors = { path = "../librustc_errors" }
2930
rustc_index = { path = "../librustc_index" }
3031
rustc_serialize = { path = "../libserialize", package = "serialize" }

src/librustc/dep_graph/dep_node.rs

+46-142
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,7 @@
5050
//! fingerprint for a given set of node parameters.
5151
5252
use crate::hir::map::DefPathHash;
53-
use crate::ich::{Fingerprint, StableHashingContext};
53+
use crate::ich::Fingerprint;
5454
use crate::mir;
5555
use crate::mir::interpret::{GlobalId, LitToConstInput};
5656
use crate::traits;
@@ -62,13 +62,13 @@ use crate::traits::query::{
6262
use crate::ty::subst::SubstsRef;
6363
use crate::ty::{self, ParamEnvAnd, Ty, TyCtxt};
6464

65-
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
6665
use rustc_hir::def_id::{CrateNum, DefId, LocalDefId, CRATE_DEF_INDEX};
6766
use rustc_hir::HirId;
6867
use rustc_span::symbol::Symbol;
69-
use std::fmt;
7068
use std::hash::Hash;
7169

70+
pub use rustc_query_system::dep_graph::{DepContext, DepNodeParams};
71+
7272
// erase!() just makes tokens go away. It's used to specify which macro argument
7373
// is repeated (i.e., which sub-expression of the macro we are in) but don't need
7474
// to actually use any of the arguments.
@@ -128,7 +128,7 @@ macro_rules! define_dep_nodes {
128128

129129
// tuple args
130130
$({
131-
return <$tuple_arg_ty as DepNodeParams>
131+
return <$tuple_arg_ty as DepNodeParams<TyCtxt<'_>>>
132132
::CAN_RECONSTRUCT_QUERY_KEY;
133133
})*
134134

@@ -212,38 +212,46 @@ macro_rules! define_dep_nodes {
212212
)*
213213
}
214214

215-
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash,
216-
RustcEncodable, RustcDecodable)]
217-
pub struct DepNode {
218-
pub kind: DepKind,
219-
pub hash: Fingerprint,
215+
pub type DepNode = rustc_query_system::dep_graph::DepNode<DepKind>;
216+
217+
pub trait DepNodeExt: Sized {
218+
/// Construct a DepNode from the given DepKind and DefPathHash. This
219+
/// method will assert that the given DepKind actually requires a
220+
/// single DefId/DefPathHash parameter.
221+
fn from_def_path_hash(def_path_hash: DefPathHash, kind: DepKind) -> Self;
222+
223+
/// Extracts the DefId corresponding to this DepNode. This will work
224+
/// if two conditions are met:
225+
///
226+
/// 1. The Fingerprint of the DepNode actually is a DefPathHash, and
227+
/// 2. the item that the DefPath refers to exists in the current tcx.
228+
///
229+
/// Condition (1) is determined by the DepKind variant of the
230+
/// DepNode. Condition (2) might not be fulfilled if a DepNode
231+
/// refers to something from the previous compilation session that
232+
/// has been removed.
233+
fn extract_def_id(&self, tcx: TyCtxt<'_>) -> Option<DefId>;
234+
235+
/// Used in testing
236+
fn from_label_string(label: &str, def_path_hash: DefPathHash)
237+
-> Result<Self, ()>;
238+
239+
/// Used in testing
240+
fn has_label_string(label: &str) -> bool;
220241
}
221242

222-
impl DepNode {
243+
impl DepNodeExt for DepNode {
223244
/// Construct a DepNode from the given DepKind and DefPathHash. This
224245
/// method will assert that the given DepKind actually requires a
225246
/// single DefId/DefPathHash parameter.
226-
pub fn from_def_path_hash(def_path_hash: DefPathHash,
227-
kind: DepKind)
228-
-> DepNode {
247+
fn from_def_path_hash(def_path_hash: DefPathHash, kind: DepKind) -> DepNode {
229248
debug_assert!(kind.can_reconstruct_query_key() && kind.has_params());
230249
DepNode {
231250
kind,
232251
hash: def_path_hash.0,
233252
}
234253
}
235254

236-
/// Creates a new, parameterless DepNode. This method will assert
237-
/// that the DepNode corresponding to the given DepKind actually
238-
/// does not require any parameters.
239-
pub fn new_no_params(kind: DepKind) -> DepNode {
240-
debug_assert!(!kind.has_params());
241-
DepNode {
242-
kind,
243-
hash: Fingerprint::ZERO,
244-
}
245-
}
246-
247255
/// Extracts the DefId corresponding to this DepNode. This will work
248256
/// if two conditions are met:
249257
///
@@ -254,20 +262,17 @@ macro_rules! define_dep_nodes {
254262
/// DepNode. Condition (2) might not be fulfilled if a DepNode
255263
/// refers to something from the previous compilation session that
256264
/// has been removed.
257-
pub fn extract_def_id(&self, tcx: TyCtxt<'_>) -> Option<DefId> {
265+
fn extract_def_id(&self, tcx: TyCtxt<'tcx>) -> Option<DefId> {
258266
if self.kind.can_reconstruct_query_key() {
259267
let def_path_hash = DefPathHash(self.hash);
260-
tcx.def_path_hash_to_def_id.as_ref()?
261-
.get(&def_path_hash).cloned()
268+
tcx.def_path_hash_to_def_id.as_ref()?.get(&def_path_hash).cloned()
262269
} else {
263270
None
264271
}
265272
}
266273

267274
/// Used in testing
268-
pub fn from_label_string(label: &str,
269-
def_path_hash: DefPathHash)
270-
-> Result<DepNode, ()> {
275+
fn from_label_string(label: &str, def_path_hash: DefPathHash) -> Result<DepNode, ()> {
271276
let kind = match label {
272277
$(
273278
stringify!($variant) => DepKind::$variant,
@@ -287,7 +292,7 @@ macro_rules! define_dep_nodes {
287292
}
288293

289294
/// Used in testing
290-
pub fn has_label_string(label: &str) -> bool {
295+
fn has_label_string(label: &str) -> bool {
291296
match label {
292297
$(
293298
stringify!($variant) => true,
@@ -308,35 +313,6 @@ macro_rules! define_dep_nodes {
308313
);
309314
}
310315

311-
impl fmt::Debug for DepNode {
312-
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
313-
write!(f, "{:?}", self.kind)?;
314-
315-
if !self.kind.has_params() && !self.kind.is_anon() {
316-
return Ok(());
317-
}
318-
319-
write!(f, "(")?;
320-
321-
crate::ty::tls::with_opt(|opt_tcx| {
322-
if let Some(tcx) = opt_tcx {
323-
if let Some(def_id) = self.extract_def_id(tcx) {
324-
write!(f, "{}", tcx.def_path_debug_str(def_id))?;
325-
} else if let Some(ref s) = tcx.dep_graph.dep_node_debug_str(*self) {
326-
write!(f, "{}", s)?;
327-
} else {
328-
write!(f, "{}", self.hash)?;
329-
}
330-
} else {
331-
write!(f, "{}", self.hash)?;
332-
}
333-
Ok(())
334-
})?;
335-
336-
write!(f, ")")
337-
}
338-
}
339-
340316
rustc_dep_node_append!([define_dep_nodes!][ <'tcx>
341317
// We use this for most things when incr. comp. is turned off.
342318
[] Null,
@@ -349,58 +325,10 @@ rustc_dep_node_append!([define_dep_nodes!][ <'tcx>
349325
[] CompileCodegenUnit(Symbol),
350326
]);
351327

352-
pub(crate) trait DepNodeParams<'tcx>: fmt::Debug + Sized {
353-
const CAN_RECONSTRUCT_QUERY_KEY: bool;
354-
355-
/// This method turns the parameters of a DepNodeConstructor into an opaque
356-
/// Fingerprint to be used in DepNode.
357-
/// Not all DepNodeParams support being turned into a Fingerprint (they
358-
/// don't need to if the corresponding DepNode is anonymous).
359-
fn to_fingerprint(&self, _: TyCtxt<'tcx>) -> Fingerprint {
360-
panic!("Not implemented. Accidentally called on anonymous node?")
361-
}
362-
363-
fn to_debug_str(&self, _: TyCtxt<'tcx>) -> String {
364-
format!("{:?}", self)
365-
}
366-
367-
/// This method tries to recover the query key from the given `DepNode`,
368-
/// something which is needed when forcing `DepNode`s during red-green
369-
/// evaluation. The query system will only call this method if
370-
/// `CAN_RECONSTRUCT_QUERY_KEY` is `true`.
371-
/// It is always valid to return `None` here, in which case incremental
372-
/// compilation will treat the query as having changed instead of forcing it.
373-
fn recover(tcx: TyCtxt<'tcx>, dep_node: &DepNode) -> Option<Self>;
374-
}
375-
376-
impl<'tcx, T> DepNodeParams<'tcx> for T
377-
where
378-
T: HashStable<StableHashingContext<'tcx>> + fmt::Debug,
379-
{
380-
default const CAN_RECONSTRUCT_QUERY_KEY: bool = false;
381-
382-
default fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
383-
let mut hcx = tcx.create_stable_hashing_context();
384-
let mut hasher = StableHasher::new();
385-
386-
self.hash_stable(&mut hcx, &mut hasher);
387-
388-
hasher.finish()
389-
}
390-
391-
default fn to_debug_str(&self, _: TyCtxt<'tcx>) -> String {
392-
format!("{:?}", *self)
393-
}
394-
395-
default fn recover(_: TyCtxt<'tcx>, _: &DepNode) -> Option<Self> {
396-
None
397-
}
398-
}
399-
400-
impl<'tcx> DepNodeParams<'tcx> for DefId {
328+
impl<'tcx> DepNodeParams<TyCtxt<'tcx>> for DefId {
401329
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;
402330

403-
fn to_fingerprint(&self, tcx: TyCtxt<'_>) -> Fingerprint {
331+
fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
404332
tcx.def_path_hash(*self).0
405333
}
406334

@@ -413,10 +341,10 @@ impl<'tcx> DepNodeParams<'tcx> for DefId {
413341
}
414342
}
415343

416-
impl<'tcx> DepNodeParams<'tcx> for LocalDefId {
344+
impl<'tcx> DepNodeParams<TyCtxt<'tcx>> for LocalDefId {
417345
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;
418346

419-
fn to_fingerprint(&self, tcx: TyCtxt<'_>) -> Fingerprint {
347+
fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
420348
self.to_def_id().to_fingerprint(tcx)
421349
}
422350

@@ -429,10 +357,10 @@ impl<'tcx> DepNodeParams<'tcx> for LocalDefId {
429357
}
430358
}
431359

432-
impl<'tcx> DepNodeParams<'tcx> for CrateNum {
360+
impl<'tcx> DepNodeParams<TyCtxt<'tcx>> for CrateNum {
433361
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;
434362

435-
fn to_fingerprint(&self, tcx: TyCtxt<'_>) -> Fingerprint {
363+
fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
436364
let def_id = DefId { krate: *self, index: CRATE_DEF_INDEX };
437365
tcx.def_path_hash(def_id).0
438366
}
@@ -446,13 +374,13 @@ impl<'tcx> DepNodeParams<'tcx> for CrateNum {
446374
}
447375
}
448376

449-
impl<'tcx> DepNodeParams<'tcx> for (DefId, DefId) {
377+
impl<'tcx> DepNodeParams<TyCtxt<'tcx>> for (DefId, DefId) {
450378
const CAN_RECONSTRUCT_QUERY_KEY: bool = false;
451379

452380
// We actually would not need to specialize the implementation of this
453381
// method but it's faster to combine the hashes than to instantiate a full
454382
// hashing context and stable-hashing state.
455-
fn to_fingerprint(&self, tcx: TyCtxt<'_>) -> Fingerprint {
383+
fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
456384
let (def_id_0, def_id_1) = *self;
457385

458386
let def_path_hash_0 = tcx.def_path_hash(def_id_0);
@@ -468,13 +396,13 @@ impl<'tcx> DepNodeParams<'tcx> for (DefId, DefId) {
468396
}
469397
}
470398

471-
impl<'tcx> DepNodeParams<'tcx> for HirId {
399+
impl<'tcx> DepNodeParams<TyCtxt<'tcx>> for HirId {
472400
const CAN_RECONSTRUCT_QUERY_KEY: bool = false;
473401

474402
// We actually would not need to specialize the implementation of this
475403
// method but it's faster to combine the hashes than to instantiate a full
476404
// hashing context and stable-hashing state.
477-
fn to_fingerprint(&self, tcx: TyCtxt<'_>) -> Fingerprint {
405+
fn to_fingerprint(&self, tcx: TyCtxt<'tcx>) -> Fingerprint {
478406
let HirId { owner, local_id } = *self;
479407

480408
let def_path_hash = tcx.def_path_hash(owner.to_def_id());
@@ -483,27 +411,3 @@ impl<'tcx> DepNodeParams<'tcx> for HirId {
483411
def_path_hash.0.combine(local_id)
484412
}
485413
}
486-
487-
/// A "work product" corresponds to a `.o` (or other) file that we
488-
/// save in between runs. These IDs do not have a `DefId` but rather
489-
/// some independent path or string that persists between runs without
490-
/// the need to be mapped or unmapped. (This ensures we can serialize
491-
/// them even in the absence of a tcx.)
492-
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, RustcEncodable, RustcDecodable)]
493-
#[derive(HashStable)]
494-
pub struct WorkProductId {
495-
hash: Fingerprint,
496-
}
497-
498-
impl WorkProductId {
499-
pub fn from_cgu_name(cgu_name: &str) -> WorkProductId {
500-
let mut hasher = StableHasher::new();
501-
cgu_name.len().hash(&mut hasher);
502-
cgu_name.hash(&mut hasher);
503-
WorkProductId { hash: hasher.finish() }
504-
}
505-
506-
pub fn from_fingerprint(fingerprint: Fingerprint) -> WorkProductId {
507-
WorkProductId { hash: fingerprint }
508-
}
509-
}

0 commit comments

Comments
 (0)