Skip to content

Commit 9ad6d05

Browse files
committed
---
yaml --- r: 157611 b: refs/heads/snap-stage3 c: 8d8d8d4 h: refs/heads/master i: 157609: 1c3a575 157607: 0df5c2c v: v3
1 parent 5450e2f commit 9ad6d05

File tree

5 files changed

+71
-78
lines changed

5 files changed

+71
-78
lines changed

[refs]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
---
22
refs/heads/master: 065caf34f5ff29e04605f95d9c5d511af219439a
33
refs/heads/snap-stage1: e33de59e47c5076a89eadeb38f4934f58a3618a6
4-
refs/heads/snap-stage3: d1fc2dec79689fe6bd37c95f3fe5b7acd476fff6
4+
refs/heads/snap-stage3: 8d8d8d4e5292c2fa4a622d981a5f85fd3d8f34d0
55
refs/heads/try: 0ee4d8b0b112c608646fa75463ab4dc59132efd9
66
refs/tags/release-0.1: 1f5c5126e96c79d22cb7862f75304136e204f105
77
refs/heads/ndm: f3868061cd7988080c30d6d5bf352a5a5fe2460b

branches/snap-stage3/mk/llvm.mk

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ endif
3838
# the stamp in the source dir.
3939
$$(LLVM_STAMP_$(1)): $(S)src/rustllvm/llvm-auto-clean-trigger
4040
@$$(call E, make: cleaning llvm)
41-
$(Q)$(MAKE) clean-llvm$(1)
41+
$(Q)$(MAKE) clean-llvm
4242
@$$(call E, make: done cleaning llvm)
4343
touch $$@
4444

branches/snap-stage3/src/librustc/middle/typeck/check/method.rs

Lines changed: 0 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -1336,16 +1336,6 @@ impl<'a, 'tcx> LookupContext<'a, 'tcx> {
13361336
self.ty_to_string(rcvr_ty),
13371337
candidate.repr(self.tcx()));
13381338

1339-
let mut rcvr_substs = candidate.rcvr_substs.clone();
1340-
1341-
if !self.enforce_object_limitations(candidate) {
1342-
// Here we change `Self` from `Trait` to `err` in the case that
1343-
// this is an illegal object method. This is necessary to prevent
1344-
// the user from getting strange, derivative errors when the method
1345-
// takes an argument/return-type of type `Self` etc.
1346-
rcvr_substs.types.get_mut_slice(SelfSpace)[0] = ty::mk_err();
1347-
}
1348-
13491339
self.enforce_drop_trait_limitations(candidate);
13501340

13511341
// Determine the values for the generic parameters of the method.
@@ -1554,71 +1544,6 @@ impl<'a, 'tcx> LookupContext<'a, 'tcx> {
15541544
}
15551545
}
15561546

