diff --git a/src/librustc/dep_graph/dep_node.rs b/src/librustc/dep_graph/dep_node.rs index 0c941a4a2301f..e261c699b6ac6 100644 --- a/src/librustc/dep_graph/dep_node.rs +++ b/src/librustc/dep_graph/dep_node.rs @@ -110,7 +110,6 @@ pub enum DepNode { // predicates for an item wind up in `ItemSignature`). AssociatedItems(D), ItemSignature(D), - FieldTy(D), SizedConstraint(D), AssociatedItemDefIds(D), InherentImpls(D), @@ -161,7 +160,6 @@ impl DepNode { TypeckItemBody, AssociatedItems, ItemSignature, - FieldTy, AssociatedItemDefIds, InherentImpls, TraitImpls, @@ -229,7 +227,6 @@ impl DepNode { TransInlinedItem(ref d) => op(d).map(TransInlinedItem), AssociatedItems(ref d) => op(d).map(AssociatedItems), ItemSignature(ref d) => op(d).map(ItemSignature), - FieldTy(ref d) => op(d).map(FieldTy), SizedConstraint(ref d) => op(d).map(SizedConstraint), AssociatedItemDefIds(ref d) => op(d).map(AssociatedItemDefIds), InherentImpls(ref d) => op(d).map(InherentImpls), diff --git a/src/librustc/middle/cstore.rs b/src/librustc/middle/cstore.rs index 484e2f1535e7a..822fb4d6770f0 100644 --- a/src/librustc/middle/cstore.rs +++ b/src/librustc/middle/cstore.rs @@ -278,8 +278,8 @@ pub trait CrateStore<'tcx> { fn item_generics<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::Generics<'tcx>; fn item_attrs(&self, def_id: DefId) -> Vec; - fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId)-> ty::TraitDef<'tcx>; - fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::AdtDefMaster<'tcx>; + fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId)-> ty::TraitDef; + fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> &'tcx ty::AdtDef; fn fn_arg_names(&self, did: DefId) -> Vec; fn inherent_implementations_for_type(&self, def_id: DefId) -> Vec; @@ -425,9 +425,9 @@ impl<'tcx> CrateStore<'tcx> for DummyCrateStore { fn item_generics<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::Generics<'tcx> { bug!("item_generics") } fn item_attrs(&self, def_id: DefId) -> Vec { bug!("item_attrs") } - fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId)-> ty::TraitDef<'tcx> + fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId)-> ty::TraitDef { bug!("trait_def") } - fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::AdtDefMaster<'tcx> + fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> &'tcx ty::AdtDef { bug!("adt_def") } fn fn_arg_names(&self, did: DefId) -> Vec { bug!("fn_arg_names") } fn inherent_implementations_for_type(&self, def_id: DefId) -> Vec { vec![] } diff --git a/src/librustc/middle/expr_use_visitor.rs b/src/librustc/middle/expr_use_visitor.rs index 01d5792441f82..b3e61f1e57067 100644 --- a/src/librustc/middle/expr_use_visitor.rs +++ b/src/librustc/middle/expr_use_visitor.rs @@ -701,7 +701,7 @@ impl<'a, 'gcx, 'tcx> ExprUseVisitor<'a, 'gcx, 'tcx> { // are properly handled. self.walk_expr(with_expr); - fn contains_field_named(field: ty::FieldDef, + fn contains_field_named(field: &ty::FieldDef, fields: &[hir::Field]) -> bool { diff --git a/src/librustc/mir/mod.rs b/src/librustc/mir/mod.rs index b3cec6ec8ff3f..3cd3580473292 100644 --- a/src/librustc/mir/mod.rs +++ b/src/librustc/mir/mod.rs @@ -462,7 +462,7 @@ pub enum TerminatorKind<'tcx> { /// lvalue evaluates to some enum; jump depending on the branch Switch { discr: Lvalue<'tcx>, - adt_def: AdtDef<'tcx>, + adt_def: &'tcx AdtDef, targets: Vec, }, @@ -866,7 +866,7 @@ pub enum ProjectionElem<'tcx, V> { /// "Downcast" to a variant of an ADT. Currently, we only introduce /// this for ADTs with more than one variant. It may be better to /// just introduce it always, or always for enums. - Downcast(AdtDef<'tcx>, usize), + Downcast(&'tcx AdtDef, usize), } /// Alias for projections as they appear in lvalues, where the base is an lvalue @@ -1035,7 +1035,7 @@ pub enum AggregateKind<'tcx> { /// The second field is variant number (discriminant), it's equal to 0 /// for struct and union expressions. The fourth field is active field /// number and is present only for union expressions. - Adt(AdtDef<'tcx>, usize, &'tcx Substs<'tcx>, Option), + Adt(&'tcx AdtDef, usize, &'tcx Substs<'tcx>, Option), Closure(DefId, ClosureSubsts<'tcx>), } diff --git a/src/librustc/mir/tcx.rs b/src/librustc/mir/tcx.rs index 73ea84e94aec5..03530945e046d 100644 --- a/src/librustc/mir/tcx.rs +++ b/src/librustc/mir/tcx.rs @@ -25,7 +25,7 @@ pub enum LvalueTy<'tcx> { Ty { ty: Ty<'tcx> }, /// Downcast to a particular variant of an enum. - Downcast { adt_def: AdtDef<'tcx>, + Downcast { adt_def: &'tcx AdtDef, substs: &'tcx Substs<'tcx>, variant_index: usize }, } diff --git a/src/librustc/traits/error_reporting.rs b/src/librustc/traits/error_reporting.rs index 2e8e45468ddcb..76a5e2764f264 100644 --- a/src/librustc/traits/error_reporting.rs +++ b/src/librustc/traits/error_reporting.rs @@ -244,11 +244,11 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> { for item in self.tcx.get_attrs(def_id).iter() { if item.check_name("rustc_on_unimplemented") { let err_sp = item.meta().span.substitute_dummy(span); - let def = self.tcx.lookup_trait_def(trait_ref.def_id); - let trait_str = def.trait_ref.to_string(); + let trait_str = self.tcx.item_path_str(trait_ref.def_id); if let Some(istring) = item.value_str() { let istring = &*istring.as_str(); - let generic_map = def.generics.types.iter().map(|param| { + let generics = self.tcx.item_generics(trait_ref.def_id); + let generic_map = generics.types.iter().map(|param| { (param.name.as_str().to_string(), trait_ref.substs.type_for_def(param).to_string()) }).collect::>(); diff --git a/src/librustc/traits/object_safety.rs b/src/librustc/traits/object_safety.rs index 0681be129b67e..ceee6c236e4e3 100644 --- a/src/librustc/traits/object_safety.rs +++ b/src/librustc/traits/object_safety.rs @@ -21,7 +21,8 @@ use super::elaborate_predicates; use hir::def_id::DefId; use traits; -use ty::{self, ToPolyTraitRef, Ty, TyCtxt, TypeFoldable}; +use ty::{self, Ty, TyCtxt, TypeFoldable}; +use ty::subst::Substs; use syntax::ast; #[derive(Clone, Debug, PartialEq, Eq, Hash)] @@ -126,9 +127,10 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } fn supertraits_reference_self(self, trait_def_id: DefId) -> bool { - let trait_def = self.lookup_trait_def(trait_def_id); - let trait_ref = trait_def.trait_ref.clone(); - let trait_ref = trait_ref.to_poly_trait_ref(); + let trait_ref = ty::Binder(ty::TraitRef { + def_id: trait_def_id, + substs: Substs::identity_for_item(self, trait_def_id) + }); let predicates = self.item_super_predicates(trait_def_id); predicates .predicates @@ -317,8 +319,10 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { // Compute supertraits of current trait lazily. if supertraits.is_none() { - let trait_def = self.lookup_trait_def(trait_def_id); - let trait_ref = ty::Binder(trait_def.trait_ref.clone()); + let trait_ref = ty::Binder(ty::TraitRef { + def_id: trait_def_id, + substs: Substs::identity_for_item(self, trait_def_id) + }); supertraits = Some(traits::supertraits(self, trait_ref).collect()); } diff --git a/src/librustc/traits/select.rs b/src/librustc/traits/select.rs index 38a228034dd05..c54c0bf74ef7a 100644 --- a/src/librustc/traits/select.rs +++ b/src/librustc/traits/select.rs @@ -2544,7 +2544,7 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> { (&ty::TyAdt(def, substs_a), &ty::TyAdt(_, substs_b)) => { let fields = def .all_fields() - .map(|f| f.unsubst_ty()) + .map(|f| tcx.item_type(f.did)) .collect::>(); // The last field of the structure has to exist and contain type parameters. diff --git a/src/librustc/traits/specialize/specialization_graph.rs b/src/librustc/traits/specialize/specialization_graph.rs index 5a6809f1fad68..a41523f2def76 100644 --- a/src/librustc/traits/specialize/specialization_graph.rs +++ b/src/librustc/traits/specialize/specialization_graph.rs @@ -297,18 +297,18 @@ impl<'a, 'gcx, 'tcx> Node { } } -pub struct Ancestors<'a, 'tcx: 'a> { - trait_def: &'a TraitDef<'tcx>, +pub struct Ancestors<'a> { + trait_def: &'a TraitDef, current_source: Option, } -impl<'a, 'tcx> Iterator for Ancestors<'a, 'tcx> { +impl<'a> Iterator for Ancestors<'a> { type Item = Node; fn next(&mut self) -> Option { let cur = self.current_source.take(); if let Some(Node::Impl(cur_impl)) = cur { let parent = self.trait_def.specialization_graph.borrow().parent(cur_impl); - if parent == self.trait_def.def_id() { + if parent == self.trait_def.def_id { self.current_source = Some(Node::Trait(parent)); } else { self.current_source = Some(Node::Impl(parent)); @@ -332,7 +332,7 @@ impl NodeItem { } } -impl<'a, 'gcx, 'tcx> Ancestors<'a, 'tcx> { +impl<'a, 'gcx, 'tcx> Ancestors<'a> { /// Search the items from the given ancestors, returning each definition /// with the given name and the given kind. #[inline] // FIXME(#35870) Avoid closures being unexported due to impl Trait. @@ -347,9 +347,7 @@ impl<'a, 'gcx, 'tcx> Ancestors<'a, 'tcx> { /// Walk up the specialization ancestors of a given impl, starting with that /// impl itself. -pub fn ancestors<'a, 'tcx>(trait_def: &'a TraitDef<'tcx>, - start_from_impl: DefId) - -> Ancestors<'a, 'tcx> { +pub fn ancestors<'a>(trait_def: &'a TraitDef, start_from_impl: DefId) -> Ancestors<'a> { Ancestors { trait_def: trait_def, current_source: Some(Node::Impl(start_from_impl)), diff --git a/src/librustc/ty/context.rs b/src/librustc/ty/context.rs index c23ee489a28f4..17c335fc9c72f 100644 --- a/src/librustc/ty/context.rs +++ b/src/librustc/ty/context.rs @@ -68,8 +68,8 @@ pub struct CtxtArenas<'tcx> { // references generics: TypedArena>, - trait_def: TypedArena>, - adt_def: TypedArena>, + trait_def: TypedArena, + adt_def: TypedArena, mir: TypedArena>>, } @@ -425,6 +425,7 @@ pub struct GlobalCtxt<'tcx> { pub impl_trait_refs: RefCell>>, pub trait_defs: RefCell>>, pub adt_defs: RefCell>>, + pub adt_sized_constraint: RefCell>>, /// Maps from the def-id of an item (trait/struct/enum/fn) to its /// associated generics and predicates. @@ -688,38 +689,17 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.global_interners.arenas.mir.alloc(RefCell::new(mir)) } - pub fn intern_trait_def(self, def: ty::TraitDef<'gcx>) - -> &'gcx ty::TraitDef<'gcx> { - let did = def.trait_ref.def_id; - let interned = self.alloc_trait_def(def); - if let Some(prev) = self.trait_defs.borrow_mut().insert(did, interned) { - bug!("Tried to overwrite interned TraitDef: {:?}", prev) - } - self.generics.borrow_mut().insert(did, interned.generics); - interned - } - - pub fn alloc_trait_def(self, def: ty::TraitDef<'gcx>) - -> &'gcx ty::TraitDef<'gcx> { + pub fn alloc_trait_def(self, def: ty::TraitDef) -> &'gcx ty::TraitDef { self.global_interners.arenas.trait_def.alloc(def) } - pub fn insert_adt_def(self, did: DefId, adt_def: ty::AdtDefMaster<'gcx>) { - // this will need a transmute when reverse-variance is removed - if let Some(prev) = self.adt_defs.borrow_mut().insert(did, adt_def) { - bug!("Tried to overwrite interned AdtDef: {:?}", prev) - } - } - - pub fn intern_adt_def(self, - did: DefId, - kind: AdtKind, - variants: Vec>) - -> ty::AdtDefMaster<'gcx> { - let def = ty::AdtDefData::new(self, did, kind, variants); - let interned = self.global_interners.arenas.adt_def.alloc(def); - self.insert_adt_def(did, interned); - interned + pub fn alloc_adt_def(self, + did: DefId, + kind: AdtKind, + variants: Vec) + -> &'gcx ty::AdtDef { + let def = ty::AdtDef::new(self, did, kind, variants); + self.global_interners.arenas.adt_def.alloc(def) } pub fn intern_stability(self, stab: attr::Stability) -> &'gcx attr::Stability { @@ -815,6 +795,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { impl_trait_refs: RefCell::new(DepTrackingMap::new(dep_graph.clone())), trait_defs: RefCell::new(DepTrackingMap::new(dep_graph.clone())), adt_defs: RefCell::new(DepTrackingMap::new(dep_graph.clone())), + adt_sized_constraint: RefCell::new(DepTrackingMap::new(dep_graph.clone())), generics: RefCell::new(DepTrackingMap::new(dep_graph.clone())), predicates: RefCell::new(DepTrackingMap::new(dep_graph.clone())), super_predicates: RefCell::new(DepTrackingMap::new(dep_graph.clone())), @@ -1392,7 +1373,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { self.mk_imm_ref(self.mk_region(ty::ReStatic), self.mk_str()) } - pub fn mk_adt(self, def: AdtDef<'tcx>, substs: &'tcx Substs<'tcx>) -> Ty<'tcx> { + pub fn mk_adt(self, def: &'tcx AdtDef, substs: &'tcx Substs<'tcx>) -> Ty<'tcx> { // take a copy of substs so that we own the vectors inside self.mk_ty(TyAdt(def, substs)) } diff --git a/src/librustc/ty/ivar.rs b/src/librustc/ty/ivar.rs deleted file mode 100644 index 634599406afb2..0000000000000 --- a/src/librustc/ty/ivar.rs +++ /dev/null @@ -1,90 +0,0 @@ -// Copyright 2015 The Rust Project Developers. See the COPYRIGHT -// file at the top-level directory of this distribution and at -// http://rust-lang.org/COPYRIGHT. -// -// Licensed under the Apache License, Version 2.0 or the MIT license -// , at your -// option. This file may not be copied, modified, or distributed -// except according to those terms. - -use dep_graph::DepNode; -use hir::def_id::DefId; -use ty::{Ty, TyS}; -use ty::tls; - -use rustc_data_structures::ivar; - -use std::fmt; -use std::marker::PhantomData; -use core::nonzero::NonZero; - -/// An IVar that contains a Ty. 'lt is a (reverse-variant) upper bound -/// on the lifetime of the IVar. This is required because of variance -/// problems: the IVar needs to be variant with respect to 'tcx (so -/// it can be referred to from Ty) but can only be modified if its -/// lifetime is exactly 'tcx. -/// -/// Safety invariants: -/// (A) self.0, if fulfilled, is a valid Ty<'tcx> -/// (B) no aliases to this value with a 'tcx longer than this -/// value's 'lt exist -/// -/// Dependency tracking: each ivar does not know what node in the -/// dependency graph it is associated with, so when you get/fulfill -/// you must supply a `DepNode` id. This should always be the same id! -/// -/// NonZero is used rather than Unique because Unique isn't Copy. -pub struct TyIVar<'tcx, 'lt: 'tcx>(ivar::Ivar>>, - PhantomData)->TyS<'tcx>>); - -impl<'tcx, 'lt> TyIVar<'tcx, 'lt> { - #[inline] - pub fn new() -> Self { - // Invariant (A) satisfied because the IVar is unfulfilled - // Invariant (B) because 'lt : 'tcx - TyIVar(ivar::Ivar::new(), PhantomData) - } - - #[inline] - pub fn get(&self, dep_node: DepNode) -> Option> { - tls::with(|tcx| tcx.dep_graph.read(dep_node)); - self.untracked_get() - } - - /// Reads the ivar without registered a dep-graph read. Use with - /// caution. - #[inline] - pub fn untracked_get(&self) -> Option> { - match self.0.get() { - None => None, - // valid because of invariant (A) - Some(v) => Some(unsafe { &*(*v as *const TyS<'tcx>) }) - } - } - - #[inline] - pub fn unwrap(&self, dep_node: DepNode) -> Ty<'tcx> { - self.get(dep_node).unwrap() - } - - pub fn fulfill(&self, dep_node: DepNode, value: Ty<'lt>) { - tls::with(|tcx| tcx.dep_graph.write(dep_node)); - - // Invariant (A) is fulfilled, because by (B), every alias - // of this has a 'tcx longer than 'lt. - let value: *const TyS<'lt> = value; - // FIXME(27214): unneeded [as *const ()] - let value = value as *const () as *const TyS<'static>; - self.0.fulfill(unsafe { NonZero::new(value) }) - } -} - -impl<'tcx, 'lt> fmt::Debug for TyIVar<'tcx, 'lt> { - fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - match self.untracked_get() { - Some(val) => write!(f, "TyIVar({:?})", val), - None => f.write_str("TyIVar()") - } - } -} diff --git a/src/librustc/ty/maps.rs b/src/librustc/ty/maps.rs index bf0445858794e..42b3544421f8b 100644 --- a/src/librustc/ty/maps.rs +++ b/src/librustc/ty/maps.rs @@ -39,8 +39,9 @@ dep_map_ty! { Predicates: ItemSignature(DefId) -> ty::GenericPredicates<'tcx> } dep_map_ty! { SuperPredicates: ItemSignature(DefId) -> ty::GenericPredicates<'tcx> } dep_map_ty! { AssociatedItemDefIds: AssociatedItemDefIds(DefId) -> Rc> } dep_map_ty! { ImplTraitRefs: ItemSignature(DefId) -> Option> } -dep_map_ty! { TraitDefs: ItemSignature(DefId) -> &'tcx ty::TraitDef<'tcx> } -dep_map_ty! { AdtDefs: ItemSignature(DefId) -> ty::AdtDefMaster<'tcx> } +dep_map_ty! { TraitDefs: ItemSignature(DefId) -> &'tcx ty::TraitDef } +dep_map_ty! { AdtDefs: ItemSignature(DefId) -> &'tcx ty::AdtDef } +dep_map_ty! { AdtSizedConstraint: SizedConstraint(DefId) -> Ty<'tcx> } dep_map_ty! { ItemVariances: ItemSignature(DefId) -> Rc> } dep_map_ty! { InherentImpls: InherentImpls(DefId) -> Vec } dep_map_ty! { ReprHints: ReprHints(DefId) -> Rc> } diff --git a/src/librustc/ty/mod.rs b/src/librustc/ty/mod.rs index 3ce092db482c4..df12c252907a5 100644 --- a/src/librustc/ty/mod.rs +++ b/src/librustc/ty/mod.rs @@ -93,7 +93,6 @@ pub mod util; mod contents; mod context; mod flags; -mod ivar; mod structural_impls; mod sty; @@ -623,10 +622,6 @@ pub struct RegionParameterDef<'tcx> { } impl<'tcx> RegionParameterDef<'tcx> { - pub fn to_early_bound_region(&self) -> ty::Region { - ty::ReEarlyBound(self.to_early_bound_region_data()) - } - pub fn to_early_bound_region_data(&self) -> ty::EarlyBoundRegion { ty::EarlyBoundRegion { index: self.index, @@ -1313,106 +1308,64 @@ bitflags! { } } -pub type AdtDef<'tcx> = &'tcx AdtDefData<'tcx, 'static>; -pub type VariantDef<'tcx> = &'tcx VariantDefData<'tcx, 'static>; -pub type FieldDef<'tcx> = &'tcx FieldDefData<'tcx, 'static>; - -// See comment on AdtDefData for explanation -pub type AdtDefMaster<'tcx> = &'tcx AdtDefData<'tcx, 'tcx>; -pub type VariantDefMaster<'tcx> = &'tcx VariantDefData<'tcx, 'tcx>; -pub type FieldDefMaster<'tcx> = &'tcx FieldDefData<'tcx, 'tcx>; - -pub struct VariantDefData<'tcx, 'container: 'tcx> { +pub struct VariantDef { /// The variant's DefId. If this is a tuple-like struct, /// this is the DefId of the struct's ctor. pub did: DefId, pub name: Name, // struct's name if this is a struct pub disr_val: Disr, - pub fields: Vec>, + pub fields: Vec, pub ctor_kind: CtorKind, } -pub struct FieldDefData<'tcx, 'container: 'tcx> { +pub struct FieldDef { pub did: DefId, pub name: Name, pub vis: Visibility, - /// TyIVar is used here to allow for variance (see the doc at - /// AdtDefData). - /// - /// Note: direct accesses to `ty` must also add dep edges. - ty: ivar::TyIVar<'tcx, 'container> } /// The definition of an abstract data type - a struct or enum. /// /// These are all interned (by intern_adt_def) into the adt_defs /// table. -/// -/// Because of the possibility of nested tcx-s, this type -/// needs 2 lifetimes: the traditional variant lifetime ('tcx) -/// bounding the lifetime of the inner types is of course necessary. -/// However, it is not sufficient - types from a child tcx must -/// not be leaked into the master tcx by being stored in an AdtDefData. -/// -/// The 'container lifetime ensures that by outliving the container -/// tcx and preventing shorter-lived types from being inserted. When -/// write access is not needed, the 'container lifetime can be -/// erased to 'static, which can be done by the AdtDef wrapper. -pub struct AdtDefData<'tcx, 'container: 'tcx> { +pub struct AdtDef { pub did: DefId, - pub variants: Vec>, + pub variants: Vec, destructor: Cell>, - flags: Cell, - sized_constraint: ivar::TyIVar<'tcx, 'container>, + flags: Cell } -impl<'tcx, 'container> PartialEq for AdtDefData<'tcx, 'container> { - // AdtDefData are always interned and this is part of TyS equality +impl PartialEq for AdtDef { + // AdtDef are always interned and this is part of TyS equality #[inline] fn eq(&self, other: &Self) -> bool { self as *const _ == other as *const _ } } -impl<'tcx, 'container> Eq for AdtDefData<'tcx, 'container> {} +impl Eq for AdtDef {} -impl<'tcx, 'container> Hash for AdtDefData<'tcx, 'container> { +impl Hash for AdtDef { #[inline] fn hash(&self, s: &mut H) { - (self as *const AdtDefData).hash(s) + (self as *const AdtDef).hash(s) } } -impl<'tcx> serialize::UseSpecializedEncodable for AdtDef<'tcx> { +impl<'tcx> serialize::UseSpecializedEncodable for &'tcx AdtDef { fn default_encode(&self, s: &mut S) -> Result<(), S::Error> { self.did.encode(s) } } -impl<'tcx> serialize::UseSpecializedDecodable for AdtDef<'tcx> {} - -impl<'a, 'gcx, 'tcx> AdtDefData<'tcx, 'static> { - #[inline] - pub fn is_uninhabited_recurse(&'tcx self, - visited: &mut FxHashSet<(DefId, &'tcx Substs<'tcx>)>, - block: Option, - cx: TyCtxt<'a, 'gcx, 'tcx>, - substs: &'tcx Substs<'tcx>) -> bool { - if !visited.insert((self.did, substs)) { - return false; - }; - self.variants.iter().all(|v| { - v.is_uninhabited_recurse(visited, block, cx, substs, self.is_union()) - }) - } -} +impl<'tcx> serialize::UseSpecializedDecodable for &'tcx AdtDef {} #[derive(Copy, Clone, Debug, Eq, PartialEq)] pub enum AdtKind { Struct, Union, Enum } -impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { +impl<'a, 'gcx, 'tcx> AdtDef { fn new(tcx: TyCtxt<'a, 'gcx, 'tcx>, did: DefId, kind: AdtKind, - variants: Vec>) -> Self { + variants: Vec) -> Self { let mut flags = AdtFlags::NO_ADT_FLAGS; let attrs = tcx.get_attrs(did); if attr::contains_name(&attrs, "fundamental") { @@ -1429,12 +1382,11 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { AdtKind::Union => flags = flags | AdtFlags::IS_UNION, AdtKind::Struct => {} } - AdtDefData { + AdtDef { did: did, variants: variants, flags: Cell::new(flags), destructor: Cell::new(None), - sized_constraint: ivar::TyIVar::new(), } } @@ -1445,6 +1397,20 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { self.flags.set(self.flags.get() | AdtFlags::IS_DTORCK_VALID) } + #[inline] + pub fn is_uninhabited_recurse(&self, + visited: &mut FxHashSet<(DefId, &'tcx Substs<'tcx>)>, + block: Option, + tcx: TyCtxt<'a, 'gcx, 'tcx>, + substs: &'tcx Substs<'tcx>) -> bool { + if !visited.insert((self.did, substs)) { + return false; + }; + self.variants.iter().all(|v| { + v.is_uninhabited_recurse(visited, block, tcx, substs, self.is_union()) + }) + } + #[inline] pub fn is_struct(&self) -> bool { !self.is_union() && !self.is_enum() @@ -1524,7 +1490,7 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { /// Asserts this is a struct and returns the struct's unique /// variant. - pub fn struct_variant(&self) -> &VariantDefData<'gcx, 'container> { + pub fn struct_variant(&self) -> &VariantDef { assert!(!self.is_enum()); &self.variants[0] } @@ -1537,14 +1503,8 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { /// Returns an iterator over all fields contained /// by this ADT. #[inline] - pub fn all_fields(&self) -> - iter::FlatMap< - slice::Iter>, - slice::Iter>, - for<'s> fn(&'s VariantDefData<'gcx, 'container>) - -> slice::Iter<'s, FieldDefData<'gcx, 'container>> - > { - self.variants.iter().flat_map(VariantDefData::fields_iter) + pub fn all_fields<'s>(&'s self) -> impl Iterator { + self.variants.iter().flat_map(|v| v.fields.iter()) } #[inline] @@ -1557,7 +1517,7 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { self.variants.iter().all(|v| v.fields.is_empty()) } - pub fn variant_with_id(&self, vid: DefId) -> &VariantDefData<'gcx, 'container> { + pub fn variant_with_id(&self, vid: DefId) -> &VariantDef { self.variants .iter() .find(|v| v.did == vid) @@ -1571,7 +1531,7 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { .expect("variant_index_with_id: unknown variant") } - pub fn variant_of_def(&self, def: Def) -> &VariantDefData<'gcx, 'container> { + pub fn variant_of_def(&self, def: Def) -> &VariantDef { match def { Def::Variant(vid) | Def::VariantCtor(vid, ..) => self.variant_with_id(vid), Def::Struct(..) | Def::StructCtor(..) | Def::Union(..) | @@ -1594,9 +1554,7 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> { None => NoDtor, } } -} -impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'tcx, 'container> { /// Returns a simpler type such that `Self: Sized` if and only /// if that type is Sized, or `TyErr` if this type is recursive. /// @@ -1615,19 +1573,9 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'tcx, 'container> { /// Due to normalization being eager, this applies even if /// the associated type is behind a pointer, e.g. issue #31299. pub fn sized_constraint(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) -> Ty<'tcx> { - match self.sized_constraint.get(DepNode::SizedConstraint(self.did)) { - None => { - let global_tcx = tcx.global_tcx(); - let this = global_tcx.lookup_adt_def_master(self.did); - this.calculate_sized_constraint_inner(global_tcx, &mut Vec::new()); - self.sized_constraint(tcx) - } - Some(ty) => ty - } + self.calculate_sized_constraint_inner(tcx.global_tcx(), &mut Vec::new()) } -} -impl<'a, 'tcx> AdtDefData<'tcx, 'tcx> { /// Calculates the Sized-constraint. /// /// As the Sized-constraint of enums can be a *set* of types, @@ -1643,42 +1591,41 @@ impl<'a, 'tcx> AdtDefData<'tcx, 'tcx> { /// such. /// - a TyError, if a type contained itself. The representability /// check should catch this case. - fn calculate_sized_constraint_inner(&'tcx self, + fn calculate_sized_constraint_inner(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, - stack: &mut Vec>) + stack: &mut Vec) + -> Ty<'tcx> { - let dep_node = || DepNode::SizedConstraint(self.did); + if let Some(ty) = tcx.adt_sized_constraint.borrow().get(&self.did) { + return ty; + } // Follow the memoization pattern: push the computation of // DepNode::SizedConstraint as our current task. - let _task = tcx.dep_graph.in_task(dep_node()); - if self.sized_constraint.untracked_get().is_some() { - // --------------- - // can skip the dep-graph read since we just pushed the task - return; - } + let _task = tcx.dep_graph.in_task(DepNode::SizedConstraint(self.did)); - if stack.contains(&self) { + if stack.contains(&self.did) { debug!("calculate_sized_constraint: {:?} is recursive", self); // This should be reported as an error by `check_representable`. // // Consider the type as Sized in the meanwhile to avoid // further errors. - self.sized_constraint.fulfill(dep_node(), tcx.types.err); - return; + tcx.adt_sized_constraint.borrow_mut().insert(self.did, tcx.types.err); + return tcx.types.err; } - stack.push(self); + stack.push(self.did); let tys : Vec<_> = self.variants.iter().flat_map(|v| { v.fields.last() }).flat_map(|f| { - self.sized_constraint_for_ty(tcx, stack, f.unsubst_ty()) + let ty = tcx.item_type(f.did); + self.sized_constraint_for_ty(tcx, stack, ty) }).collect(); let self_ = stack.pop().unwrap(); - assert_eq!(self_, self); + assert_eq!(self_, self.did); let ty = match tys.len() { _ if tys.references_error() => tcx.types.err, @@ -1687,24 +1634,26 @@ impl<'a, 'tcx> AdtDefData<'tcx, 'tcx> { _ => tcx.intern_tup(&tys[..]) }; - match self.sized_constraint.get(dep_node()) { + let old = tcx.adt_sized_constraint.borrow().get(&self.did).cloned(); + match old { Some(old_ty) => { debug!("calculate_sized_constraint: {:?} recurred", self); - assert_eq!(old_ty, tcx.types.err) + assert_eq!(old_ty, tcx.types.err); + old_ty } None => { debug!("calculate_sized_constraint: {:?} => {:?}", self, ty); - self.sized_constraint.fulfill(dep_node(), ty) + tcx.adt_sized_constraint.borrow_mut().insert(self.did, ty); + ty } } } - fn sized_constraint_for_ty( - &'tcx self, - tcx: TyCtxt<'a, 'tcx, 'tcx>, - stack: &mut Vec>, - ty: Ty<'tcx> - ) -> Vec> { + fn sized_constraint_for_ty(&self, + tcx: TyCtxt<'a, 'tcx, 'tcx>, + stack: &mut Vec, + ty: Ty<'tcx>) + -> Vec> { let result = match ty.sty { TyBool | TyChar | TyInt(..) | TyUint(..) | TyFloat(..) | TyBox(..) | TyRawPtr(..) | TyRef(..) | TyFnDef(..) | TyFnPtr(_) | @@ -1726,12 +1675,9 @@ impl<'a, 'tcx> AdtDefData<'tcx, 'tcx> { TyAdt(adt, substs) => { // recursive case - let adt = tcx.lookup_adt_def_master(adt.did); - adt.calculate_sized_constraint_inner(tcx, stack); let adt_ty = - adt.sized_constraint - .unwrap(DepNode::SizedConstraint(adt.did)) - .subst(tcx, substs); + adt.calculate_sized_constraint_inner(tcx, stack) + .subst(tcx, substs); debug!("sized_constraint_for_ty({:?}) intermediate = {:?}", ty, adt_ty); if let ty::TyTuple(ref tys) = adt_ty.sty { @@ -1780,16 +1726,11 @@ impl<'a, 'tcx> AdtDefData<'tcx, 'tcx> { } } -impl<'tcx, 'container> VariantDefData<'tcx, 'container> { - #[inline] - fn fields_iter(&self) -> slice::Iter> { - self.fields.iter() - } - +impl<'a, 'gcx, 'tcx> VariantDef { #[inline] pub fn find_field_named(&self, name: ast::Name) - -> Option<&FieldDefData<'tcx, 'container>> { + -> Option<&FieldDef> { self.fields.iter().find(|f| f.name == name) } @@ -1801,55 +1742,32 @@ impl<'tcx, 'container> VariantDefData<'tcx, 'container> { } #[inline] - pub fn field_named(&self, name: ast::Name) -> &FieldDefData<'tcx, 'container> { + pub fn field_named(&self, name: ast::Name) -> &FieldDef { self.find_field_named(name).unwrap() } -} -impl<'a, 'gcx, 'tcx> VariantDefData<'tcx, 'static> { #[inline] - pub fn is_uninhabited_recurse(&'tcx self, + pub fn is_uninhabited_recurse(&self, visited: &mut FxHashSet<(DefId, &'tcx Substs<'tcx>)>, block: Option, - cx: TyCtxt<'a, 'gcx, 'tcx>, + tcx: TyCtxt<'a, 'gcx, 'tcx>, substs: &'tcx Substs<'tcx>, is_union: bool) -> bool { if is_union { - self.fields.iter().all(|f| f.is_uninhabited_recurse(visited, block, cx, substs)) + self.fields.iter().all(|f| f.is_uninhabited_recurse(visited, block, tcx, substs)) } else { - self.fields.iter().any(|f| f.is_uninhabited_recurse(visited, block, cx, substs)) + self.fields.iter().any(|f| f.is_uninhabited_recurse(visited, block, tcx, substs)) } } } -impl<'a, 'gcx, 'tcx, 'container> FieldDefData<'tcx, 'container> { - pub fn new(did: DefId, - name: Name, - vis: Visibility) -> Self { - FieldDefData { - did: did, - name: name, - vis: vis, - ty: ivar::TyIVar::new() - } - } - +impl<'a, 'gcx, 'tcx> FieldDef { pub fn ty(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, subst: &Substs<'tcx>) -> Ty<'tcx> { - self.unsubst_ty().subst(tcx, subst) - } - - pub fn unsubst_ty(&self) -> Ty<'tcx> { - self.ty.unwrap(DepNode::FieldTy(self.did)) - } - - pub fn fulfill_ty(&self, ty: Ty<'container>) { - self.ty.fulfill(DepNode::FieldTy(self.did), ty); + tcx.item_type(self.did).subst(tcx, subst) } -} -impl<'a, 'gcx, 'tcx> FieldDefData<'tcx, 'static> { #[inline] - pub fn is_uninhabited_recurse(&'tcx self, + pub fn is_uninhabited_recurse(&self, visited: &mut FxHashSet<(DefId, &'tcx Substs<'tcx>)>, block: Option, tcx: TyCtxt<'a, 'gcx, 'tcx>, @@ -2295,7 +2213,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { // Returns `ty::VariantDef` if `def` refers to a struct, // or variant or their constructors, panics otherwise. - pub fn expect_variant_def(self, def: Def) -> VariantDef<'tcx> { + pub fn expect_variant_def(self, def: Def) -> &'tcx VariantDef { match def { Def::Variant(did) | Def::VariantCtor(did, ..) => { let enum_did = self.parent_def_id(did).unwrap(); @@ -2398,28 +2316,18 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { } /// Given the did of a trait, returns its canonical trait ref. - pub fn lookup_trait_def(self, did: DefId) -> &'gcx TraitDef<'gcx> { + pub fn lookup_trait_def(self, did: DefId) -> &'gcx TraitDef { lookup_locally_or_in_crate_store( "trait_defs", did, &self.trait_defs, || self.alloc_trait_def(self.sess.cstore.trait_def(self.global_tcx(), did)) ) } - /// Given the did of an ADT, return a master reference to its - /// definition. Unless you are planning on fulfilling the ADT's fields, - /// use lookup_adt_def instead. - pub fn lookup_adt_def_master(self, did: DefId) -> AdtDefMaster<'gcx> { + /// Given the did of an ADT, return a reference to its definition. + pub fn lookup_adt_def(self, did: DefId) -> &'gcx AdtDef { lookup_locally_or_in_crate_store( "adt_defs", did, &self.adt_defs, - || self.sess.cstore.adt_def(self.global_tcx(), did) - ) - } - - /// Given the did of an ADT, return a reference to its definition. - pub fn lookup_adt_def(self, did: DefId) -> AdtDef<'gcx> { - // when reverse-variance goes away, a transmute:: - // would be needed here. - self.lookup_adt_def_master(did) + || self.sess.cstore.adt_def(self.global_tcx(), did)) } /// Given the did of an item, returns its generics. diff --git a/src/librustc/ty/sty.rs b/src/librustc/ty/sty.rs index 667db5b673054..59f774b954cf9 100644 --- a/src/librustc/ty/sty.rs +++ b/src/librustc/ty/sty.rs @@ -113,7 +113,7 @@ pub enum TypeVariants<'tcx> { /// That is, even after substitution it is possible that there are type /// variables. This happens when the `TyAdt` corresponds to an ADT /// definition and not a concrete use of it. - TyAdt(AdtDef<'tcx>, &'tcx Substs<'tcx>), + TyAdt(&'tcx AdtDef, &'tcx Substs<'tcx>), /// `Box`; this is nominally a struct in the documentation, but is /// special-cased internally. For example, it is possible to implicitly @@ -1267,7 +1267,7 @@ impl<'a, 'gcx, 'tcx> TyS<'tcx> { } } - pub fn ty_adt_def(&self) -> Option> { + pub fn ty_adt_def(&self) -> Option<&'tcx AdtDef> { match self.sty { TyAdt(adt, _) => Some(adt), _ => None diff --git a/src/librustc/ty/subst.rs b/src/librustc/ty/subst.rs index 41fcb09fb2dc7..d6f61a12a3c6e 100644 --- a/src/librustc/ty/subst.rs +++ b/src/librustc/ty/subst.rs @@ -165,6 +165,14 @@ impl<'tcx> Decodable for Kind<'tcx> { pub type Substs<'tcx> = Slice>; impl<'a, 'gcx, 'tcx> Substs<'tcx> { + /// Creates a Substs that maps each generic parameter to itself. + pub fn identity_for_item(tcx: TyCtxt<'a, 'gcx, 'tcx>, def_id: DefId) + -> &'tcx Substs<'tcx> { + Substs::for_item(tcx, def_id, |def, _| { + tcx.mk_region(ty::ReEarlyBound(def.to_early_bound_region_data())) + }, |def, _| tcx.mk_param_from_def(def)) + } + /// Creates a Substs for generic parameter definitions, /// by calling closures to obtain each region and type. /// The closures get to observe the Substs as they're diff --git a/src/librustc/ty/trait_def.rs b/src/librustc/ty/trait_def.rs index fd81065e61d49..c6d862b23bd5e 100644 --- a/src/librustc/ty/trait_def.rs +++ b/src/librustc/ty/trait_def.rs @@ -19,7 +19,9 @@ use hir; use util::nodemap::FxHashMap; /// A trait's definition with type information. -pub struct TraitDef<'tcx> { +pub struct TraitDef { + pub def_id: DefId, + pub unsafety: hir::Unsafety, /// If `true`, then this trait had the `#[rustc_paren_sugar]` @@ -28,15 +30,6 @@ pub struct TraitDef<'tcx> { /// be usable with the sugar (or without it). pub paren_sugar: bool, - /// Generic type definitions. Note that `Self` is listed in here - /// as having a single bound, the trait itself (e.g., in the trait - /// `Eq`, there is a single bound `Self : Eq`). This is so that - /// default methods get to assume that the `Self` parameters - /// implements the trait. - pub generics: &'tcx ty::Generics<'tcx>, - - pub trait_ref: ty::TraitRef<'tcx>, - // Impls of a trait. To allow for quicker lookup, the impls are indexed by a // simplified version of their `Self` type: impls with a simplifiable `Self` // are stored in `nonblanket_impls` keyed by it, while all other impls are @@ -72,18 +65,16 @@ pub struct TraitDef<'tcx> { pub def_path_hash: u64, } -impl<'a, 'gcx, 'tcx> TraitDef<'tcx> { - pub fn new(unsafety: hir::Unsafety, +impl<'a, 'gcx, 'tcx> TraitDef { + pub fn new(def_id: DefId, + unsafety: hir::Unsafety, paren_sugar: bool, - generics: &'tcx ty::Generics<'tcx>, - trait_ref: ty::TraitRef<'tcx>, def_path_hash: u64) - -> TraitDef<'tcx> { + -> TraitDef { TraitDef { + def_id: def_id, paren_sugar: paren_sugar, unsafety: unsafety, - generics: generics, - trait_ref: trait_ref, nonblanket_impls: RefCell::new(FxHashMap()), blanket_impls: RefCell::new(vec![]), flags: Cell::new(ty::TraitFlags::NO_TRAIT_FLAGS), @@ -92,10 +83,6 @@ impl<'a, 'gcx, 'tcx> TraitDef<'tcx> { } } - pub fn def_id(&self) -> DefId { - self.trait_ref.def_id - } - // returns None if not yet calculated pub fn object_safety(&self) -> Option { if self.flags.get().intersects(TraitFlags::OBJECT_SAFETY_VALID) { @@ -117,11 +104,11 @@ impl<'a, 'gcx, 'tcx> TraitDef<'tcx> { } fn write_trait_impls(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) { - tcx.dep_graph.write(DepNode::TraitImpls(self.trait_ref.def_id)); + tcx.dep_graph.write(DepNode::TraitImpls(self.def_id)); } fn read_trait_impls(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>) { - tcx.dep_graph.read(DepNode::TraitImpls(self.trait_ref.def_id)); + tcx.dep_graph.read(DepNode::TraitImpls(self.def_id)); } /// Records a basic trait-to-implementation mapping. @@ -203,13 +190,13 @@ impl<'a, 'gcx, 'tcx> TraitDef<'tcx> { .insert(tcx, impl_def_id) } - pub fn ancestors(&'a self, of_impl: DefId) -> specialization_graph::Ancestors<'a, 'tcx> { + pub fn ancestors(&'a self, of_impl: DefId) -> specialization_graph::Ancestors<'a> { specialization_graph::ancestors(self, of_impl) } pub fn for_each_impl(&self, tcx: TyCtxt<'a, 'gcx, 'tcx>, mut f: F) { self.read_trait_impls(tcx); - tcx.populate_implementations_for_trait_if_necessary(self.trait_ref.def_id); + tcx.populate_implementations_for_trait_if_necessary(self.def_id); for &impl_def_id in self.blanket_impls.borrow().iter() { f(impl_def_id); @@ -231,7 +218,7 @@ impl<'a, 'gcx, 'tcx> TraitDef<'tcx> { { self.read_trait_impls(tcx); - tcx.populate_implementations_for_trait_if_necessary(self.trait_ref.def_id); + tcx.populate_implementations_for_trait_if_necessary(self.def_id); for &impl_def_id in self.blanket_impls.borrow().iter() { f(impl_def_id); diff --git a/src/librustc/ty/util.rs b/src/librustc/ty/util.rs index 6ba4b8d2da77b..6bb9d67db6f65 100644 --- a/src/librustc/ty/util.rs +++ b/src/librustc/ty/util.rs @@ -366,7 +366,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> { /// `adt` that do not strictly outlive the adt value itself. /// (This allows programs to make cyclic structures without /// resorting to unasfe means; see RFCs 769 and 1238). - pub fn is_adt_dtorck(self, adt: ty::AdtDef) -> bool { + pub fn is_adt_dtorck(self, adt: &ty::AdtDef) -> bool { let dtor_method = match adt.destructor() { Some(dtor) => dtor, None => return false @@ -773,7 +773,7 @@ impl<'a, 'tcx> ty::TyS<'tcx> { } } - fn same_struct_or_enum<'tcx>(ty: Ty<'tcx>, def: ty::AdtDef<'tcx>) -> bool { + fn same_struct_or_enum<'tcx>(ty: Ty<'tcx>, def: &'tcx ty::AdtDef) -> bool { match ty.sty { TyAdt(ty_def, _) => { ty_def == def diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index d839df80a12ac..b4c87e0ce426e 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -388,14 +388,15 @@ impl<'tcx> fmt::Debug for ty::ExistentialTraitRef<'tcx> { } } -impl<'tcx> fmt::Debug for ty::TraitDef<'tcx> { +impl fmt::Debug for ty::TraitDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - write!(f, "TraitDef(generics={:?}, trait_ref={:?})", - self.generics, self.trait_ref) + ty::tls::with(|tcx| { + write!(f, "{}", tcx.item_path_str(self.def_id)) + }) } } -impl<'tcx, 'container> fmt::Debug for ty::AdtDefData<'tcx, 'container> { +impl fmt::Debug for ty::AdtDef { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { ty::tls::with(|tcx| { write!(f, "{}", tcx.item_path_str(self.did)) diff --git a/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs b/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs index 49ef5dd7a1725..4f49bfc9725b3 100644 --- a/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs +++ b/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs @@ -442,7 +442,7 @@ impl<'b, 'tcx> ElaborateDropsCtxt<'b, 'tcx> { fn move_paths_for_fields(&self, base_lv: &Lvalue<'tcx>, variant_path: MovePathIndex, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, substs: &'tcx Substs<'tcx>) -> Vec<(Lvalue<'tcx>, Option)> { @@ -619,7 +619,7 @@ impl<'b, 'tcx> ElaborateDropsCtxt<'b, 'tcx> { fn open_drop_for_variant<'a>(&mut self, c: &DropCtxt<'a, 'tcx>, drop_block: &mut Option, - adt: ty::AdtDef<'tcx>, + adt: &'tcx ty::AdtDef, substs: &'tcx Substs<'tcx>, variant_index: usize) -> BasicBlock @@ -652,7 +652,7 @@ impl<'b, 'tcx> ElaborateDropsCtxt<'b, 'tcx> { } fn open_drop_for_adt<'a>(&mut self, c: &DropCtxt<'a, 'tcx>, - adt: ty::AdtDef<'tcx>, substs: &'tcx Substs<'tcx>) + adt: &'tcx ty::AdtDef, substs: &'tcx Substs<'tcx>) -> BasicBlock { debug!("open_drop_for_adt({:?}, {:?}, {:?})", c, adt, substs); diff --git a/src/librustc_const_eval/_match.rs b/src/librustc_const_eval/_match.rs index db24ad0fd67ce..23771f4bae3dc 100644 --- a/src/librustc_const_eval/_match.rs +++ b/src/librustc_const_eval/_match.rs @@ -223,10 +223,8 @@ pub enum Constructor { Slice(usize), } -impl Constructor { - fn variant_for_adt<'tcx, 'container, 'a>(&self, - adt: &'a ty::AdtDefData<'tcx, 'container>) - -> &'a ty::VariantDefData<'tcx, 'container> { +impl<'tcx> Constructor { + fn variant_for_adt(&self, adt: &'tcx ty::AdtDef) -> &'tcx ty::VariantDef { match self { &Variant(vid) => adt.variant_with_id(vid), &Single => { diff --git a/src/librustc_const_eval/pattern.rs b/src/librustc_const_eval/pattern.rs index 8e803da98f89d..e93178c89c22b 100644 --- a/src/librustc_const_eval/pattern.rs +++ b/src/librustc_const_eval/pattern.rs @@ -66,7 +66,7 @@ pub enum PatternKind<'tcx> { /// Foo(...) or Foo{...} or Foo, where `Foo` is a variant name from an adt with >1 variants Variant { - adt_def: AdtDef<'tcx>, + adt_def: &'tcx AdtDef, variant_index: usize, subpatterns: Vec>, }, @@ -487,32 +487,22 @@ impl<'tcx, T: PatternFoldable<'tcx>> PatternFoldable<'tcx> for Option { } } -macro_rules! CopyImpls { - ($($ty:ty),+) => { +macro_rules! CloneImpls { + (<$lt_tcx:tt> $($ty:ty),+) => { $( - impl<'tcx> PatternFoldable<'tcx> for $ty { - fn super_fold_with>(&self, _: &mut F) -> Self { - self.clone() - } - } - )+ - } -} - -macro_rules! TcxCopyImpls { - ($($ty:ident),+) => { - $( - impl<'tcx> PatternFoldable<'tcx> for $ty<'tcx> { - fn super_fold_with>(&self, _: &mut F) -> Self { - *self + impl<$lt_tcx> PatternFoldable<$lt_tcx> for $ty { + fn super_fold_with>(&self, _: &mut F) -> Self { + Clone::clone(self) } } )+ } } -CopyImpls!{ Span, Field, Mutability, ast::Name, ast::NodeId, usize, ConstVal } -TcxCopyImpls!{ Ty, BindingMode, AdtDef } +CloneImpls!{ <'tcx> + Span, Field, Mutability, ast::Name, ast::NodeId, usize, ConstVal, + Ty<'tcx>, BindingMode<'tcx>, &'tcx AdtDef +} impl<'tcx> PatternFoldable<'tcx> for FieldPattern<'tcx> { fn super_fold_with>(&self, folder: &mut F) -> Self { diff --git a/src/librustc_lint/types.rs b/src/librustc_lint/types.rs index 6e9467d63dd1f..bba31c8237d18 100644 --- a/src/librustc_lint/types.rs +++ b/src/librustc_lint/types.rs @@ -396,7 +396,7 @@ enum FfiResult { /// expanded to cover NonZero raw pointers and newtypes. /// FIXME: This duplicates code in trans. fn is_repr_nullable_ptr<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - def: ty::AdtDef<'tcx>, + def: &'tcx ty::AdtDef, substs: &Substs<'tcx>) -> bool { if def.variants.len() == 2 { diff --git a/src/librustc_metadata/cstore_impl.rs b/src/librustc_metadata/cstore_impl.rs index c41c3afb83ed5..3150f74e61e7c 100644 --- a/src/librustc_metadata/cstore_impl.rs +++ b/src/librustc_metadata/cstore_impl.rs @@ -115,13 +115,13 @@ impl<'tcx> CrateStore<'tcx> for cstore::CStore { self.get_crate_data(def_id.krate).get_item_attrs(def_id.index) } - fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::TraitDef<'tcx> + fn trait_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::TraitDef { self.dep_graph.read(DepNode::MetaData(def)); self.get_crate_data(def.krate).get_trait_def(def.index, tcx) } - fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> ty::AdtDefMaster<'tcx> + fn adt_def<'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>, def: DefId) -> &'tcx ty::AdtDef { self.dep_graph.read(DepNode::MetaData(def)); self.get_crate_data(def.krate).get_adt_def(def.index, tcx) diff --git a/src/librustc_metadata/decoder.rs b/src/librustc_metadata/decoder.rs index 308cd6a83db7e..fe536b69c61d5 100644 --- a/src/librustc_metadata/decoder.rs +++ b/src/librustc_metadata/decoder.rs @@ -422,8 +422,8 @@ impl<'a, 'tcx> SpecializedDecoder<&'tcx ty::BareFnTy<'tcx>> for DecodeContext<'a } } -impl<'a, 'tcx> SpecializedDecoder> for DecodeContext<'a, 'tcx> { - fn specialized_decode(&mut self) -> Result, Self::Error> { +impl<'a, 'tcx> SpecializedDecoder<&'tcx ty::AdtDef> for DecodeContext<'a, 'tcx> { + fn specialized_decode(&mut self) -> Result<&'tcx ty::AdtDef, Self::Error> { let def_id = DefId::decode(self)?; Ok(self.tcx().lookup_adt_def(def_id)) } @@ -557,23 +557,22 @@ impl<'a, 'tcx> CrateMetadata { pub fn get_trait_def(&self, item_id: DefIndex, tcx: TyCtxt<'a, 'tcx, 'tcx>) - -> ty::TraitDef<'tcx> { + -> ty::TraitDef { let data = match self.entry(item_id).kind { EntryKind::Trait(data) => data.decode(self), _ => bug!(), }; - ty::TraitDef::new(data.unsafety, + ty::TraitDef::new(self.local_def_id(item_id), + data.unsafety, data.paren_sugar, - tcx.item_generics(self.local_def_id(item_id)), - data.trait_ref.decode((self, tcx)), self.def_path(item_id).unwrap().deterministic_hash(tcx)) } fn get_variant(&self, item: &Entry<'tcx>, index: DefIndex) - -> (ty::VariantDefData<'tcx, 'tcx>, Option) { + -> (ty::VariantDef, Option) { let data = match item.kind { EntryKind::Variant(data) | EntryKind::Struct(data) | @@ -581,28 +580,26 @@ impl<'a, 'tcx> CrateMetadata { _ => bug!(), }; - let fields = item.children - .decode(self) - .map(|index| { + (ty::VariantDef { + did: self.local_def_id(data.struct_ctor.unwrap_or(index)), + name: self.item_name(item), + fields: item.children.decode(self).map(|index| { let f = self.entry(index); - ty::FieldDefData::new(self.local_def_id(index), self.item_name(&f), f.visibility) - }) - .collect(); - - (ty::VariantDefData { - did: self.local_def_id(data.struct_ctor.unwrap_or(index)), - name: self.item_name(item), - fields: fields, - disr_val: ConstInt::Infer(data.disr), - ctor_kind: data.ctor_kind, - }, - data.struct_ctor) + ty::FieldDef { + did: self.local_def_id(index), + name: self.item_name(&f), + vis: f.visibility + } + }).collect(), + disr_val: ConstInt::Infer(data.disr), + ctor_kind: data.ctor_kind, + }, data.struct_ctor) } pub fn get_adt_def(&self, item_id: DefIndex, tcx: TyCtxt<'a, 'tcx, 'tcx>) - -> ty::AdtDefMaster<'tcx> { + -> &'tcx ty::AdtDef { let item = self.entry(item_id); let did = self.local_def_id(item_id); let mut ctor_index = None; @@ -627,26 +624,10 @@ impl<'a, 'tcx> CrateMetadata { _ => bug!("get_adt_def called on a non-ADT {:?}", did), }; - let adt = tcx.intern_adt_def(did, kind, variants); + let adt = tcx.alloc_adt_def(did, kind, variants); if let Some(ctor_index) = ctor_index { // Make adt definition available through constructor id as well. - tcx.insert_adt_def(self.local_def_id(ctor_index), adt); - } - - // this needs to be done *after* the variant is interned, - // to support recursive structures - for variant in &adt.variants { - for field in &variant.fields { - debug!("evaluating the type of {:?}::{:?}", - variant.name, - field.name); - let ty = self.get_type(field.did.index, tcx); - field.fulfill_ty(ty); - debug!("evaluating the type of {:?}::{:?}: {:?}", - variant.name, - field.name, - ty); - } + tcx.adt_defs.borrow_mut().insert(self.local_def_id(ctor_index), adt); } adt diff --git a/src/librustc_metadata/encoder.rs b/src/librustc_metadata/encoder.rs index 6abc81d74dc0a..83904b24de328 100644 --- a/src/librustc_metadata/encoder.rs +++ b/src/librustc_metadata/encoder.rs @@ -736,7 +736,6 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> { unsafety: trait_def.unsafety, paren_sugar: trait_def.paren_sugar, has_default_impl: tcx.trait_has_default_impl(def_id), - trait_ref: self.lazy(&trait_def.trait_ref), super_predicates: self.lazy(&tcx.item_super_predicates(def_id)), }; diff --git a/src/librustc_metadata/schema.rs b/src/librustc_metadata/schema.rs index c2acb2e0d7002..00c3709435de5 100644 --- a/src/librustc_metadata/schema.rs +++ b/src/librustc_metadata/schema.rs @@ -276,7 +276,6 @@ pub struct TraitData<'tcx> { pub unsafety: hir::Unsafety, pub paren_sugar: bool, pub has_default_impl: bool, - pub trait_ref: Lazy>, pub super_predicates: Lazy>, } diff --git a/src/librustc_mir/build/matches/mod.rs b/src/librustc_mir/build/matches/mod.rs index 786299c370d82..e06d940de7e58 100644 --- a/src/librustc_mir/build/matches/mod.rs +++ b/src/librustc_mir/build/matches/mod.rs @@ -301,7 +301,7 @@ pub struct MatchPair<'pat, 'tcx:'pat> { enum TestKind<'tcx> { // test the branches of enum Switch { - adt_def: AdtDef<'tcx>, + adt_def: &'tcx AdtDef, variants: BitVector, }, diff --git a/src/librustc_mir/build/matches/test.rs b/src/librustc_mir/build/matches/test.rs index 948ba7338cddb..cb449037aeba3 100644 --- a/src/librustc_mir/build/matches/test.rs +++ b/src/librustc_mir/build/matches/test.rs @@ -615,7 +615,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { fn candidate_after_variant_switch<'pat>(&mut self, match_pair_index: usize, - adt_def: ty::AdtDef<'tcx>, + adt_def: &'tcx ty::AdtDef, variant_index: usize, subpatterns: &'pat [FieldPattern<'tcx>], candidate: &Candidate<'pat, 'tcx>) diff --git a/src/librustc_mir/hair/cx/expr.rs b/src/librustc_mir/hair/cx/expr.rs index 94bf8936fe61b..e850f6c4b045c 100644 --- a/src/librustc_mir/hair/cx/expr.rs +++ b/src/librustc_mir/hair/cx/expr.rs @@ -1003,7 +1003,7 @@ fn capture_freevar<'a, 'gcx, 'tcx>(cx: &mut Cx<'a, 'gcx, 'tcx>, } /// Converts a list of named fields (i.e. for struct-like struct/enum ADTs) into FieldExprRef. -fn field_refs<'tcx>(variant: VariantDef<'tcx>, +fn field_refs<'tcx>(variant: &'tcx VariantDef, fields: &'tcx [hir::Field]) -> Vec> { diff --git a/src/librustc_mir/hair/cx/mod.rs b/src/librustc_mir/hair/cx/mod.rs index 32639cc3f8696..e7a6b40c830bd 100644 --- a/src/librustc_mir/hair/cx/mod.rs +++ b/src/librustc_mir/hair/cx/mod.rs @@ -155,11 +155,11 @@ impl<'a, 'gcx, 'tcx> Cx<'a, 'gcx, 'tcx> { bug!("found no method `{}` in `{:?}`", method_name, trait_def_id); } - pub fn num_variants(&mut self, adt_def: ty::AdtDef) -> usize { + pub fn num_variants(&mut self, adt_def: &ty::AdtDef) -> usize { adt_def.variants.len() } - pub fn all_fields(&mut self, adt_def: ty::AdtDef, variant_index: usize) -> Vec { + pub fn all_fields(&mut self, adt_def: &ty::AdtDef, variant_index: usize) -> Vec { (0..adt_def.variants[variant_index].fields.len()) .map(Field::new) .collect() diff --git a/src/librustc_mir/hair/mod.rs b/src/librustc_mir/hair/mod.rs index 50eee7723964e..22c07f1903bac 100644 --- a/src/librustc_mir/hair/mod.rs +++ b/src/librustc_mir/hair/mod.rs @@ -221,7 +221,7 @@ pub enum ExprKind<'tcx> { fields: Vec>, }, Adt { - adt_def: AdtDef<'tcx>, + adt_def: &'tcx AdtDef, variant_index: usize, substs: &'tcx Substs<'tcx>, fields: Vec>, diff --git a/src/librustc_privacy/lib.rs b/src/librustc_privacy/lib.rs index 1071203af2bc5..145b9176f6b13 100644 --- a/src/librustc_privacy/lib.rs +++ b/src/librustc_privacy/lib.rs @@ -405,7 +405,7 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> { } // Checks that a field is in scope. - fn check_field(&mut self, span: Span, def: ty::AdtDef<'tcx>, field: ty::FieldDef<'tcx>) { + fn check_field(&mut self, span: Span, def: &'tcx ty::AdtDef, field: &'tcx ty::FieldDef) { if !def.is_enum() && !field.vis.is_accessible_from(self.curitem, &self.tcx.map) { struct_span_err!(self.tcx.sess, span, E0451, "field `{}` of {} `{}` is private", field.name, def.variant_descr(), self.tcx.item_path_str(def.did)) diff --git a/src/librustc_save_analysis/dump_visitor.rs b/src/librustc_save_analysis/dump_visitor.rs index c3b1649662a45..4cd28e0a46daf 100644 --- a/src/librustc_save_analysis/dump_visitor.rs +++ b/src/librustc_save_analysis/dump_visitor.rs @@ -941,7 +941,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> { ex: &ast::Expr, path: &ast::Path, fields: &Vec, - variant: ty::VariantDef, + variant: &ty::VariantDef, base: &Option>) { self.write_sub_paths_truncated(path, false); diff --git a/src/librustc_save_analysis/lib.rs b/src/librustc_save_analysis/lib.rs index 7a2b74c06db8a..33b9f8c9034e8 100644 --- a/src/librustc_save_analysis/lib.rs +++ b/src/librustc_save_analysis/lib.rs @@ -621,7 +621,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> { pub fn get_field_ref_data(&self, field_ref: &ast::Field, - variant: ty::VariantDef, + variant: &ty::VariantDef, parent: NodeId) -> Option { let f = variant.field_named(field_ref.ident.node.name); diff --git a/src/librustc_trans/collector.rs b/src/librustc_trans/collector.rs index 7416b86bfebf3..087fe4decbf1d 100644 --- a/src/librustc_trans/collector.rs +++ b/src/librustc_trans/collector.rs @@ -803,9 +803,10 @@ fn find_drop_glue_neighbors<'a, 'tcx>(scx: &SharedCrateContext<'a, 'tcx>, } ty::TyAdt(adt_def, substs) => { for field in adt_def.all_fields() { + let field_type = scx.tcx().item_type(field.did); let field_type = monomorphize::apply_param_substs(scx, substs, - &field.unsubst_ty()); + &field_type); let field_type = glue::get_drop_glue_type(scx.tcx(), field_type); if glue::type_needs_drop(scx.tcx(), field_type) { diff --git a/src/librustc_trans/debuginfo/metadata.rs b/src/librustc_trans/debuginfo/metadata.rs index 8bbe50af0651c..df0e1f1fc052a 100644 --- a/src/librustc_trans/debuginfo/metadata.rs +++ b/src/librustc_trans/debuginfo/metadata.rs @@ -882,7 +882,7 @@ impl<'tcx> MemberDescriptionFactory<'tcx> { // Creates MemberDescriptions for the fields of a struct struct StructMemberDescriptionFactory<'tcx> { - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, substs: &'tcx Substs<'tcx>, is_simd: bool, span: Span, @@ -1024,7 +1024,7 @@ fn prepare_tuple_metadata<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>, //=----------------------------------------------------------------------------- struct UnionMemberDescriptionFactory<'tcx> { - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, substs: &'tcx Substs<'tcx>, span: Span, } @@ -1338,7 +1338,7 @@ enum EnumDiscriminantInfo { fn describe_enum_variant<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>, enum_type: Ty<'tcx>, struct_def: &layout::Struct, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, discriminant_info: EnumDiscriminantInfo, containing_scope: DIScope, span: Span) @@ -1357,7 +1357,7 @@ fn describe_enum_variant<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>, ref l @ _ => bug!("This should be unreachable. Type is {:#?} layout is {:#?}", enum_type, l) }; - let mut field_tys = variant.fields.iter().map(|f: ty::FieldDef<'tcx>| { + let mut field_tys = variant.fields.iter().map(|f| { monomorphize::field_ty(cx.tcx(), &substs, f) }).collect::>(); diff --git a/src/librustc_trans/glue.rs b/src/librustc_trans/glue.rs index 06d0b1e19828e..90bc29c39e9b5 100644 --- a/src/librustc_trans/glue.rs +++ b/src/librustc_trans/glue.rs @@ -504,7 +504,7 @@ fn drop_structural_ty<'blk, 'tcx>(cx: Block<'blk, 'tcx>, fn iter_variant<'blk, 'tcx>(cx: Block<'blk, 'tcx>, t: Ty<'tcx>, av: adt::MaybeSizedValue, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, substs: &Substs<'tcx>) -> Block<'blk, 'tcx> { let _icx = push_ctxt("iter_variant"); diff --git a/src/librustc_trans/monomorphize.rs b/src/librustc_trans/monomorphize.rs index 270ce79620f8b..8f05cc793ef22 100644 --- a/src/librustc_trans/monomorphize.rs +++ b/src/librustc_trans/monomorphize.rs @@ -60,7 +60,7 @@ pub fn apply_param_substs<'a, 'tcx, T>(scx: &SharedCrateContext<'a, 'tcx>, /// Returns the normalized type of a struct field pub fn field_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, param_substs: &Substs<'tcx>, - f: ty::FieldDef<'tcx>) + f: &'tcx ty::FieldDef) -> Ty<'tcx> { tcx.normalize_associated_type(&f.ty(tcx, param_substs)) diff --git a/src/librustc_typeck/astconv.rs b/src/librustc_typeck/astconv.rs index 032ad6efe1f0f..7d2019280e34a 100644 --- a/src/librustc_typeck/astconv.rs +++ b/src/librustc_typeck/astconv.rs @@ -93,7 +93,7 @@ pub trait AstConv<'gcx, 'tcx> { /// Returns the `TraitDef` for a given trait. This allows you to /// figure out the set of type parameters defined on the trait. fn get_trait_def(&self, span: Span, id: DefId) - -> Result<&'tcx ty::TraitDef<'tcx>, ErrorReported>; + -> Result<&'tcx ty::TraitDef, ErrorReported>; /// Ensure that the super-predicates for the trait with the given /// id are available and also for the transitive set of diff --git a/src/librustc_typeck/check/_match.rs b/src/librustc_typeck/check/_match.rs index 6e2b42881a709..15f383c5787d5 100644 --- a/src/librustc_typeck/check/_match.rs +++ b/src/librustc_typeck/check/_match.rs @@ -626,7 +626,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { adt_ty: Ty<'tcx>, pat_id: ast::NodeId, span: Span, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, fields: &'gcx [Spanned], etc: bool) { let tcx = self.tcx; diff --git a/src/librustc_typeck/check/dropck.rs b/src/librustc_typeck/check/dropck.rs index 1a5dfc8797ed0..e13c4ea314f06 100644 --- a/src/librustc_typeck/check/dropck.rs +++ b/src/librustc_typeck/check/dropck.rs @@ -589,7 +589,7 @@ fn has_dtor_of_interest<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, // // then revises input: `Foo<'r,i64,&'r i64>` to: `Foo<'static,i64,()>` fn revise_self_ty<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>, - adt_def: ty::AdtDef<'tcx>, + adt_def: &'tcx ty::AdtDef, impl_def_id: DefId, substs: &Substs<'tcx>) -> Ty<'tcx> { diff --git a/src/librustc_typeck/check/method/mod.rs b/src/librustc_typeck/check/method/mod.rs index f2dcc174d55bb..2e66f6290a022 100644 --- a/src/librustc_typeck/check/method/mod.rs +++ b/src/librustc_typeck/check/method/mod.rs @@ -192,13 +192,6 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { m_name, trait_def_id); - let trait_def = self.tcx.lookup_trait_def(trait_def_id); - - if let Some(ref input_types) = opt_input_types { - assert_eq!(trait_def.generics.types.len() - 1, input_types.len()); - } - assert!(trait_def.generics.regions.is_empty()); - // Construct a trait-reference `self_ty : Trait` let substs = Substs::for_item(self.tcx, trait_def_id, diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 8d51f52e9986e..1099d5b060ef5 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1041,7 +1041,7 @@ fn report_forbidden_specialization<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } fn check_specialization_validity<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - trait_def: &ty::TraitDef<'tcx>, + trait_def: &ty::TraitDef, impl_id: DefId, impl_item: &hir::ImplItem) { @@ -1401,7 +1401,7 @@ impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> { } fn get_trait_def(&self, _: Span, id: DefId) - -> Result<&'tcx ty::TraitDef<'tcx>, ErrorReported> + -> Result<&'tcx ty::TraitDef, ErrorReported> { Ok(self.tcx().lookup_trait_def(id)) } @@ -1987,7 +1987,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { // Indifferent to privacy flags pub fn field_ty(&self, span: Span, - field: ty::FieldDef<'tcx>, + field: &'tcx ty::FieldDef, substs: &Substs<'tcx>) -> Ty<'tcx> { @@ -3073,7 +3073,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { } // Return an hint about the closest match in field names - fn suggest_field_name(variant: ty::VariantDef<'tcx>, + fn suggest_field_name(variant: &'tcx ty::VariantDef, field: &Spanned, skip : Vec) -> Option { @@ -3166,7 +3166,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { fn report_unknown_field(&self, ty: Ty<'tcx>, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, field: &hir::Field, skip_fields: &[hir::Field], kind_name: &str) { @@ -3210,7 +3210,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { adt_ty: Ty<'tcx>, expr_id: ast::NodeId, span: Span, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, ast_fields: &'gcx [hir::Field], check_completeness: bool) { let tcx = self.tcx; @@ -3326,7 +3326,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> { pub fn check_struct_path(&self, qpath: &hir::QPath, node_id: ast::NodeId) - -> Option<(ty::VariantDef<'tcx>, Ty<'tcx>)> { + -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> { let path_span = match *qpath { hir::QPath::Resolved(_, ref path) => path.span, hir::QPath::TypeRelative(ref qself, _) => qself.span diff --git a/src/librustc_typeck/check/wfcheck.rs b/src/librustc_typeck/check/wfcheck.rs index b041fb41abf95..7870b3677d0d0 100644 --- a/src/librustc_typeck/check/wfcheck.rs +++ b/src/librustc_typeck/check/wfcheck.rs @@ -285,12 +285,7 @@ impl<'ccx, 'gcx> CheckTypeWellFormedVisitor<'ccx, 'gcx> { } }); - let trait_def = self.tcx().lookup_trait_def(trait_def_id); - - let has_ty_params = - trait_def.generics - .types - .len() > 1; + let has_ty_params = self.tcx().item_generics(trait_def_id).types.len() > 1; // We use an if-else here, since the generics will also trigger // an extraneous error message when we find predicates like diff --git a/src/librustc_typeck/coherence/mod.rs b/src/librustc_typeck/coherence/mod.rs index 30472f85db120..f575d4d8bab7a 100644 --- a/src/librustc_typeck/coherence/mod.rs +++ b/src/librustc_typeck/coherence/mod.rs @@ -395,7 +395,7 @@ impl<'a, 'gcx, 'tcx> CoherenceChecker<'a, 'gcx, 'tcx> { .filter_map(|(i, f)| { let (a, b) = (f.ty(tcx, substs_a), f.ty(tcx, substs_b)); - if f.unsubst_ty().is_phantom_data() { + if tcx.item_type(f.did).is_phantom_data() { // Ignore PhantomData fields return None; } diff --git a/src/librustc_typeck/collect.rs b/src/librustc_typeck/collect.rs index cbe0a1c4bf3ac..3bb7d6a77ba5c 100644 --- a/src/librustc_typeck/collect.rs +++ b/src/librustc_typeck/collect.rs @@ -329,20 +329,21 @@ impl<'a,'tcx> CrateCtxt<'a,'tcx> { } /// Loads the trait def for a given trait, returning ErrorReported if a cycle arises. - fn get_trait_def(&self, trait_id: DefId) - -> &'tcx ty::TraitDef<'tcx> + fn get_trait_def(&self, def_id: DefId) + -> &'tcx ty::TraitDef { let tcx = self.tcx; - if let Some(trait_id) = tcx.map.as_local_node_id(trait_id) { + if let Some(trait_id) = tcx.map.as_local_node_id(def_id) { let item = match tcx.map.get(trait_id) { hir_map::NodeItem(item) => item, _ => bug!("get_trait_def({:?}): not an item", trait_id) }; + generics_of_def_id(self, def_id); trait_def_of_item(self, &item) } else { - tcx.lookup_trait_def(trait_id) + tcx.lookup_trait_def(def_id) } } @@ -392,7 +393,7 @@ impl<'a, 'tcx> AstConv<'tcx, 'tcx> for ItemCtxt<'a, 'tcx> { } fn get_trait_def(&self, span: Span, id: DefId) - -> Result<&'tcx ty::TraitDef<'tcx>, ErrorReported> + -> Result<&'tcx ty::TraitDef, ErrorReported> { self.ccx.cycle_check(span, AstConvRequest::GetTraitDef(id), || { Ok(self.ccx.get_trait_def(id)) @@ -616,10 +617,10 @@ fn convert_field<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, struct_generics: &'tcx ty::Generics<'tcx>, struct_predicates: &ty::GenericPredicates<'tcx>, field: &hir::StructField, - ty_f: ty::FieldDefMaster<'tcx>) + ty_f: &'tcx ty::FieldDef) { let tt = ccx.icx(struct_predicates).to_ty(&ExplicitRscope, &field.ty); - ty_f.fulfill_ty(tt); + ccx.tcx.item_types.borrow_mut().insert(ty_f.did, tt); let def_id = ccx.tcx.map.local_def_id(field.id); ccx.tcx.item_types.borrow_mut().insert(def_id, tt); @@ -716,6 +717,7 @@ fn ensure_no_ty_param_bounds(ccx: &CrateCtxt, fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { let tcx = ccx.tcx; debug!("convert: item {} with id {}", it.name, it.id); + let def_id = ccx.tcx.map.local_def_id(it.id); match it.node { // These don't define types. hir::ItemExternCrate(_) | hir::ItemUse(..) | hir::ItemMod(_) => { @@ -726,12 +728,11 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { } } hir::ItemEnum(ref enum_definition, _) => { - let def_id = ccx.tcx.map.local_def_id(it.id); let ty = type_of_def_id(ccx, def_id); let generics = generics_of_def_id(ccx, def_id); let predicates = predicates_of_item(ccx, it); convert_enum_variant_types(ccx, - tcx.lookup_adt_def_master(ccx.tcx.map.local_def_id(it.id)), + tcx.lookup_adt_def(ccx.tcx.map.local_def_id(it.id)), ty, generics, predicates, @@ -756,7 +757,6 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { _) => { // Create generics from the generics specified in the impl head. debug!("convert: ast_generics={:?}", generics); - let def_id = ccx.tcx.map.local_def_id(it.id); generics_of_def_id(ccx, def_id); let mut ty_predicates = ty_generic_predicates(ccx, generics, None, vec![], false); @@ -786,8 +786,8 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { tcx.predicates.borrow_mut().insert(def_id, ty_predicates.clone()); }, hir::ItemTrait(.., ref trait_items) => { - let trait_def = trait_def_of_item(ccx, it); - let def_id = trait_def.trait_ref.def_id; + generics_of_def_id(ccx, def_id); + trait_def_of_item(ccx, it); let _: Result<(), ErrorReported> = // any error is already reported, can ignore ccx.ensure_super_predicates(it.span, def_id); convert_trait_predicates(ccx, it); @@ -838,12 +838,11 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { }, hir::ItemStruct(ref struct_def, _) | hir::ItemUnion(ref struct_def, _) => { - let def_id = ccx.tcx.map.local_def_id(it.id); let ty = type_of_def_id(ccx, def_id); let generics = generics_of_def_id(ccx, def_id); let predicates = predicates_of_item(ccx, it); - let variant = tcx.lookup_adt_def_master(def_id).struct_variant(); + let variant = tcx.lookup_adt_def(def_id).struct_variant(); for (f, ty_f) in struct_def.fields().iter().zip(variant.fields.iter()) { convert_field(ccx, generics, &predicates, f, ty_f) @@ -855,13 +854,11 @@ fn convert_item(ccx: &CrateCtxt, it: &hir::Item) { }, hir::ItemTy(_, ref generics) => { ensure_no_ty_param_bounds(ccx, it.span, generics, "type"); - let def_id = ccx.tcx.map.local_def_id(it.id); type_of_def_id(ccx, def_id); generics_of_def_id(ccx, def_id); predicates_of_item(ccx, it); }, _ => { - let def_id = ccx.tcx.map.local_def_id(it.id); type_of_def_id(ccx, def_id); generics_of_def_id(ccx, def_id); predicates_of_item(ccx, it); @@ -914,7 +911,7 @@ fn convert_impl_item(ccx: &CrateCtxt, impl_item: &hir::ImplItem) { fn convert_variant_ctor<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, ctor_id: ast::NodeId, - variant: ty::VariantDef<'tcx>, + variant: &'tcx ty::VariantDef, ty: Ty<'tcx>, predicates: ty::GenericPredicates<'tcx>) { let tcx = ccx.tcx; @@ -926,7 +923,7 @@ fn convert_variant_ctor<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, let inputs: Vec<_> = variant.fields .iter() - .map(|field| field.unsubst_ty()) + .map(|field| tcx.item_type(field.did)) .collect(); let substs = mk_item_substs(&ccx.icx(&predicates), ccx.tcx.map.span(ctor_id), def_id); @@ -946,7 +943,7 @@ fn convert_variant_ctor<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, } fn convert_enum_variant_types<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, - def: ty::AdtDefMaster<'tcx>, + def: &'tcx ty::AdtDef, ty: Ty<'tcx>, generics: &'tcx ty::Generics<'tcx>, predicates: ty::GenericPredicates<'tcx>, @@ -974,7 +971,7 @@ fn convert_struct_variant<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, name: ast::Name, disr_val: ty::Disr, def: &hir::VariantData) - -> ty::VariantDefData<'tcx, 'tcx> { + -> ty::VariantDef { let mut seen_fields: FxHashMap = FxHashMap(); let node_id = ccx.tcx.map.as_local_node_id(did).unwrap(); let fields = def.fields().iter().map(|f| { @@ -991,10 +988,13 @@ fn convert_struct_variant<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, seen_fields.insert(f.name, f.span); } - ty::FieldDefData::new(fid, f.name, - ty::Visibility::from_hir(&f.vis, node_id, ccx.tcx)) + ty::FieldDef { + did: fid, + name: f.name, + vis: ty::Visibility::from_hir(&f.vis, node_id, ccx.tcx) + } }).collect(); - ty::VariantDefData { + ty::VariantDef { did: did, name: name, disr_val: disr_val, @@ -1006,29 +1006,34 @@ fn convert_struct_variant<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, fn convert_struct_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item, def: &hir::VariantData) - -> ty::AdtDefMaster<'tcx> + -> &'tcx ty::AdtDef { let did = ccx.tcx.map.local_def_id(it.id); // Use separate constructor id for unit/tuple structs and reuse did for braced structs. let ctor_id = if !def.is_struct() { Some(ccx.tcx.map.local_def_id(def.id())) } else { None }; let variants = vec![convert_struct_variant(ccx, ctor_id.unwrap_or(did), it.name, ConstInt::Infer(0), def)]; - let adt = ccx.tcx.intern_adt_def(did, AdtKind::Struct, variants); + let adt = ccx.tcx.alloc_adt_def(did, AdtKind::Struct, variants); if let Some(ctor_id) = ctor_id { // Make adt definition available through constructor id as well. - ccx.tcx.insert_adt_def(ctor_id, adt); + ccx.tcx.adt_defs.borrow_mut().insert(ctor_id, adt); } + + ccx.tcx.adt_defs.borrow_mut().insert(did, adt); adt } fn convert_union_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item, def: &hir::VariantData) - -> ty::AdtDefMaster<'tcx> + -> &'tcx ty::AdtDef { let did = ccx.tcx.map.local_def_id(it.id); let variants = vec![convert_struct_variant(ccx, did, it.name, ConstInt::Infer(0), def)]; - ccx.tcx.intern_adt_def(did, AdtKind::Union, variants) + + let adt = ccx.tcx.alloc_adt_def(did, AdtKind::Union, variants); + ccx.tcx.adt_defs.borrow_mut().insert(did, adt); + adt } fn evaluate_disr_expr(ccx: &CrateCtxt, repr_ty: attr::IntType, e: &hir::Expr) @@ -1082,7 +1087,7 @@ fn convert_union_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, fn convert_enum_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item, def: &hir::EnumDef) - -> ty::AdtDefMaster<'tcx> + -> &'tcx ty::AdtDef { let tcx = ccx.tcx; let did = tcx.map.local_def_id(it.id); @@ -1110,7 +1115,10 @@ fn convert_enum_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, let did = tcx.map.local_def_id(v.node.data.id()); convert_struct_variant(ccx, did, v.node.name, disr, &v.node.data) }).collect(); - tcx.intern_adt_def(tcx.map.local_def_id(it.id), AdtKind::Enum, variants) + + let adt = tcx.alloc_adt_def(did, AdtKind::Enum, variants); + tcx.adt_defs.borrow_mut().insert(did, adt); + adt } /// Ensures that the super-predicates of the trait with def-id @@ -1155,10 +1163,15 @@ fn ensure_super_predicates_step(ccx: &CrateCtxt, // In-scope when converting the superbounds for `Trait` are // that `Self:Trait` as well as any bounds that appear on the // generic types: - let trait_def = trait_def_of_item(ccx, item); + generics_of_def_id(ccx, trait_def_id); + trait_def_of_item(ccx, item); + let trait_ref = ty::TraitRef { + def_id: trait_def_id, + substs: Substs::identity_for_item(tcx, trait_def_id) + }; let self_predicate = ty::GenericPredicates { parent: None, - predicates: vec![trait_def.trait_ref.to_predicate()] + predicates: vec![trait_ref.to_predicate()] }; let scope = &(generics, &self_predicate); @@ -1203,54 +1216,41 @@ fn ensure_super_predicates_step(ccx: &CrateCtxt, def_ids } -fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, - it: &hir::Item) - -> &'tcx ty::TraitDef<'tcx> -{ +fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item) -> &'tcx ty::TraitDef { let def_id = ccx.tcx.map.local_def_id(it.id); let tcx = ccx.tcx; - if let Some(def) = tcx.trait_defs.borrow().get(&def_id) { - return def.clone(); - } + tcx.trait_defs.memoize(def_id, || { + let unsafety = match it.node { + hir::ItemTrait(unsafety, ..) => unsafety, + _ => span_bug!(it.span, "trait_def_of_item invoked on non-trait"), + }; - let (unsafety, generics) = match it.node { - hir::ItemTrait(unsafety, ref generics, _, _) => { - (unsafety, generics) + let paren_sugar = tcx.has_attr(def_id, "rustc_paren_sugar"); + if paren_sugar && !ccx.tcx.sess.features.borrow().unboxed_closures { + let mut err = ccx.tcx.sess.struct_span_err( + it.span, + "the `#[rustc_paren_sugar]` attribute is a temporary means of controlling \ + which traits can use parenthetical notation"); + help!(&mut err, + "add `#![feature(unboxed_closures)]` to \ + the crate attributes to use it"); + err.emit(); } - _ => span_bug!(it.span, "trait_def_of_item invoked on non-trait"), - }; - - let paren_sugar = tcx.has_attr(def_id, "rustc_paren_sugar"); - if paren_sugar && !ccx.tcx.sess.features.borrow().unboxed_closures { - let mut err = ccx.tcx.sess.struct_span_err( - it.span, - "the `#[rustc_paren_sugar]` attribute is a temporary means of controlling \ - which traits can use parenthetical notation"); - help!(&mut err, - "add `#![feature(unboxed_closures)]` to \ - the crate attributes to use it"); - err.emit(); - } - - let ty_generics = generics_of_def_id(ccx, def_id); - let substs = mk_item_substs(&ccx.icx(generics), it.span, def_id); - - let def_path_hash = tcx.def_path(def_id).deterministic_hash(tcx); - let trait_ref = ty::TraitRef::new(def_id, substs); - let trait_def = ty::TraitDef::new(unsafety, paren_sugar, ty_generics, trait_ref, - def_path_hash); - - tcx.intern_trait_def(trait_def) + let def_path_hash = tcx.def_path(def_id).deterministic_hash(tcx); + tcx.alloc_trait_def(ty::TraitDef::new(def_id, unsafety, paren_sugar, def_path_hash)) + }) } fn convert_trait_predicates<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item) { let tcx = ccx.tcx; - let trait_def = trait_def_of_item(ccx, it); let def_id = ccx.tcx.map.local_def_id(it.id); + generics_of_def_id(ccx, def_id); + trait_def_of_item(ccx, it); + let (generics, items) = match it.node { hir::ItemTrait(_, ref generics, _, ref items) => (generics, items), ref s => { @@ -1272,7 +1272,11 @@ fn convert_trait_predicates<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item) // Add in a predicate that `Self:Trait` (where `Trait` is the // current trait). This is needed for builtin bounds. - let self_predicate = trait_def.trait_ref.to_poly_trait_ref().to_predicate(); + let trait_ref = ty::TraitRef { + def_id: def_id, + substs: Substs::identity_for_item(tcx, def_id) + }; + let self_predicate = trait_ref.to_poly_trait_ref().to_predicate(); base_predicates.push(self_predicate); // add in the explicit where-clauses @@ -1282,7 +1286,7 @@ fn convert_trait_predicates<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &hir::Item) let assoc_predicates = predicates_for_associated_types(ccx, generics, &trait_predicates, - trait_def.trait_ref, + trait_ref, items); trait_predicates.predicates.extend(assoc_predicates); @@ -1581,7 +1585,10 @@ fn type_of_def_id<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, NodeExpr(&hir::Expr { node: hir::ExprClosure(..), .. }) => { ccx.tcx.mk_closure(def_id, Substs::for_item( ccx.tcx, def_id, - |def, _| ccx.tcx.mk_region(def.to_early_bound_region()), + |def, _| { + let region = def.to_early_bound_region_data(); + ccx.tcx.mk_region(ty::ReEarlyBound(region)) + }, |def, _| ccx.tcx.mk_param_from_def(def) )) } @@ -2096,7 +2103,5 @@ pub fn mk_item_substs<'gcx: 'tcx, 'tcx>(astconv: &AstConv<'gcx, 'tcx>, bug!("ErrorReported returned, but no errors reports?") } - Substs::for_item(tcx, def_id, - |def, _| tcx.mk_region(def.to_early_bound_region()), - |def, _| tcx.mk_param_from_def(def)) + Substs::identity_for_item(tcx, def_id) } diff --git a/src/librustc_typeck/variance/constraints.rs b/src/librustc_typeck/variance/constraints.rs index f34753c227d71..ded9df25d5c66 100644 --- a/src/librustc_typeck/variance/constraints.rs +++ b/src/librustc_typeck/variance/constraints.rs @@ -92,14 +92,18 @@ impl<'a, 'tcx, 'v> ItemLikeVisitor<'v> for ConstraintContext<'a, 'tcx> { for field in tcx.lookup_adt_def(did).all_fields() { self.add_constraints_from_ty(generics, - field.unsubst_ty(), + tcx.item_type(field.did), self.covariant); } } hir::ItemTrait(..) => { - let trait_def = tcx.lookup_trait_def(did); - self.add_constraints_from_trait_ref(&trait_def.generics, - trait_def.trait_ref, + let generics = tcx.item_generics(did); + let trait_ref = ty::TraitRef { + def_id: did, + substs: Substs::identity_for_item(tcx, did) + }; + self.add_constraints_from_trait_ref(generics, + trait_ref, self.invariant); } @@ -279,7 +283,7 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> { trait_ref, variance); - let trait_def = self.tcx().lookup_trait_def(trait_ref.def_id); + let trait_generics = self.tcx().item_generics(trait_ref.def_id); // This edge is actually implied by the call to // `lookup_trait_def`, but I'm trying to be future-proof. See @@ -288,8 +292,8 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> { self.add_constraints_from_substs(generics, trait_ref.def_id, - &trait_def.generics.types, - &trait_def.generics.regions, + &trait_generics.types, + &trait_generics.regions, trait_ref.substs, variance); } @@ -356,7 +360,7 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> { ty::TyProjection(ref data) => { let trait_ref = &data.trait_ref; - let trait_def = self.tcx().lookup_trait_def(trait_ref.def_id); + let trait_generics = self.tcx().item_generics(trait_ref.def_id); // This edge is actually implied by the call to // `lookup_trait_def`, but I'm trying to be future-proof. See @@ -365,8 +369,8 @@ impl<'a, 'tcx> ConstraintContext<'a, 'tcx> { self.add_constraints_from_substs(generics, trait_ref.def_id, - &trait_def.generics.types, - &trait_def.generics.regions, + &trait_generics.types, + &trait_generics.regions, trait_ref.substs, variance); } diff --git a/src/librustdoc/clean/inline.rs b/src/librustdoc/clean/inline.rs index bf739abe3da0d..94e9fdbfc3e2c 100644 --- a/src/librustdoc/clean/inline.rs +++ b/src/librustdoc/clean/inline.rs @@ -151,14 +151,13 @@ pub fn record_extern_fqn(cx: &DocContext, did: DefId, kind: clean::TypeKind) { } pub fn build_external_trait(cx: &DocContext, did: DefId) -> clean::Trait { - let def = cx.tcx.lookup_trait_def(did); let trait_items = cx.tcx.associated_items(did).map(|item| item.clean(cx)).collect(); let predicates = cx.tcx.item_predicates(did); - let generics = (def.generics, &predicates).clean(cx); + let generics = (cx.tcx.item_generics(did), &predicates).clean(cx); let generics = filter_non_trait_generics(did, generics); let (generics, supertrait_bounds) = separate_supertrait_bounds(generics); clean::Trait { - unsafety: def.unsafety, + unsafety: cx.tcx.lookup_trait_def(did).unsafety, generics: generics, items: trait_items, bounds: supertrait_bounds, diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 7f8be4d633144..bc8472bb6b760 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -1395,9 +1395,8 @@ impl<'tcx> Clean for ty::AssociatedItem { // are actually located on the trait/impl itself, so we need to load // all of the generics from there and then look for bounds that are // applied to this associated type in question. - let def = cx.tcx.lookup_trait_def(did); let predicates = cx.tcx.item_predicates(did); - let generics = (def.generics, &predicates).clean(cx); + let generics = (cx.tcx.item_generics(did), &predicates).clean(cx); generics.where_predicates.iter().filter_map(|pred| { let (name, self_type, trait_, bounds) = match *pred { WherePredicate::BoundPredicate { @@ -1927,7 +1926,7 @@ impl Clean for hir::StructField { } } -impl<'tcx> Clean for ty::FieldDefData<'tcx, 'static> { +impl<'tcx> Clean for ty::FieldDef { fn clean(&self, cx: &DocContext) -> Item { Item { name: Some(self.name).clean(cx), @@ -1937,7 +1936,7 @@ impl<'tcx> Clean for ty::FieldDefData<'tcx, 'static> { stability: get_stability(cx, self.did), deprecation: get_deprecation(cx, self.did), def_id: self.did, - inner: StructFieldItem(self.unsubst_ty().clean(cx)), + inner: StructFieldItem(cx.tcx.item_type(self.did).clean(cx)), } } } @@ -2084,13 +2083,13 @@ impl Clean for doctree::Variant { } } -impl<'tcx> Clean for ty::VariantDefData<'tcx, 'static> { +impl<'tcx> Clean for ty::VariantDef { fn clean(&self, cx: &DocContext) -> Item { let kind = match self.ctor_kind { CtorKind::Const => VariantKind::CLike, CtorKind::Fn => { VariantKind::Tuple( - self.fields.iter().map(|f| f.unsubst_ty().clean(cx)).collect() + self.fields.iter().map(|f| cx.tcx.item_type(f.did).clean(cx)).collect() ) } CtorKind::Fictive => { @@ -2106,7 +2105,7 @@ impl<'tcx> Clean for ty::VariantDefData<'tcx, 'static> { def_id: field.did, stability: get_stability(cx, field.did), deprecation: get_deprecation(cx, field.did), - inner: StructFieldItem(field.unsubst_ty().clean(cx)) + inner: StructFieldItem(cx.tcx.item_type(field.did).clean(cx)) } }).collect() })