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.
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.
12 use middle::def_id::DefId;
13 use middle::subst::{self, Subst};
14 use middle::ty::{BrAnon, BrEnv, BrFresh, BrNamed};
15 use middle::ty::{TyBool, TyChar, TyStruct, TyEnum};
16 use middle::ty::{TyError, TyStr, TyArray, TySlice, TyFloat, TyFnDef, TyFnPtr};
17 use middle::ty::{TyParam, TyRawPtr, TyRef, TyTuple};
18 use middle::ty::TyClosure;
19 use middle::ty::{TyBox, TyTrait, TyInt, TyUint, TyInfer};
20 use middle::ty::{self, Ty, TyCtxt, TypeFoldable};
24 use syntax::parse::token;
25 use syntax::ast::CRATE_NODE_ID;
28 pub fn verbose() -> bool {
29 ty::tls::with(|tcx| tcx.sess.verbose())
32 fn fn_sig(f: &mut fmt::Formatter,
38 let mut inputs = inputs.iter();
39 if let Some(&ty) = inputs.next() {
42 write!(f, ", {}", ty)?;
51 ty::FnConverging(ty) => {
53 write!(f, " -> {}", ty)?;
63 /// Namespace of the path given to parameterized to print.
64 #[derive(Copy, Clone, PartialEq)]
70 pub fn parameterized<GG>(f: &mut fmt::Formatter,
71 substs: &subst::Substs,
74 projections: &[ty::ProjectionPredicate],
77 where GG: for<'tcx> FnOnce(&TyCtxt<'tcx>) -> ty::Generics<'tcx>
79 if let (Ns::Value, Some(self_ty)) = (ns, substs.self_ty()) {
80 write!(f, "<{} as ", self_ty)?;
83 let (fn_trait_kind, verbose, last_name) = ty::tls::with(|tcx| {
84 let (did, last_name) = if ns == Ns::Value {
85 // Try to get the impl/trait parent, if this is an
86 // associated value item (method or constant).
87 tcx.trait_of_item(did).or_else(|| tcx.impl_of_method(did))
88 .map_or((did, None), |parent| (parent, Some(tcx.item_name(did))))
92 write!(f, "{}", tcx.item_path_str(did))?;
93 Ok((tcx.lang_items.fn_trait_kind(did), tcx.sess.verbose(), last_name))
97 let mut start_or_continue = |f: &mut fmt::Formatter, start: &str, cont: &str| {
100 write!(f, "{}", start)
102 write!(f, "{}", cont)
107 for region in &substs.regions {
108 start_or_continue(f, "<", ", ")?;
109 write!(f, "{:?}", region)?;
111 for &ty in &substs.types {
112 start_or_continue(f, "<", ", ")?;
113 write!(f, "{}", ty)?;
115 for projection in projections {
116 start_or_continue(f, "<", ", ")?;
118 projection.projection_ty.item_name,
121 return start_or_continue(f, "", ">");
124 if fn_trait_kind.is_some() && projections.len() == 1 {
125 let projection_ty = projections[0].ty;
126 if let TyTuple(ref args) = substs.types.get_slice(subst::TypeSpace)[0].sty {
127 return fn_sig(f, args, false, ty::FnConverging(projection_ty));
131 for &r in &substs.regions {
132 start_or_continue(f, "<", ", ")?;
133 let s = r.to_string();
135 // This happens when the value of the region
136 // parameter is not easily serialized. This may be
137 // because the user omitted it in the first place,
138 // or because it refers to some block in the code,
139 // etc. I'm not sure how best to serialize this.
146 // It is important to execute this conditionally, only if -Z
147 // verbose is false. Otherwise, debug logs can sometimes cause
148 // ICEs trying to fetch the generics early in the pipeline. This
149 // is kind of a hacky workaround in that -Z verbose is required to
151 let tps = substs.types.get_slice(subst::TypeSpace);
152 let num_defaults = ty::tls::with(|tcx| {
153 let generics = get_generics(tcx);
155 let has_self = substs.self_ty().is_some();
156 let ty_params = generics.types.get_slice(subst::TypeSpace);
157 if ty_params.last().map_or(false, |def| def.default.is_some()) {
158 let substs = tcx.lift(&substs);
159 ty_params.iter().zip(tps).rev().take_while(|&(def, &actual)| {
162 if !has_self && default.has_self_ty() {
163 // In an object type, there is no `Self`, and
164 // thus if the default value references Self,
165 // the user will be required to give an
166 // explicit value. We can't even do the
167 // substitution below to check without causing
171 let default = tcx.lift(&default);
172 substs.and_then(|substs| default.subst(tcx, substs)) == Some(actual)
183 for &ty in &tps[..tps.len() - num_defaults] {
184 start_or_continue(f, "<", ", ")?;
185 write!(f, "{}", ty)?;
188 for projection in projections {
189 start_or_continue(f, "<", ", ")?;
191 projection.projection_ty.item_name,
195 start_or_continue(f, "", ">")?;
197 // For values, also print their name and type parameters.
199 if substs.self_ty().is_some() {
203 if let Some(name) = last_name {
204 write!(f, "::{}", name)?;
206 let tps = substs.types.get_slice(subst::FnSpace);
208 write!(f, "::<{}", tps[0])?;
209 for ty in &tps[1..] {
210 write!(f, ", {}", ty)?;
219 fn in_binder<'tcx, T, U>(f: &mut fmt::Formatter,
221 original: &ty::Binder<T>,
222 lifted: Option<ty::Binder<U>>) -> fmt::Result
223 where T: fmt::Display, U: fmt::Display + TypeFoldable<'tcx>
225 // Replace any anonymous late-bound regions with named
226 // variants, using gensym'd identifiers, so that we can
227 // clearly differentiate between named and unnamed regions in
228 // the output. We'll probably want to tweak this over time to
229 // decide just how much information to give.
230 let value = if let Some(v) = lifted {
233 return write!(f, "{}", original.0);
236 let mut empty = true;
237 let mut start_or_continue = |f: &mut fmt::Formatter, start: &str, cont: &str| {
240 write!(f, "{}", start)
242 write!(f, "{}", cont)
246 let new_value = tcx.replace_late_bound_regions(&value, |br| {
247 let _ = start_or_continue(f, "for<", ", ");
248 ty::ReLateBound(ty::DebruijnIndex::new(1), match br {
249 ty::BrNamed(_, name) => {
250 let _ = write!(f, "{}", name);
256 let name = token::intern("'r");
257 let _ = write!(f, "{}", name);
258 ty::BrNamed(tcx.map.local_def_id(CRATE_NODE_ID), name)
263 start_or_continue(f, "", "> ")?;
264 write!(f, "{}", new_value)
267 /// This curious type is here to help pretty-print trait objects. In
268 /// a trait object, the projections are stored separately from the
269 /// main trait bound, but in fact we want to package them together
270 /// when printing out; they also have separate binders, but we want
271 /// them to share a binder when we print them out. (And the binder
272 /// pretty-printing logic is kind of clever and we don't want to
273 /// reproduce it.) So we just repackage up the structure somewhat.
275 /// Right now there is only one trait in an object that can have
276 /// projection bounds, so we just stuff them altogether. But in
277 /// reality we should eventually sort things out better.
278 #[derive(Clone, Debug)]
279 struct TraitAndProjections<'tcx>(ty::TraitRef<'tcx>, Vec<ty::ProjectionPredicate<'tcx>>);
281 impl<'tcx> TypeFoldable<'tcx> for TraitAndProjections<'tcx> {
282 fn super_fold_with<F:ty::fold::TypeFolder<'tcx>>(&self, folder: &mut F) -> Self {
283 TraitAndProjections(self.0.fold_with(folder), self.1.fold_with(folder))
286 fn super_visit_with<V: ty::fold::TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool {
287 self.0.visit_with(visitor) || self.1.visit_with(visitor)
291 impl<'tcx> fmt::Display for TraitAndProjections<'tcx> {
292 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
293 let TraitAndProjections(ref trait_ref, ref projection_bounds) = *self;
294 parameterized(f, trait_ref.substs,
298 |tcx| tcx.lookup_trait_def(trait_ref.def_id).generics.clone())
302 impl<'tcx> fmt::Display for ty::TraitTy<'tcx> {
303 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
304 let bounds = &self.bounds;
306 // Generate the main trait ref, including associated types.
307 ty::tls::with(|tcx| {
308 let principal = tcx.lift(&self.principal.0)
309 .expect("could not lift TraitRef for printing");
310 let projections = tcx.lift(&bounds.projection_bounds[..])
311 .expect("could not lift projections for printing");
312 let projections = projections.into_iter().map(|p| p.0).collect();
314 let tap = ty::Binder(TraitAndProjections(principal, projections));
315 in_binder(f, tcx, &ty::Binder(""), Some(tap))
319 for bound in &bounds.builtin_bounds {
320 write!(f, " + {:?}", bound)?;
323 // FIXME: It'd be nice to compute from context when this bound
324 // is implied, but that's non-trivial -- we'd perhaps have to
325 // use thread-local data of some kind? There are also
326 // advantages to just showing the region, since it makes
327 // people aware that it's there.
328 let bound = bounds.region_bound.to_string();
329 if !bound.is_empty() {
330 write!(f, " + {}", bound)?;
337 impl<'tcx> fmt::Debug for ty::TypeParameterDef<'tcx> {
338 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
339 write!(f, "TypeParameterDef({}, {:?}, {:?}/{})",
342 self.space, self.index)
346 impl fmt::Debug for ty::RegionParameterDef {
347 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
348 write!(f, "RegionParameterDef({}, {:?}, {:?}/{}, {:?})",
351 self.space, self.index,
356 impl<'tcx> fmt::Debug for ty::TyS<'tcx> {
357 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
358 write!(f, "{}", *self)
362 impl<'tcx> fmt::Display for ty::TypeAndMut<'tcx> {
363 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
365 if self.mutbl == hir::MutMutable { "mut " } else { "" },
370 impl<'tcx> fmt::Debug for subst::Substs<'tcx> {
371 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
372 write!(f, "Substs[types={:?}, regions={:?}]",
373 self.types, self.regions)
377 impl<'tcx> fmt::Debug for ty::ItemSubsts<'tcx> {
378 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
379 write!(f, "ItemSubsts({:?})", self.substs)
383 impl<'tcx> fmt::Debug for ty::TraitRef<'tcx> {
384 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
385 // when printing out the debug representation, we don't need
386 // to enumerate the `for<...>` etc because the debruijn index
387 // tells you everything you need to know.
388 match self.substs.self_ty() {
389 None => write!(f, "{}", *self),
390 Some(self_ty) => write!(f, "<{:?} as {}>", self_ty, *self)
395 impl<'tcx> fmt::Debug for ty::TraitDef<'tcx> {
396 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
397 write!(f, "TraitDef(generics={:?}, trait_ref={:?})",
398 self.generics, self.trait_ref)
402 impl<'tcx, 'container> fmt::Debug for ty::AdtDefData<'tcx, 'container> {
403 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
404 ty::tls::with(|tcx| {
405 write!(f, "{}", tcx.item_path_str(self.did))
410 impl<'tcx> fmt::Debug for ty::adjustment::AutoAdjustment<'tcx> {
411 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
413 ty::adjustment::AdjustReifyFnPointer => {
414 write!(f, "AdjustReifyFnPointer")
416 ty::adjustment::AdjustUnsafeFnPointer => {
417 write!(f, "AdjustUnsafeFnPointer")
419 ty::adjustment::AdjustMutToConstPointer => {
420 write!(f, "AdjustMutToConstPointer")
422 ty::adjustment::AdjustDerefRef(ref data) => {
423 write!(f, "{:?}", data)
429 impl<'tcx> fmt::Debug for ty::adjustment::AutoDerefRef<'tcx> {
430 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
431 write!(f, "AutoDerefRef({}, unsize={:?}, {:?})",
432 self.autoderefs, self.unsize, self.autoref)
436 impl<'tcx> fmt::Debug for ty::TraitTy<'tcx> {
437 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
438 write!(f, "TraitTy({:?},{:?})",
444 impl<'tcx> fmt::Debug for ty::Predicate<'tcx> {
445 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
447 ty::Predicate::Trait(ref a) => write!(f, "{:?}", a),
448 ty::Predicate::Equate(ref pair) => write!(f, "{:?}", pair),
449 ty::Predicate::RegionOutlives(ref pair) => write!(f, "{:?}", pair),
450 ty::Predicate::TypeOutlives(ref pair) => write!(f, "{:?}", pair),
451 ty::Predicate::Projection(ref pair) => write!(f, "{:?}", pair),
452 ty::Predicate::WellFormed(ty) => write!(f, "WF({:?})", ty),
453 ty::Predicate::ObjectSafe(trait_def_id) => {
454 write!(f, "ObjectSafe({:?})", trait_def_id)
460 impl fmt::Display for ty::BoundRegion {
461 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
463 return write!(f, "{:?}", *self);
467 BrNamed(_, name) => write!(f, "{}", name),
468 BrAnon(_) | BrFresh(_) | BrEnv => Ok(())
473 impl fmt::Debug for ty::BoundRegion {
474 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
476 BrAnon(n) => write!(f, "BrAnon({:?})", n),
477 BrFresh(n) => write!(f, "BrFresh({:?})", n),
478 BrNamed(did, name) => {
479 write!(f, "BrNamed({:?}, {:?})", did, name)
481 BrEnv => "BrEnv".fmt(f),
486 impl fmt::Debug for ty::Region {
487 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
489 ty::ReEarlyBound(ref data) => {
490 write!(f, "ReEarlyBound({:?}, {}, {})",
496 ty::ReLateBound(binder_id, ref bound_region) => {
497 write!(f, "ReLateBound({:?}, {:?})",
502 ty::ReFree(ref fr) => write!(f, "{:?}", fr),
505 write!(f, "ReScope({:?})", id)
508 ty::ReStatic => write!(f, "ReStatic"),
510 ty::ReVar(ref vid) => {
511 write!(f, "{:?}", vid)
514 ty::ReSkolemized(id, ref bound_region) => {
515 write!(f, "ReSkolemized({}, {:?})", id.index, bound_region)
518 ty::ReEmpty => write!(f, "ReEmpty")
523 impl<'tcx> fmt::Debug for ty::ClosureTy<'tcx> {
524 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
525 write!(f, "ClosureTy({},{:?},{})",
532 impl<'tcx> fmt::Debug for ty::ClosureUpvar<'tcx> {
533 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
534 write!(f, "ClosureUpvar({:?},{:?})",
540 impl<'a, 'tcx> fmt::Debug for ty::ParameterEnvironment<'a, 'tcx> {
541 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
542 write!(f, "ParameterEnvironment(\
544 implicit_region_bound={:?}, \
545 caller_bounds={:?})",
547 self.implicit_region_bound,
552 impl<'tcx> fmt::Debug for ty::ObjectLifetimeDefault {
553 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
555 ty::ObjectLifetimeDefault::Ambiguous => write!(f, "Ambiguous"),
556 ty::ObjectLifetimeDefault::BaseDefault => write!(f, "BaseDefault"),
557 ty::ObjectLifetimeDefault::Specific(ref r) => write!(f, "{:?}", r),
562 impl fmt::Display for ty::Region {
563 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
565 return write!(f, "{:?}", *self);
568 // These printouts are concise. They do not contain all the information
569 // the user might want to diagnose an error, but there is basically no way
570 // to fit that into a short string. Hence the recommendation to use
571 // `explain_region()` or `note_and_explain_region()`.
573 ty::ReEarlyBound(ref data) => {
574 write!(f, "{}", data.name)
576 ty::ReLateBound(_, br) |
577 ty::ReFree(ty::FreeRegion { bound_region: br, .. }) |
578 ty::ReSkolemized(_, br) => {
582 ty::ReVar(_) => Ok(()),
583 ty::ReStatic => write!(f, "'static"),
584 ty::ReEmpty => write!(f, "'<empty>"),
589 impl fmt::Debug for ty::FreeRegion {
590 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
591 write!(f, "ReFree({:?}, {:?})",
592 self.scope, self.bound_region)
596 impl fmt::Debug for ty::Variance {
597 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
598 f.write_str(match *self {
599 ty::Covariant => "+",
600 ty::Contravariant => "-",
601 ty::Invariant => "o",
602 ty::Bivariant => "*",
607 impl fmt::Debug for ty::ItemVariances {
608 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
609 write!(f, "ItemVariances(types={:?}, regions={:?})",
610 self.types, self.regions)
614 impl<'tcx> fmt::Debug for ty::GenericPredicates<'tcx> {
615 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
616 write!(f, "GenericPredicates({:?})", self.predicates)
620 impl<'tcx> fmt::Debug for ty::InstantiatedPredicates<'tcx> {
621 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
622 write!(f, "InstantiatedPredicates({:?})",
627 impl<'tcx> fmt::Debug for ty::ImplOrTraitItem<'tcx> {
628 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
629 write!(f, "ImplOrTraitItem(")?;
631 ty::ImplOrTraitItem::MethodTraitItem(ref i) => write!(f, "{:?}", i),
632 ty::ImplOrTraitItem::ConstTraitItem(ref i) => write!(f, "{:?}", i),
633 ty::ImplOrTraitItem::TypeTraitItem(ref i) => write!(f, "{:?}", i),
639 impl<'tcx> fmt::Display for ty::FnSig<'tcx> {
640 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
642 fn_sig(f, &self.inputs, self.variadic, self.output)
646 impl<'tcx> fmt::Debug for ty::ExistentialBounds<'tcx> {
647 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
648 let mut empty = true;
649 let mut maybe_continue = |f: &mut fmt::Formatter| {
658 let region_str = format!("{:?}", self.region_bound);
659 if !region_str.is_empty() {
661 write!(f, "{}", region_str)?;
664 for bound in &self.builtin_bounds {
666 write!(f, "{:?}", bound)?;
669 for projection_bound in &self.projection_bounds {
671 write!(f, "{:?}", projection_bound)?;
678 impl fmt::Display for ty::BuiltinBounds {
679 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
680 let mut bounds = self.iter();
681 if let Some(bound) = bounds.next() {
682 write!(f, "{:?}", bound)?;
683 for bound in bounds {
684 write!(f, " + {:?}", bound)?;
691 impl fmt::Debug for ty::TyVid {
692 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
693 write!(f, "_#{}t", self.index)
697 impl fmt::Debug for ty::IntVid {
698 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
699 write!(f, "_#{}i", self.index)
703 impl fmt::Debug for ty::FloatVid {
704 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
705 write!(f, "_#{}f", self.index)
709 impl fmt::Debug for ty::RegionVid {
710 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
711 write!(f, "'_#{}r", self.index)
715 impl<'tcx> fmt::Debug for ty::FnSig<'tcx> {
716 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
717 write!(f, "({:?}; variadic: {})->{:?}", self.inputs, self.variadic, self.output)
721 impl fmt::Debug for ty::InferTy {
722 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
724 ty::TyVar(ref v) => v.fmt(f),
725 ty::IntVar(ref v) => v.fmt(f),
726 ty::FloatVar(ref v) => v.fmt(f),
727 ty::FreshTy(v) => write!(f, "FreshTy({:?})", v),
728 ty::FreshIntTy(v) => write!(f, "FreshIntTy({:?})", v),
729 ty::FreshFloatTy(v) => write!(f, "FreshFloatTy({:?})", v)
734 impl fmt::Debug for ty::IntVarValue {
735 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
737 ty::IntType(ref v) => v.fmt(f),
738 ty::UintType(ref v) => v.fmt(f),
743 // The generic impl doesn't work yet because projections are not
744 // normalized under HRTB.
745 /*impl<T> fmt::Display for ty::Binder<T>
746 where T: fmt::Display + for<'a> ty::Lift<'a>,
747 for<'a> <T as ty::Lift<'a>>::Lifted: fmt::Display + TypeFoldable<'a>
749 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
750 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
754 impl<'tcx> fmt::Display for ty::Binder<ty::TraitRef<'tcx>> {
755 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
756 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
760 impl<'tcx> fmt::Display for ty::Binder<ty::TraitPredicate<'tcx>> {
761 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
762 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
766 impl<'tcx> fmt::Display for ty::Binder<ty::EquatePredicate<'tcx>> {
767 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
768 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
772 impl<'tcx> fmt::Display for ty::Binder<ty::ProjectionPredicate<'tcx>> {
773 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
774 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
778 impl<'tcx> fmt::Display for ty::Binder<ty::OutlivesPredicate<Ty<'tcx>, ty::Region>> {
779 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
780 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
784 impl fmt::Display for ty::Binder<ty::OutlivesPredicate<ty::Region, ty::Region>> {
785 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
786 ty::tls::with(|tcx| in_binder(f, tcx, self, tcx.lift(self)))
790 impl<'tcx> fmt::Display for ty::TraitRef<'tcx> {
791 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
792 parameterized(f, self.substs, self.def_id, Ns::Type, &[],
793 |tcx| tcx.lookup_trait_def(self.def_id).generics.clone())
797 impl<'tcx> fmt::Display for ty::TypeVariants<'tcx> {
798 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
800 TyBool => write!(f, "bool"),
801 TyChar => write!(f, "char"),
802 TyInt(t) => write!(f, "{}", t.ty_to_string()),
803 TyUint(t) => write!(f, "{}", t.ty_to_string()),
804 TyFloat(t) => write!(f, "{}", t.ty_to_string()),
805 TyBox(typ) => write!(f, "Box<{}>", typ),
806 TyRawPtr(ref tm) => {
807 write!(f, "*{} {}", match tm.mutbl {
808 hir::MutMutable => "mut",
809 hir::MutImmutable => "const",
812 TyRef(r, ref tm) => {
814 let s = r.to_string();
821 TyTuple(ref tys) => {
823 let mut tys = tys.iter();
824 if let Some(&ty) = tys.next() {
825 write!(f, "{},", ty)?;
826 if let Some(&ty) = tys.next() {
827 write!(f, " {}", ty)?;
829 write!(f, ", {}", ty)?;
835 TyFnDef(def_id, substs, ref bare_fn) => {
836 if bare_fn.unsafety == hir::Unsafety::Unsafe {
837 write!(f, "unsafe ")?;
840 if bare_fn.abi != Abi::Rust {
841 write!(f, "extern {} ", bare_fn.abi)?;
844 write!(f, "{} {{", bare_fn.sig.0)?;
845 parameterized(f, substs, def_id, Ns::Value, &[],
846 |tcx| tcx.lookup_item_type(def_id).generics)?;
849 TyFnPtr(ref bare_fn) => {
850 if bare_fn.unsafety == hir::Unsafety::Unsafe {
851 write!(f, "unsafe ")?;
854 if bare_fn.abi != Abi::Rust {
855 write!(f, "extern {} ", bare_fn.abi)?;
858 write!(f, "{}", bare_fn.sig.0)
860 TyInfer(infer_ty) => write!(f, "{}", infer_ty),
861 TyError => write!(f, "[type error]"),
862 TyParam(ref param_ty) => write!(f, "{}", param_ty),
863 TyEnum(def, substs) | TyStruct(def, substs) => {
864 ty::tls::with(|tcx| {
865 if def.did.is_local() &&
866 !tcx.tcache.borrow().contains_key(&def.did) {
867 write!(f, "{}<..>", tcx.item_path_str(def.did))
869 parameterized(f, substs, def.did, Ns::Type, &[],
870 |tcx| tcx.lookup_item_type(def.did).generics)
874 TyTrait(ref data) => write!(f, "{}", data),
875 ty::TyProjection(ref data) => write!(f, "{}", data),
876 TyStr => write!(f, "str"),
877 TyClosure(did, ref substs) => ty::tls::with(|tcx| {
878 write!(f, "[closure")?;
880 if let Some(node_id) = tcx.map.as_local_node_id(did) {
881 write!(f, "@{:?}", tcx.map.span(node_id))?;
883 tcx.with_freevars(node_id, |freevars| {
884 for (freevar, upvar_ty) in freevars.iter().zip(&substs.upvar_tys) {
885 let node_id = freevar.def.var_id();
889 tcx.local_var_name_str(node_id),
896 // cross-crate closure types should only be
897 // visible in trans bug reports, I imagine.
898 write!(f, "@{:?}", did)?;
900 for (index, upvar_ty) in substs.upvar_tys.iter().enumerate() {
901 write!(f, "{}{}:{}", sep, index, upvar_ty)?;
908 TyArray(ty, sz) => write!(f, "[{}; {}]", ty, sz),
909 TySlice(ty) => write!(f, "[{}]", ty)
914 impl<'tcx> fmt::Display for ty::TyS<'tcx> {
915 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
916 write!(f, "{}", self.sty)
920 impl fmt::Debug for ty::UpvarId {
921 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
922 write!(f, "UpvarId({};`{}`;{})",
924 ty::tls::with(|tcx| tcx.local_var_name_str(self.var_id)),
925 self.closure_expr_id)
929 impl fmt::Debug for ty::UpvarBorrow {
930 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
931 write!(f, "UpvarBorrow({:?}, {:?})",
932 self.kind, self.region)
936 impl fmt::Display for ty::InferTy {
937 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
938 let print_var_ids = verbose();
940 ty::TyVar(ref vid) if print_var_ids => write!(f, "{:?}", vid),
941 ty::IntVar(ref vid) if print_var_ids => write!(f, "{:?}", vid),
942 ty::FloatVar(ref vid) if print_var_ids => write!(f, "{:?}", vid),
943 ty::TyVar(_) | ty::IntVar(_) | ty::FloatVar(_) => write!(f, "_"),
944 ty::FreshTy(v) => write!(f, "FreshTy({})", v),
945 ty::FreshIntTy(v) => write!(f, "FreshIntTy({})", v),
946 ty::FreshFloatTy(v) => write!(f, "FreshFloatTy({})", v)
951 impl fmt::Display for ty::ExplicitSelfCategory {
952 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
953 f.write_str(match *self {
954 ty::ExplicitSelfCategory::Static => "static",
955 ty::ExplicitSelfCategory::ByValue => "self",
956 ty::ExplicitSelfCategory::ByReference(_, hir::MutMutable) => {
959 ty::ExplicitSelfCategory::ByReference(_, hir::MutImmutable) => "&self",
960 ty::ExplicitSelfCategory::ByBox => "Box<self>",
965 impl fmt::Display for ty::ParamTy {
966 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
967 write!(f, "{}", self.name)
971 impl fmt::Debug for ty::ParamTy {
972 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
973 write!(f, "{}/{:?}.{}", self, self.space, self.idx)
977 impl<'tcx, T, U> fmt::Display for ty::OutlivesPredicate<T,U>
978 where T: fmt::Display, U: fmt::Display
980 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
981 write!(f, "{} : {}", self.0, self.1)
985 impl<'tcx> fmt::Display for ty::EquatePredicate<'tcx> {
986 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
987 write!(f, "{} == {}", self.0, self.1)
991 impl<'tcx> fmt::Debug for ty::TraitPredicate<'tcx> {
992 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
993 write!(f, "TraitPredicate({:?})",
998 impl<'tcx> fmt::Display for ty::TraitPredicate<'tcx> {
999 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1000 write!(f, "{} : {}",
1001 self.trait_ref.self_ty(),
1006 impl<'tcx> fmt::Debug for ty::ProjectionPredicate<'tcx> {
1007 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1008 write!(f, "ProjectionPredicate({:?}, {:?})",
1014 impl<'tcx> fmt::Display for ty::ProjectionPredicate<'tcx> {
1015 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1016 write!(f, "{} == {}",
1022 impl<'tcx> fmt::Display for ty::ProjectionTy<'tcx> {
1023 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1024 write!(f, "{:?}::{}",
1030 impl<'tcx> fmt::Display for ty::Predicate<'tcx> {
1031 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1033 ty::Predicate::Trait(ref data) => write!(f, "{}", data),
1034 ty::Predicate::Equate(ref predicate) => write!(f, "{}", predicate),
1035 ty::Predicate::RegionOutlives(ref predicate) => write!(f, "{}", predicate),
1036 ty::Predicate::TypeOutlives(ref predicate) => write!(f, "{}", predicate),
1037 ty::Predicate::Projection(ref predicate) => write!(f, "{}", predicate),
1038 ty::Predicate::WellFormed(ty) => write!(f, "{} well-formed", ty),
1039 ty::Predicate::ObjectSafe(trait_def_id) =>
1040 ty::tls::with(|tcx| {
1041 write!(f, "the trait `{}` is object-safe", tcx.item_path_str(trait_def_id))