From 57aa0eb0aa0f4fc502ef8b1d3543cb02c2092932 Mon Sep 17 00:00:00 2001 From: Eduard Burtescu Date: Tue, 22 Apr 2014 02:21:52 +0300 Subject: [PATCH] rustc: de-@ middle::ty. --- src/librustc/metadata/csearch.rs | 10 +- src/librustc/metadata/decoder.rs | 43 ++- src/librustc/metadata/encoder.rs | 13 +- src/librustc/metadata/tydecode.rs | 2 +- src/librustc/metadata/tyencode.rs | 4 +- src/librustc/middle/kind.rs | 6 +- src/librustc/middle/lint.rs | 5 +- src/librustc/middle/privacy.rs | 2 +- src/librustc/middle/trans/base.rs | 17 +- src/librustc/middle/trans/callee.rs | 4 +- src/librustc/middle/trans/debuginfo.rs | 9 +- src/librustc/middle/trans/monomorphize.rs | 2 +- src/librustc/middle/trans/reflect.rs | 16 +- src/librustc/middle/ty.rs | 291 ++++++++---------- src/librustc/middle/typeck/astconv.rs | 32 +- src/librustc/middle/typeck/check/method.rs | 43 +-- src/librustc/middle/typeck/check/mod.rs | 39 +-- src/librustc/middle/typeck/check/regionck.rs | 2 +- src/librustc/middle/typeck/check/vtable.rs | 59 ++-- src/librustc/middle/typeck/coherence.rs | 11 +- src/librustc/middle/typeck/collect.rs | 60 ++-- src/librustc/middle/typeck/infer/coercion.rs | 18 +- src/librustc/middle/typeck/infer/combine.rs | 1 + .../middle/typeck/infer/error_reporting.rs | 19 +- src/librustc/middle/typeck/infer/glb.rs | 18 +- src/librustc/middle/typeck/infer/lattice.rs | 32 +- src/librustc/middle/typeck/infer/lub.rs | 18 +- src/librustc/middle/typeck/infer/mod.rs | 26 +- .../typeck/infer/region_inference/mod.rs | 22 +- src/librustc/middle/typeck/infer/sub.rs | 18 +- src/librustc/middle/typeck/variance.rs | 15 +- src/librustc/util/ppaux.rs | 9 +- src/libsyntax/util/small_vector.rs | 9 + 33 files changed, 440 insertions(+), 435 deletions(-) diff --git a/src/librustc/metadata/csearch.rs b/src/librustc/metadata/csearch.rs index a01e088a9f4c..4ebf4a52e418 100644 --- a/src/librustc/metadata/csearch.rs +++ b/src/librustc/metadata/csearch.rs @@ -107,10 +107,10 @@ pub fn maybe_get_item_ast(tcx: &ty::ctxt, def: ast::DefId, } pub fn get_enum_variants(tcx: &ty::ctxt, def: ast::DefId) - -> Vec<@ty::VariantInfo> { + -> Vec> { let cstore = &tcx.sess.cstore; let cdata = cstore.get_crate_data(def.krate); - return decoder::get_enum_variants(cstore.intr.clone(), &*cdata, def.node, tcx) + decoder::get_enum_variants(cstore.intr.clone(), &*cdata, def.node, tcx) } /// Returns information about the given implementation. @@ -147,13 +147,13 @@ pub fn get_item_variances(cstore: &cstore::CStore, pub fn get_provided_trait_methods(tcx: &ty::ctxt, def: ast::DefId) - -> Vec<@ty::Method> { + -> Vec> { let cstore = &tcx.sess.cstore; let cdata = cstore.get_crate_data(def.krate); decoder::get_provided_trait_methods(cstore.intr.clone(), &*cdata, def.node, tcx) } -pub fn get_supertraits(tcx: &ty::ctxt, def: ast::DefId) -> Vec<@ty::TraitRef> { +pub fn get_supertraits(tcx: &ty::ctxt, def: ast::DefId) -> Vec> { let cstore = &tcx.sess.cstore; let cdata = cstore.get_crate_data(def.krate); decoder::get_supertraits(&*cdata, def.node, tcx) @@ -224,7 +224,7 @@ pub fn get_field_type(tcx: &ty::ctxt, class_id: ast::DefId, // Given a def_id for an impl, return the trait it implements, // if there is one. pub fn get_impl_trait(tcx: &ty::ctxt, - def: ast::DefId) -> Option<@ty::TraitRef> { + def: ast::DefId) -> Option> { let cstore = &tcx.sess.cstore; let cdata = cstore.get_crate_data(def.krate); decoder::get_impl_trait(&*cdata, def.node, tcx) diff --git a/src/librustc/metadata/decoder.rs b/src/librustc/metadata/decoder.rs index 74156510fac5..37d9d3417c9f 100644 --- a/src/librustc/metadata/decoder.rs +++ b/src/librustc/metadata/decoder.rs @@ -386,7 +386,7 @@ pub fn get_trait_def(cdata: Cmd, generics: ty::Generics {type_param_defs: tp_defs, region_param_defs: rp_defs}, bounds: bounds, - trait_ref: @item_trait_ref(item_doc, tcx, cdata) + trait_ref: Rc::new(item_trait_ref(item_doc, tcx, cdata)) } } @@ -410,11 +410,11 @@ pub fn get_type(cdata: Cmd, id: ast::NodeId, tcx: &ty::ctxt) pub fn get_impl_trait(cdata: Cmd, id: ast::NodeId, - tcx: &ty::ctxt) -> Option<@ty::TraitRef> + tcx: &ty::ctxt) -> Option> { let item_doc = lookup_item(id, cdata.data()); reader::maybe_get_doc(item_doc, tag_item_trait_ref).map(|tp| { - @doc_trait_ref(tp, tcx, cdata) + Rc::new(doc_trait_ref(tp, tcx, cdata)) }) } @@ -675,27 +675,27 @@ pub fn maybe_get_item_ast(cdata: Cmd, tcx: &ty::ctxt, id: ast::NodeId, } pub fn get_enum_variants(intr: Rc, cdata: Cmd, id: ast::NodeId, - tcx: &ty::ctxt) -> Vec<@ty::VariantInfo> { + tcx: &ty::ctxt) -> Vec> { let data = cdata.data(); let items = reader::get_doc(reader::Doc(data), tag_items); let item = find_item(id, items); - let mut infos: Vec<@ty::VariantInfo> = Vec::new(); - let variant_ids = enum_variant_ids(item, cdata); let mut disr_val = 0; - for did in variant_ids.iter() { + enum_variant_ids(item, cdata).iter().map(|did| { let item = find_item(did.node, items); let ctor_ty = item_type(ast::DefId { krate: cdata.cnum, node: id}, item, tcx, cdata); let name = item_name(&*intr, item); let arg_tys = match ty::get(ctor_ty).sty { - ty::ty_bare_fn(ref f) => f.sig.inputs.clone(), - _ => Vec::new(), // Nullary enum variant. + ty::ty_bare_fn(ref f) => f.sig.inputs.clone(), + _ => Vec::new(), // Nullary enum variant. }; match variant_disr_val(item) { - Some(val) => { disr_val = val; } - _ => { /* empty */ } + Some(val) => { disr_val = val; } + _ => { /* empty */ } } - infos.push(@ty::VariantInfo{ + let old_disr_val = disr_val; + disr_val += 1; + Rc::new(ty::VariantInfo { args: arg_tys, arg_names: None, ctor_ty: ctor_ty, @@ -703,11 +703,10 @@ pub fn get_enum_variants(intr: Rc, cdata: Cmd, id: ast::NodeId, // I'm not even sure if we encode visibility // for variants -- TEST -- tjc id: *did, - disr_val: disr_val, - vis: ast::Inherited}); - disr_val += 1; - } - return infos; + disr_val: old_disr_val, + vis: ast::Inherited + }) + }).collect() } fn get_explicit_self(item: ebml::Doc) -> ast::ExplicitSelf_ { @@ -816,8 +815,8 @@ pub fn get_item_variances(cdata: Cmd, id: ast::NodeId) -> ty::ItemVariances { } pub fn get_provided_trait_methods(intr: Rc, cdata: Cmd, - id: ast::NodeId, tcx: &ty::ctxt) -> - Vec<@ty::Method> { + id: ast::NodeId, tcx: &ty::ctxt) + -> Vec> { let data = cdata.data(); let item = lookup_item(id, data); let mut result = Vec::new(); @@ -827,7 +826,7 @@ pub fn get_provided_trait_methods(intr: Rc, cdata: Cmd, let mth = lookup_item(did.node, data); if item_method_sort(mth) == 'p' { - result.push(@get_method(intr.clone(), cdata, did.node, tcx)); + result.push(Rc::new(get_method(intr.clone(), cdata, did.node, tcx))); } true }); @@ -837,7 +836,7 @@ pub fn get_provided_trait_methods(intr: Rc, cdata: Cmd, /// Returns the supertraits of the given trait. pub fn get_supertraits(cdata: Cmd, id: ast::NodeId, tcx: &ty::ctxt) - -> Vec<@ty::TraitRef> { + -> Vec> { let mut results = Vec::new(); let item_doc = lookup_item(id, cdata.data()); reader::tagged_docs(item_doc, tag_item_super_trait_ref, |trait_doc| { @@ -846,7 +845,7 @@ pub fn get_supertraits(cdata: Cmd, id: ast::NodeId, tcx: &ty::ctxt) // FIXME(#8559): The builtin bounds shouldn't be encoded in the first place. let trait_ref = doc_trait_ref(trait_doc, tcx, cdata); if tcx.lang_items.to_builtin_kind(trait_ref.def_id).is_none() { - results.push(@trait_ref); + results.push(Rc::new(trait_ref)); } true }); diff --git a/src/librustc/metadata/encoder.rs b/src/librustc/metadata/encoder.rs index a3f32cb93ac8..ab03e6476112 100644 --- a/src/librustc/metadata/encoder.rs +++ b/src/librustc/metadata/encoder.rs @@ -422,7 +422,7 @@ fn encode_reexported_static_trait_methods(ecx: &EncodeContext, -> bool { match ecx.tcx.trait_methods_cache.borrow().find(&exp.def_id) { Some(methods) => { - for &m in methods.iter() { + for m in methods.iter() { if m.explicit_self == ast::SelfStatic { encode_reexported_static_method(ebml_w, exp, m.def_id, m.ident); } @@ -1057,7 +1057,7 @@ fn encode_info_for_item(ecx: &EncodeContext, for ast_trait_ref in opt_trait.iter() { let trait_ref = ty::node_id_to_trait_ref( tcx, ast_trait_ref.ref_id); - encode_trait_ref(ebml_w, ecx, trait_ref, tag_item_trait_ref); + encode_trait_ref(ebml_w, ecx, &*trait_ref, tag_item_trait_ref); let impl_vtables = ty::lookup_impl_vtables(tcx, def_id); encode_impl_vtables(ebml_w, ecx, &impl_vtables); } @@ -1078,10 +1078,9 @@ fn encode_info_for_item(ecx: &EncodeContext, val: method_def_id.node as i64, pos: ebml_w.writer.tell().unwrap(), }); - let m = ty::method(tcx, method_def_id); encode_info_for_method(ecx, ebml_w, - m, + &*ty::method(tcx, method_def_id), path.clone(), false, item.id, @@ -1099,7 +1098,7 @@ fn encode_info_for_item(ecx: &EncodeContext, trait_def.generics.type_param_defs(), tag_items_data_item_ty_param_bounds); encode_region_param_defs(ebml_w, trait_def.generics.region_param_defs()); - encode_trait_ref(ebml_w, ecx, trait_def.trait_ref, tag_item_trait_ref); + encode_trait_ref(ebml_w, ecx, &*trait_def.trait_ref, tag_item_trait_ref); encode_name(ebml_w, item.ident.name); encode_attributes(ebml_w, item.attrs.as_slice()); encode_visibility(ebml_w, vis); @@ -1118,7 +1117,7 @@ fn encode_info_for_item(ecx: &EncodeContext, // the builtin-kinds-as-supertraits. See corresponding fixme in decoder. for ast_trait_ref in super_traits.iter() { let trait_ref = ty::node_id_to_trait_ref(ecx.tcx, ast_trait_ref.ref_id); - encode_trait_ref(ebml_w, ecx, trait_ref, tag_item_super_trait_ref); + encode_trait_ref(ebml_w, ecx, &*trait_ref, tag_item_super_trait_ref); } // Encode the implementations of this trait. @@ -1140,7 +1139,7 @@ fn encode_info_for_item(ecx: &EncodeContext, ebml_w.start_tag(tag_items_data_item); - encode_method_ty_fields(ecx, ebml_w, method_ty); + encode_method_ty_fields(ecx, ebml_w, &*method_ty); encode_parent_item(ebml_w, def_id); diff --git a/src/librustc/metadata/tydecode.rs b/src/librustc/metadata/tydecode.rs index cc2d76d936ff..3ba8dd3b30f0 100644 --- a/src/librustc/metadata/tydecode.rs +++ b/src/librustc/metadata/tydecode.rs @@ -592,7 +592,7 @@ fn parse_bounds(st: &mut PState, conv: conv_did) -> ty::ParamBounds { param_bounds.builtin_bounds.add(ty::BoundShare); } 'I' => { - param_bounds.trait_bounds.push(@parse_trait_ref(st, |x,y| conv(x,y))); + param_bounds.trait_bounds.push(Rc::new(parse_trait_ref(st, |x,y| conv(x,y)))); } '.' => { return param_bounds; diff --git a/src/librustc/metadata/tyencode.rs b/src/librustc/metadata/tyencode.rs index 46e03bf8997c..13d24e7a1d05 100644 --- a/src/librustc/metadata/tyencode.rs +++ b/src/librustc/metadata/tyencode.rs @@ -366,9 +366,9 @@ fn enc_bounds(w: &mut MemWriter, cx: &ctxt, bs: &ty::ParamBounds) { } } - for &tp in bs.trait_bounds.iter() { + for tp in bs.trait_bounds.iter() { mywrite!(w, "I"); - enc_trait_ref(w, cx, tp); + enc_trait_ref(w, cx, &**tp); } mywrite!(w, "."); diff --git a/src/librustc/middle/kind.rs b/src/librustc/middle/kind.rs index dee6af17e802..e6c885e56f17 100644 --- a/src/librustc/middle/kind.rs +++ b/src/librustc/middle/kind.rs @@ -112,9 +112,9 @@ fn check_impl_of_trait(cx: &mut Context, it: &Item, trait_ref: &TraitRef, self_t .find(&trait_ref.ref_id) .expect("trait ref not in def map!"); let trait_def_id = ast_util::def_id_of_def(ast_trait_def); - let trait_def = *cx.tcx.trait_defs.borrow() - .find(&trait_def_id) - .expect("trait def not in trait-defs map!"); + let trait_def = cx.tcx.trait_defs.borrow() + .find_copy(&trait_def_id) + .expect("trait def not in trait-defs map!"); // If this trait has builtin-kind supertraits, meet them. let self_ty: ty::t = ty::node_id_to_type(cx.tcx, it.id); diff --git a/src/librustc/middle/lint.rs b/src/librustc/middle/lint.rs index 299ff1078032..d1cc7d7bc401 100644 --- a/src/librustc/middle/lint.rs +++ b/src/librustc/middle/lint.rs @@ -53,6 +53,7 @@ use std::i16; use std::i32; use std::i64; use std::i8; +use std::rc::Rc; use std::to_str::ToStr; use std::u16; use std::u32; @@ -678,7 +679,7 @@ impl<'a> AstConv for Context<'a>{ ty::lookup_item_type(self.tcx, id) } - fn get_trait_def(&self, id: ast::DefId) -> @ty::TraitDef { + fn get_trait_def(&self, id: ast::DefId) -> Rc { ty::lookup_trait_def(self.tcx, id) } @@ -1465,7 +1466,7 @@ fn check_missing_doc_method(cx: &Context, m: &ast::Method) { node: m.id }; - match cx.tcx.methods.borrow().find(&did).map(|method| *method) { + match cx.tcx.methods.borrow().find_copy(&did) { None => cx.tcx.sess.span_bug(m.span, "missing method descriptor?!"), Some(md) => { match md.container { diff --git a/src/librustc/middle/privacy.rs b/src/librustc/middle/privacy.rs index 4877bfc5cce6..427a7f406b01 100644 --- a/src/librustc/middle/privacy.rs +++ b/src/librustc/middle/privacy.rs @@ -254,7 +254,7 @@ impl<'a> Visitor<()> for EmbargoVisitor<'a> { _ => true, }; let tr = ty::impl_trait_ref(self.tcx, local_def(item.id)); - let public_trait = tr.map_or(false, |tr| { + let public_trait = tr.clone().map_or(false, |tr| { !is_local(tr.def_id) || self.exported_items.contains(&tr.def_id.node) }); diff --git a/src/librustc/middle/trans/base.rs b/src/librustc/middle/trans/base.rs index 086989f2874b..aba03e7c79d1 100644 --- a/src/librustc/middle/trans/base.rs +++ b/src/librustc/middle/trans/base.rs @@ -75,6 +75,7 @@ use libc::c_uint; use std::c_str::ToCStr; use std::cell::{Cell, RefCell}; use std::local_data; +use std::rc::Rc; use syntax::abi::{X86, X86_64, Arm, Mips, Rust, RustIntrinsic}; use syntax::ast_util::{local_def, is_local}; use syntax::attr::AttrMetaMethods; @@ -637,7 +638,7 @@ pub fn iter_structural_ty<'r, cx: &'b Block<'b>, repr: &adt::Repr, av: ValueRef, - variant: @ty::VariantInfo, + variant: &ty::VariantInfo, tps: &[ty::t], f: val_and_ty_fn<'r,'b>) -> &'b Block<'b> { @@ -694,7 +695,7 @@ pub fn iter_structural_ty<'r, match adt::trans_switch(cx, repr, av) { (_match::single, None) => { - cx = iter_variant(cx, repr, av, *variants.get(0), + cx = iter_variant(cx, repr, av, &**variants.get(0), substs.tps.as_slice(), f); } (_match::switch, Some(lldiscrim_a)) => { @@ -720,7 +721,7 @@ pub fn iter_structural_ty<'r, iter_variant(variant_cx, repr, av, - *variant, + &**variant, substs.tps.as_slice(), |x,y,z| f(x,y,z)); Br(variant_cx, next_cx.llbb); @@ -1525,11 +1526,11 @@ fn trans_enum_variant_or_tuple_like_struct(ccx: &CrateContext, finish_fn(&fcx, bcx); } -pub fn trans_enum_def(ccx: &CrateContext, enum_definition: &ast::EnumDef, - id: ast::NodeId, vi: @Vec<@ty::VariantInfo>, - i: &mut uint) { +fn trans_enum_def(ccx: &CrateContext, enum_definition: &ast::EnumDef, + id: ast::NodeId, vi: &[Rc], + i: &mut uint) { for &variant in enum_definition.variants.iter() { - let disr_val = vi.get(*i).disr_val; + let disr_val = vi[*i].disr_val; *i += 1; match variant.node.kind { @@ -1592,7 +1593,7 @@ pub fn trans_item(ccx: &CrateContext, item: &ast::Item) { if !generics.is_type_parameterized() { let vi = ty::enum_variants(ccx.tcx(), local_def(item.id)); let mut i = 0; - trans_enum_def(ccx, enum_definition, item.id, vi, &mut i); + trans_enum_def(ccx, enum_definition, item.id, vi.as_slice(), &mut i); } } ast::ItemStatic(_, m, expr) => { diff --git a/src/librustc/middle/trans/callee.rs b/src/librustc/middle/trans/callee.rs index 05636666f9ca..642ae86a9798 100644 --- a/src/librustc/middle/trans/callee.rs +++ b/src/librustc/middle/trans/callee.rs @@ -318,7 +318,7 @@ pub fn trans_fn_ref_with_vtables( // Compute the first substitution let first_subst = make_substs_for_receiver_types( - tcx, impl_id, trait_ref, method); + tcx, impl_id, &*trait_ref, &*method); // And compose them let new_substs = first_subst.subst(tcx, &substs); @@ -333,7 +333,7 @@ pub fn trans_fn_ref_with_vtables( let (param_vtables, self_vtables) = resolve_default_method_vtables(bcx, impl_id, - method, &substs, vtables); + &*method, &substs, vtables); debug!("trans_fn_with_vtables - default method: \ self_vtable = {}, param_vtables = {}", diff --git a/src/librustc/middle/trans/debuginfo.rs b/src/librustc/middle/trans/debuginfo.rs index ffab654e964e..d01157e53a8d 100644 --- a/src/librustc/middle/trans/debuginfo.rs +++ b/src/librustc/middle/trans/debuginfo.rs @@ -144,6 +144,7 @@ use util::ppaux; use std::c_str::{CString, ToCStr}; use std::cell::{Cell, RefCell}; +use std::rc::Rc; use collections::HashMap; use collections::HashSet; use libc::{c_uint, c_ulonglong, c_longlong}; @@ -1389,7 +1390,7 @@ fn prepare_tuple_metadata(cx: &CrateContext, struct GeneralMemberDescriptionFactory { type_rep: @adt::Repr, - variants: @Vec<@ty::VariantInfo> , + variants: Rc>>, discriminant_type_metadata: ValueRef, containing_scope: DIScope, file_metadata: DIFile, @@ -1412,7 +1413,7 @@ impl GeneralMemberDescriptionFactory { let (variant_type_metadata, variant_llvm_type, member_desc_factory) = describe_enum_variant(cx, struct_def, - *self.variants.get(i), + &**self.variants.get(i), Some(self.discriminant_type_metadata), self.containing_scope, self.file_metadata, @@ -1617,7 +1618,7 @@ fn prepare_enum_metadata(cx: &CrateContext, member_description_factory) = describe_enum_variant(cx, struct_def, - *variants.get(0), + &**variants.get(0), None, containing_scope, file_metadata, @@ -1676,7 +1677,7 @@ fn prepare_enum_metadata(cx: &CrateContext, member_description_factory) = describe_enum_variant(cx, struct_def, - *variants.get(nndiscr as uint), + &**variants.get(nndiscr as uint), None, containing_scope, file_metadata, diff --git a/src/librustc/middle/trans/monomorphize.rs b/src/librustc/middle/trans/monomorphize.rs index 7a026c2b45d6..aa6e2dafd835 100644 --- a/src/librustc/middle/trans/monomorphize.rs +++ b/src/librustc/middle/trans/monomorphize.rs @@ -243,7 +243,7 @@ pub fn monomorphic_fn(ccx: &CrateContext, ast_map::NodeVariant(v) => { let parent = ccx.tcx.map.get_parent(fn_id.node); let tvs = ty::enum_variants(ccx.tcx(), local_def(parent)); - let this_tv = *tvs.iter().find(|tv| { tv.id.node == fn_id.node}).unwrap(); + let this_tv = tvs.iter().find(|tv| { tv.id.node == fn_id.node}).unwrap(); let d = mk_lldecl(); set_inline_hint(d); match v.node.kind { diff --git a/src/librustc/middle/trans/reflect.rs b/src/librustc/middle/trans/reflect.rs index 1ccdecfaaf42..d6bd84d18f09 100644 --- a/src/librustc/middle/trans/reflect.rs +++ b/src/librustc/middle/trans/reflect.rs @@ -25,6 +25,7 @@ use middle::trans::type_of::*; use middle::ty; use util::ppaux::ty_to_str; +use std::rc::Rc; use arena::TypedArena; use libc::c_uint; use syntax::ast::DefId; @@ -33,15 +34,15 @@ use syntax::ast_map; use syntax::parse::token::{InternedString, special_idents}; use syntax::parse::token; -pub struct Reflector<'a> { +pub struct Reflector<'a, 'b> { visitor_val: ValueRef, - visitor_methods: @Vec<@ty::Method> , - final_bcx: &'a Block<'a>, + visitor_methods: &'a [Rc], + final_bcx: &'b Block<'b>, tydesc_ty: Type, - bcx: &'a Block<'a> + bcx: &'b Block<'b> } -impl<'a> Reflector<'a> { +impl<'a, 'b> Reflector<'a, 'b> { pub fn c_uint(&mut self, u: uint) -> ValueRef { C_uint(self.bcx.ccx(), u) } @@ -92,7 +93,7 @@ impl<'a> Reflector<'a> { format!("couldn't find visit method for {}", ty_name)); let mth_ty = ty::mk_bare_fn(tcx, - self.visitor_methods.get(mth_idx).fty.clone()); + self.visitor_methods[mth_idx].fty.clone()); let v = self.visitor_val; debug!("passing {} args:", args.len()); let mut bcx = self.bcx; @@ -401,9 +402,10 @@ pub fn emit_calls_to_trait_visit_ty<'a>( let final = fcx.new_temp_block("final"); let tydesc_ty = ty::get_tydesc_ty(bcx.tcx()).unwrap(); let tydesc_ty = type_of(bcx.ccx(), tydesc_ty); + let visitor_methods = ty::trait_methods(bcx.tcx(), visitor_trait_id); let mut r = Reflector { visitor_val: visitor_val, - visitor_methods: ty::trait_methods(bcx.tcx(), visitor_trait_id), + visitor_methods: visitor_methods.as_slice(), final_bcx: final, tydesc_ty: tydesc_ty, bcx: bcx diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 865d82b67799..59563013911c 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -38,9 +38,11 @@ use std::cmp; use std::fmt::Show; use std::fmt; use std::hash::{Hash, sip}; +use std::iter::AdditiveIterator; use std::ops; use std::rc::Rc; use collections::{HashMap, HashSet}; +use syntax::abi; use syntax::ast::*; use syntax::ast_util::{is_local, lit_is_str}; use syntax::ast_util; @@ -51,7 +53,7 @@ use syntax::parse::token; use syntax::parse::token::InternedString; use syntax::{ast, ast_map}; use syntax::owned_slice::OwnedSlice; -use syntax::abi; +use syntax::util::small_vector::SmallVector; use collections::enum_set::{EnumSet, CLike}; pub type Disr = u64; @@ -267,18 +269,18 @@ pub struct ctxt { pub node_type_substs: RefCell>>, // Maps from a method to the method "descriptor" - pub methods: RefCell>, + pub methods: RefCell>>, // Maps from a trait def-id to a list of the def-ids of its methods - pub trait_method_def_ids: RefCell >>, + pub trait_method_def_ids: RefCell>>>, // A cache for the trait_methods() routine - pub trait_methods_cache: RefCell >>, + pub trait_methods_cache: RefCell>>>>, - pub impl_trait_cache: RefCell>>, + pub impl_trait_cache: RefCell>>>, - pub trait_refs: RefCell>, - pub trait_defs: RefCell>, + pub trait_refs: RefCell>>, + pub trait_defs: RefCell>>, pub map: ast_map::Map, pub intrinsic_defs: RefCell>, @@ -289,20 +291,20 @@ pub struct ctxt { pub needs_unwind_cleanup_cache: RefCell>, pub tc_cache: RefCell>, pub ast_ty_to_ty_cache: RefCell>, - pub enum_var_cache: RefCell >>, + pub enum_var_cache: RefCell>>>>, pub ty_param_defs: RefCell>, pub adjustments: RefCell>, pub normalized_cache: RefCell>, pub lang_items: middle::lang_items::LanguageItems, // A mapping of fake provided method def_ids to the default implementation pub provided_method_sources: RefCell>, - pub supertraits: RefCell >>, + pub supertraits: RefCell>>>>, pub superstructs: RefCell>>, - pub struct_fields: RefCell>>, + pub struct_fields: RefCell>>>, // Maps from def-id of a type or region parameter to its // (inferred) variance. - pub item_variance_map: RefCell>, + pub item_variance_map: RefCell>>, // A mapping from the def ID of an enum or struct type to the def ID // of the method that implements its destructor. If the type is not @@ -314,12 +316,12 @@ pub struct ctxt { pub destructors: RefCell, // Maps a trait onto a list of impls of that trait. - pub trait_impls: RefCell>>>, + pub trait_impls: RefCell>>>>, // Maps a DefId of a type to a list of its inherent impls. // Contains implementations of methods that are inherent to a type. // Methods in these implementations don't need to be exported. - pub inherent_impls: RefCell>>>, + pub inherent_impls: RefCell>>>>, // Maps a DefId of an impl to a list of its methods. // Note that this contains all of the impls that we know about, @@ -826,7 +828,7 @@ pub enum type_err { #[deriving(Eq, TotalEq, Hash)] pub struct ParamBounds { pub builtin_bounds: BuiltinBounds, - pub trait_bounds: Vec<@TraitRef> + pub trait_bounds: Vec> } pub type BuiltinBounds = EnumSet; @@ -1036,7 +1038,7 @@ pub struct ParameterEnvironment { pub free_substs: ty::substs, /// Bound on the Self parameter - pub self_param_bound: Option<@TraitRef>, + pub self_param_bound: Option>, /// Bounds on each numbered type parameter pub type_param_bounds: Vec , @@ -1062,7 +1064,7 @@ pub struct ty_param_bounds_and_ty { pub struct TraitDef { pub generics: Generics, pub bounds: BuiltinBounds, - pub trait_ref: @ty::TraitRef, + pub trait_ref: Rc, } pub struct ty_param_substs_and_ty { @@ -2174,7 +2176,7 @@ pub fn type_contents(cx: &ctxt, ty: t) -> TypeContents { // Self may be bounded if the associated trait has builtin kinds // for supertraits. If so we can use those bounds. let trait_def = lookup_trait_def(cx, def_id); - let traits = [trait_def.trait_ref]; + let traits = [trait_def.trait_ref.clone()]; kind_bounds_to_contents(cx, trait_def.bounds, traits) } @@ -2269,7 +2271,7 @@ pub fn type_contents(cx: &ctxt, ty: t) -> TypeContents { fn kind_bounds_to_contents(cx: &ctxt, bounds: BuiltinBounds, - traits: &[@TraitRef]) + traits: &[Rc]) -> TypeContents { let _i = indenter(); let mut tc = TC::All; @@ -2288,7 +2290,7 @@ pub fn type_contents(cx: &ctxt, ty: t) -> TypeContents { // those inherited from traits with builtin-kind-supertraits. fn each_inherited_builtin_bound(cx: &ctxt, bounds: BuiltinBounds, - traits: &[@TraitRef], + traits: &[Rc], f: |BuiltinBound|) { for bound in bounds.iter() { f(bound); @@ -2654,12 +2656,12 @@ pub fn index(t: t) -> Option { } } -pub fn node_id_to_trait_ref(cx: &ctxt, id: ast::NodeId) -> @ty::TraitRef { +pub fn node_id_to_trait_ref(cx: &ctxt, id: ast::NodeId) -> Rc { match cx.trait_refs.borrow().find(&id) { - Some(&t) => t, - None => cx.sess.bug( - format!("node_id_to_trait_ref: no trait ref for node `{}`", - cx.map.node_to_str(id))) + Some(t) => t.clone(), + None => cx.sess.bug( + format!("node_id_to_trait_ref: no trait ref for node `{}`", + cx.map.node_to_str(id))) } } @@ -3045,8 +3047,8 @@ pub fn method_call_type_param_defs(tcx: &ctxt, origin: typeck::MethodOrigin) // method bounds, so we must preprend the tps from the // trait itself. This ought to be harmonized. let trait_type_param_defs = - lookup_trait_def(tcx, trt_id).generics.type_param_defs(); - Rc::new(Vec::from_slice(trait_type_param_defs).append( + Vec::from_slice(lookup_trait_def(tcx, trt_id).generics.type_param_defs()); + Rc::new(trait_type_param_defs.append( ty::trait_method(tcx, trt_id, n_mth).generics.type_param_defs())) } } @@ -3255,7 +3257,7 @@ pub fn field_idx_strict(tcx: &ctxt, name: ast::Name, fields: &[field]) fields.iter().map(|f| token::get_ident(f.ident).get().to_str()).collect::>())); } -pub fn method_idx(id: ast::Ident, meths: &[@Method]) -> Option { +pub fn method_idx(id: ast::Ident, meths: &[Rc]) -> Option { meths.iter().position(|m| m.ident == id) } @@ -3479,42 +3481,29 @@ pub fn provided_source(cx: &ctxt, id: ast::DefId) -> Option { cx.provided_method_sources.borrow().find(&id).map(|x| *x) } -pub fn provided_trait_methods(cx: &ctxt, id: ast::DefId) -> Vec<@Method> { +pub fn provided_trait_methods(cx: &ctxt, id: ast::DefId) -> Vec> { if is_local(id) { - { - match cx.map.find(id.node) { - Some(ast_map::NodeItem(item)) => { - match item.node { - ItemTrait(_, _, ref ms) => { - let (_, p) = - ast_util::split_trait_methods(ms.as_slice()); - p.iter() - .map(|m| method(cx, ast_util::local_def(m.id))) - .collect() - } - _ => { - cx.sess.bug(format!("provided_trait_methods: \ - `{:?}` is not a trait", - id)) - } + match cx.map.find(id.node) { + Some(ast_map::NodeItem(item)) => { + match item.node { + ItemTrait(_, _, ref ms) => { + let (_, p) = ast_util::split_trait_methods(ms.as_slice()); + p.iter().map(|m| method(cx, ast_util::local_def(m.id))).collect() } - } - _ => { - cx.sess.bug(format!("provided_trait_methods: `{:?}` is not \ - a trait", - id)) + _ => cx.sess.bug(format!("provided_trait_methods: `{}` is not a trait", id)) } } + _ => cx.sess.bug(format!("provided_trait_methods: `{}` is not a trait", id)) } } else { csearch::get_provided_trait_methods(cx, id) } } -pub fn trait_supertraits(cx: &ctxt, id: ast::DefId) -> @Vec<@TraitRef> { +pub fn trait_supertraits(cx: &ctxt, id: ast::DefId) -> Rc>> { // Check the cache. match cx.supertraits.borrow().find(&id) { - Some(&trait_refs) => { return trait_refs; } + Some(trait_refs) => { return trait_refs.clone(); } None => {} // Continue. } @@ -3524,12 +3513,12 @@ pub fn trait_supertraits(cx: &ctxt, id: ast::DefId) -> @Vec<@TraitRef> { // Get the supertraits out of the metadata and create the // TraitRef for each. - let result = @csearch::get_supertraits(cx, id); - cx.supertraits.borrow_mut().insert(id, result); - return result; + let result = Rc::new(csearch::get_supertraits(cx, id)); + cx.supertraits.borrow_mut().insert(id, result.clone()); + result } -pub fn trait_ref_supertraits(cx: &ctxt, trait_ref: &ty::TraitRef) -> Vec<@TraitRef> { +pub fn trait_ref_supertraits(cx: &ctxt, trait_ref: &ty::TraitRef) -> Vec> { let supertrait_refs = trait_supertraits(cx, trait_ref.def_id); supertrait_refs.iter().map( |supertrait_ref| supertrait_ref.subst(cx, &trait_ref.substs)).collect() @@ -3563,44 +3552,46 @@ fn lookup_locally_or_in_crate_store( v } -pub fn trait_method(cx: &ctxt, trait_did: ast::DefId, idx: uint) -> @Method { +pub fn trait_method(cx: &ctxt, trait_did: ast::DefId, idx: uint) -> Rc { let method_def_id = *ty::trait_method_def_ids(cx, trait_did).get(idx); ty::method(cx, method_def_id) } -pub fn trait_methods(cx: &ctxt, trait_did: ast::DefId) -> @Vec<@Method> { +pub fn trait_methods(cx: &ctxt, trait_did: ast::DefId) -> Rc>> { let mut trait_methods = cx.trait_methods_cache.borrow_mut(); - match trait_methods.find(&trait_did) { - Some(&methods) => methods, + match trait_methods.find_copy(&trait_did) { + Some(methods) => methods, None => { let def_ids = ty::trait_method_def_ids(cx, trait_did); - let methods = @def_ids.iter().map(|d| ty::method(cx, *d)).collect(); - trait_methods.insert(trait_did, methods); + let methods: Rc>> = Rc::new(def_ids.iter().map(|d| { + ty::method(cx, *d) + }).collect()); + trait_methods.insert(trait_did, methods.clone()); methods } } } -pub fn method(cx: &ctxt, id: ast::DefId) -> @Method { +pub fn method(cx: &ctxt, id: ast::DefId) -> Rc { lookup_locally_or_in_crate_store("methods", id, &mut *cx.methods.borrow_mut(), || { - @csearch::get_method(cx, id) + Rc::new(csearch::get_method(cx, id)) }) } -pub fn trait_method_def_ids(cx: &ctxt, id: ast::DefId) -> @Vec { +pub fn trait_method_def_ids(cx: &ctxt, id: ast::DefId) -> Rc> { lookup_locally_or_in_crate_store("trait_method_def_ids", id, &mut *cx.trait_method_def_ids.borrow_mut(), || { - @csearch::get_trait_method_def_ids(&cx.sess.cstore, id) + Rc::new(csearch::get_trait_method_def_ids(&cx.sess.cstore, id)) }) } -pub fn impl_trait_ref(cx: &ctxt, id: ast::DefId) -> Option<@TraitRef> { +pub fn impl_trait_ref(cx: &ctxt, id: ast::DefId) -> Option> { match cx.impl_trait_cache.borrow().find(&id) { - Some(&ret) => { return ret; } + Some(ret) => { return ret.clone(); } None => {} } @@ -3626,8 +3617,8 @@ pub fn impl_trait_ref(cx: &ctxt, id: ast::DefId) -> Option<@TraitRef> { csearch::get_impl_trait(cx, id) }; - cx.impl_trait_cache.borrow_mut().insert(id, ret); - return ret; + cx.impl_trait_cache.borrow_mut().insert(id, ret.clone()); + ret } pub fn trait_ref_to_def_id(tcx: &ctxt, tr: &ast::TraitRef) -> ast::DefId { @@ -3730,18 +3721,18 @@ impl VariantInfo { pub fn substd_enum_variants(cx: &ctxt, id: ast::DefId, substs: &substs) - -> Vec<@VariantInfo> { + -> Vec> { enum_variants(cx, id).iter().map(|variant_info| { let substd_args = variant_info.args.iter() .map(|aty| subst(cx, substs, *aty)).collect(); let substd_ctor_ty = subst(cx, substs, variant_info.ctor_ty); - @VariantInfo { + Rc::new(VariantInfo { args: substd_args, ctor_ty: substd_ctor_ty, ..(**variant_info).clone() - } + }) }).collect() } @@ -3810,27 +3801,26 @@ pub fn type_is_empty(cx: &ctxt, t: t) -> bool { } } -pub fn enum_variants(cx: &ctxt, id: ast::DefId) -> @Vec<@VariantInfo> { +pub fn enum_variants(cx: &ctxt, id: ast::DefId) -> Rc>> { match cx.enum_var_cache.borrow().find(&id) { - Some(&variants) => return variants, + Some(variants) => return variants.clone(), _ => { /* fallthrough */ } } let result = if ast::LOCAL_CRATE != id.krate { - @csearch::get_enum_variants(cx, id) + Rc::new(csearch::get_enum_variants(cx, id)) } else { /* Although both this code and check_enum_variants in typeck/check call eval_const_expr, it should never get called twice for the same expr, since check_enum_variants also updates the enum_var_cache */ - { - match cx.map.get(id.node) { - ast_map::NodeItem(item) => { - match item.node { + match cx.map.get(id.node) { + ast_map::NodeItem(item) => { + match item.node { ast::ItemEnum(ref enum_definition, _) => { let mut last_discriminant: Option = None; - @enum_definition.variants.iter().map(|&variant| { + Rc::new(enum_definition.variants.iter().map(|&variant| { let mut discriminant = match last_discriminant { Some(val) => val + 1, @@ -3848,40 +3838,33 @@ pub fn enum_variants(cx: &ctxt, id: ast::DefId) -> @Vec<@VariantInfo> { Ok(_) => { cx.sess .span_err(e.span, - "expected signed integer \ - constant"); + "expected signed integer constant"); } Err(ref err) => { cx.sess .span_err(e.span, - format!("expected \ - constant: {}", + format!("expected constant: {}", *err)); } }, None => {} }; - let variant_info = - @VariantInfo::from_ast_variant(cx, - variant, - discriminant); last_discriminant = Some(discriminant); - variant_info - - }).collect() + Rc::new(VariantInfo::from_ast_variant(cx, variant, + discriminant)) + }).collect()) } _ => { cx.sess.bug("enum_variants: id not bound to an enum") } - } - } - _ => cx.sess.bug("enum_variants: id not bound to an enum") + } } + _ => cx.sess.bug("enum_variants: id not bound to an enum") } }; - cx.enum_var_cache.borrow_mut().insert(id, result); + cx.enum_var_cache.borrow_mut().insert(id, result.clone()); result } @@ -3890,17 +3873,11 @@ pub fn enum_variants(cx: &ctxt, id: ast::DefId) -> @Vec<@VariantInfo> { pub fn enum_variant_with_id(cx: &ctxt, enum_id: ast::DefId, variant_id: ast::DefId) - -> @VariantInfo { - let variants = enum_variants(cx, enum_id); - let mut i = 0; - while i < variants.len() { - let variant = *variants.get(i); - if variant.id == variant_id { - return variant - } - i += 1; - } - cx.sess.bug("enum_variant_with_id(): no variant exists with that ID"); + -> Rc { + enum_variants(cx, enum_id).iter() + .find(|variant| variant.id == variant_id) + .expect("enum_variant_with_id(): no variant exists with that ID") + .clone() } @@ -3923,19 +3900,19 @@ pub fn lookup_impl_vtables(cx: &ctxt, } /// Given the did of a trait, returns its canonical trait ref. -pub fn lookup_trait_def(cx: &ctxt, did: ast::DefId) -> @ty::TraitDef { +pub fn lookup_trait_def(cx: &ctxt, did: ast::DefId) -> Rc { let mut trait_defs = cx.trait_defs.borrow_mut(); - match trait_defs.find(&did) { - Some(&trait_def) => { + match trait_defs.find_copy(&did) { + Some(trait_def) => { // The item is in this crate. The caller should have added it to the // type cache already - return trait_def; + trait_def } None => { assert!(did.krate != ast::LOCAL_CRATE); - let trait_def = @csearch::get_trait_def(cx, did); - trait_defs.insert(did, trait_def); - return trait_def; + let trait_def = Rc::new(csearch::get_trait_def(cx, did)); + trait_defs.insert(did, trait_def.clone()); + trait_def } } } @@ -3943,7 +3920,7 @@ pub fn lookup_trait_def(cx: &ctxt, did: ast::DefId) -> @ty::TraitDef { /// Iterate over meta_items of a definition. // (This should really be an iterator, but that would require csearch and // decoder to use iterators instead of higher-order functions.) -pub fn each_attr(tcx: &ctxt, did: DefId, f: |@MetaItem| -> bool) -> bool { +pub fn each_attr(tcx: &ctxt, did: DefId, f: |@ast::MetaItem| -> bool) -> bool { if is_local(did) { let item = tcx.map.expect_item(did.node); item.attrs.iter().advance(|attr| f(attr.node.value)) @@ -4017,20 +3994,21 @@ pub fn lookup_field_type(tcx: &ctxt, // Lookup all ancestor structs of a struct indicated by did. That is the reflexive, // transitive closure of doing a single lookup in cx.superstructs. -fn lookup_super_structs(cx: &ctxt, - did: ast::DefId) -> Vec { - let mut this_result: Vec = vec!(did); - match cx.superstructs.borrow().find(&did) { - Some(&Some(def_id)) => { - let ss: Vec = lookup_super_structs(cx, def_id); - this_result.extend(ss.move_iter()); - this_result - }, - Some(&None) => this_result, - None => { - cx.sess.bug( - format!("ID not mapped to super-struct: {}", - cx.map.node_to_str(did.node))); +fn each_super_struct(cx: &ctxt, mut did: ast::DefId, f: |ast::DefId|) { + let superstructs = cx.superstructs.borrow(); + + loop { + f(did); + match superstructs.find(&did) { + Some(&Some(def_id)) => { + did = def_id; + }, + Some(&None) => break, + None => { + cx.sess.bug( + format!("ID not mapped to super-struct: {}", + cx.map.node_to_str(did.node))); + } } } } @@ -4043,26 +4021,22 @@ pub fn lookup_struct_fields(cx: &ctxt, did: ast::DefId) -> Vec { // we have to walk the inheritance chain of the struct to get all the // structs (explicit and inherited) for a struct. If this is expensive // we could cache the whole list of fields here. - let structs = lookup_super_structs(cx, did); let struct_fields = cx.struct_fields.borrow(); - let results: Vec<&@Vec> = structs.iter().map(|s| { - match struct_fields.find(s) { - Some(fields) => fields, + let mut results: SmallVector<&[field_ty]> = SmallVector::zero(); + each_super_struct(cx, did, |s| { + match struct_fields.find(&s) { + Some(fields) => results.push(fields.as_slice()), _ => { cx.sess.bug( format!("ID not mapped to struct fields: {}", cx.map.node_to_str(did.node))); } } - }).collect(); + }); - let len = results.iter().map(|x| x.len()).fold(0, |a, b| a + b); + let len = results.as_slice().iter().map(|x| x.len()).sum(); let mut result: Vec = Vec::with_capacity(len); - for rs in results.iter() { - for r in rs.iter() { - result.push(*r); - } - } + result.extend(results.as_slice().iter().flat_map(|rs| rs.iter().map(|&f| f))); assert!(result.len() == len); result } else { @@ -4293,31 +4267,31 @@ pub fn eval_repeat_count(tcx: &T, count_expr: &ast::Expr) -> // relation on the supertraits from each bounded trait's constraint // list. pub fn each_bound_trait_and_supertraits(tcx: &ctxt, - bounds: &[@TraitRef], - f: |@TraitRef| -> bool) + bounds: &[Rc], + f: |Rc| -> bool) -> bool { - for &bound_trait_ref in bounds.iter() { + for bound_trait_ref in bounds.iter() { let mut supertrait_set = HashMap::new(); let mut trait_refs = Vec::new(); let mut i = 0; // Seed the worklist with the trait from the bound supertrait_set.insert(bound_trait_ref.def_id, ()); - trait_refs.push(bound_trait_ref); + trait_refs.push(bound_trait_ref.clone()); // Add the given trait ty to the hash map while i < trait_refs.len() { debug!("each_bound_trait_and_supertraits(i={:?}, trait_ref={})", i, trait_refs.get(i).repr(tcx)); - if !f(*trait_refs.get(i)) { + if !f(trait_refs.get(i).clone()) { return false; } // Add supertraits to supertrait_set let supertrait_refs = trait_ref_supertraits(tcx, - *trait_refs.get(i)); - for &supertrait_ref in supertrait_refs.iter() { + &**trait_refs.get(i)); + for supertrait_ref in supertrait_refs.iter() { debug!("each_bound_trait_and_supertraits(supertrait_ref={})", supertrait_ref.repr(tcx)); @@ -4325,7 +4299,7 @@ pub fn each_bound_trait_and_supertraits(tcx: &ctxt, if !supertrait_set.contains_key(&d_id) { // FIXME(#5527) Could have same trait multiple times supertrait_set.insert(d_id, ()); - trait_refs.push(supertrait_ref); + trait_refs.push(supertrait_ref.clone()); } } @@ -4350,7 +4324,7 @@ pub fn get_opaque_ty(tcx: &ctxt) -> Result { } pub fn visitor_object_ty(tcx: &ctxt, - region: ty::Region) -> Result<(@TraitRef, t), ~str> { + region: ty::Region) -> Result<(Rc, t), ~str> { let trait_lang_item = match tcx.lang_items.require(TyVisitorTraitLangItem) { Ok(id) => id, Err(s) => { return Err(s); } @@ -4360,8 +4334,8 @@ pub fn visitor_object_ty(tcx: &ctxt, self_ty: None, tps: Vec::new() }; - let trait_ref = @TraitRef { def_id: trait_lang_item, substs: substs }; - Ok((trait_ref, + let trait_ref = Rc::new(TraitRef { def_id: trait_lang_item, substs: substs }); + Ok((trait_ref.clone(), mk_trait(tcx, trait_ref.def_id, trait_ref.substs.clone(), @@ -4369,10 +4343,10 @@ pub fn visitor_object_ty(tcx: &ctxt, EmptyBuiltinBounds()))) } -pub fn item_variances(tcx: &ctxt, item_id: ast::DefId) -> @ItemVariances { +pub fn item_variances(tcx: &ctxt, item_id: ast::DefId) -> Rc { lookup_locally_or_in_crate_store( "item_variance_map", item_id, &mut *tcx.item_variance_map.borrow_mut(), - || @csearch::get_item_variances(&tcx.sess.cstore, item_id)) + || Rc::new(csearch::get_item_variances(&tcx.sess.cstore, item_id))) } /// Records a trait-to-implementation mapping. @@ -4386,7 +4360,7 @@ pub fn record_trait_implementation(tcx: &ctxt, } None => {} } - tcx.trait_impls.borrow_mut().insert(trait_def_id, @RefCell::new(vec!(impl_def_id))); + tcx.trait_impls.borrow_mut().insert(trait_def_id, Rc::new(RefCell::new(vec!(impl_def_id)))); } /// Populates the type context with all the implementations for the given type @@ -4430,7 +4404,8 @@ pub fn populate_implementations_for_type_if_necessary(tcx: &ctxt, } None => {} } - tcx.inherent_impls.borrow_mut().insert(type_id, @RefCell::new(vec!(impl_def_id))); + tcx.inherent_impls.borrow_mut().insert(type_id, + Rc::new(RefCell::new(vec!(impl_def_id)))); } }); @@ -4500,7 +4475,7 @@ pub fn trait_of_method(tcx: &ctxt, def_id: ast::DefId) if def_id.krate != LOCAL_CRATE { return csearch::get_trait_of_method(&tcx.sess.cstore, def_id, tcx); } - match tcx.methods.borrow().find(&def_id).map(|m| *m) { + match tcx.methods.borrow().find_copy(&def_id) { Some(method) => { match method.container { TraitContainer(def_id) => Some(def_id), @@ -4520,7 +4495,7 @@ pub fn trait_of_method(tcx: &ctxt, def_id: ast::DefId) pub fn trait_method_of_method(tcx: &ctxt, def_id: ast::DefId) -> Option { let method = match tcx.methods.borrow().find(&def_id) { - Some(&m) => m, + Some(m) => m.clone(), None => return None, }; let name = method.ident.name; @@ -4689,7 +4664,7 @@ impl Variance { pub fn construct_parameter_environment( tcx: &ctxt, - self_bound: Option<@TraitRef>, + self_bound: Option>, item_type_params: &[TypeParameterDef], method_type_params: &[TypeParameterDef], item_region_params: &[RegionParameterDef], @@ -4704,7 +4679,7 @@ pub fn construct_parameter_environment( // // map Self => Self - let self_ty = self_bound.map(|t| ty::mk_self(tcx, t.def_id)); + let self_ty = self_bound.as_ref().map(|t| ty::mk_self(tcx, t.def_id)); // map A => A let num_item_type_params = item_type_params.len(); diff --git a/src/librustc/middle/typeck/astconv.rs b/src/librustc/middle/typeck/astconv.rs index 5de2a60114a7..6ae68bdbad12 100644 --- a/src/librustc/middle/typeck/astconv.rs +++ b/src/librustc/middle/typeck/astconv.rs @@ -60,6 +60,7 @@ use middle::typeck::rscope::{RegionScope}; use middle::typeck::lookup_def_tcx; use util::ppaux::Repr; +use std::rc::Rc; use syntax::abi; use syntax::{ast, ast_util}; use syntax::codemap::Span; @@ -69,7 +70,7 @@ use syntax::print::pprust::{lifetime_to_str, path_to_str}; pub trait AstConv { fn tcx<'a>(&'a self) -> &'a ty::ctxt; fn get_item_ty(&self, id: ast::DefId) -> ty::ty_param_bounds_and_ty; - fn get_trait_def(&self, id: ast::DefId) -> @ty::TraitDef; + fn get_trait_def(&self, id: ast::DefId) -> Rc; // what type should we use when a type is omitted? fn ty_infer(&self, span: Span) -> ty::t; @@ -261,25 +262,16 @@ pub fn ast_path_to_substs_and_ty( - this: &AC, - rscope: &RS, - trait_def_id: ast::DefId, - self_ty: Option, - path: &ast::Path) -> @ty::TraitRef -{ - let trait_def = - this.get_trait_def(trait_def_id); - let substs = - ast_path_substs( - this, - rscope, - &trait_def.generics, - self_ty, - path); - let trait_ref = - @ty::TraitRef {def_id: trait_def_id, - substs: substs}; - return trait_ref; + this: &AC, + rscope: &RS, + trait_def_id: ast::DefId, + self_ty: Option, + path: &ast::Path) -> Rc { + let trait_def = this.get_trait_def(trait_def_id); + Rc::new(ty::TraitRef { + def_id: trait_def_id, + substs: ast_path_substs(this, rscope, &trait_def.generics, self_ty, path) + }) } pub fn ast_path_to_ty( diff --git a/src/librustc/middle/typeck/check/method.rs b/src/librustc/middle/typeck/check/method.rs index b2b0054fb4d3..3b33a17d5825 100644 --- a/src/librustc/middle/typeck/check/method.rs +++ b/src/librustc/middle/typeck/check/method.rs @@ -30,7 +30,7 @@ itself (note that inherent impls can only be defined in the same module as the type itself). Inherent candidates are not always derived from impls. If you have a -trait instance, such as a value of type `@ToStr`, then the trait +trait instance, such as a value of type `~ToStr`, then the trait methods (`to_str()`, in this case) are inherently associated with it. Another case is type parameters, in which case the methods of their bounds are inherent. @@ -97,7 +97,7 @@ use util::ppaux; use util::ppaux::Repr; use collections::HashSet; -use std::result; +use std::rc::Rc; use syntax::ast::{DefId, SelfValue, SelfRegion}; use syntax::ast::{SelfUniq, SelfStatic}; use syntax::ast::{MutMutable, MutImmutable}; @@ -203,7 +203,7 @@ pub fn lookup_in_trait<'a>( // to a trait and its supertraits. fn get_method_index(tcx: &ty::ctxt, trait_ref: &TraitRef, - subtrait: @TraitRef, + subtrait: Rc, n_method: uint) -> uint { // We need to figure the "real index" of the method in a // listing of all the methods of an object. We do this by @@ -311,7 +311,7 @@ struct LookupContext<'a> { struct Candidate { rcvr_match_condition: RcvrMatchCondition, rcvr_substs: ty::substs, - method_ty: @ty::Method, + method_ty: Rc, origin: MethodOrigin, } @@ -412,7 +412,7 @@ impl<'a> LookupContext<'a> { * `self.inherent_candidates`. See comment at the start of * the file. To find the inherent candidates, we repeatedly * deref the self-ty to find the "base-type". So, for - * example, if the receiver is @@C where `C` is a struct type, + * example, if the receiver is ~~C where `C` is a struct type, * we'll want to find the inherent impls for `C`. */ @@ -511,12 +511,15 @@ impl<'a> LookupContext<'a> { self_ty: Some(ty::mk_err()), ..(*substs).clone() }; - let trait_ref = @TraitRef { def_id: did, substs: rcvr_substs.clone() }; + let trait_ref = Rc::new(TraitRef { + def_id: did, + substs: rcvr_substs.clone() + }); - self.push_inherent_candidates_from_bounds_inner(&[trait_ref], + self.push_inherent_candidates_from_bounds_inner(&[trait_ref.clone()], |new_trait_ref, m, method_num, _bound_num| { - let vtable_index = get_method_index(tcx, new_trait_ref, - trait_ref, method_num); + let vtable_index = get_method_index(tcx, &*new_trait_ref, + trait_ref.clone(), method_num); let mut m = (*m).clone(); // We need to fix up the transformed self type. *m.fty.sig.inputs.get_mut(0) = @@ -526,7 +529,7 @@ impl<'a> LookupContext<'a> { Some(Candidate { rcvr_match_condition: RcvrMatchesIfObject(did), rcvr_substs: new_trait_ref.substs.clone(), - method_ty: @m, + method_ty: Rc::new(m), origin: MethodObject(MethodObject { trait_id: new_trait_ref.def_id, object_trait_id: did, @@ -563,14 +566,14 @@ impl<'a> LookupContext<'a> { debug!("push_inherent_candidates_from_self()"); self.push_inherent_candidates_from_bounds( rcvr_ty, - [self.fcx.inh.param_env.self_param_bound.unwrap()], + [self.fcx.inh.param_env.self_param_bound.clone().unwrap()], restrict_to, param_self) } fn push_inherent_candidates_from_bounds(&mut self, self_ty: ty::t, - bounds: &[@TraitRef], + bounds: &[Rc], restrict_to: Option, param: param_index) { self.push_inherent_candidates_from_bounds_inner(bounds, @@ -600,9 +603,9 @@ impl<'a> LookupContext<'a> { // Do a search through a list of bounds, using a callback to actually // create the candidates. fn push_inherent_candidates_from_bounds_inner(&mut self, - bounds: &[@TraitRef], - mk_cand: |tr: @TraitRef, - m: @ty::Method, + bounds: &[Rc], + mk_cand: |tr: Rc, + m: Rc, method_num: uint, bound_num: uint| -> Option) { @@ -618,7 +621,7 @@ impl<'a> LookupContext<'a> { m.explicit_self != ast::SelfStatic && m.ident.name == self.m_name }) { Some(pos) => { - let method = *trait_methods.get(pos); + let method = trait_methods.get(pos).clone(); match mk_cand(bound_trait_ref, method, pos, this_bound_idx) { Some(cand) => { @@ -692,8 +695,8 @@ impl<'a> LookupContext<'a> { candidates.push(Candidate { rcvr_match_condition: RcvrMatchesIfSubtype(impl_ty), rcvr_substs: impl_substs, + origin: MethodStatic(method.def_id), method_ty: method, - origin: MethodStatic(method.def_id) }); } @@ -874,7 +877,7 @@ impl<'a> LookupContext<'a> { } ty_trait(~ty::TyTrait { def_id: trt_did, substs: trt_substs, bounds: b, .. }) => { - // Coerce ~/@/&Trait instances to &Trait. + // Coerce ~/&Trait instances to &Trait. self.search_for_some_kind_of_autorefd_method( AutoBorrowObj, autoderefs, [MutImmutable, MutMutable], @@ -1184,8 +1187,8 @@ impl<'a> LookupContext<'a> { let span = self.self_expr.map_or(self.span, |e| e.span); match self.fcx.mk_subty(false, infer::Misc(span), rcvr_ty, transformed_self_ty) { - result::Ok(_) => {} - result::Err(_) => { + Ok(_) => {} + Err(_) => { self.bug(format!("{} was a subtype of {} but now is not?", self.ty_to_str(rcvr_ty), self.ty_to_str(transformed_self_ty))); diff --git a/src/librustc/middle/typeck/check/mod.rs b/src/librustc/middle/typeck/check/mod.rs index 57f6eb72516a..42061d681447 100644 --- a/src/librustc/middle/typeck/check/mod.rs +++ b/src/librustc/middle/typeck/check/mod.rs @@ -117,7 +117,7 @@ use util::nodemap::{FnvHashMap, NodeMap}; use std::cell::{Cell, RefCell}; use collections::HashMap; use std::mem::replace; -use std::result; +use std::rc::Rc; use std::vec::Vec; use syntax::abi; use syntax::ast::{Provided, Required}; @@ -622,9 +622,9 @@ pub fn check_item(ccx: &CrateCtxt, it: &ast::Item) { it.span, &impl_tpt.generics, ast_trait_ref, - impl_trait_ref, + &*impl_trait_ref, ms.as_slice()); - vtable::resolve_impl(ccx.tcx, it, &impl_tpt.generics, impl_trait_ref); + vtable::resolve_impl(ccx.tcx, it, &impl_tpt.generics, &*impl_trait_ref); } None => { } } @@ -640,7 +640,7 @@ pub fn check_item(ccx: &CrateCtxt, it: &ast::Item) { } Provided(m) => { check_method_body(ccx, &trait_def.generics, - Some(trait_def.trait_ref), m); + Some(trait_def.trait_ref.clone()), m); } } } @@ -682,7 +682,7 @@ pub fn check_item(ccx: &CrateCtxt, it: &ast::Item) { fn check_method_body(ccx: &CrateCtxt, item_generics: &ty::Generics, - self_bound: Option<@ty::TraitRef>, + self_bound: Option>, method: &ast::Method) { /*! * Type checks a method body. @@ -744,10 +744,10 @@ fn check_impl_methods_against_trait(ccx: &CrateCtxt, Some(trait_method_ty) => { compare_impl_method(ccx.tcx, impl_generics, - impl_method_ty, + &*impl_method_ty, impl_method.span, impl_method.body.id, - *trait_method_ty, + &**trait_method_ty, &impl_trait_ref.substs); } None => { @@ -800,7 +800,7 @@ fn check_impl_methods_against_trait(ccx: &CrateCtxt, */ fn compare_impl_method(tcx: &ty::ctxt, impl_generics: &ty::Generics, - impl_m: @ty::Method, + impl_m: &ty::Method, impl_m_span: Span, impl_m_body_id: ast::NodeId, trait_m: &ty::Method, @@ -973,8 +973,8 @@ fn compare_impl_method(tcx: &ty::ctxt, match infer::mk_subty(&infcx, false, infer::MethodCompatCheck(impl_m_span), impl_fty, trait_fty) { - result::Ok(()) => {} - result::Err(ref terr) => { + Ok(()) => {} + Err(ref terr) => { tcx.sess.span_err( impl_m_span, format!("method `{}` has an incompatible type for trait: {}", @@ -992,7 +992,7 @@ impl<'a> AstConv for FnCtxt<'a> { ty::lookup_item_type(self.tcx(), id) } - fn get_trait_def(&self, id: ast::DefId) -> @ty::TraitDef { + fn get_trait_def(&self, id: ast::DefId) -> Rc { ty::lookup_trait_def(self.tcx(), id) } @@ -1175,8 +1175,8 @@ impl<'a> FnCtxt<'a> { infer::ExprAssignable(expr.span), sub, sup) { - Ok(None) => result::Ok(()), - Err(ref e) => result::Err((*e)), + Ok(None) => Ok(()), + Err(ref e) => Err((*e)), Ok(Some(adjustment)) => { self.write_adjustment(expr.id, adjustment); Ok(()) @@ -2844,8 +2844,8 @@ fn check_expr_with_unifier(fcx: &FnCtxt, match expr_opt { None => match fcx.mk_eqty(false, infer::Misc(expr.span), ret_ty, ty::mk_nil()) { - result::Ok(_) => { /* fall through */ } - result::Err(_) => { + Ok(_) => { /* fall through */ } + Err(_) => { tcx.sess.span_err( expr.span, "`return;` in function returning non-nil"); @@ -3541,10 +3541,10 @@ pub fn check_enum_variants(ccx: &CrateCtxt, vs: &[ast::P], id: ast::NodeId, hint: attr::ReprAttr) - -> Vec<@ty::VariantInfo> { + -> Vec> { let rty = ty::node_id_to_type(ccx.tcx, id); - let mut variants: Vec<@ty::VariantInfo> = Vec::new(); + let mut variants: Vec> = Vec::new(); let mut disr_vals: Vec = Vec::new(); let mut prev_disr_val: Option = None; @@ -3600,7 +3600,8 @@ pub fn check_enum_variants(ccx: &CrateCtxt, } disr_vals.push(current_disr_val); - let variant_info = @VariantInfo::from_ast_variant(ccx.tcx, v, current_disr_val); + let variant_info = Rc::new(VariantInfo::from_ast_variant(ccx.tcx, v, + current_disr_val)); prev_disr_val = Some(current_disr_val); variants.push(variant_info); @@ -3622,7 +3623,7 @@ pub fn check_enum_variants(ccx: &CrateCtxt, let variants = do_check(ccx, vs, id, hint); // cache so that ty::enum_variants won't repeat this work - ccx.tcx.enum_var_cache.borrow_mut().insert(local_def(id), @variants); + ccx.tcx.enum_var_cache.borrow_mut().insert(local_def(id), Rc::new(variants)); // Check that it is possible to represent this enum. check_representable(ccx.tcx, sp, id, "enum"); diff --git a/src/librustc/middle/typeck/check/regionck.rs b/src/librustc/middle/typeck/check/regionck.rs index 7273023e1bfe..94cbd3a3a750 100644 --- a/src/librustc/middle/typeck/check/regionck.rs +++ b/src/librustc/middle/typeck/check/regionck.rs @@ -1008,7 +1008,7 @@ fn constrain_regions_in_type( // for regions that are as-yet-unknown. } else if r_sub == minimum_lifetime { rcx.fcx.mk_subr( - true, origin, + true, origin.clone(), r_sub, r_sup); } else { rcx.fcx.mk_subr( diff --git a/src/librustc/middle/typeck/check/vtable.rs b/src/librustc/middle/typeck/check/vtable.rs index 792c89e43f9c..bb57fa2646bf 100644 --- a/src/librustc/middle/typeck/check/vtable.rs +++ b/src/librustc/middle/typeck/check/vtable.rs @@ -27,6 +27,7 @@ use util::common::indenter; use util::ppaux; use util::ppaux::Repr; +use std::rc::Rc; use collections::HashSet; use syntax::ast; use syntax::ast_util; @@ -137,7 +138,7 @@ fn lookup_vtables_for_param(vcx: &VtableContext, // Substitute the values of the type parameters that may // appear in the bound. - let trait_ref = substs.as_ref().map_or(trait_ref, |substs| { + let trait_ref = substs.as_ref().map_or(trait_ref.clone(), |substs| { debug!("about to subst: {}, {}", trait_ref.repr(tcx), substs.repr(tcx)); trait_ref.subst(tcx, *substs) @@ -145,13 +146,13 @@ fn lookup_vtables_for_param(vcx: &VtableContext, debug!("after subst: {}", trait_ref.repr(tcx)); - match lookup_vtable(vcx, span, ty, trait_ref, is_early) { + match lookup_vtable(vcx, span, ty, trait_ref.clone(), is_early) { Some(vtable) => param_result.push(vtable), None => { vcx.tcx().sess.span_fatal(span, format!("failed to find an implementation of \ trait {} for {}", - vcx.infcx.trait_ref_to_str(trait_ref), + vcx.infcx.trait_ref_to_str(&*trait_ref), vcx.infcx.ty_to_str(ty))); } } @@ -173,8 +174,8 @@ fn lookup_vtables_for_param(vcx: &VtableContext, fn relate_trait_refs(vcx: &VtableContext, span: Span, - act_trait_ref: @ty::TraitRef, - exp_trait_ref: @ty::TraitRef) { + act_trait_ref: Rc, + exp_trait_ref: Rc) { /*! * * Checks that an implementation of `act_trait_ref` is suitable @@ -185,17 +186,17 @@ fn relate_trait_refs(vcx: &VtableContext, match infer::mk_sub_trait_refs(vcx.infcx, false, infer::RelateTraitRefs(span), - act_trait_ref, - exp_trait_ref) { + act_trait_ref.clone(), + exp_trait_ref.clone()) { Ok(()) => {} // Ok. Err(ref err) => { // There is an error, but we need to do some work to make // the message good. // Resolve any type vars in the trait refs let r_act_trait_ref = - vcx.infcx.resolve_type_vars_in_trait_ref_if_possible(act_trait_ref); + vcx.infcx.resolve_type_vars_in_trait_ref_if_possible(&*act_trait_ref); let r_exp_trait_ref = - vcx.infcx.resolve_type_vars_in_trait_ref_if_possible(exp_trait_ref); + vcx.infcx.resolve_type_vars_in_trait_ref_if_possible(&*exp_trait_ref); // Only print the message if there aren't any previous type errors // inside the types. if !ty::trait_ref_contains_error(&r_act_trait_ref) && @@ -216,12 +217,12 @@ fn relate_trait_refs(vcx: &VtableContext, fn lookup_vtable(vcx: &VtableContext, span: Span, ty: ty::t, - trait_ref: @ty::TraitRef, + trait_ref: Rc, is_early: bool) -> Option { debug!("lookup_vtable(ty={}, trait_ref={})", vcx.infcx.ty_to_str(ty), - vcx.infcx.trait_ref_to_str(trait_ref)); + vcx.infcx.trait_ref_to_str(&*trait_ref)); let _i = indenter(); let ty = match fixup_ty(vcx, span, ty, is_early) { @@ -242,23 +243,23 @@ fn lookup_vtable(vcx: &VtableContext, ty::ty_param(param_ty {idx: n, ..}) => { let env_bounds = &vcx.param_env.type_param_bounds; if env_bounds.len() > n { - let type_param_bounds: &[@ty::TraitRef] = + let type_param_bounds: &[Rc] = env_bounds.get(n).trait_bounds.as_slice(); lookup_vtable_from_bounds(vcx, span, type_param_bounds, param_numbered(n), - trait_ref) + trait_ref.clone()) } else { None } } ty::ty_self(_) => { - let self_param_bound = vcx.param_env.self_param_bound.unwrap(); + let self_param_bound = vcx.param_env.self_param_bound.clone().unwrap(); lookup_vtable_from_bounds(vcx, span, [self_param_bound], param_self, - trait_ref) + trait_ref.clone()) } // Default case just falls through @@ -276,9 +277,9 @@ fn lookup_vtable(vcx: &VtableContext, // of them are the vtable we are looking for. fn lookup_vtable_from_bounds(vcx: &VtableContext, span: Span, - bounds: &[@ty::TraitRef], + bounds: &[Rc], param: param_index, - trait_ref: @ty::TraitRef) + trait_ref: Rc) -> Option { let tcx = vcx.tcx(); @@ -289,7 +290,7 @@ fn lookup_vtable_from_bounds(vcx: &VtableContext, bound_trait_ref.repr(vcx.tcx())); if bound_trait_ref.def_id == trait_ref.def_id { - relate_trait_refs(vcx, span, bound_trait_ref, trait_ref); + relate_trait_refs(vcx, span, bound_trait_ref, trait_ref.clone()); let vtable = vtable_param(param, n_bound); debug!("found param vtable: {:?}", vtable); @@ -306,7 +307,7 @@ fn lookup_vtable_from_bounds(vcx: &VtableContext, fn search_for_vtable(vcx: &VtableContext, span: Span, ty: ty::t, - trait_ref: @ty::TraitRef, + trait_ref: Rc, is_early: bool) -> Option { let tcx = vcx.tcx(); @@ -388,13 +389,13 @@ fn search_for_vtable(vcx: &VtableContext, // some value of U) with some_trait. This would fail if T // and U weren't compatible. - debug!("(checking vtable) @2 relating trait \ + debug!("(checking vtable) \\#2 relating trait \ ty {} to of_trait_ref {}", - vcx.infcx.trait_ref_to_str(trait_ref), - vcx.infcx.trait_ref_to_str(of_trait_ref)); + vcx.infcx.trait_ref_to_str(&*trait_ref), + vcx.infcx.trait_ref_to_str(&*of_trait_ref)); let of_trait_ref = of_trait_ref.subst(tcx, &substs); - relate_trait_refs(vcx, span, of_trait_ref, trait_ref); + relate_trait_refs(vcx, span, of_trait_ref, trait_ref.clone()); // Recall that trait_ref -- the trait type we're casting to -- @@ -429,7 +430,7 @@ fn search_for_vtable(vcx: &VtableContext, they will be unified with the bounds for \ the target ty, {}", vcx.infcx.tys_to_str(substs_f.tps.as_slice()), - vcx.infcx.trait_ref_to_str(trait_ref)); + vcx.infcx.trait_ref_to_str(&*trait_ref)); // Next, we unify the fixed-up substitutions for the impl self // ty with the substitutions from the trait type that we're @@ -438,7 +439,7 @@ fn search_for_vtable(vcx: &VtableContext, // I am a little confused about this, since it seems to be // very similar to the relate_trait_refs we already do, // but problems crop up if it is removed, so... -sully - connect_trait_tps(vcx, span, &substs_f, trait_ref, impl_did); + connect_trait_tps(vcx, span, &substs_f, trait_ref.clone(), impl_did); // Finally, we register that we found a matching impl, and // record the def ID of the impl as well as the resolved list @@ -502,7 +503,7 @@ fn fixup_ty(vcx: &VtableContext, fn connect_trait_tps(vcx: &VtableContext, span: Span, impl_substs: &ty::substs, - trait_ref: @ty::TraitRef, + trait_ref: Rc, impl_did: ast::DefId) { let tcx = vcx.tcx(); @@ -561,14 +562,14 @@ pub fn early_resolve_expr(ex: &ast::Expr, fcx: &FnCtxt, is_early: bool) { }; let vcx = fcx.vtable_context(); - let target_trait_ref = @ty::TraitRef { + let target_trait_ref = Rc::new(ty::TraitRef { def_id: target_def_id, substs: ty::substs { tps: target_substs.tps.clone(), regions: target_substs.regions.clone(), self_ty: Some(typ) } - }; + }); let param_bounds = ty::ParamBounds { builtin_bounds: ty::EmptyBuiltinBounds(), @@ -761,7 +762,7 @@ pub fn resolve_impl(tcx: &ty::ctxt, // but that falls out of doing this. let param_bounds = ty::ParamBounds { builtin_bounds: ty::EmptyBuiltinBounds(), - trait_bounds: vec!(@impl_trait_ref) + trait_bounds: vec!(Rc::new(impl_trait_ref)) }; let t = ty::node_id_to_type(tcx, impl_item.id); let t = t.subst(tcx, ¶m_env.free_substs); diff --git a/src/librustc/middle/typeck/coherence.rs b/src/librustc/middle/typeck/coherence.rs index 1ee227089bc0..3a50b0681e8b 100644 --- a/src/librustc/middle/typeck/coherence.rs +++ b/src/librustc/middle/typeck/coherence.rs @@ -330,13 +330,13 @@ impl<'a> CoherenceChecker<'a> { // Create substitutions for the various trait parameters. let new_method_ty = - @subst_receiver_types_in_method_ty( + Rc::new(subst_receiver_types_in_method_ty( tcx, impl_id, trait_ref, new_did, - *trait_method, - Some(trait_method.def_id)); + &**trait_method, + Some(trait_method.def_id))); debug!("new_method_ty={}", new_method_ty.repr(tcx)); all_methods.push(new_did); @@ -376,7 +376,8 @@ impl<'a> CoherenceChecker<'a> { None => {} } - tcx.inherent_impls.borrow_mut().insert(base_def_id, @RefCell::new(vec!(impl_def_id))); + tcx.inherent_impls.borrow_mut().insert(base_def_id, + Rc::new(RefCell::new(vec!(impl_def_id)))); } fn add_trait_impl(&self, base_def_id: DefId, impl_def_id: DefId) { @@ -575,7 +576,7 @@ impl<'a> CoherenceChecker<'a> { trait_ref.ref_id); self.instantiate_default_methods(local_def(item.id), - ty_trait_ref, + &*ty_trait_ref, &mut methods); } diff --git a/src/librustc/middle/typeck/collect.rs b/src/librustc/middle/typeck/collect.rs index dda5d8f0f399..0102001aa3cd 100644 --- a/src/librustc/middle/typeck/collect.rs +++ b/src/librustc/middle/typeck/collect.rs @@ -126,7 +126,7 @@ impl<'a> AstConv for CrateCtxt<'a> { } } - fn get_trait_def(&self, id: ast::DefId) -> @ty::TraitDef { + fn get_trait_def(&self, id: ast::DefId) -> Rc { get_trait_def(self, id) } @@ -195,7 +195,7 @@ pub fn ensure_trait_methods(ccx: &CrateCtxt, trait_id: ast::NodeId) { // For each method, construct a suitable ty::Method and // store it into the `tcx.methods` table: for m in ms.iter() { - let ty_method = @match m { + let ty_method = Rc::new(match m { &ast::Required(ref m) => { ty_method_of_trait_method( ccx, trait_id, &trait_ty_generics, @@ -209,10 +209,10 @@ pub fn ensure_trait_methods(ccx: &CrateCtxt, trait_id: ast::NodeId) { &m.id, &m.ident, &m.explicit_self, &m.generics, &m.fn_style, m.decl) } - }; + }); if ty_method.explicit_self == ast::SelfStatic { - make_static_method_ty(ccx, trait_id, ty_method, + make_static_method_ty(ccx, trait_id, &*ty_method, &trait_ty_generics); } @@ -221,7 +221,7 @@ pub fn ensure_trait_methods(ccx: &CrateCtxt, trait_id: ast::NodeId) { } // Add an entry mapping - let method_def_ids = @ms.iter().map(|m| { + let method_def_ids = Rc::new(ms.iter().map(|m| { match m { &ast::Required(ref ty_method) => { local_def(ty_method.id) @@ -230,7 +230,7 @@ pub fn ensure_trait_methods(ccx: &CrateCtxt, trait_id: ast::NodeId) { local_def(method.id) } } - }).collect(); + }).collect()); let trait_def_id = local_def(trait_id); tcx.trait_method_def_ids.borrow_mut() @@ -412,7 +412,7 @@ pub fn ensure_supertraits(ccx: &CrateCtxt, assert!(!tcx.supertraits.borrow().contains_key(&local_def(id))); let self_ty = ty::mk_self(ccx.tcx, local_def(id)); - let mut ty_trait_refs: Vec<@ty::TraitRef> = Vec::new(); + let mut ty_trait_refs: Vec> = Vec::new(); let mut bounds = ty::EmptyBuiltinBounds(); for ast_trait_ref in ast_trait_refs.iter() { let trait_def_id = ty::trait_ref_to_def_id(ccx.tcx, ast_trait_ref); @@ -434,7 +434,7 @@ pub fn ensure_supertraits(ccx: &CrateCtxt, } } - tcx.supertraits.borrow_mut().insert(local_def(id), @ty_trait_refs); + tcx.supertraits.borrow_mut().insert(local_def(id), Rc::new(ty_trait_refs)); bounds } @@ -489,12 +489,12 @@ fn convert_methods(ccx: &CrateCtxt, let num_rcvr_ty_params = rcvr_ty_generics.type_param_defs().len(); let m_ty_generics = ty_generics_for_fn_or_method(ccx, &m.generics, num_rcvr_ty_params); - let mty = @ty_of_method(ccx, - container, - *m, - untransformed_rcvr_ty, - rcvr_ast_generics, - rcvr_visibility); + let mty = Rc::new(ty_of_method(ccx, + container, + *m, + untransformed_rcvr_ty, + rcvr_ast_generics, + rcvr_visibility)); let fty = ty::mk_bare_fn(tcx, mty.fty.clone()); debug!("method {} (id {}) has type {}", m.ident.repr(ccx.tcx), @@ -726,7 +726,7 @@ pub fn convert_struct(ccx: &CrateCtxt, result }).collect(); - tcx.struct_fields.borrow_mut().insert(local_def(id), @field_tys); + tcx.struct_fields.borrow_mut().insert(local_def(id), Rc::new(field_tys)); let super_struct = match struct_def.super_struct { Some(t) => match t.node { @@ -813,8 +813,7 @@ pub fn convert_foreign(ccx: &CrateCtxt, i: &ast::ForeignItem) { pub fn instantiate_trait_ref(ccx: &CrateCtxt, ast_trait_ref: &ast::TraitRef, - self_ty: ty::t) -> @ty::TraitRef -{ + self_ty: ty::t) -> Rc { /*! * Instantiates the path for the given trait reference, assuming that * it's bound to a valid trait type. Returns the def_id for the defining @@ -831,8 +830,8 @@ pub fn instantiate_trait_ref(ccx: &CrateCtxt, ccx, &rscope, trait_did, Some(self_ty), &ast_trait_ref.path); ccx.tcx.trait_refs.borrow_mut().insert(ast_trait_ref.ref_id, - trait_ref); - return trait_ref; + trait_ref.clone()); + trait_ref } _ => { ccx.tcx.sess.span_fatal( @@ -843,7 +842,7 @@ pub fn instantiate_trait_ref(ccx: &CrateCtxt, } } -fn get_trait_def(ccx: &CrateCtxt, trait_id: ast::DefId) -> @ty::TraitDef { +fn get_trait_def(ccx: &CrateCtxt, trait_id: ast::DefId) -> Rc { if trait_id.krate != ast::LOCAL_CRATE { return ty::lookup_trait_def(ccx.tcx, trait_id) } @@ -855,11 +854,11 @@ fn get_trait_def(ccx: &CrateCtxt, trait_id: ast::DefId) -> @ty::TraitDef { } } -pub fn trait_def_of_item(ccx: &CrateCtxt, it: &ast::Item) -> @ty::TraitDef { +pub fn trait_def_of_item(ccx: &CrateCtxt, it: &ast::Item) -> Rc { let def_id = local_def(it.id); let tcx = ccx.tcx; match tcx.trait_defs.borrow().find(&def_id) { - Some(&def) => return def, + Some(def) => return def.clone(), _ => {} } @@ -872,13 +871,16 @@ pub fn trait_def_of_item(ccx: &CrateCtxt, it: &ast::Item) -> @ty::TraitDef { it.id, it.span, supertraits.as_slice()); - let trait_ref = @ty::TraitRef {def_id: def_id, - substs: substs}; - let trait_def = @ty::TraitDef {generics: ty_generics, - bounds: bounds, - trait_ref: trait_ref}; - tcx.trait_defs.borrow_mut().insert(def_id, trait_def); - return trait_def; + let trait_def = Rc::new(ty::TraitDef { + generics: ty_generics, + bounds: bounds, + trait_ref: Rc::new(ty::TraitRef { + def_id: def_id, + substs: substs + }) + }); + tcx.trait_defs.borrow_mut().insert(def_id, trait_def.clone()); + trait_def } ref s => { tcx.sess.span_bug( diff --git a/src/librustc/middle/typeck/infer/coercion.rs b/src/librustc/middle/typeck/infer/coercion.rs index 4081d68954fe..e921674ad83f 100644 --- a/src/librustc/middle/typeck/infer/coercion.rs +++ b/src/librustc/middle/typeck/infer/coercion.rs @@ -195,7 +195,7 @@ impl<'f> Coerce<'f> { } pub fn subtype(&self, a: ty::t, b: ty::t) -> CoerceResult { - match Sub(*self.get_ref()).tys(a, b) { + match Sub(self.get_ref().clone()).tys(a, b) { Ok(_) => Ok(None), // No coercion required. Err(ref e) => Err(*e) } @@ -232,8 +232,9 @@ impl<'f> Coerce<'f> { // to type check, we will construct the type that `&M*expr` would // yield. - let sub = Sub(*self.get_ref()); - let r_borrow = self.get_ref().infcx.next_region_var(Coercion(self.get_ref().trace)); + let sub = Sub(self.get_ref().clone()); + let coercion = Coercion(self.get_ref().trace.clone()); + let r_borrow = self.get_ref().infcx.next_region_var(coercion); let inner_ty = match *sty_a { ty::ty_box(typ) | ty::ty_uniq(typ) => typ, @@ -269,7 +270,8 @@ impl<'f> Coerce<'f> { } }; - let r_a = self.get_ref().infcx.next_region_var(Coercion(self.get_ref().trace)); + let coercion = Coercion(self.get_ref().trace.clone()); + let r_a = self.get_ref().infcx.next_region_var(coercion); let a_borrowed = ty::mk_str(self.get_ref().infcx.tcx, VstoreSlice(r_a)); if_ok!(self.subtype(a_borrowed, b)); Ok(Some(AutoDerefRef(AutoDerefRef { @@ -288,8 +290,9 @@ impl<'f> Coerce<'f> { a.inf_str(self.get_ref().infcx), sty_a, b.inf_str(self.get_ref().infcx)); - let sub = Sub(*self.get_ref()); - let r_borrow = self.get_ref().infcx.next_region_var(Coercion(self.get_ref().trace)); + let sub = Sub(self.get_ref().clone()); + let coercion = Coercion(self.get_ref().trace.clone()); + let r_borrow = self.get_ref().infcx.next_region_var(coercion); let ty_inner = match *sty_a { ty::ty_uniq(t) | ty::ty_ptr(ty::mt{ty: t, ..}) | ty::ty_rptr(_, ty::mt{ty: t, ..}) => match ty::get(t).sty { @@ -324,7 +327,8 @@ impl<'f> Coerce<'f> { b.inf_str(self.get_ref().infcx)); let tcx = self.get_ref().infcx.tcx; - let r_a = self.get_ref().infcx.next_region_var(Coercion(self.get_ref().trace)); + let coercion = Coercion(self.get_ref().trace.clone()); + let r_a = self.get_ref().infcx.next_region_var(coercion); let a_borrowed = match *sty_a { ty::ty_trait(~ty::TyTrait { def_id, ref substs, bounds, .. }) => { diff --git a/src/librustc/middle/typeck/infer/combine.rs b/src/librustc/middle/typeck/infer/combine.rs index 098a3e278e7b..54cf6524664c 100644 --- a/src/librustc/middle/typeck/infer/combine.rs +++ b/src/librustc/middle/typeck/infer/combine.rs @@ -324,6 +324,7 @@ pub trait Combine { } } +#[deriving(Clone)] pub struct CombineFields<'a> { pub infcx: &'a InferCtxt<'a>, pub a_is_expected: bool, diff --git a/src/librustc/middle/typeck/infer/error_reporting.rs b/src/librustc/middle/typeck/infer/error_reporting.rs index 6ba727f9d4d1..a5d41b15d5d3 100644 --- a/src/librustc/middle/typeck/infer/error_reporting.rs +++ b/src/librustc/middle/typeck/infer/error_reporting.rs @@ -76,6 +76,7 @@ use middle::typeck::infer::region_inference::ProcessedErrors; use middle::typeck::infer::region_inference::SameRegions; use std::cell::{Cell, RefCell}; use std::char::from_u32; +use std::rc::Rc; use std::strbuf::StrBuf; use syntax::ast; use syntax::ast_map; @@ -158,7 +159,7 @@ impl<'a> ErrorReporting for InferCtxt<'a> { let p_errors = self.process_errors(errors); let errors = if p_errors.is_empty() { errors } else { &p_errors }; for error in errors.iter() { - match *error { + match error.clone() { ConcreteFailure(origin, sub, sup) => { self.report_concrete_failure(origin, sub, sup); } @@ -206,7 +207,7 @@ impl<'a> ErrorReporting for InferCtxt<'a> { let mut same_regions = Vec::new(); let mut processed_errors = Vec::new(); for error in errors.iter() { - match *error { + match error.clone() { ConcreteFailure(origin, sub, sup) => { debug!("processing ConcreteFailure") let trace = match origin { @@ -661,10 +662,10 @@ impl<'a> ErrorReporting for InferCtxt<'a> { same_regions: &[SameRegions]) { self.give_suggestion(same_regions); for vo in var_origins.iter() { - self.report_inference_failure(*vo); + self.report_inference_failure(vo.clone()); } - for &(trace, terr) in trace_origins.iter() { - self.report_type_error(trace, &terr); + for &(ref trace, terr) in trace_origins.iter() { + self.report_type_error(trace.clone(), &terr); } } @@ -1391,12 +1392,12 @@ impl Resolvable for ty::t { } } -impl Resolvable for @ty::TraitRef { - fn resolve(&self, infcx: &InferCtxt) -> @ty::TraitRef { - @infcx.resolve_type_vars_in_trait_ref_if_possible(*self) +impl Resolvable for Rc { + fn resolve(&self, infcx: &InferCtxt) -> Rc { + Rc::new(infcx.resolve_type_vars_in_trait_ref_if_possible(&**self)) } fn contains_error(&self) -> bool { - ty::trait_ref_contains_error(*self) + ty::trait_ref_contains_error(&**self) } } diff --git a/src/librustc/middle/typeck/infer/glb.rs b/src/librustc/middle/typeck/infer/glb.rs index 9f87993279cf..32bc7eedf2fc 100644 --- a/src/librustc/middle/typeck/infer/glb.rs +++ b/src/librustc/middle/typeck/infer/glb.rs @@ -38,11 +38,11 @@ impl<'f> Combine for Glb<'f> { fn infcx<'a>(&'a self) -> &'a InferCtxt<'a> { self.get_ref().infcx } fn tag(&self) -> ~str { "glb".to_owned() } fn a_is_expected(&self) -> bool { self.get_ref().a_is_expected } - fn trace(&self) -> TypeTrace { self.get_ref().trace } + fn trace(&self) -> TypeTrace { self.get_ref().trace.clone() } - fn sub<'a>(&'a self) -> Sub<'a> { Sub(*self.get_ref()) } - fn lub<'a>(&'a self) -> Lub<'a> { Lub(*self.get_ref()) } - fn glb<'a>(&'a self) -> Glb<'a> { Glb(*self.get_ref()) } + fn sub<'a>(&'a self) -> Sub<'a> { Sub(self.get_ref().clone()) } + fn lub<'a>(&'a self) -> Lub<'a> { Lub(self.get_ref().clone()) } + fn glb<'a>(&'a self) -> Glb<'a> { Glb(self.get_ref().clone()) } fn mts(&self, a: &ty::mt, b: &ty::mt) -> cres { let tcx = self.get_ref().infcx.tcx; @@ -78,7 +78,7 @@ impl<'f> Combine for Glb<'f> { } fn contratys(&self, a: ty::t, b: ty::t) -> cres { - Lub(*self.get_ref()).tys(a, b) + self.lub().tys(a, b) } fn fn_styles(&self, a: FnStyle, b: FnStyle) -> cres { @@ -108,12 +108,12 @@ impl<'f> Combine for Glb<'f> { a.inf_str(self.get_ref().infcx), b.inf_str(self.get_ref().infcx)); - Ok(self.get_ref().infcx.region_vars.glb_regions(Subtype(self.get_ref().trace), a, b)) + Ok(self.get_ref().infcx.region_vars.glb_regions(Subtype(self.trace()), a, b)) } fn contraregions(&self, a: ty::Region, b: ty::Region) -> cres { - Lub(*self.get_ref()).regions(a, b) + self.lub().regions(a, b) } fn tys(&self, a: ty::t, b: ty::t) -> cres { @@ -137,11 +137,11 @@ impl<'f> Combine for Glb<'f> { // Instantiate each bound region with a fresh region variable. let (a_with_fresh, a_map) = self.get_ref().infcx.replace_late_bound_regions_with_fresh_regions( - self.get_ref().trace, a); + self.trace(), a); let a_vars = var_ids(self, &a_map); let (b_with_fresh, b_map) = self.get_ref().infcx.replace_late_bound_regions_with_fresh_regions( - self.get_ref().trace, b); + self.trace(), b); let b_vars = var_ids(self, &b_map); // Collect constraints. diff --git a/src/librustc/middle/typeck/infer/lattice.rs b/src/librustc/middle/typeck/infer/lattice.rs index 83cc92942444..ebfb17a88763 100644 --- a/src/librustc/middle/typeck/infer/lattice.rs +++ b/src/librustc/middle/typeck/infer/lattice.rs @@ -47,26 +47,26 @@ use util::common::indenter; use collections::HashMap; -pub trait LatticeValue { - fn sub(cf: &CombineFields, a: &Self, b: &Self) -> ures; - fn lub(cf: &CombineFields, a: &Self, b: &Self) -> cres; - fn glb(cf: &CombineFields, a: &Self, b: &Self) -> cres; +trait LatticeValue { + fn sub(cf: CombineFields, a: &Self, b: &Self) -> ures; + fn lub(cf: CombineFields, a: &Self, b: &Self) -> cres; + fn glb(cf: CombineFields, a: &Self, b: &Self) -> cres; } pub type LatticeOp<'a, T> = - |cf: &CombineFields, a: &T, b: &T|: 'a -> cres; + |cf: CombineFields, a: &T, b: &T|: 'a -> cres; impl LatticeValue for ty::t { - fn sub(cf: &CombineFields, a: &ty::t, b: &ty::t) -> ures { - Sub(*cf).tys(*a, *b).to_ures() + fn sub(cf: CombineFields, a: &ty::t, b: &ty::t) -> ures { + Sub(cf).tys(*a, *b).to_ures() } - fn lub(cf: &CombineFields, a: &ty::t, b: &ty::t) -> cres { - Lub(*cf).tys(*a, *b) + fn lub(cf: CombineFields, a: &ty::t, b: &ty::t) -> cres { + Lub(cf).tys(*a, *b) } - fn glb(cf: &CombineFields, a: &ty::t, b: &ty::t) -> cres { - Glb(*cf).tys(*a, *b) + fn glb(cf: CombineFields, a: &ty::t, b: &ty::t) -> cres { + Glb(cf).tys(*a, *b) } } @@ -142,7 +142,7 @@ impl<'f> CombineFieldsLatticeMethods for CombineFields<'f> { match (&a_bounds.ub, &b_bounds.lb) { (&Some(ref a_ub), &Some(ref b_lb)) => { let r = self.infcx.try( - || LatticeValue::sub(self, a_ub, b_lb)); + || LatticeValue::sub(self.clone(), a_ub, b_lb)); match r { Ok(()) => { return Ok(()); @@ -232,7 +232,7 @@ impl<'f> CombineFieldsLatticeMethods for CombineFields<'f> { (&Some(_), &None) => Ok((*a).clone()), (&None, &Some(_)) => Ok((*b).clone()), (&Some(ref v_a), &Some(ref v_b)) => { - lattice_op(self, v_a, v_b).and_then(|v| Ok(Some(v))) + lattice_op(self.clone(), v_a, v_b).and_then(|v| Ok(Some(v))) } } } @@ -314,7 +314,7 @@ impl<'f> CombineFieldsLatticeMethods for CombineFields<'f> { uok() } (&Some(ref t_a), &Some(ref t_b)) => { - LatticeValue::sub(self, t_a, t_b) + LatticeValue::sub(self.clone(), t_a, t_b) } } } @@ -337,7 +337,7 @@ pub trait TyLatticeDir { } impl<'f> LatticeDir for Lub<'f> { - fn combine_fields<'a>(&'a self) -> CombineFields<'a> { *self.get_ref() } + fn combine_fields<'a>(&'a self) -> CombineFields<'a> { self.get_ref().clone() } fn bnd(&self, b: &Bounds) -> Option { b.ub.clone() } fn with_bnd(&self, b: &Bounds, t: T) -> Bounds { Bounds { ub: Some(t), ..(*b).clone() } @@ -351,7 +351,7 @@ impl<'f> TyLatticeDir for Lub<'f> { } impl<'f> LatticeDir for Glb<'f> { - fn combine_fields<'a>(&'a self) -> CombineFields<'a> { *self.get_ref() } + fn combine_fields<'a>(&'a self) -> CombineFields<'a> { self.get_ref().clone() } fn bnd(&self, b: &Bounds) -> Option { b.lb.clone() } fn with_bnd(&self, b: &Bounds, t: T) -> Bounds { Bounds { lb: Some(t), ..(*b).clone() } diff --git a/src/librustc/middle/typeck/infer/lub.rs b/src/librustc/middle/typeck/infer/lub.rs index d42205f00356..d09bbc4253ba 100644 --- a/src/librustc/middle/typeck/infer/lub.rs +++ b/src/librustc/middle/typeck/infer/lub.rs @@ -37,11 +37,11 @@ impl<'f> Combine for Lub<'f> { fn infcx<'a>(&'a self) -> &'a InferCtxt<'a> { self.get_ref().infcx } fn tag(&self) -> ~str { "lub".to_owned() } fn a_is_expected(&self) -> bool { self.get_ref().a_is_expected } - fn trace(&self) -> TypeTrace { self.get_ref().trace } + fn trace(&self) -> TypeTrace { self.get_ref().trace.clone() } - fn sub<'a>(&'a self) -> Sub<'a> { Sub(*self.get_ref()) } - fn lub<'a>(&'a self) -> Lub<'a> { Lub(*self.get_ref()) } - fn glb<'a>(&'a self) -> Glb<'a> { Glb(*self.get_ref()) } + fn sub<'a>(&'a self) -> Sub<'a> { Sub(self.get_ref().clone()) } + fn lub<'a>(&'a self) -> Lub<'a> { Lub(self.get_ref().clone()) } + fn glb<'a>(&'a self) -> Glb<'a> { Glb(self.get_ref().clone()) } fn mts(&self, a: &ty::mt, b: &ty::mt) -> cres { let tcx = self.get_ref().infcx.tcx; @@ -72,7 +72,7 @@ impl<'f> Combine for Lub<'f> { } fn contratys(&self, a: ty::t, b: ty::t) -> cres { - Glb(*self.get_ref()).tys(a, b) + self.glb().tys(a, b) } fn fn_styles(&self, a: FnStyle, b: FnStyle) -> cres { @@ -98,7 +98,7 @@ impl<'f> Combine for Lub<'f> { fn contraregions(&self, a: ty::Region, b: ty::Region) -> cres { - return Glb(*self.get_ref()).regions(a, b); + self.glb().regions(a, b) } fn regions(&self, a: ty::Region, b: ty::Region) -> cres { @@ -107,7 +107,7 @@ impl<'f> Combine for Lub<'f> { a.inf_str(self.get_ref().infcx), b.inf_str(self.get_ref().infcx)); - Ok(self.get_ref().infcx.region_vars.lub_regions(Subtype(self.get_ref().trace), a, b)) + Ok(self.get_ref().infcx.region_vars.lub_regions(Subtype(self.trace()), a, b)) } fn fn_sigs(&self, a: &ty::FnSig, b: &ty::FnSig) -> cres { @@ -123,10 +123,10 @@ impl<'f> Combine for Lub<'f> { // Instantiate each bound region with a fresh region variable. let (a_with_fresh, a_map) = self.get_ref().infcx.replace_late_bound_regions_with_fresh_regions( - self.get_ref().trace, a); + self.trace(), a); let (b_with_fresh, _) = self.get_ref().infcx.replace_late_bound_regions_with_fresh_regions( - self.get_ref().trace, b); + self.trace(), b); // Collect constraints. let sig0 = if_ok!(super_fn_sigs(self, &a_with_fresh, &b_with_fresh)); diff --git a/src/librustc/middle/typeck/infer/mod.rs b/src/librustc/middle/typeck/infer/mod.rs index 449fc5d9b9f1..258f286d8f02 100644 --- a/src/librustc/middle/typeck/infer/mod.rs +++ b/src/librustc/middle/typeck/infer/mod.rs @@ -38,7 +38,7 @@ use middle::typeck::infer::to_str::InferStr; use middle::typeck::infer::unify::{ValsAndBindings, Root}; use middle::typeck::infer::error_reporting::ErrorReporting; use std::cell::{Cell, RefCell}; -use std::result; +use std::rc::Rc; use syntax::ast::{MutImmutable, MutMutable}; use syntax::ast; use syntax::codemap; @@ -129,7 +129,7 @@ pub enum TypeOrigin { #[deriving(Clone)] pub enum ValuePairs { Types(ty::expected_found), - TraitRefs(ty::expected_found<@ty::TraitRef>), + TraitRefs(ty::expected_found>), } /// The trace designates the path through inference that we took to @@ -301,7 +301,7 @@ pub fn common_supertype(cx: &InferCtxt, values: Types(expected_found(a_is_expected, a, b)) }; - let result = cx.commit(|| cx.lub(a_is_expected, trace).tys(a, b)); + let result = cx.commit(|| cx.lub(a_is_expected, trace.clone()).tys(a, b)); match result { Ok(t) => t, Err(ref err) => { @@ -375,8 +375,8 @@ pub fn mk_eqty(cx: &InferCtxt, pub fn mk_sub_trait_refs(cx: &InferCtxt, a_is_expected: bool, origin: TypeOrigin, - a: @ty::TraitRef, - b: @ty::TraitRef) + a: Rc, + b: Rc) -> ures { debug!("mk_sub_trait_refs({} <: {})", @@ -385,10 +385,10 @@ pub fn mk_sub_trait_refs(cx: &InferCtxt, cx.commit(|| { let trace = TypeTrace { origin: origin, - values: TraitRefs(expected_found(a_is_expected, a, b)) + values: TraitRefs(expected_found(a_is_expected, a.clone(), b.clone())) }; let suber = cx.sub(a_is_expected, trace); - suber.trait_refs(a, b) + suber.trait_refs(&*a, &*b) }) }).to_ures() } @@ -666,8 +666,8 @@ impl<'a> InferCtxt<'a> { pub fn resolve_type_vars_if_possible(&self, typ: ty::t) -> ty::t { match resolve_type(self, typ, resolve_nested_tvar | resolve_ivar) { - result::Ok(new_type) => new_type, - result::Err(_) => typ + Ok(new_type) => new_type, + Err(_) => typ } } @@ -854,7 +854,7 @@ impl Repr for TypeOrigin { impl SubregionOrigin { pub fn span(&self) -> Span { match *self { - Subtype(a) => a.span(), + Subtype(ref a) => a.span(), InfStackClosure(a) => a, InvokeClosure(a) => a, DerefPointer(a) => a, @@ -877,7 +877,7 @@ impl SubregionOrigin { impl Repr for SubregionOrigin { fn repr(&self, tcx: &ty::ctxt) -> ~str { match *self { - Subtype(a) => format!("Subtype({})", a.repr(tcx)), + Subtype(ref a) => format!("Subtype({})", a.repr(tcx)), InfStackClosure(a) => format!("InfStackClosure({})", a.repr(tcx)), InvokeClosure(a) => format!("InvokeClosure({})", a.repr(tcx)), DerefPointer(a) => format!("DerefPointer({})", a.repr(tcx)), @@ -907,7 +907,7 @@ impl RegionVariableOrigin { AddrOfRegion(a) => a, AddrOfSlice(a) => a, Autoref(a) => a, - Coercion(a) => a.span(), + Coercion(ref a) => a.span(), EarlyBoundRegion(a, _) => a, LateBoundRegion(a, _) => a, BoundRegionInFnType(a, _) => a, @@ -925,7 +925,7 @@ impl Repr for RegionVariableOrigin { AddrOfRegion(a) => format!("AddrOfRegion({})", a.repr(tcx)), AddrOfSlice(a) => format!("AddrOfSlice({})", a.repr(tcx)), Autoref(a) => format!("Autoref({})", a.repr(tcx)), - Coercion(a) => format!("Coercion({})", a.repr(tcx)), + Coercion(ref a) => format!("Coercion({})", a.repr(tcx)), EarlyBoundRegion(a, b) => format!("EarlyBoundRegion({},{})", a.repr(tcx), b.repr(tcx)), LateBoundRegion(a, b) => format!("LateBoundRegion({},{})", diff --git a/src/librustc/middle/typeck/infer/region_inference/mod.rs b/src/librustc/middle/typeck/infer/region_inference/mod.rs index a446b94027b2..bb6d479870b9 100644 --- a/src/librustc/middle/typeck/infer/region_inference/mod.rs +++ b/src/librustc/middle/typeck/infer/region_inference/mod.rs @@ -212,7 +212,7 @@ impl<'a> RegionVarBindings<'a> { pub fn new_region_var(&self, origin: RegionVariableOrigin) -> RegionVid { let id = self.num_vars(); - self.var_origins.borrow_mut().push(origin); + self.var_origins.borrow_mut().push(origin.clone()); let vid = RegionVid { id: id }; if self.in_snapshot() { self.undo_log.borrow_mut().push(AddVar(vid)); @@ -330,9 +330,9 @@ impl<'a> RegionVarBindings<'a> { _ => { self.combine_vars( - Lub, a, b, origin, + Lub, a, b, origin.clone(), |this, old_r, new_r| - this.make_subregion(origin, old_r, new_r)) + this.make_subregion(origin.clone(), old_r, new_r)) } } } @@ -354,9 +354,9 @@ impl<'a> RegionVarBindings<'a> { _ => { self.combine_vars( - Glb, a, b, origin, + Glb, a, b, origin.clone(), |this, old_r, new_r| - this.make_subregion(origin, new_r, old_r)) + this.make_subregion(origin.clone(), new_r, old_r)) } } } @@ -1150,10 +1150,10 @@ impl<'a> RegionVarBindings<'a> { if !self.is_subregion_of(lower_bound.region, upper_bound.region) { errors.push(SubSupConflict( - *self.var_origins.borrow().get(node_idx.to_uint()), - lower_bound.origin, + self.var_origins.borrow().get(node_idx.to_uint()).clone(), + lower_bound.origin.clone(), lower_bound.region, - upper_bound.origin, + upper_bound.origin.clone(), upper_bound.region)); return; } @@ -1200,10 +1200,10 @@ impl<'a> RegionVarBindings<'a> { Ok(_) => {} Err(_) => { errors.push(SupSupConflict( - *self.var_origins.borrow().get(node_idx.to_uint()), - upper_bound_1.origin, + self.var_origins.borrow().get(node_idx.to_uint()).clone(), + upper_bound_1.origin.clone(), upper_bound_1.region, - upper_bound_2.origin, + upper_bound_2.origin.clone(), upper_bound_2.region)); return; } diff --git a/src/librustc/middle/typeck/infer/sub.rs b/src/librustc/middle/typeck/infer/sub.rs index 6d02094669cb..2c8acd0573b7 100644 --- a/src/librustc/middle/typeck/infer/sub.rs +++ b/src/librustc/middle/typeck/infer/sub.rs @@ -37,15 +37,16 @@ impl<'f> Combine for Sub<'f> { fn infcx<'a>(&'a self) -> &'a InferCtxt<'a> { self.get_ref().infcx } fn tag(&self) -> ~str { "sub".to_owned() } fn a_is_expected(&self) -> bool { self.get_ref().a_is_expected } - fn trace(&self) -> TypeTrace { self.get_ref().trace } + fn trace(&self) -> TypeTrace { self.get_ref().trace.clone() } - fn sub<'a>(&'a self) -> Sub<'a> { Sub(*self.get_ref()) } - fn lub<'a>(&'a self) -> Lub<'a> { Lub(*self.get_ref()) } - fn glb<'a>(&'a self) -> Glb<'a> { Glb(*self.get_ref()) } + fn sub<'a>(&'a self) -> Sub<'a> { Sub(self.get_ref().clone()) } + fn lub<'a>(&'a self) -> Lub<'a> { Lub(self.get_ref().clone()) } + fn glb<'a>(&'a self) -> Glb<'a> { Glb(self.get_ref().clone()) } fn contratys(&self, a: ty::t, b: ty::t) -> cres { let opp = CombineFields { - a_is_expected: !self.get_ref().a_is_expected,.. *self.get_ref() + a_is_expected: !self.get_ref().a_is_expected, + ..self.get_ref().clone() }; Sub(opp).tys(b, a) } @@ -53,7 +54,8 @@ impl<'f> Combine for Sub<'f> { fn contraregions(&self, a: ty::Region, b: ty::Region) -> cres { let opp = CombineFields { - a_is_expected: !self.get_ref().a_is_expected,.. *self.get_ref() + a_is_expected: !self.get_ref().a_is_expected, + ..self.get_ref().clone() }; Sub(opp).regions(b, a) } @@ -63,7 +65,7 @@ impl<'f> Combine for Sub<'f> { self.tag(), a.inf_str(self.get_ref().infcx), b.inf_str(self.get_ref().infcx)); - self.get_ref().infcx.region_vars.make_subregion(Subtype(self.get_ref().trace), a, b); + self.get_ref().infcx.region_vars.make_subregion(Subtype(self.trace()), a, b); Ok(a) } @@ -167,7 +169,7 @@ impl<'f> Combine for Sub<'f> { // region variable. let (a_sig, _) = self.get_ref().infcx.replace_late_bound_regions_with_fresh_regions( - self.get_ref().trace, a); + self.trace(), a); // Second, we instantiate each bound region in the supertype with a // fresh concrete region. diff --git a/src/librustc/middle/typeck/variance.rs b/src/librustc/middle/typeck/variance.rs index 907153d6cbee..9e7c221d3c55 100644 --- a/src/librustc/middle/typeck/variance.rs +++ b/src/librustc/middle/typeck/variance.rs @@ -197,6 +197,7 @@ use arena; use arena::Arena; use middle::ty; use std::fmt; +use std::rc::Rc; use syntax::ast; use syntax::ast_map; use syntax::ast_util; @@ -254,7 +255,7 @@ struct TermsContext<'a> { tcx: &'a ty::ctxt, arena: &'a Arena, - empty_variances: @ty::ItemVariances, + empty_variances: Rc, // Maps from the node id of a type/generic parameter to the // corresponding inferred index. @@ -286,9 +287,11 @@ fn determine_parameters_to_be_inferred<'a>(tcx: &'a ty::ctxt, // cache and share the variance struct used for items with // no type/region parameters - empty_variances: @ty::ItemVariances { self_param: None, - type_params: OwnedSlice::empty(), - region_params: OwnedSlice::empty() } + empty_variances: Rc::new(ty::ItemVariances { + self_param: None, + type_params: OwnedSlice::empty(), + region_params: OwnedSlice::empty() + }) }; visit::walk_crate(&mut terms_cx, krate, ()); @@ -362,7 +365,7 @@ impl<'a> Visitor<()> for TermsContext<'a> { if self.num_inferred() == inferreds_on_entry { let newly_added = self.tcx.item_variance_map.borrow_mut().insert( ast_util::local_def(item.id), - self.empty_variances); + self.empty_variances.clone()); assert!(newly_added); } @@ -1016,7 +1019,7 @@ impl<'a> SolveContext<'a> { } let newly_added = tcx.item_variance_map.borrow_mut() - .insert(item_def_id, @item_variances); + .insert(item_def_id, Rc::new(item_variances)); assert!(newly_added); } } diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index 3038dc8259fa..316b5c6a45a6 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -22,6 +22,7 @@ use middle::ty::{ty_uniq, ty_trait, ty_int, ty_uint, ty_infer}; use middle::ty; use middle::typeck; +use std::rc::Rc; use std::strbuf::StrBuf; use syntax::abi; use syntax::ast_map; @@ -497,6 +498,12 @@ impl Repr for () { } } +impl Repr for Rc { + fn repr(&self, tcx: &ctxt) -> ~str { + (&**self).repr(tcx) + } +} + impl Repr for @T { fn repr(&self, tcx: &ctxt) -> ~str { (&**self).repr(tcx) @@ -887,7 +894,7 @@ impl Repr for Span { } } -impl UserString for @A { +impl UserString for Rc { fn user_string(&self, tcx: &ctxt) -> ~str { let this: &A = &**self; this.user_string(tcx) diff --git a/src/libsyntax/util/small_vector.rs b/src/libsyntax/util/small_vector.rs index 792673e32981..693407b854fb 100644 --- a/src/libsyntax/util/small_vector.rs +++ b/src/libsyntax/util/small_vector.rs @@ -9,6 +9,7 @@ // except according to those terms. use std::mem; +use std::slice; use std::vec; /// A vector type optimized for cases where the size is almost always 0 or 1 @@ -61,6 +62,14 @@ impl SmallVector { SmallVector { repr: Many(vs) } } + pub fn as_slice<'a>(&'a self) -> &'a [T] { + match self.repr { + Zero => &[], + One(ref v) => slice::ref_slice(v), + Many(ref vs) => vs.as_slice() + } + } + pub fn push(&mut self, v: T) { match self.repr { Zero => self.repr = One(v),