Use lookup_locally_or_in_crate_store more often
This commit is contained in:
parent
c7711002bb
commit
f4ee40ead2
@ -1215,11 +1215,11 @@ fn encode_info_for_item(ecx: &EncodeContext,
|
||||
encode_name(rbml_w, item.ident.name);
|
||||
encode_unsafety(rbml_w, unsafety);
|
||||
|
||||
let trait_ref = ty::impl_id_to_trait_ref(tcx, item.id);
|
||||
let trait_ref = ty::impl_trait_ref(tcx, local_def(item.id)).unwrap();
|
||||
encode_trait_ref(rbml_w, ecx, trait_ref, tag_item_trait_ref);
|
||||
rbml_w.end_tag();
|
||||
}
|
||||
ast::ItemImpl(unsafety, polarity, _, ref opt_trait, ref ty, ref ast_items) => {
|
||||
ast::ItemImpl(unsafety, polarity, _, _, ref ty, ref ast_items) => {
|
||||
// We need to encode information about the default methods we
|
||||
// have inherited, so we drive this based on the impl structure.
|
||||
let impl_items = tcx.impl_items.borrow();
|
||||
@ -1269,8 +1269,7 @@ fn encode_info_for_item(ecx: &EncodeContext,
|
||||
}
|
||||
rbml_w.end_tag();
|
||||
}
|
||||
if opt_trait.is_some() {
|
||||
let trait_ref = ty::impl_id_to_trait_ref(tcx, item.id);
|
||||
if let Some(trait_ref) = ty::impl_trait_ref(tcx, local_def(item.id)) {
|
||||
encode_trait_ref(rbml_w, ecx, trait_ref, tag_item_trait_ref);
|
||||
}
|
||||
encode_path(rbml_w, path.clone());
|
||||
|
@ -650,9 +650,7 @@ pub struct ctxt<'tcx> {
|
||||
/// A cache for the trait_items() routine
|
||||
pub trait_items_cache: RefCell<DefIdMap<Rc<Vec<ImplOrTraitItem<'tcx>>>>>,
|
||||
|
||||
pub impl_trait_cache: RefCell<DefIdMap<Option<TraitRef<'tcx>>>>,
|
||||
|
||||
pub impl_trait_refs: RefCell<NodeMap<TraitRef<'tcx>>>,
|
||||
pub impl_trait_refs: RefCell<DefIdMap<Option<TraitRef<'tcx>>>>,
|
||||
pub trait_defs: RefCell<DefIdMap<&'tcx TraitDef<'tcx>>>,
|
||||
|
||||
/// Maps from the def-id of an item (trait/struct/enum/fn) to its
|
||||
@ -675,7 +673,6 @@ pub struct ctxt<'tcx> {
|
||||
pub freevars: RefCell<FreevarMap>,
|
||||
pub tcache: RefCell<DefIdMap<TypeScheme<'tcx>>>,
|
||||
pub rcache: RefCell<FnvHashMap<creader_cache_key, Ty<'tcx>>>,
|
||||
pub short_names_cache: RefCell<FnvHashMap<Ty<'tcx>, String>>,
|
||||
pub tc_cache: RefCell<FnvHashMap<Ty<'tcx>, TypeContents>>,
|
||||
pub ast_ty_to_ty_cache: RefCell<NodeMap<Ty<'tcx>>>,
|
||||
pub enum_var_cache: RefCell<DefIdMap<Rc<Vec<Rc<VariantInfo<'tcx>>>>>>,
|
||||
@ -2741,7 +2738,7 @@ pub fn mk_ctxt<'tcx>(s: Session,
|
||||
def_map: def_map,
|
||||
node_types: RefCell::new(FnvHashMap()),
|
||||
item_substs: RefCell::new(NodeMap()),
|
||||
impl_trait_refs: RefCell::new(NodeMap()),
|
||||
impl_trait_refs: RefCell::new(DefIdMap()),
|
||||
trait_defs: RefCell::new(DefIdMap()),
|
||||
predicates: RefCell::new(DefIdMap()),
|
||||
super_predicates: RefCell::new(DefIdMap()),
|
||||
@ -2750,14 +2747,12 @@ pub fn mk_ctxt<'tcx>(s: Session,
|
||||
freevars: freevars,
|
||||
tcache: RefCell::new(DefIdMap()),
|
||||
rcache: RefCell::new(FnvHashMap()),
|
||||
short_names_cache: RefCell::new(FnvHashMap()),
|
||||
tc_cache: RefCell::new(FnvHashMap()),
|
||||
ast_ty_to_ty_cache: RefCell::new(NodeMap()),
|
||||
enum_var_cache: RefCell::new(DefIdMap()),
|
||||
impl_or_trait_items: RefCell::new(DefIdMap()),
|
||||
trait_item_def_ids: RefCell::new(DefIdMap()),
|
||||
trait_items_cache: RefCell::new(DefIdMap()),
|
||||
impl_trait_cache: RefCell::new(DefIdMap()),
|
||||
ty_param_defs: RefCell::new(NodeMap()),
|
||||
adjustments: RefCell::new(NodeMap()),
|
||||
normalized_cache: RefCell::new(FnvHashMap()),
|
||||
@ -4464,16 +4459,6 @@ pub fn named_element_ty<'tcx>(cx: &ctxt<'tcx>,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn impl_id_to_trait_ref<'tcx>(cx: &ctxt<'tcx>, id: ast::NodeId)
|
||||
-> ty::TraitRef<'tcx> {
|
||||
match cx.impl_trait_refs.borrow().get(&id) {
|
||||
Some(ty) => *ty,
|
||||
None => cx.sess.bug(
|
||||
&format!("impl_id_to_trait_ref: no trait ref for impl `{}`",
|
||||
cx.map.node_to_string(id)))
|
||||
}
|
||||
}
|
||||
|
||||
pub fn node_id_to_type<'tcx>(cx: &ctxt<'tcx>, id: ast::NodeId) -> Ty<'tcx> {
|
||||
match node_id_to_type_opt(cx, id) {
|
||||
Some(ty) => ty,
|
||||
@ -5268,12 +5253,12 @@ pub fn associated_consts<'tcx>(cx: &ctxt<'tcx>, id: ast::DefId)
|
||||
/// the future).
|
||||
fn lookup_locally_or_in_crate_store<V, F>(descr: &str,
|
||||
def_id: ast::DefId,
|
||||
map: &mut DefIdMap<V>,
|
||||
map: &RefCell<DefIdMap<V>>,
|
||||
load_external: F) -> V where
|
||||
V: Clone,
|
||||
F: FnOnce() -> V,
|
||||
{
|
||||
match map.get(&def_id).cloned() {
|
||||
match map.borrow().get(&def_id).cloned() {
|
||||
Some(v) => { return v; }
|
||||
None => { }
|
||||
}
|
||||
@ -5282,7 +5267,7 @@ fn lookup_locally_or_in_crate_store<V, F>(descr: &str,
|
||||
panic!("No def'n found for {:?} in tcx.{}", def_id, descr);
|
||||
}
|
||||
let v = load_external();
|
||||
map.insert(def_id, v.clone());
|
||||
map.borrow_mut().insert(def_id, v.clone());
|
||||
v
|
||||
}
|
||||
|
||||
@ -5348,13 +5333,9 @@ pub fn custom_coerce_unsized_kind<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
|
||||
|
||||
pub fn impl_or_trait_item<'tcx>(cx: &ctxt<'tcx>, id: ast::DefId)
|
||||
-> ImplOrTraitItem<'tcx> {
|
||||
lookup_locally_or_in_crate_store("impl_or_trait_items",
|
||||
id,
|
||||
&mut *cx.impl_or_trait_items
|
||||
.borrow_mut(),
|
||||
|| {
|
||||
csearch::get_impl_or_trait_item(cx, id)
|
||||
})
|
||||
lookup_locally_or_in_crate_store(
|
||||
"impl_or_trait_items", id, &cx.impl_or_trait_items,
|
||||
|| csearch::get_impl_or_trait_item(cx, id))
|
||||
}
|
||||
|
||||
/// Returns the parameter index that the given associated type corresponds to.
|
||||
@ -5881,37 +5862,35 @@ pub fn lookup_item_type<'tcx>(cx: &ctxt<'tcx>,
|
||||
did: ast::DefId)
|
||||
-> TypeScheme<'tcx> {
|
||||
lookup_locally_or_in_crate_store(
|
||||
"tcache", did, &mut *cx.tcache.borrow_mut(),
|
||||
"tcache", did, &cx.tcache,
|
||||
|| csearch::get_type(cx, did))
|
||||
}
|
||||
|
||||
/// Given the did of a trait, returns its canonical trait ref.
|
||||
pub fn lookup_trait_def<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
|
||||
-> &'tcx TraitDef<'tcx> {
|
||||
memoized(&cx.trait_defs, did, |did: DefId| {
|
||||
assert!(did.krate != ast::LOCAL_CRATE);
|
||||
cx.arenas.trait_defs.alloc(csearch::get_trait_def(cx, did))
|
||||
})
|
||||
lookup_locally_or_in_crate_store(
|
||||
"trait_defs", did, &cx.trait_defs,
|
||||
|| cx.arenas.trait_defs.alloc(csearch::get_trait_def(cx, did))
|
||||
)
|
||||
}
|
||||
|
||||
/// Given the did of an item, returns its full set of predicates.
|
||||
pub fn lookup_predicates<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
|
||||
-> GenericPredicates<'tcx>
|
||||
{
|
||||
memoized(&cx.predicates, did, |did: DefId| {
|
||||
assert!(did.krate != ast::LOCAL_CRATE);
|
||||
csearch::get_predicates(cx, did)
|
||||
})
|
||||
lookup_locally_or_in_crate_store(
|
||||
"predicates", did, &cx.predicates,
|
||||
|| csearch::get_predicates(cx, did))
|
||||
}
|
||||
|
||||
/// Given the did of a trait, returns its superpredicates.
|
||||
pub fn lookup_super_predicates<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
|
||||
-> GenericPredicates<'tcx>
|
||||
{
|
||||
memoized(&cx.super_predicates, did, |did: DefId| {
|
||||
assert!(did.krate != ast::LOCAL_CRATE);
|
||||
csearch::get_super_predicates(cx, did)
|
||||
})
|
||||
lookup_locally_or_in_crate_store(
|
||||
"super_predicates", did, &cx.super_predicates,
|
||||
|| csearch::get_super_predicates(cx, did))
|
||||
}
|
||||
|
||||
pub fn predicates<'tcx>(
|
||||
@ -6281,7 +6260,7 @@ pub fn required_region_bounds<'tcx>(tcx: &ctxt<'tcx>,
|
||||
|
||||
pub fn item_variances(tcx: &ctxt, item_id: ast::DefId) -> Rc<ItemVariances> {
|
||||
lookup_locally_or_in_crate_store(
|
||||
"item_variance_map", item_id, &mut *tcx.item_variance_map.borrow_mut(),
|
||||
"item_variance_map", item_id, &tcx.item_variance_map,
|
||||
|| Rc::new(csearch::get_item_variances(&tcx.sess.cstore, item_id)))
|
||||
}
|
||||
|
||||
|
@ -81,7 +81,8 @@ impl<'ccx, 'tcx> CheckTypeWellFormedVisitor<'ccx, 'tcx> {
|
||||
self.check_impl(item);
|
||||
}
|
||||
ast::ItemImpl(_, ast::ImplPolarity::Negative, _, Some(_), _, _) => {
|
||||
let trait_ref = ty::impl_id_to_trait_ref(ccx.tcx, item.id);
|
||||
let trait_ref = ty::impl_trait_ref(ccx.tcx,
|
||||
local_def(item.id)).unwrap();
|
||||
ty::populate_implementations_for_trait_if_necessary(ccx.tcx, trait_ref.def_id);
|
||||
match ccx.tcx.lang_items.to_builtin_kind(trait_ref.def_id) {
|
||||
Some(ty::BoundSend) | Some(ty::BoundSync) => {}
|
||||
|
@ -36,7 +36,7 @@ use std::cell::RefCell;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast::{Crate, DefId};
|
||||
use syntax::ast::{Item, ItemImpl};
|
||||
use syntax::ast::{LOCAL_CRATE, TraitRef};
|
||||
use syntax::ast::{LOCAL_CRATE};
|
||||
use syntax::ast;
|
||||
use syntax::ast_map::NodeItem;
|
||||
use syntax::ast_map;
|
||||
@ -100,11 +100,8 @@ struct CoherenceCheckVisitor<'a, 'tcx: 'a> {
|
||||
|
||||
impl<'a, 'tcx, 'v> visit::Visitor<'v> for CoherenceCheckVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &Item) {
|
||||
|
||||
//debug!("(checking coherence) item '{}'", token::get_ident(item.ident));
|
||||
|
||||
if let ItemImpl(_, _, _, ref opt_trait, _, _) = item.node {
|
||||
self.cc.check_implementation(item, opt_trait.as_ref())
|
||||
if let ItemImpl(..) = item.node {
|
||||
self.cc.check_implementation(item)
|
||||
}
|
||||
|
||||
visit::walk_item(self, item);
|
||||
@ -141,7 +138,7 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
self.check_implementations_of_coerce_unsized();
|
||||
}
|
||||
|
||||
fn check_implementation(&self, item: &Item, opt_trait: Option<&TraitRef>) {
|
||||
fn check_implementation(&self, item: &Item) {
|
||||
let tcx = self.crate_context.tcx;
|
||||
let impl_did = local_def(item.id);
|
||||
let self_type = ty::lookup_item_type(tcx, impl_did);
|
||||
@ -151,8 +148,8 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
|
||||
let impl_items = self.create_impl_from_item(item);
|
||||
|
||||
if opt_trait.is_some() {
|
||||
let trait_ref = ty::impl_id_to_trait_ref(self.crate_context.tcx, item.id);
|
||||
if let Some(trait_ref) = ty::impl_trait_ref(self.crate_context.tcx,
|
||||
impl_did) {
|
||||
debug!("(checking implementation) adding impl for trait '{}', item '{}'",
|
||||
trait_ref.repr(self.crate_context.tcx),
|
||||
token::get_ident(item.ident));
|
||||
@ -161,22 +158,13 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
item.span,
|
||||
trait_ref.def_id);
|
||||
self.add_trait_impl(trait_ref, impl_did);
|
||||
}
|
||||
|
||||
// Add the implementation to the mapping from implementation to base
|
||||
// type def ID, if there is a base type for this implementation and
|
||||
// the implementation does not have any associated traits.
|
||||
match get_base_type_def_id(&self.inference_context,
|
||||
item.span,
|
||||
self_type.ty) {
|
||||
None => {
|
||||
// Nothing to do.
|
||||
}
|
||||
Some(base_type_def_id) => {
|
||||
// FIXME: Gather up default methods?
|
||||
if opt_trait.is_none() {
|
||||
self.add_inherent_impl(base_type_def_id, impl_did);
|
||||
}
|
||||
} else {
|
||||
// Add the implementation to the mapping from implementation to base
|
||||
// type def ID, if there is a base type for this implementation and
|
||||
// the implementation does not have any associated traits.
|
||||
if let Some(base_type_def_id) = get_base_type_def_id(
|
||||
&self.inference_context, item.span, self_type.ty) {
|
||||
self.add_inherent_impl(base_type_def_id, impl_did);
|
||||
}
|
||||
}
|
||||
|
||||
@ -267,7 +255,7 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
// Converts an implementation in the AST to a vector of items.
|
||||
fn create_impl_from_item(&self, item: &Item) -> Vec<ImplOrTraitItemId> {
|
||||
match item.node {
|
||||
ItemImpl(_, _, _, ref opt_trait, _, ref impl_items) => {
|
||||
ItemImpl(_, _, _, _, _, ref impl_items) => {
|
||||
let mut items: Vec<ImplOrTraitItemId> =
|
||||
impl_items.iter().map(|impl_item| {
|
||||
match impl_item.node {
|
||||
@ -287,10 +275,8 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
}
|
||||
}).collect();
|
||||
|
||||
if opt_trait.is_some() {
|
||||
let trait_ref = ty::impl_id_to_trait_ref(self.crate_context.tcx,
|
||||
item.id);
|
||||
|
||||
if let Some(trait_ref) = ty::impl_trait_ref(self.crate_context.tcx,
|
||||
local_def(item.id)) {
|
||||
self.instantiate_default_methods(local_def(item.id),
|
||||
&trait_ref,
|
||||
&mut items);
|
||||
@ -453,8 +439,8 @@ impl<'a, 'tcx> CoherenceChecker<'a, 'tcx> {
|
||||
}
|
||||
|
||||
let source = ty::lookup_item_type(tcx, impl_did).ty;
|
||||
let trait_ref = ty::impl_id_to_trait_ref(self.crate_context.tcx,
|
||||
impl_did.node);
|
||||
let trait_ref = ty::impl_trait_ref(self.crate_context.tcx,
|
||||
impl_did).unwrap();
|
||||
let target = *trait_ref.substs.types.get(subst::TypeSpace, 0);
|
||||
debug!("check_implementations_of_coerce_unsized: {} -> {} (bound)",
|
||||
source.repr(tcx), target.repr(tcx));
|
||||
|
@ -820,7 +820,7 @@ fn convert_item(ccx: &CrateCtxt, it: &ast::Item) {
|
||||
|
||||
ty::record_trait_has_default_impl(tcx, trait_ref.def_id);
|
||||
|
||||
tcx.impl_trait_refs.borrow_mut().insert(it.id, trait_ref);
|
||||
tcx.impl_trait_refs.borrow_mut().insert(local_def(it.id), Some(trait_ref));
|
||||
}
|
||||
ast::ItemImpl(_, _,
|
||||
ref generics,
|
||||
@ -828,7 +828,6 @@ fn convert_item(ccx: &CrateCtxt, it: &ast::Item) {
|
||||
ref selfty,
|
||||
ref impl_items) => {
|
||||
// Create generics from the generics specified in the impl head.
|
||||
|
||||
debug!("convert: ast_generics={:?}", generics);
|
||||
let ty_generics = ty_generics_for_type_or_impl(ccx, generics);
|
||||
let ty_predicates = ty_generic_predicates_for_type_or_impl(ccx, generics);
|
||||
@ -926,14 +925,16 @@ fn convert_item(ccx: &CrateCtxt, it: &ast::Item) {
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(ref ast_trait_ref) = *opt_trait_ref {
|
||||
let trait_ref =
|
||||
astconv::instantiate_mono_trait_ref(&ccx.icx(&ty_predicates),
|
||||
&ExplicitRscope,
|
||||
ast_trait_ref,
|
||||
Some(selfty));
|
||||
|
||||
tcx.impl_trait_refs.borrow_mut().insert(it.id, trait_ref);
|
||||
if let &Some(ref ast_trait_ref) = opt_trait_ref {
|
||||
tcx.impl_trait_refs.borrow_mut().insert(
|
||||
local_def(it.id),
|
||||
Some(astconv::instantiate_mono_trait_ref(&ccx.icx(&ty_predicates),
|
||||
&ExplicitRscope,
|
||||
ast_trait_ref,
|
||||
Some(selfty)))
|
||||
);
|
||||
} else {
|
||||
tcx.impl_trait_refs.borrow_mut().insert(local_def(it.id), None);
|
||||
}
|
||||
|
||||
enforce_impl_params_are_constrained(tcx,
|
||||
|
Loading…
Reference in New Issue
Block a user