Skip to content

Commit 46c7a11

Browse files
Privatize TraitObject.principal and add a method accessor, returning Option.
1 parent 0b399e5 commit 46c7a11

29 files changed

+142
-103
lines changed

src/librustc/traits/coherence.rs

Lines changed: 7 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -225,14 +225,12 @@ fn ty_is_local(tcx: TyCtxt, ty: Ty, infer_is_local: InferIsLocal) -> bool {
225225

226226
fn fundamental_ty(tcx: TyCtxt, ty: Ty) -> bool {
227227
match ty.sty {
228-
ty::TyBox(..) | ty::TyRef(..) =>
229-
true,
230-
ty::TyAdt(def, _) =>
231-
def.is_fundamental(),
232-
ty::TyTrait(ref data) =>
233-
tcx.has_attr(data.principal.def_id(), "fundamental"),
234-
_ =>
235-
false
228+
ty::TyBox(..) | ty::TyRef(..) => true,
229+
ty::TyAdt(def, _) => def.is_fundamental(),
230+
ty::TyTrait(ref data) => {
231+
data.principal().map_or(false, |p| tcx.has_attr(p.def_id(), "fundamental"))
232+
}
233+
_ => false
236234
}
237235
}
238236

@@ -273,7 +271,7 @@ fn ty_is_local_constructor(tcx: TyCtxt, ty: Ty, infer_is_local: InferIsLocal)->
273271
}
274272

275273
ty::TyTrait(ref tt) => {
276-
tt.principal.def_id().is_local()
274+
tt.principal().map_or(false, |p| p.def_id().is_local())
277275
}
278276

279277
ty::TyError => {

src/librustc/traits/select.rs

Lines changed: 21 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1528,7 +1528,10 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
15281528
_ => {}
15291529
}
15301530

1531-
data.principal.with_self_ty(this.tcx(), self_ty)
1531+
match data.principal() {
1532+
Some(ref p) => p.with_self_ty(this.tcx(), self_ty),
1533+
None => return,
1534+
}
15321535
}
15331536
ty::TyInfer(ty::TyVar(_)) => {
15341537
debug!("assemble_candidates_from_object_ty: ambiguous");
@@ -1611,8 +1614,11 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
16111614
//
16121615
// We always upcast when we can because of reason
16131616
// #2 (region bounds).
1614-
data_a.principal.def_id() == data_b.principal.def_id() &&
1615-
data_a.builtin_bounds.is_superset(&data_b.builtin_bounds)
1617+
match (data_a.principal(), data_b.principal()) {
1618+
(Some(ref a), Some(ref b)) => a.def_id() == b.def_id() &&
1619+
data_a.builtin_bounds.is_superset(&data_b.builtin_bounds),
1620+
_ => false
1621+
}
16161622
}
16171623

