Skip to content
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

introduce canonical queries, use for normalization and dropck-outlives #48411

Merged
merged 27 commits into from
Mar 13, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
f873c1e
require `Lifted` types to outlive `'tcx`
nikomatsakis Feb 14, 2018
23837c1
improve TypeFoldable/Lift macros and make a bunch of stuff use them
nikomatsakis Feb 9, 2018
5ddcd09
add `TypeRelation` and `Lift` impls for `Kind`
nikomatsakis Feb 9, 2018
10ae216
fix typo in comment
nikomatsakis Feb 9, 2018
d0aff85
make regions "traceable" so you can do `infcx.at(..).eq(r1, r2)`
nikomatsakis Feb 9, 2018
0037cca
comment the purpose of `TransNormalize`
nikomatsakis Feb 9, 2018
652b3b7
random reformatting
nikomatsakis Feb 21, 2018
1d377d1
add handy helper for Cell<usize>, used for perf stats
nikomatsakis Feb 20, 2018
6d0f931
refactor `ParamEnv::empty(Reveal)` into two distinct methods
nikomatsakis Feb 10, 2018
64d4ed3
move ParamEnv methods from `ty/util` to `ty/mod`
nikomatsakis Feb 14, 2018
80b4c45
change `ParamEnv::and` to sometimes keep the environment [VIC]
nikomatsakis Feb 20, 2018
993c148
add `canonicalize` method to `InferCtxt` [VIC]
nikomatsakis Feb 9, 2018
8c024fd
in `Foo(X)` dep-nodes, allow X to be a `ty` not a `tt`
nikomatsakis Feb 23, 2018
3a50b41
introduce `infcx.at(..).normalize(..)` operation [VIC]
nikomatsakis Feb 25, 2018
ca87d24
introduce `infcx.at(..).dropck_outlives(..)` operaton [VIC]
nikomatsakis Feb 21, 2018
211d9ad
introduce `tcx.normalize_erasing_regions(..)` operaton [VIC]
nikomatsakis Feb 21, 2018
e4728e4
transition various normalization functions to the new methods
nikomatsakis Mar 3, 2018
0a2ac85
move `drain_fulfillment_cx_or_panic` to be private to traits::trans
nikomatsakis Feb 13, 2018
36e5092
add some debug output
nikomatsakis Feb 26, 2018
1e4e632
add regression tests for various MIR bugs that get fixed
nikomatsakis Feb 27, 2018
03c5428
short-circuit `dropck_outlives` for simple cases
nikomatsakis Mar 7, 2018
0d17f95
short-circuit work when instantiating query responses
nikomatsakis Mar 7, 2018
6288faa
`trans_apply_param_substs` => `subst_and_normalize_erasing_regions`
nikomatsakis Mar 9, 2018
fc04c41
add a debug assertion that only outlives-oblig. result from norm.
nikomatsakis Mar 9, 2018
d326738
replace inline docs with references to rustc-guide
nikomatsakis Mar 11, 2018
29dc902
remove dead code
nikomatsakis Mar 11, 2018
17c4103
add "text" sections for things that seem likely to be a problem
nikomatsakis Mar 11, 2018
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
14 changes: 14 additions & 0 deletions src/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

54 changes: 30 additions & 24 deletions src/librustc/dep_graph/dep_node.rs
Original file line number Diff line number Diff line change
Expand Up @@ -67,11 +67,12 @@ use hir::{HirId, ItemLocalId};

use ich::{Fingerprint, StableHashingContext};
use rustc_data_structures::stable_hasher::{StableHasher, HashStable};
use ty::{TyCtxt, Instance, InstanceDef, ParamEnv, ParamEnvAnd, PolyTraitRef, Ty};
use ty::subst::Substs;
use std::fmt;
use std::hash::Hash;
use syntax_pos::symbol::InternedString;
use traits::query::{CanonicalProjectionGoal, CanonicalTyGoal};
use ty::{TyCtxt, Instance, InstanceDef, ParamEnv, ParamEnvAnd, PolyTraitRef, Ty};
use ty::subst::Substs;

// erase!() just makes tokens go away. It's used to specify which macro argument
// is repeated (i.e. which sub-expression of the macro we are in) but don't need
Expand All @@ -80,6 +81,10 @@ macro_rules! erase {
($x:tt) => ({})
}

macro_rules! replace {
($x:tt with $($y:tt)*) => ($($y)*)
}

