Skip to content

Commit 32cb44b

Browse files
committed
auto merge of #14022 : pcwalton/rust/explicit-self, r=pnkfelix
r? @nikomatsakis
2 parents 459ffc2 + 00c70d1 commit 32cb44b

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+662
-192
lines changed

src/librustc/metadata/csearch.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -132,7 +132,8 @@ pub fn get_method(tcx: &ty::ctxt, def: ast::DefId) -> ty::Method {
132132

133133
pub fn get_method_name_and_explicit_self(cstore: &cstore::CStore,
134134
def: ast::DefId)
135-
-> (ast::Ident, ast::ExplicitSelf_)
135+
-> (ast::Ident,
136+
ty::ExplicitSelfCategory)
136137
{
137138
let cdata = cstore.get_crate_data(def.krate);
138139
decoder::get_method_name_and_explicit_self(cstore.intr.clone(), &*cdata, def.node)

src/librustc/metadata/decoder.rs

+14-11
Original file line numberDiff line numberDiff line change
@@ -724,7 +724,7 @@ pub fn get_enum_variants(intr: Rc<IdentInterner>, cdata: Cmd, id: ast::NodeId,
724724
}).collect()
725725
}
726726

727-
fn get_explicit_self(item: ebml::Doc) -> ast::ExplicitSelf_ {
727+
fn get_explicit_self(item: ebml::Doc) -> ty::ExplicitSelfCategory {
728728
fn get_mutability(ch: u8) -> ast::Mutability {
729729
match ch as char {
730730
'i' => ast::MutImmutable,
@@ -738,12 +738,15 @@ fn get_explicit_self(item: ebml::Doc) -> ast::ExplicitSelf_ {
738738

739739
let explicit_self_kind = string.as_bytes()[0];
740740
match explicit_self_kind as char {
741-
's' => ast::SelfStatic,
742-
'v' => ast::SelfValue(special_idents::self_),
743-
'~' => ast::SelfUniq(special_idents::self_),
741+
's' => ty::StaticExplicitSelfCategory,
742+
'v' => ty::ByValueExplicitSelfCategory,
743+
'~' => ty::ByBoxExplicitSelfCategory,
744744
// FIXME(#4846) expl. region
745-
'&' => ast::SelfRegion(None, get_mutability(string.as_bytes()[1]),
746-
special_idents::self_),
745+
'&' => {
746+
ty::ByReferenceExplicitSelfCategory(
747+
ty::ReEmpty,
748+
get_mutability(string.as_bytes()[1]))
749+
}
747750
_ => fail!("unknown self type code: `{}`", explicit_self_kind as char)
748751
}
749752
}
@@ -761,11 +764,11 @@ pub fn get_impl_methods(cdata: Cmd, impl_id: ast::NodeId) -> Vec<ast::DefId> {
761764
methods
762765
}
763766

764-
pub fn get_method_name_and_explicit_self(
765-
intr: Rc<IdentInterner>,
766-
cdata: Cmd,
767-
id: ast::NodeId) -> (ast::Ident, ast::ExplicitSelf_)
768-
{
767+
pub fn get_method_name_and_explicit_self(intr: Rc<IdentInterner>,
768+
cdata: Cmd,
769+
id: ast::NodeId)
770+
-> (ast::Ident,
771+
ty::ExplicitSelfCategory) {
769772
let method_doc = lookup_item(id, cdata.data());
770773
let name = item_name(&*intr, method_doc);
771774
let explicit_self = get_explicit_self(method_doc);

src/librustc/metadata/encoder.rs

+19-12
Original file line numberDiff line numberDiff line change
@@ -402,7 +402,7 @@ fn encode_reexported_static_base_methods(ecx: &EncodeContext,
402402
for base_impl_did in implementations.borrow().iter() {
403403
for &method_did in impl_methods.get(base_impl_did).iter() {
404404
let m = ty::method(ecx.tcx, method_did);
405-
if m.explicit_self == ast::SelfStatic {
405+
if m.explicit_self == ty::StaticExplicitSelfCategory {
406406
encode_reexported_static_method(ebml_w, exp, m.def_id, m.ident);
407407
}
408408
}
@@ -421,7 +421,7 @@ fn encode_reexported_static_trait_methods(ecx: &EncodeContext,
421421
match ecx.tcx.trait_methods_cache.borrow().find(&exp.def_id) {
422422
Some(methods) => {
423423
for m in methods.iter() {
424-
if m.explicit_self == ast::SelfStatic {
424+
if m.explicit_self == ty::StaticExplicitSelfCategory {
425425
encode_reexported_static_method(ebml_w, exp, m.def_id, m.ident);
426426
}
427427
}
@@ -623,15 +623,22 @@ fn encode_visibility(ebml_w: &mut Encoder, visibility: Visibility) {
623623
ebml_w.end_tag();
624624
}
625625

626-
fn encode_explicit_self(ebml_w: &mut Encoder, explicit_self: ast::ExplicitSelf_) {
626+
fn encode_explicit_self(ebml_w: &mut Encoder,
627+
explicit_self: &ty::ExplicitSelfCategory) {
627628
ebml_w.start_tag(tag_item_trait_method_explicit_self);
628629

629630
// Encode the base self type.
630-
match explicit_self {
631-
SelfStatic => { ebml_w.writer.write(&[ 's' as u8 ]); }
632-
SelfValue(_) => { ebml_w.writer.write(&[ 'v' as u8 ]); }
633-
SelfUniq(_) => { ebml_w.writer.write(&[ '~' as u8 ]); }
634-
SelfRegion(_, m, _) => {
631+
match *explicit_self {
632+
ty::StaticExplicitSelfCategory => {
633+
ebml_w.writer.write(&[ 's' as u8 ]);
634+
}
635+
ty::ByValueExplicitSelfCategory => {
636+
ebml_w.writer.write(&[ 'v' as u8 ]);
637+
}
638+
ty::ByBoxExplicitSelfCategory => {
639+
ebml_w.writer.write(&[ '~' as u8 ]);
640+
}
641+
ty::ByReferenceExplicitSelfCategory(_, m) => {
635642
// FIXME(#4846) encode custom lifetime
636643
ebml_w.writer.write(&['&' as u8]);
637644
encode_mutability(ebml_w, m);
@@ -748,10 +755,10 @@ fn encode_method_ty_fields(ecx: &EncodeContext,
748755
tag_item_method_tps);
749756
encode_method_fty(ecx, ebml_w, &method_ty.fty);
750757
encode_visibility(ebml_w, method_ty.vis);
751-
encode_explicit_self(ebml_w, method_ty.explicit_self);
758+
encode_explicit_self(ebml_w, &method_ty.explicit_self);
752759
let fn_style = method_ty.fty.fn_style;
753760
match method_ty.explicit_self {
754-
ast::SelfStatic => {
761+
ty::StaticExplicitSelfCategory => {
755762
encode_family(ebml_w, fn_style_static_method_family(fn_style));
756763
}
757764
_ => encode_family(ebml_w, style_fn_family(fn_style))
@@ -1206,7 +1213,7 @@ fn encode_info_for_item(ecx: &EncodeContext,
12061213
encode_path(ebml_w, path.clone().chain(Some(elem).move_iter()));
12071214

12081215
match method_ty.explicit_self {
1209-
SelfStatic => {
1216+
ty::StaticExplicitSelfCategory => {
12101217
encode_family(ebml_w,
12111218
fn_style_static_method_family(
12121219
method_ty.fty.fn_style));
@@ -1233,7 +1240,7 @@ fn encode_info_for_item(ecx: &EncodeContext,
12331240
encode_attributes(ebml_w, m.attrs.as_slice());
12341241
// If this is a static method, we've already encoded
12351242
// this.
1236-
if method_ty.explicit_self != SelfStatic {
1243+
if method_ty.explicit_self != ty::StaticExplicitSelfCategory {
12371244
// FIXME: I feel like there is something funny going on.
12381245
let pty = ty::lookup_item_type(tcx, method_def_id);
12391246
encode_bounds_and_type(ebml_w, ecx, &pty);

src/librustc/middle/region.rs

+10
Original file line numberDiff line numberDiff line change
@@ -314,6 +314,16 @@ impl RegionMaps {
314314
self.sub_free_region(sub_fr, super_fr)
315315
}
316316

317+
(ty::ReEarlyBound(param_id_a, param_space_a, index_a, _),
318+
ty::ReEarlyBound(param_id_b, param_space_b, index_b, _)) => {
319+
// This case is used only to make sure that explicitly-
320+
// specified `Self` types match the real self type in
321+
// implementations.
322+
param_id_a == param_id_b &&
323+
param_space_a == param_space_b &&
324+
index_a == index_b
325+
}
326+
317327
_ => {
318328
false
319329
}

src/librustc/middle/resolve.rs

+54-13
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,14 @@
1111
#![allow(non_camel_case_types)]
1212

1313
use driver::session::Session;
14+
use lint;
1415
use metadata::csearch;
1516
use metadata::decoder::{DefLike, DlDef, DlField, DlImpl};
1617
use middle::def::*;
1718
use middle::lang_items::LanguageItems;
1819
use middle::pat_util::pat_bindings;
1920
use middle::subst::{ParamSpace, FnSpace, TypeSpace};
20-
use lint;
21+
use middle::ty::{ExplicitSelfCategory, StaticExplicitSelfCategory};
2122
use util::nodemap::{NodeMap, DefIdSet, FnvHashMap};
2223

2324
use syntax::ast::*;
@@ -287,6 +288,24 @@ enum ModulePrefixResult {
287288
PrefixFound(Rc<Module>, uint)
288289
}
289290

291+
#[deriving(Clone, Eq, PartialEq)]
292+
enum MethodIsStaticFlag {
293+
MethodIsNotStatic,
294+
MethodIsStatic,
295+
}
296+
297+
impl MethodIsStaticFlag {
298+
fn from_explicit_self_category(explicit_self_category:
299+
ExplicitSelfCategory)
300+
-> MethodIsStaticFlag {
301+
if explicit_self_category == StaticExplicitSelfCategory {
302+
MethodIsStatic
303+
} else {
304+
MethodIsNotStatic
305+
}
306+
}
307+
}
308+
290309
#[deriving(PartialEq)]
291310
enum NameSearchType {
292311
/// We're doing a name search in order to resolve a `use` directive.
@@ -805,7 +824,8 @@ struct Resolver<'a> {
805824

806825
graph_root: NameBindings,
807826

808-
method_map: RefCell<FnvHashMap<(Name, DefId), ast::ExplicitSelf_>>,
827+
method_map: RefCell<FnvHashMap<(Name, DefId), MethodIsStaticFlag>>,
828+
809829
structs: FnvHashMap<DefId, Vec<Name>>,
810830

811831
// The number of imports that are currently unresolved.
@@ -1361,17 +1381,19 @@ impl<'a> Resolver<'a> {
13611381
let ident = ty_m.ident;
13621382

13631383
// Add it as a name in the trait module.
1364-
let def = match ty_m.explicit_self.node {
1384+
let (def, static_flag) = match ty_m.explicit_self.node {
13651385
SelfStatic => {
13661386
// Static methods become `def_static_method`s.
1367-
DefStaticMethod(local_def(ty_m.id),
1387+
(DefStaticMethod(local_def(ty_m.id),
13681388
FromTrait(local_def(item.id)),
1369-
ty_m.fn_style)
1389+
ty_m.fn_style),
1390+
MethodIsStatic)
13701391
}
13711392
_ => {
13721393
// Non-static methods become `def_method`s.
1373-
DefMethod(local_def(ty_m.id),
1374-
Some(local_def(item.id)))
1394+
(DefMethod(local_def(ty_m.id),
1395+
Some(local_def(item.id))),
1396+
MethodIsNotStatic)
13751397
}
13761398
};
13771399

@@ -1382,8 +1404,9 @@ impl<'a> Resolver<'a> {
13821404
ty_m.span);
13831405
method_name_bindings.define_value(def, ty_m.span, true);
13841406

1385-
self.method_map.borrow_mut().insert((ident.name, def_id),
1386-
ty_m.explicit_self.node);
1407+
self.method_map
1408+
.borrow_mut()
1409+
.insert((ident.name, def_id), static_flag);
13871410
}
13881411

13891412
name_bindings.define_type(DefTrait(def_id), sp, is_public);
@@ -1670,7 +1693,11 @@ impl<'a> Resolver<'a> {
16701693
trait method '{}'",
16711694
token::get_ident(method_name));
16721695

1673-
self.method_map.borrow_mut().insert((method_name.name, def_id), explicit_self);
1696+
self.method_map
1697+
.borrow_mut()
1698+
.insert((method_name.name, def_id),
1699+
MethodIsStaticFlag::from_explicit_self_category(
1700+
explicit_self));
16741701

16751702
if is_exported {
16761703
self.external_exports.insert(method_def_id);
@@ -3678,6 +3705,13 @@ impl<'a> Resolver<'a> {
36783705
this.resolve_type(&*argument.ty);
36793706
}
36803707

3708+
match ty_m.explicit_self.node {
3709+
SelfExplicit(ref typ, _) => {
3710+
this.resolve_type(*typ)
3711+
}
3712+
_ => {}
3713+
}
3714+
36813715
this.resolve_type(&*ty_m.decl.output);
36823716
});
36833717
}
@@ -4009,7 +4043,14 @@ impl<'a> Resolver<'a> {
40094043
method.id,
40104044
rib_kind);
40114045

4012-
self.resolve_function(rib_kind, Some(method.pe_fn_decl()), type_parameters,
4046+
match method.pe_explicit_self().node {
4047+
SelfExplicit(ref typ, _) => self.resolve_type(*typ),
4048+
_ => {}
4049+
}
4050+
4051+
self.resolve_function(rib_kind,
4052+
Some(method.pe_fn_decl()),
4053+
type_parameters,
40134054
method.pe_body());
40144055
}
40154056

@@ -4765,7 +4806,7 @@ impl<'a> Resolver<'a> {
47654806
match containing_module.def_id.get() {
47664807
Some(def_id) => {
47674808
match self.method_map.borrow().find(&(ident.name, def_id)) {
4768-
Some(x) if *x == SelfStatic => (),
4809+
Some(&MethodIsStatic) => (),
47694810
None => (),
47704811
_ => {
47714812
debug!("containing module was a trait or impl \
@@ -5037,7 +5078,7 @@ impl<'a> Resolver<'a> {
50375078
let path_str = self.path_idents_to_string(&trait_ref.path);
50385079

50395080
match method_map.find(&(name, did)) {
5040-
Some(&SelfStatic) => return StaticTraitMethod(path_str),
5081+
Some(&MethodIsStatic) => return StaticTraitMethod(path_str),
50415082
Some(_) => return TraitMethod,
50425083
None => {}
50435084
}

src/librustc/middle/trans/meth.rs

+6-9
Original file line numberDiff line numberDiff line change
@@ -502,15 +502,12 @@ fn emit_vtable_methods(bcx: &Block,
502502
ExprId(0),
503503
substs.clone(),
504504
vtables.clone());
505-
match m.explicit_self {
506-
ast::SelfValue(_) => {
507-
fn_ref = trans_unboxing_shim(bcx,
508-
fn_ref,
509-
&*m,
510-
m_id,
511-
substs.clone());
512-
},
513-
_ => {}
505+
if m.explicit_self == ty::ByValueExplicitSelfCategory {
506+
fn_ref = trans_unboxing_shim(bcx,
507+
fn_ref,
508+
&*m,
509+
m_id,
510+
substs.clone());
514511
}
515512
fn_ref
516513
}

src/librustc/middle/ty.rs

+16-2
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ pub struct Method {
8585
pub ident: ast::Ident,
8686
pub generics: ty::Generics,
8787
pub fty: BareFnTy,
88-
pub explicit_self: ast::ExplicitSelf_,
88+
pub explicit_self: ExplicitSelfCategory,
8989
pub vis: ast::Visibility,
9090
pub def_id: ast::DefId,
9191
pub container: MethodContainer,
@@ -98,7 +98,7 @@ impl Method {
9898
pub fn new(ident: ast::Ident,
9999
generics: ty::Generics,
100100
fty: BareFnTy,
101-
explicit_self: ast::ExplicitSelf_,
101+
explicit_self: ExplicitSelfCategory,
102102
vis: ast::Visibility,
103103
def_id: ast::DefId,
104104
container: MethodContainer,
@@ -311,6 +311,9 @@ pub struct ctxt {
311311
/// (inferred) variance.
312312
pub item_variance_map: RefCell<DefIdMap<Rc<ItemVariances>>>,
313313

314+
/// True if the variance has been computed yet; false otherwise.
315+
pub variance_computed: Cell<bool>,
316+
314317
/// A mapping from the def ID of an enum or struct type to the def ID
315318
/// of the method that implements its destructor. If the type is not
316319
/// present in this map, it does not have a destructor. This map is
@@ -1055,6 +1058,7 @@ pub fn mk_ctxt(s: Session,
10551058
ctxt {
10561059
named_region_map: named_region_map,
10571060
item_variance_map: RefCell::new(DefIdMap::new()),
1061+
variance_computed: Cell::new(false),
10581062
interner: RefCell::new(FnvHashMap::new()),
10591063
next_id: Cell::new(primitives::LAST_PRIMITIVE_ID),
10601064
sess: s,
@@ -4767,3 +4771,13 @@ impl mc::Typer for ty::ctxt {
47674771
self.upvar_borrow_map.borrow().get_copy(&upvar_id)
47684772
}
47694773
}
4774+
4775+
/// The category of explicit self.
4776+
#[deriving(Clone, Eq, PartialEq)]
4777+
pub enum ExplicitSelfCategory {
4778+
StaticExplicitSelfCategory,
4779+
ByValueExplicitSelfCategory,
4780+
ByReferenceExplicitSelfCategory(Region, ast::Mutability),
4781+
ByBoxExplicitSelfCategory,
4782+
}
4783+

0 commit comments

Comments
 (0)