16181624
// T -> Trait.
@@ -2167,7 +2173,8 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
21672173
match self_ty.sty {
21682174
ty::TyTrait(ref data) => {
21692175
// OK to skip the binder, it is reintroduced below
2170-
let input_types = data.principal.input_types();
2176+
let principal = data.principal().unwrap();
2177+
let input_types = principal.input_types();
21712178
let assoc_types = data.projection_bounds.iter()
21722179
.map(|pb| pb.skip_binder().ty);
21732180
let all_types: Vec<_> = input_types.chain(assoc_types)
@@ -2301,7 +2308,7 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
23012308
let self_ty = self.infcx.shallow_resolve(*obligation.self_ty().skip_binder());
23022309
let poly_trait_ref = match self_ty.sty {
23032310
ty::TyTrait(ref data) => {
2304-
data.principal.with_self_ty(self.tcx(), self_ty)
2311+
data.principal().unwrap().with_self_ty(self.tcx(), self_ty)
23052312
}
23062313
_ => {
23072314
span_bug!(obligation.cause.span,
@@ -2471,12 +2478,13 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
24712478
// Trait+Kx+'a -> Trait+Ky+'b (upcasts).
24722479
(&ty::TyTrait(ref data_a), &ty::TyTrait(ref data_b)) => {
24732480
// See assemble_candidates_for_unsizing for more info.
2474-
let new_trait = tcx.mk_trait(ty::TraitObject {
2475-
principal: data_a.principal,
2476-
region_bound: data_b.region_bound,
2477-
builtin_bounds: data_b.builtin_bounds,
2478-
projection_bounds: data_a.projection_bounds.clone(),
2479-
});
2481+
let new_trait = tcx.mk_trait(ty::TraitObject::new(
2482+
data_a.principal(),
2483+
data_b.region_bound,
2484+
data_b.builtin_bounds,
2485+
data_a.projection_bounds.clone(),
2486+
));
2487+
let origin = TypeOrigin::Misc(obligation.cause.span);
24802488
let InferOk { obligations, .. } =
24812489
self.infcx.sub_types(false, &obligation.cause, new_trait, target)
24822490
.map_err(|_| Unimplemented)?;
@@ -2499,7 +2507,7 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
24992507
data.builtin_bounds.iter().flat_map(|bound| {
25002508
tcx.lang_items.from_builtin_kind(bound).ok()
25012509
})
2502-
.chain(Some(data.principal.def_id()));
2510+
.chain(data.principal().map(|ref p| p.def_id()));
25032511
if let Some(did) = object_dids.find(|did| {
25042512
!tcx.is_object_safe(*did)
25052513
}) {
@@ -2516,7 +2524,7 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> {
25162524
};
25172525

25182526
// Create the obligation for casting from T to Trait.
2519-
push(data.principal.with_self_ty(tcx, source).to_predicate());
2527+
push(data.principal().unwrap().with_self_ty(tcx, source).to_predicate());
25202528

25212529
// We can only make objects from sized types.
25222530
let mut builtin_bounds = data.builtin_bounds;

src/librustc/ty/error.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -215,7 +215,8 @@ impl<'a, 'gcx, 'lcx, 'tcx> ty::TyS<'tcx> {
215215
ty::TyFnDef(..) => format!("fn item"),
216216
ty::TyFnPtr(_) => "fn pointer".to_string(),
217217
ty::TyTrait(ref inner) => {
218-
format!("trait {}", tcx.item_path_str(inner.principal.def_id()))
218+
inner.principal().map_or_else(|| "trait".to_string(),
219+
|p| format!("trait {}", tcx.item_path_str(p.def_id())))
219220
}
220221
ty::TyClosure(..) => "closure".to_string(),
221222
ty::TyTuple(_) => "tuple".to_string(),

src/librustc/ty/fast_reject.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ pub fn simplify_type<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>,
6060
ty::TyArray(..) | ty::TySlice(_) => Some(ArraySimplifiedType),
6161
ty::TyRawPtr(_) => Some(PtrSimplifiedType),
6262
ty::TyTrait(ref trait_info) => {
63-
Some(TraitSimplifiedType(trait_info.principal.def_id()))
63+
trait_info.principal().map(|p| TraitSimplifiedType(p.def_id()))
6464
}
6565
ty::TyRef(_, mt) => {
6666
// since we introduce auto-refs during method lookup, we

src/librustc/ty/flags.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ impl FlagComputation {
123123

124124
&ty::TyTrait(ref obj) => {
125125
let mut computation = FlagComputation::new();
126-
computation.add_substs(obj.principal.skip_binder().substs);
126+
computation.add_substs(obj.principal().unwrap().skip_binder().substs);
127127
for projection_bound in &obj.projection_bounds {
128128
let mut proj_computation = FlagComputation::new();
129129
proj_computation.add_existential_projection(&projection_bound.0);

src/librustc/ty/item_path.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -316,7 +316,7 @@ pub fn characteristic_def_id_of_type(ty: Ty) -> Option<DefId> {
316316
match ty.sty {
317317
ty::TyAdt(adt_def, _) => Some(adt_def.did),
318318

319-
ty::TyTrait(ref data) => Some(data.principal.def_id()),
319+
ty::TyTrait(ref data) => data.principal().map(|ref p| p.def_id()),
320320

321321
ty::TyArray(subty, _) |
322322
ty::TySlice(subty) |

src/librustc/ty/relate.rs

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -417,7 +417,11 @@ pub fn super_relate_tys<'a, 'gcx, 'tcx, R>(relation: &mut R,
417417

418418
(&ty::TyTrait(ref a_obj), &ty::TyTrait(ref b_obj)) =>
419419
{
420-
let principal = relation.relate(&a_obj.principal, &b_obj.principal)?;
420+
let principal = match (a_obj.principal(), b_obj.principal()) {
421+
(Some(ref a_p), Some(ref b_p)) => Some(relation.relate(a_p, b_p)?),
422+
(None, None) => None,
423+
_ => return Err(TypeError::Sorts(expected_found(relation, &a, &b))),
424+
};
421425
let r =
422426
relation.with_cause(
423427
Cause::ExistentialRegionBound,
@@ -426,12 +430,7 @@ pub fn super_relate_tys<'a, 'gcx, 'tcx, R>(relation: &mut R,
426430
&b_obj.region_bound))?;
427431
let nb = relation.relate(&a_obj.builtin_bounds, &b_obj.builtin_bounds)?;
428432
let pb = relation.relate(&a_obj.projection_bounds, &b_obj.projection_bounds)?;
429-
Ok(tcx.mk_trait(ty::TraitObject {
430-
principal: principal,
431-
region_bound: r,
432-
builtin_bounds: nb,
433-
projection_bounds: pb
434-
}))
433+
Ok(tcx.mk_trait(ty::TraitObject::new(principal, r, nb, pb)))
435434
}
436435

437436
(&ty::TyClosure(a_id, a_substs),

src/librustc/ty/structural_impls.rs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -429,16 +429,16 @@ impl<'tcx, T:TypeFoldable<'tcx>> TypeFoldable<'tcx> for ty::Binder<T> {
429429

430430
impl<'tcx> TypeFoldable<'tcx> for ty::TraitObject<'tcx> {
431431
fn super_fold_with<'gcx: 'tcx, F: TypeFolder<'gcx, 'tcx>>(&self, folder: &mut F) -> Self {
432-
ty::TraitObject {
433-
principal: self.principal.fold_with(folder),
434-
region_bound: self.region_bound.fold_with(folder),
435-
builtin_bounds: self.builtin_bounds,
436-
projection_bounds: self.projection_bounds.fold_with(folder),
437-
}
432+
ty::TraitObject::new(
433+
self.principal().map(|p| p.fold_with(folder)),
434+
self.region_bound.fold_with(folder),
435+
self.builtin_bounds,
436+
self.projection_bounds.fold_with(folder),
437+
)
438438
}
439439

440440
fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool {
441-
self.principal.visit_with(visitor) ||
441+
self.principal().map(|p| p.visit_with(visitor)).unwrap_or(true) ||
442442
self.region_bound.visit_with(visitor) ||
443443
self.projection_bounds.visit_with(visitor)
444444
}

src/librustc/ty/sty.rs

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -277,12 +277,29 @@ impl<'a, 'gcx, 'acx, 'tcx> ClosureSubsts<'tcx> {
277277

278278
#[derive(Clone, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable)]
279279
pub struct TraitObject<'tcx> {
280-
pub principal: PolyExistentialTraitRef<'tcx>,
280+
principal: Option<PolyExistentialTraitRef<'tcx>>,
281281
pub region_bound: &'tcx ty::Region,
282282
pub builtin_bounds: BuiltinBounds,
283283
pub projection_bounds: Vec<PolyExistentialProjection<'tcx>>,
284284
}
285285

286+
impl<'tcx> TraitObject<'tcx> {
287+
pub fn new(principal: Option<PolyExistentialTraitRef<'tcx>>, region_bound: &'tcx ty::Region,
288+
builtin_bounds: BuiltinBounds, projection_bounds: Vec<PolyExistentialProjection<'tcx>>)
289+
-> Self {
290+
TraitObject {
291+
principal: principal,
292+
region_bound: region_bound,
293+
builtin_bounds: builtin_bounds,
294+
projection_bounds: projection_bounds,
295+
}
296+
}
297+
298+
pub fn principal(&self) -> Option<PolyExistentialTraitRef<'tcx>> {
299+
self.principal
300+
}
301+
}
302+
286303
/// A complete reference to a trait. These take numerous guises in syntax,
287304
/// but perhaps the most recognizable form is in a where clause:
288305
///
@@ -1221,7 +1238,7 @@ impl<'a, 'gcx, 'tcx> TyS<'tcx> {
12211238

12221239
pub fn ty_to_def_id(&self) -> Option<DefId> {
12231240
match self.sty {
1224-
TyTrait(ref tt) => Some(tt.principal.def_id()),
1241+
TyTrait(ref tt) => tt.principal().map(|p| p.def_id()),
12251242
TyAdt(def, _) => Some(def.did),
12261243
TyClosure(id, _) => Some(id),
12271244
_ => None
@@ -1245,7 +1262,7 @@ impl<'a, 'gcx, 'tcx> TyS<'tcx> {
12451262
}
12461263
TyTrait(ref obj) => {
12471264
let mut v = vec![obj.region_bound];
1248-
v.extend(obj.principal.skip_binder().substs.regions());
1265+
v.extend(obj.principal().unwrap().skip_binder().substs.regions());
12491266
v
12501267
}
12511268
TyAdt(_, substs) | TyAnon(_, substs) => {

src/librustc/ty/util.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -532,7 +532,9 @@ impl<'a, 'gcx, 'tcx, H: Hasher> TypeVisitor<'tcx> for TypeIdHasher<'a, 'gcx, 'tc
532532
self.hash(f.sig.inputs().skip_binder().len());
533533
}
534534
TyTrait(ref data) => {
535-
self.def_id(data.principal.def_id());
535+
if let Some(ref p) = data.principal() {
536+
self.def_id(p.def_id());
537+
}
536538
self.hash(data.builtin_bounds);
537539
}
538540
TyTuple(tys) => {

src/librustc/ty/walk.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,10 @@ fn push_subtypes<'tcx>(stack: &mut TypeWalkerStack<'tcx>, parent_ty: Ty<'tcx>) {
9393
stack.extend(data.trait_ref.substs.types().rev());
9494
}
9595
ty::TyTrait(ref obj) => {
96-
stack.extend(obj.principal.input_types().rev());
96+
match obj.principal() {
97+
Some(ref p) => stack.extend(p.input_types().rev()),
98+
None => {}
99+
}
97100
stack.extend(obj.projection_bounds.iter().map(|pred| {
98101
pred.0.ty
99102
}).rev());

src/librustc/ty/wf.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -394,7 +394,7 @@ impl<'a, 'gcx, 'tcx> WfPredicates<'a, 'gcx, 'tcx> {
394394
data.builtin_bounds.iter().flat_map(|bound| {
395395
tcx.lang_items.from_builtin_kind(bound).ok()
396396
})
397-
.chain(Some(data.principal.def_id()));
397+
.chain(data.principal().map(|ref p| p.def_id()));
398398
self.out.extend(
399399
component_traits.map(|did| { traits::Obligation::new(
400400
cause.clone(),
@@ -492,7 +492,7 @@ impl<'a, 'gcx, 'tcx> WfPredicates<'a, 'gcx, 'tcx> {
492492
if !data.has_escaping_regions() {
493493
let implicit_bounds =
494494
object_region_bounds(self.infcx.tcx,
495-
data.principal,
495+
data.principal().unwrap(),
496496
data.builtin_bounds);
497497

498498
let explicit_bound = data.region_bound;

src/librustc/util/ppaux.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -339,7 +339,7 @@ impl<'tcx> fmt::Display for ty::TraitObject<'tcx> {
339339
// Use a type that can't appear in defaults of type parameters.
340340
let dummy_self = tcx.mk_infer(ty::FreshTy(0));
341341

342-
let principal = tcx.lift(&self.principal)
342+
let principal = self.principal().and_then(|ref p| tcx.lift(p))
343343
.expect("could not lift TraitRef for printing")
344344
.with_self_ty(tcx, dummy_self).0;
345345
let projections = self.projection_bounds.iter().map(|p| {
@@ -466,7 +466,7 @@ impl<'tcx> fmt::Debug for ty::TraitObject<'tcx> {
466466
};
467467

468468
maybe_continue(f)?;
469-
write!(f, "{:?}", self.principal)?;
469+
write!(f, "{:?}", self.principal())?;
470470

471471
let region_str = format!("{:?}", self.region_bound);
472472
if !region_str.is_empty() {

src/librustc_trans/base.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -302,7 +302,7 @@ pub fn unsized_info<'ccx, 'tcx>(ccx: &CrateContext<'ccx, 'tcx>,
302302
old_info.expect("unsized_info: missing old info for trait upcast")
303303
}
304304
(_, &ty::TyTrait(ref data)) => {
305-
let trait_ref = data.principal.with_self_ty(ccx.tcx(), source);
305+
let trait_ref = data.principal().unwrap().with_self_ty(ccx.tcx(), source);
306306
let trait_ref = ccx.tcx().erase_regions(&trait_ref);
307307
consts::ptrcast(meth::get_vtable(ccx, trait_ref),
308308
Type::vtable_ptr(ccx))

src/librustc_trans/collector.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1004,7 +1004,7 @@ fn create_trans_items_for_vtable_methods<'a, 'tcx>(scx: &SharedCrateContext<'a,
10041004
assert!(!trait_ty.needs_subst() && !impl_ty.needs_subst());
10051005

10061006
if let ty::TyTrait(ref trait_ty) = trait_ty.sty {
1007-
let poly_trait_ref = trait_ty.principal.with_self_ty(scx.tcx(), impl_ty);
1007+
let poly_trait_ref = trait_ty.principal().unwrap().with_self_ty(scx.tcx(), impl_ty);
10081008
let param_substs = scx.tcx().intern_substs(&[]);
10091009

10101010
// Walk all methods of the trait, including those of its supertraits

src/librustc_trans/debuginfo/metadata.rs

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -431,8 +431,13 @@ fn trait_pointer_metadata<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
431431
// type is assigned the correct name, size, namespace, and source location.
432432
// But it does not describe the trait's methods.
433433

434-
let def_id = match trait_type.sty {
435-
ty::TyTrait(ref data) => data.principal.def_id(),
434+
let containing_scope = match trait_type.sty {
435+
ty::TyTrait(ref data) => if let Some(principal) = data.principal() {
436+
let def_id = principal.def_id();
437+
get_namespace_and_span_for_item(cx, def_id).0
438+
} else {
439+
NO_SCOPE_METADATA
440+
},
436441
_ => {
437442
bug!("debuginfo: Unexpected trait-object type in \
438443
trait_pointer_metadata(): {:?}",
@@ -444,8 +449,6 @@ fn trait_pointer_metadata<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
444449
let trait_type_name =
445450
compute_debuginfo_type_name(cx, trait_object_type, false);
446451

447-
let (containing_scope, _) = get_namespace_and_span_for_item(cx, def_id);
448-
449452
let trait_llvm_type = type_of::type_of(cx, trait_object_type);
450453
let file_metadata = unknown_file_metadata(cx);
451454

src/librustc_trans/debuginfo/type_names.rs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -94,10 +94,12 @@ pub fn push_debuginfo_type_name<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
9494
output.push(']');
9595
},
9696
ty::TyTrait(ref trait_data) => {
97-
let principal = cx.tcx().erase_late_bound_regions_and_normalize(
98-
&trait_data.principal);
99-
push_item_name(cx, principal.def_id, false, output);
100-
push_type_params(cx, principal.substs, output);
97+
if let Some(principal) = trait_data.principal() {
98+
let principal = cx.tcx().erase_late_bound_regions_and_normalize(
99+
&principal);
100+
push_item_name(cx, principal.def_id, false, output);
101+
push_type_params(cx, principal.substs, output);
102+
}
101103
},
102104
ty::TyFnDef(.., &ty::BareFnTy{ unsafety, abi, ref sig } ) |
103105
ty::TyFnPtr(&ty::BareFnTy{ unsafety, abi, ref sig } ) => {

src/librustc_trans/trans_item.rs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -458,10 +458,12 @@ impl<'a, 'tcx> DefPathBasedNames<'a, 'tcx> {
458458
output.push(']');
459459
},
460460
ty::TyTrait(ref trait_data) => {
461-
self.push_def_path(trait_data.principal.def_id(), output);
462-
self.push_type_params(trait_data.principal.skip_binder().substs,
463-
&trait_data.projection_bounds,
464-
output);
461+
if let Some(principal) = trait_data.principal() {
462+
self.push_def_path(principal.def_id(), output);
463+
self.push_type_params(principal.skip_binder().substs,
464+
&trait_data.projection_bounds,
465+
output);
466+
}
465467
},
466468
ty::TyFnDef(.., &ty::BareFnTy{ unsafety, abi, ref sig } ) |
467469
ty::TyFnPtr(&ty::BareFnTy{ unsafety, abi, ref sig } ) => {

0 commit comments

Comments
 (0)