macro_rules! is_anon_attr {
(anon) => (true);
($attr:ident) => (false);
Expand Down Expand Up @@ -111,7 +116,7 @@ macro_rules! define_dep_nodes {
(<$tcx:tt>
$(
[$($attr:ident),* ]
$variant:ident $(( $($tuple_arg:tt),* ))*
$variant:ident $(( $tuple_arg_ty:ty $(,)* ))*
$({ $($struct_arg_name:ident : $struct_arg_ty:ty),* })*
,)*
) => (
Expand All @@ -134,7 +139,7 @@ macro_rules! define_dep_nodes {

// tuple args
$({
return <( $($tuple_arg,)* ) as DepNodeParams>
return <$tuple_arg_ty as DepNodeParams>
::CAN_RECONSTRUCT_QUERY_KEY;
})*

Expand Down Expand Up @@ -186,7 +191,7 @@ macro_rules! define_dep_nodes {
DepKind :: $variant => {
// tuple args
$({
$(erase!($tuple_arg);)*
erase!($tuple_arg_ty);
return true;
})*

Expand All @@ -205,7 +210,7 @@ macro_rules! define_dep_nodes {

pub enum DepConstructor<$tcx> {
$(
$variant $(( $($tuple_arg),* ))*
$variant $(( $tuple_arg_ty ))*
$({ $($struct_arg_name : $struct_arg_ty),* })*
),*
}
Expand All @@ -227,15 +232,14 @@ macro_rules! define_dep_nodes {
{
match dep {
$(
DepConstructor :: $variant $(( $($tuple_arg),* ))*
DepConstructor :: $variant $(( replace!(($tuple_arg_ty) with arg) ))*
$({ $($struct_arg_name),* })*
=>
{
// tuple args
$({
let tupled_args = ( $($tuple_arg,)* );
let hash = DepNodeParams::to_fingerprint(&tupled_args,
tcx);
erase!($tuple_arg_ty);
let hash = DepNodeParams::to_fingerprint(&arg, tcx);
let dep_node = DepNode {
kind: DepKind::$variant,
hash
Expand All @@ -247,7 +251,7 @@ macro_rules! define_dep_nodes {
tcx.sess.opts.debugging_opts.query_dep_graph)
{
tcx.dep_graph.register_dep_node_debug_str(dep_node, || {
tupled_args.to_debug_str(tcx)
arg.to_debug_str(tcx)
});
}

Expand Down Expand Up @@ -631,7 +635,9 @@ define_dep_nodes!( <'tcx>
[] CodegenUnit(InternedString),
[] CompileCodegenUnit(InternedString),
[input] OutputFilenames,
[anon] NormalizeTy,
[] NormalizeProjectionTy(CanonicalProjectionGoal<'tcx>),
[] NormalizeTyAfterErasingRegions(ParamEnvAnd<'tcx, Ty<'tcx>>),
[] DropckOutlives(CanonicalTyGoal<'tcx>),

[] SubstituteNormalizeAndTestPredicates { key: (DefId, &'tcx Substs<'tcx>) },

Expand Down Expand Up @@ -679,43 +685,43 @@ impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a, T> DepNodeParams<'a, 'gcx, 'tcx> for T
}
}

impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for (DefId,) {
impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for DefId {
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;

fn to_fingerprint(&self, tcx: TyCtxt) -> Fingerprint {
tcx.def_path_hash(self.0).0
tcx.def_path_hash(*self).0
}

fn to_debug_str(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> String {
tcx.item_path_str(self.0)
tcx.item_path_str(*self)
}
}

impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for (DefIndex,) {
impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for DefIndex {
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;

fn to_fingerprint(&self, tcx: TyCtxt) -> Fingerprint {
tcx.hir.definitions().def_path_hash(self.0).0
tcx.hir.definitions().def_path_hash(*self).0
}

fn to_debug_str(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> String {
tcx.item_path_str(DefId::local(self.0))
tcx.item_path_str(DefId::local(*self))
}
}

impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for (CrateNum,) {
impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for CrateNum {
const CAN_RECONSTRUCT_QUERY_KEY: bool = true;

fn to_fingerprint(&self, tcx: TyCtxt) -> Fingerprint {
let def_id = DefId {
krate: self.0,
krate: *self,
index: CRATE_DEF_INDEX,
};
tcx.def_path_hash(def_id).0
}

fn to_debug_str(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> String {
tcx.crate_name(self.0).as_str().to_string()
tcx.crate_name(*self).as_str().to_string()
}
}

Expand Down Expand Up @@ -743,17 +749,17 @@ impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for (DefId, De
}
}

impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for (HirId,) {
impl<'a, 'gcx: 'tcx + 'a, 'tcx: 'a> DepNodeParams<'a, 'gcx, 'tcx> for HirId {
const CAN_RECONSTRUCT_QUERY_KEY: bool = false;

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

let def_path_hash = tcx.def_path_hash(DefId::local(owner));
let local_id = Fingerprint::from_smaller_hash(local_id as u64);
Expand Down
65 changes: 57 additions & 8 deletions src/librustc/ich/impls_ty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ use std::cell::RefCell;
use std::hash as std_hash;
use std::mem;
use middle::region;
use infer;
use traits;
use ty;
use mir;
Expand Down Expand Up @@ -85,6 +86,9 @@ for ty::RegionKind {
ty::ReEmpty => {
// No variant fields to hash for these ...
}
ty::ReCanonical(c) => {
c.hash_stable(hcx, hasher);
}
ty::ReLateBound(db, ty::BrAnon(i)) => {
db.depth.hash_stable(hcx, hasher);
i.hash_stable(hcx, hasher);
Expand Down Expand Up @@ -130,6 +134,16 @@ impl<'a> HashStable<StableHashingContext<'a>> for ty::RegionVid {
}
}

impl<'gcx> HashStable<StableHashingContext<'gcx>> for ty::CanonicalVar {
#[inline]
fn hash_stable<W: StableHasherResult>(&self,
hcx: &mut StableHashingContext<'gcx>,
hasher: &mut StableHasher<W>) {
use rustc_data_structures::indexed_vec::Idx;
self.index().hash_stable(hcx, hasher);
}
}

impl<'a, 'gcx> HashStable<StableHashingContext<'a>>
for ty::adjustment::AutoBorrow<'gcx> {
fn hash_stable<W: StableHasherResult>(&self,
Expand Down Expand Up @@ -1003,12 +1017,6 @@ impl_stable_hash_for!(struct ty::Destructor {
did
});

impl_stable_hash_for!(struct ty::DtorckConstraint<'tcx> {
outlives,
dtorck_types
});


impl<'a> HashStable<StableHashingContext<'a>> for ty::CrateVariancesMap {
fn hash_stable<W: StableHasherResult>(&self,
hcx: &mut StableHashingContext<'a>,
Expand Down Expand Up @@ -1229,11 +1237,52 @@ for traits::VtableGeneratorData<'gcx, N> where N: HashStable<StableHashingContex
}
}

impl<'gcx> HashStable<StableHashingContext<'gcx>>
impl<'a> HashStable<StableHashingContext<'a>>
for ty::UniverseIndex {
fn hash_stable<W: StableHasherResult>(&self,
hcx: &mut StableHashingContext<'gcx>,
hcx: &mut StableHashingContext<'a>,
hasher: &mut StableHasher<W>) {
self.depth().hash_stable(hcx, hasher);
}
}

impl_stable_hash_for!(
impl<'tcx, V> for struct infer::canonical::Canonical<'tcx, V> {
variables, value
}
);

impl_stable_hash_for!(
impl<'tcx> for struct infer::canonical::CanonicalVarValues<'tcx> {
var_values
}
);

impl_stable_hash_for!(struct infer::canonical::CanonicalVarInfo {
kind
});

impl_stable_hash_for!(enum infer::canonical::CanonicalVarKind {
Ty(k),
Region
});

impl_stable_hash_for!(enum infer::canonical::CanonicalTyVarKind {
General,
Int,
Float
});

impl_stable_hash_for!(
impl<'tcx, R> for struct infer::canonical::QueryResult<'tcx, R> {
var_values, region_constraints, certainty, value
}
);

impl_stable_hash_for!(struct infer::canonical::QueryRegionConstraints<'tcx> {
region_outlives, ty_outlives
});

impl_stable_hash_for!(enum infer::canonical::Certainty {
Proven, Ambiguous
});
20 changes: 17 additions & 3 deletions src/librustc/infer/at.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,9 +40,9 @@ use super::*;
use ty::relate::{Relate, TypeRelation};

pub struct At<'a, 'gcx: 'tcx, 'tcx: 'a> {
infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
cause: &'a ObligationCause<'tcx>,
param_env: ty::ParamEnv<'tcx>,
pub infcx: &'a InferCtxt<'a, 'gcx, 'tcx>,
pub cause: &'a ObligationCause<'tcx>,
pub param_env: ty::ParamEnv<'tcx>,
}

pub struct Trace<'a, 'gcx: 'tcx, 'tcx: 'a> {
Expand Down Expand Up @@ -281,6 +281,20 @@ impl<'tcx> ToTrace<'tcx> for Ty<'tcx> {
}
}

impl<'tcx> ToTrace<'tcx> for ty::Region<'tcx> {
fn to_trace(cause: &ObligationCause<'tcx>,
a_is_expected: bool,
a: Self,
b: Self)
-> TypeTrace<'tcx>
{
TypeTrace {
cause: cause.clone(),
values: Regions(ExpectedFound::new(a_is_expected, a, b))
}
}
}

impl<'tcx> ToTrace<'tcx> for ty::TraitRef<'tcx> {
fn to_trace(cause: &ObligationCause<'tcx>,
a_is_expected: bool,
Expand Down
Loading