Skip to content

Commit bdfeb65

Browse files
committed
Forbid the Sized bound on unsized types
closes #16800
1 parent f2b87e9 commit bdfeb65

File tree

3 files changed

+48
-7
lines changed

3 files changed

+48
-7
lines changed

src/librustc/diagnostics.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -167,5 +167,6 @@ register_diagnostics!(
167167
E0155,
168168
E0156,
169169
E0157,
170-
E0158
170+
E0158,
171+
E0159
171172
)

src/librustc/middle/kind.rs

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

11-
1211
use middle::freevars::freevar_entry;
1312
use middle::freevars;
1413
use middle::subst;
@@ -593,15 +592,15 @@ fn check_ty(cx: &mut Context, aty: &Ty) {
593592
match aty.node {
594593
TyPath(_, _, id) => {
595594
match cx.tcx.item_substs.borrow().find(&id) {
596-
None => { }
595+
None => {}
597596
Some(ref item_substs) => {
598597
let def_map = cx.tcx.def_map.borrow();
599598
let did = def_map.get_copy(&id).def_id();
600-
let generics = ty::lookup_item_type(cx.tcx, did).generics;
601-
for def in generics.types.iter() {
599+
let ty = ty::lookup_item_type(cx.tcx, did);
600+
for def in ty.generics.types.iter() {
602601
let ty = *item_substs.substs.types.get(def.space,
603602
def.index);
604-
check_typaram_bounds(cx, aty.span, ty, def)
603+
check_typaram_bounds(cx, aty.span, ty, def);
605604
}
606605
}
607606
}
@@ -645,6 +644,20 @@ pub fn check_typaram_bounds(cx: &Context,
645644
});
646645
}
647646

647+
// Check that the programmer has not added the `Sized` bound to a trait type
648+
// which would fool the compiler into thinking that trait types are sized, when
649+
// they are really unsized.
650+
fn check_false_sized(cx: &Context, sp: Span, ty: ty::t) {
651+
match ty::get(ty).sty {
652+
ty::ty_trait(..) if ty::type_is_sized(cx.tcx, ty) => {
653+
span_err!(cx.tcx.sess, sp, E0159,
654+
"explicitly adding `Sized` bound to an unsized type `{}`",
655+
ty_to_string(cx.tcx, ty));
656+
}
657+
_ => {}
658+
}
659+
}
660+
648661
fn check_bounds_on_structs_or_enums_in_type_if_possible(cx: &mut Context,
649662
span: Span,
650663
ty: ty::t) {
@@ -674,7 +687,8 @@ fn check_bounds_on_structs_or_enums_in_type_if_possible(cx: &mut Context,
674687
.zip(polytype.generics
675688
.types
676689
.iter()) {
677-
check_typaram_bounds(cx, span, *ty, type_param_def)
690+
check_typaram_bounds(cx, span, *ty, type_param_def);
691+
check_false_sized(cx, span, *ty);
678692
}
679693

680694
// Check trait bounds.
@@ -702,6 +716,7 @@ fn check_bounds_on_structs_or_enums_in_type_if_possible(cx: &mut Context,
702716
cx.tcx)).as_slice());
703717
})
704718
}
719+
ty::ty_uniq(ty) => check_false_sized(cx, span, ty),
705720
_ => {}
706721
}
707722
});

src/test/compile-fail/bad-sized.rs

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
2+
// file at the top-level directory of this distribution and at
3+
// http://rust-lang.org/COPYRIGHT.
4+
//
5+
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6+
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7+
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8+
// option. This file may not be copied, modified, or distributed
9+
// except according to those terms.
10+
11+
use std::cell::RefCell;
12+
13+
trait Trait {}
14+
15+
pub fn main() {
16+
let x: Vec<Trait + Sized> = Vec::new();
17+
//~^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
18+
//~^^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
19+
let x: Vec<Box<Trait + Sized>> = Vec::new();
20+
//~^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
21+
//~^^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
22+
let x: Vec<Box<RefCell<Trait + Sized>>> = Vec::new();
23+
//~^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
24+
//~^^ ERROR explicitly adding `Sized` bound to an unsized type `Trait+Sized`
25+
}

0 commit comments

Comments
 (0)