Skip to content

kill the fake provided method stubs #28778

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Oct 1, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/librustc/metadata/common.rs
Original file line number Diff line number Diff line change
Expand Up @@ -180,7 +180,7 @@ pub const tag_mod_child: usize = 0x7b;
pub const tag_misc_info: usize = 0x108; // top-level only
pub const tag_misc_info_crate_items: usize = 0x7c;

pub const tag_item_method_provided_source: usize = 0x7d;
// GAP 0x7d
pub const tag_item_impl_vtables: usize = 0x7e;

pub const tag_impls: usize = 0x109; // top-level only
Expand Down
55 changes: 25 additions & 30 deletions src/librustc/metadata/decoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -187,12 +187,6 @@ fn item_def_id(d: rbml::Doc, cdata: Cmd) -> DefId {
translated_def_id(cdata, reader::get_doc(d, tag_def_id))
}

fn get_provided_source(d: rbml::Doc, cdata: Cmd) -> Option<DefId> {
reader::maybe_get_doc(d, tag_item_method_provided_source).map(|doc| {
translated_def_id(cdata, doc)
})
}

fn reexports<'a>(d: rbml::Doc<'a>) -> reader::TaggedDocsIterator<'a> {
reader::tagged_docs(d, tag_items_data_item_reexport)
}
Expand Down Expand Up @@ -276,11 +270,14 @@ fn item_to_def_like(cdata: Cmd, item: rbml::Doc, did: DefId) -> DefLike {
match fam {
Constant => {
// Check whether we have an associated const item.
if item_sort(item) == Some('C') {
DlDef(def::DefAssociatedConst(did))
} else {
// Regular const item.
DlDef(def::DefConst(did))
match item_sort(item) {
Some('C') | Some('c') => {
DlDef(def::DefAssociatedConst(did))
}
_ => {
// Regular const item.
DlDef(def::DefConst(did))
}
}
}
ImmStatic => DlDef(def::DefStatic(did, false)),
Expand Down Expand Up @@ -818,7 +815,7 @@ pub fn get_impl_items(cdata: Cmd, impl_id: ast::NodeId)
reader::tagged_docs(cdata.lookup_item(impl_id), tag_item_impl_item).map(|doc| {
let def_id = item_def_id(doc, cdata);
match item_sort(doc) {
Some('C') => ty::ConstTraitItemId(def_id),
Some('C') | Some('c') => ty::ConstTraitItemId(def_id),
Some('r') | Some('p') => ty::MethodTraitItemId(def_id),
Some('t') => ty::TypeTraitItemId(def_id),
_ => panic!("unknown impl item sort"),
Expand Down Expand Up @@ -864,24 +861,22 @@ pub fn get_impl_or_trait_item<'tcx>(intr: Rc<IdentInterner>,
let vis = item_visibility(item_doc);

match item_sort(item_doc) {
Some('C') => {
sort @ Some('C') | sort @ Some('c') => {
let ty = doc_type(item_doc, tcx, cdata);
let default = get_provided_source(item_doc, cdata);
ty::ConstTraitItem(Rc::new(ty::AssociatedConst {
name: name,
ty: ty,
vis: vis,
def_id: def_id,
container: container,
default: default,
has_value: sort == Some('C')
}))
}
Some('r') | Some('p') => {
let generics = doc_generics(item_doc, tcx, cdata, tag_method_ty_generics);
let predicates = doc_predicates(item_doc, tcx, cdata, tag_method_ty_generics);
let fty = doc_method_fty(item_doc, tcx, cdata);
let explicit_self = get_explicit_self(item_doc);
let provided_source = get_provided_source(item_doc, cdata);

ty::MethodTraitItem(Rc::new(ty::Method::new(name,
generics,
Expand All @@ -890,8 +885,7 @@ pub fn get_impl_or_trait_item<'tcx>(intr: Rc<IdentInterner>,
explicit_self,
vis,
def_id,
container,
provided_source)))
container)))
}
Some('t') => {
let ty = maybe_doc_type(item_doc, tcx, cdata);
Expand All @@ -913,7 +907,7 @@ pub fn get_trait_item_def_ids(cdata: Cmd, id: ast::NodeId)
reader::tagged_docs(item, tag_item_trait_item).map(|mth| {
let def_id = item_def_id(mth, cdata);
match item_sort(mth) {
Some('C') => ty::ConstTraitItemId(def_id),
Some('C') | Some('c') => ty::ConstTraitItemId(def_id),
Some('r') | Some('p') => ty::MethodTraitItemId(def_id),
Some('t') => ty::TypeTraitItemId(def_id),
_ => panic!("unknown trait item sort"),
Expand Down Expand Up @@ -967,18 +961,19 @@ pub fn get_associated_consts<'tcx>(intr: Rc<IdentInterner>,
let did = item_def_id(ac_id, cdata);
let ac_doc = cdata.lookup_item(did.node);

if item_sort(ac_doc) == Some('C') {
let trait_item = get_impl_or_trait_item(intr.clone(),
cdata,
did.node,
tcx);
if let ty::ConstTraitItem(ref ac) = trait_item {
Some((*ac).clone())
} else {
None
match item_sort(ac_doc) {
Some('C') | Some('c') => {
let trait_item = get_impl_or_trait_item(intr.clone(),
cdata,
did.node,
tcx);
if let ty::ConstTraitItem(ref ac) = trait_item {
Some((*ac).clone())
} else {
None
}
}
} else {
None
_ => None
}
})
}).collect()
Expand Down
20 changes: 7 additions & 13 deletions src/librustc/metadata/encoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -609,13 +609,6 @@ fn encode_parent_sort(rbml_w: &mut Encoder, sort: char) {
rbml_w.wr_tagged_u8(tag_item_trait_parent_sort, sort as u8);
}

fn encode_provided_source(rbml_w: &mut Encoder,
source_opt: Option<DefId>) {
if let Some(source) = source_opt {
rbml_w.wr_tagged_u64(tag_item_method_provided_source, def_to_u64(source));
}
}

fn encode_field<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
rbml_w: &mut Encoder,
field: ty::FieldDef<'tcx>,
Expand Down Expand Up @@ -776,7 +769,6 @@ fn encode_method_ty_fields<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
}
_ => encode_family(rbml_w, METHOD_FAMILY)
}
encode_provided_source(rbml_w, method_ty.provided_source);
}

fn encode_info_for_associated_const(ecx: &EncodeContext,
Expand All @@ -795,7 +787,6 @@ fn encode_info_for_associated_const(ecx: &EncodeContext,
encode_name(rbml_w, associated_const.name);
encode_visibility(rbml_w, associated_const.vis);
encode_family(rbml_w, 'C');
encode_provided_source(rbml_w, associated_const.default);

encode_parent_item(rbml_w, DefId::local(parent_id));
encode_item_sort(rbml_w, 'C');
Expand Down Expand Up @@ -1367,13 +1358,10 @@ fn encode_info_for_item(ecx: &EncodeContext,
encode_def_id(rbml_w, associated_const.def_id);
encode_visibility(rbml_w, associated_const.vis);

encode_provided_source(rbml_w, associated_const.default);

let elem = ast_map::PathName(associated_const.name);
encode_path(rbml_w,
path.clone().chain(Some(elem)));

encode_item_sort(rbml_w, 'C');
encode_family(rbml_w, 'C');

encode_bounds_and_type_for_item(rbml_w, ecx,
Expand Down Expand Up @@ -1429,7 +1417,13 @@ fn encode_info_for_item(ecx: &EncodeContext,
let trait_item = &*ms[i];
encode_attributes(rbml_w, &trait_item.attrs);
match trait_item.node {
hir::ConstTraitItem(_, _) => {
hir::ConstTraitItem(_, ref default) => {
if default.is_some() {
encode_item_sort(rbml_w, 'C');
} else {
encode_item_sort(rbml_w, 'c');
}

encode_inlined_item(ecx, rbml_w,
InlinedItemRef::TraitItem(def_id, trait_item));
}
Expand Down
3 changes: 0 additions & 3 deletions src/librustc/middle/ty/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -235,8 +235,6 @@ pub struct ctxt<'tcx> {
pub ty_param_defs: RefCell<NodeMap<ty::TypeParameterDef<'tcx>>>,
pub normalized_cache: RefCell<FnvHashMap<Ty<'tcx>, Ty<'tcx>>>,
pub lang_items: middle::lang_items::LanguageItems,
/// A mapping of fake provided method def_ids to the default implementation
pub provided_method_sources: RefCell<DefIdMap<DefId>>,

/// Maps from def-id of a type or region parameter to its
/// (inferred) variance.
Expand Down Expand Up @@ -471,7 +469,6 @@ impl<'tcx> ctxt<'tcx> {
ty_param_defs: RefCell::new(NodeMap()),
normalized_cache: RefCell::new(FnvHashMap()),
lang_items: lang_items,
provided_method_sources: RefCell::new(DefIdMap()),
inherent_impls: RefCell::new(DefIdMap()),
impl_items: RefCell::new(DefIdMap()),
used_unsafe: RefCell::new(NodeSet()),
Expand Down
26 changes: 5 additions & 21 deletions src/librustc/middle/ty/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -235,9 +235,6 @@ pub struct Method<'tcx> {
pub vis: hir::Visibility,
pub def_id: DefId,
pub container: ImplOrTraitItemContainer,

// If this method is provided, we need to know where it came from
pub provided_source: Option<DefId>
}

impl<'tcx> Method<'tcx> {
Expand All @@ -248,8 +245,7 @@ impl<'tcx> Method<'tcx> {
explicit_self: ExplicitSelfCategory,
vis: hir::Visibility,
def_id: DefId,
container: ImplOrTraitItemContainer,
provided_source: Option<DefId>)
container: ImplOrTraitItemContainer)
-> Method<'tcx> {
Method {
name: name,
Expand All @@ -260,7 +256,6 @@ impl<'tcx> Method<'tcx> {
vis: vis,
def_id: def_id,
container: container,
provided_source: provided_source
}
}

Expand Down Expand Up @@ -293,7 +288,7 @@ pub struct AssociatedConst<'tcx> {
pub vis: hir::Visibility,
pub def_id: DefId,
pub container: ImplOrTraitItemContainer,
pub default: Option<DefId>,
pub has_value: bool
}

#[derive(Clone, Copy, Debug)]
Expand Down Expand Up @@ -2105,10 +2100,6 @@ impl<'tcx> ctxt<'tcx> {
}
}

pub fn provided_source(&self, id: DefId) -> Option<DefId> {
self.provided_method_sources.borrow().get(&id).cloned()
}

pub fn provided_trait_methods(&self, id: DefId) -> Vec<Rc<Method<'tcx>>> {
if id.is_local() {
if let ItemTrait(_, _, _, ref ms) = self.map.expect_item(id.node).node {
Expand Down Expand Up @@ -2477,16 +2468,9 @@ impl<'tcx> ctxt<'tcx> {
// the map. This is a bit unfortunate.
for impl_item_def_id in &impl_items {
let method_def_id = impl_item_def_id.def_id();
match self.impl_or_trait_item(method_def_id) {
MethodTraitItem(method) => {
if let Some(source) = method.provided_source {
self.provided_method_sources
.borrow_mut()
.insert(method_def_id, source);
}
}
_ => {}
}
// load impl items eagerly for convenience
// FIXME: we may want to load these lazily
self.impl_or_trait_item(method_def_id);
}

// Store the implementation info.
Expand Down
55 changes: 54 additions & 1 deletion src/librustc/middle/ty/util.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use back::svh::Svh;
use middle::const_eval::{self, ConstVal, ErrKind};
use middle::const_eval::EvalHint::UncheckedExprHint;
use middle::def_id::DefId;
use middle::subst;
use middle::subst::{self, Subst, Substs};
use middle::infer;
use middle::pat_util;
use middle::traits;
Expand All @@ -26,6 +26,7 @@ use util::num::ToPrimitive;

use std::cmp;
use std::hash::{Hash, SipHasher, Hasher};
use std::rc::Rc;
use syntax::ast::{self, Name};
use syntax::attr::{self, AttrMetaMethods, SignedInt, UnsignedInt};
use syntax::codemap::Span;
Expand Down Expand Up @@ -646,6 +647,58 @@ impl<'tcx> ty::ctxt<'tcx> {
}
}

#[derive(Debug)]
pub struct ImplMethod<'tcx> {
pub method: Rc<ty::Method<'tcx>>,
pub substs: Substs<'tcx>,
pub is_provided: bool
}

impl<'tcx> ty::ctxt<'tcx> {
#[inline(never)] // is this perfy enough?
pub fn get_impl_method(&self,
impl_def_id: DefId,
substs: Substs<'tcx>,
name: Name)
-> ImplMethod<'tcx>
{
// there don't seem to be nicer accessors to these:
let impl_or_trait_items_map = self.impl_or_trait_items.borrow();

for impl_item in &self.impl_items.borrow()[&impl_def_id] {
if let ty::MethodTraitItem(ref meth) =
impl_or_trait_items_map[&impl_item.def_id()] {
if meth.name == name {
return ImplMethod {
method: meth.clone(),
substs: substs,
is_provided: false
}
}
}
}

// It is not in the impl - get the default from the trait.
let trait_ref = self.impl_trait_ref(impl_def_id).unwrap();
for trait_item in self.trait_items(trait_ref.def_id).iter() {
if let &ty::MethodTraitItem(ref meth) = trait_item {
if meth.name == name {
let impl_to_trait_substs = self
.make_substs_for_receiver_types(&trait_ref, meth);
return ImplMethod {
method: meth.clone(),
substs: impl_to_trait_substs.subst(self, &substs),
is_provided: true
}
}
}
}

self.sess.bug(&format!("method {:?} not found in {:?}",
name, impl_def_id))
}
}

impl<'tcx> ty::TyS<'tcx> {
fn impls_bound<'a>(&'tcx self, param_env: &ParameterEnvironment<'a,'tcx>,
bound: ty::BuiltinBound,
Expand Down
13 changes: 0 additions & 13 deletions src/librustc_privacy/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -725,19 +725,6 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
span: Span,
method_id: DefId,
name: ast::Name) {
// If the method is a default method, we need to use the def_id of
// the default implementation.
let method_id = match self.tcx.impl_or_trait_item(method_id) {
ty::MethodTraitItem(method_type) => {
method_type.provided_source.unwrap_or(method_id)
}
_ => {
self.tcx.sess
.span_bug(span,
"got non-method item in check_static_method")
}
};

self.report_error(self.ensure_public(span,
method_id,
None,
Expand Down
Loading