1557-
fn enforce_object_limitations(&self, candidate: &Candidate) -> bool {
1558-
/*!
1559-
* There are some limitations to calling functions through an
1560-
* object, because (a) the self type is not known
1561-
* (that's the whole point of a trait instance, after all, to
1562-
* obscure the self type) and (b) the call must go through a
1563-
* vtable and hence cannot be monomorphized.
1564-
*/
1565-
1566-
match candidate.origin {
1567-
MethodStatic(..) |
1568-
MethodTypeParam(..) |
1569-
MethodStaticUnboxedClosure(..) => {
1570-
return true; // not a call to a trait instance
1571-
}
1572-
MethodTraitObject(..) => {}
1573-
}
1574-
1575-
match candidate.method_ty.explicit_self {
1576-
ty::StaticExplicitSelfCategory => { // reason (a) above
1577-
self.tcx().sess.span_err(
1578-
self.span,
1579-
"cannot call a method without a receiver \
1580-
through an object");
1581-
return false;
1582-
}
1583-
1584-
ty::ByValueExplicitSelfCategory |
1585-
ty::ByReferenceExplicitSelfCategory(..) |
1586-
ty::ByBoxExplicitSelfCategory => {}
1587-
}
1588-
1589-
// reason (a) above
1590-
let check_for_self_ty = |ty| -> bool {
1591-
if ty::type_has_self(ty) {
1592-
span_err!(self.tcx().sess, self.span, E0038,
1593-
"cannot call a method whose type contains a \
1594-
self-type through an object");
1595-
false
1596-
} else {
1597-
true
1598-
}
1599-
};
1600-
let ref sig = candidate.method_ty.fty.sig;
1601-
for &input_ty in sig.inputs[1..].iter() {
1602-
if !check_for_self_ty(input_ty) {
1603-
return false;
1604-
}
1605-
}
1606-
if let ty::FnConverging(result_type) = sig.output {
1607-
if !check_for_self_ty(result_type) {
1608-
return false;
1609-
}
1610-
}
1611-
1612-
if candidate.method_ty.generics.has_type_params(subst::FnSpace) {
1613-
// reason (b) above
1614-
span_err!(self.tcx().sess, self.span, E0039,
1615-
"cannot call a generic method through an object");
1616-
return false;
1617-
}
1618-
1619-
true
1620-
}
1621-
16221547
fn enforce_drop_trait_limitations(&self, candidate: &Candidate) {
16231548
// No code can call the finalize method explicitly.
16241549
let bad = match candidate.origin {

branches/snap-stage3/src/librustc/middle/typeck/check/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1687,6 +1687,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
16871687
self.register_unsize_obligations(span, &**u)
16881688
}
16891689
ty::UnsizeVtable(ref ty_trait, self_ty) => {
1690+
vtable2::check_object_safety(self.tcx(), ty_trait, span);
16901691
// If the type is `Foo+'a`, ensures that the type
16911692
// being cast to `Foo+'a` implements `Foo`:
16921693
vtable::register_object_cast_obligations(self,

branches/snap-stage3/src/librustc/middle/typeck/check/vtable.rs

Lines changed: 68 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
// option. This file may not be copied, modified, or distributed
99
// except according to those terms.
1010

11-
use middle::subst::{SelfSpace};
11+
use middle::subst::{SelfSpace, FnSpace};
1212
use middle::traits;
1313
use middle::traits::{SelectionError, OutputTypeParameterMismatch, Overflow, Unimplemented};
1414
use middle::traits::{Obligation, obligation_for_builtin_bound};
@@ -46,6 +46,7 @@ pub fn check_object_cast(fcx: &FnCtxt,
4646

4747
// Ensure that if ~T is cast to ~Trait, then T : Trait
4848
push_cast_obligation(fcx, cast_expr, object_trait, referent_ty);
49+
check_object_safety(fcx.tcx(), object_trait, source_expr.span);
4950
}
5051

5152
(&ty::ty_rptr(referent_region, ty::mt { ty: referent_ty,
@@ -68,6 +69,8 @@ pub fn check_object_cast(fcx: &FnCtxt,
6869
infer::RelateObjectBound(source_expr.span),
6970
target_region,
7071
referent_region);
72+
73+
check_object_safety(fcx.tcx(), object_trait, source_expr.span);
7174
}
7275
}
7376

@@ -128,6 +131,70 @@ pub fn check_object_cast(fcx: &FnCtxt,
128131
}
129132
}
130133

134+
// TODO comment
135+
pub fn check_object_safety(tcx: &ty::ctxt, object_trait: &ty::TyTrait, span: Span) {
136+
let trait_items = ty::trait_items(tcx, object_trait.def_id);
137+
for item in trait_items.iter() {
138+
match *item {
139+
ty::MethodTraitItem(ref m) => check_object_safety_of_method(tcx, &**m, span),
140+
ty::TypeTraitItem(_) => {}
141+
}
142+
}
143+
144+
// TODO error messages
145+
fn check_object_safety_of_method(tcx: &ty::ctxt, method: &ty::Method, span: Span) {
146+
/*!
147+
* There are some limitations to calling functions through an
148+
* object, because (a) the self type is not known
149+
* (that's the whole point of a trait instance, after all, to
150+
* obscure the self type) and (b) the call must go through a
151+
* vtable and hence cannot be monomorphized.
152+
*/
153+
154+
match method.explicit_self {
155+
ty::ByValueExplicitSelfCategory => { // reason (a) above
156+
tcx.sess.span_err(
157+
span,
158+
"cannot call a method with a by-value receiver \
159+
through a trait object");
160+
}
161+
162+
ty::StaticExplicitSelfCategory |
163+
ty::ByReferenceExplicitSelfCategory(..) |
164+
ty::ByBoxExplicitSelfCategory => {}
165+
}
166+
167+
// reason (a) above
168+
let check_for_self_ty = |ty| {
169+
if ty::type_has_self(ty) {
170+
span_err!(tcx.sess, span, E0038,
171+
"cannot call a method whose type contains a \
172+
self-type through an object: {}", ::util::ppaux::ty_to_string(tcx, ty));
173+
true
174+
} else {
175+
false
176+
}
177+
};
178+
let ref sig = method.fty.sig;
179+
let mut found_self_ty = false;
180+
for &input_ty in sig.inputs.tail().iter() {
181+
if check_for_self_ty(input_ty) {
182+
found_self_ty = true;
183+
break;
184+
}
185+
}
186+
if !found_self_ty {
187+
check_for_self_ty(sig.output);
188+
}
189+
190+
if method.generics.has_type_params(FnSpace) {
191+
// reason (b) above
192+
span_err!(tcx.sess, span, E0039,
193+
"cannot call a generic method through an object");
194+
}
195+
}
196+
}
197+
131198
pub fn register_object_cast_obligations(fcx: &FnCtxt,
132199
span: Span,
133200
object_trait: &ty::TyTrait,

0 commit comments

Comments
 (0)