about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2019-06-20 15:11:08 +0000
committerbors <bors@rust-lang.org>2019-06-20 15:11:08 +0000
commitf0c2bdf52e0c8bce258f1bbb5652c9691b7f3193 (patch)
treeb3749284593cdf105aa814ac103a9036ce10f901 /src
parentc1a5edd939bb3303d4ff1a4380a7a7378244938d (diff)
parent3606003a5bf808c399cc9bae2e825dba4040f193 (diff)
downloadrust-f0c2bdf52e0c8bce258f1bbb5652c9691b7f3193.tar.gz
rust-f0c2bdf52e0c8bce258f1bbb5652c9691b7f3193.zip
Auto merge of #61998 - eddyb:type-name-params, r=oli-obk
rustc_mir: support type parameters by printing them as `_`.

Fixes #61894.
r? @oli-obk
Diffstat (limited to 'src')
-rw-r--r--src/librustc_mir/interpret/intrinsics/type_name.rs47
-rw-r--r--src/test/run-pass/issues/issue-61894.rs19
2 files changed, 45 insertions, 21 deletions
diff --git a/src/librustc_mir/interpret/intrinsics/type_name.rs b/src/librustc_mir/interpret/intrinsics/type_name.rs
index 5ca3531c98b..f207cfc6b39 100644
--- a/src/librustc_mir/interpret/intrinsics/type_name.rs
+++ b/src/librustc_mir/interpret/intrinsics/type_name.rs
@@ -31,9 +31,9 @@ impl<'tcx> Printer<'tcx> for AbsolutePathPrinter<'tcx> {
         Ok(self)
     }
 
-    fn print_type(self, ty: Ty<'tcx>) -> Result<Self::Type, Self::Error> {
+    fn print_type(mut self, ty: Ty<'tcx>) -> Result<Self::Type, Self::Error> {
         match ty.sty {
-            // types without identity
+            // Types without identity.
             | ty::Bool
             | ty::Char
             | ty::Int(_)
@@ -48,28 +48,33 @@ impl<'tcx> Printer<'tcx> for AbsolutePathPrinter<'tcx> {
             | ty::Never
             | ty::Tuple(_)
             | ty::Dynamic(_, _)
-            | ty::Adt(..)
-            | ty::Foreign(_)
-            // should be unreachable, but there's no hurt in printing it (and better than ICEing)
-            | ty::Error
             => self.pretty_print_type(ty),
-            | ty::Infer(_)
-            | ty::Bound(_, _)
+
+            // Placeholders (all printed as `_` to uniformize them).
             | ty::Param(_)
+            | ty::Bound(..)
             | ty::Placeholder(_)
-            | ty::Projection(_)
-            | ty::UnnormalizedProjection(_)
-            | ty::GeneratorWitness(_)
-            => bug!(
-                "{:#?} in `type_name` should not happen because we are always monomorphized",
-                ty,
-            ),
-            // types with identity (print the module path instead)
-            | ty::FnDef(did, substs)
-            | ty::Opaque(did, substs)
-            => self.print_def_path(did, substs),
-            ty::Closure(did, substs) => self.print_def_path(did, substs.substs),
-            ty::Generator(did, substs, _) => self.print_def_path(did, substs.substs),
+            | ty::Infer(_)
+            | ty::Error
+            => {
+                write!(self, "_")?;
+                Ok(self)
+            }
+
+            // Types with identity (print the module path).
+            | ty::Adt(&ty::AdtDef { did: def_id, .. }, substs)
+            | ty::FnDef(def_id, substs)
+            | ty::Opaque(def_id, substs)
+            | ty::Projection(ty::ProjectionTy { item_def_id: def_id, substs })
+            | ty::UnnormalizedProjection(ty::ProjectionTy { item_def_id: def_id, substs })
+            | ty::Closure(def_id, ty::ClosureSubsts { substs })
+            | ty::Generator(def_id, ty::GeneratorSubsts { substs }, _)
+            => self.print_def_path(def_id, substs),
+            ty::Foreign(def_id) => self.print_def_path(def_id, &[]),
+
+            ty::GeneratorWitness(_) => {
+                bug!("type_name: unexpected `GeneratorWitness`")
+            }
         }
     }
 
diff --git a/src/test/run-pass/issues/issue-61894.rs b/src/test/run-pass/issues/issue-61894.rs
new file mode 100644
index 00000000000..9ab969be46a
--- /dev/null
+++ b/src/test/run-pass/issues/issue-61894.rs
@@ -0,0 +1,19 @@
+#![feature(core_intrinsics)]
+
+use std::intrinsics::type_name;
+
+struct Bar<M>(M);
+
+impl<M> Bar<M> {
+    fn foo(&self) -> &'static str {
+        fn f() {}
+        fn type_name_of<T>(_: T) -> &'static str {
+            unsafe { type_name::<T>() }
+        }
+        type_name_of(f)
+    }
+}
+
+fn main() {
+    assert_eq!(Bar(()).foo(), "issue_61894::Bar<_>::foo::f");
+}