about summary refs log tree commit diff
diff options
context:
space:
mode:
authorGuillaume Gomez <guillaume1.gomez@gmail.com>2020-01-04 13:17:29 +0100
committerGitHub <noreply@github.com>2020-01-04 13:17:29 +0100
commit1140ceebccdf9ab00bce927dd71dbe5957486ef2 (patch)
treeb66e79853f903fa8d5845f556c7e9d46e1361be2
parenta469b1785d7ff414abe718cf013440ca0ead7e42 (diff)
parente9990bc65f8e44fd2843478ac685bb79c0a50ed0 (diff)
downloadrust-1140ceebccdf9ab00bce927dd71dbe5957486ef2.tar.gz
rust-1140ceebccdf9ab00bce927dd71dbe5957486ef2.zip
Rollup merge of #67823 - euclio:drop-improvements, r=petrochenkov
improve some `Drop`-related error messages
-rw-r--r--src/librustc_typeck/check/dropck.rs34
-rw-r--r--src/librustc_typeck/coherence/builtin.rs47
-rw-r--r--src/test/ui/dropck/drop-on-non-struct.rs7
-rw-r--r--src/test/ui/dropck/drop-on-non-struct.stderr14
-rw-r--r--src/test/ui/error-codes/E0117.rs3
-rw-r--r--src/test/ui/error-codes/E0117.stderr4
-rw-r--r--src/test/ui/error-codes/E0120.stderr4
-rw-r--r--src/test/ui/issues/issue-17959.rs2
-rw-r--r--src/test/ui/issues/issue-17959.stderr16
-rw-r--r--src/test/ui/issues/issue-38868.stderr4
-rw-r--r--src/test/ui/issues/issue-41974.stderr4
-rw-r--r--src/test/ui/reject-specialized-drops-8142.rs27
-rw-r--r--src/test/ui/reject-specialized-drops-8142.stderr96
13 files changed, 151 insertions, 111 deletions
diff --git a/src/librustc_typeck/check/dropck.rs b/src/librustc_typeck/check/dropck.rs
index 6f2d529bc34..004fce7e35b 100644
--- a/src/librustc_typeck/check/dropck.rs
+++ b/src/librustc_typeck/check/dropck.rs
@@ -47,7 +47,6 @@ pub fn check_drop_impl(tcx: TyCtxt<'_>, drop_impl_did: DefId) -> Result<(), Erro
 
             ensure_drop_predicates_are_implied_by_item_defn(
                 tcx,
-                drop_impl_did,
                 dtor_predicates,
                 adt_def.did,
                 self_to_impl_substs,
@@ -95,16 +94,23 @@ fn ensure_drop_params_and_item_params_correspond<'tcx>(
             }
             Err(_) => {
                 let item_span = tcx.def_span(self_type_did);
+                let self_descr = tcx
+                    .def_kind(self_type_did)
+                    .map(|kind| kind.descr(self_type_did))
+                    .unwrap_or("type");
                 struct_span_err!(
                     tcx.sess,
                     drop_impl_span,
                     E0366,
-                    "Implementations of Drop cannot be specialized"
+                    "`Drop` impls cannot be specialized"
                 )
                 .span_note(
                     item_span,
-                    "Use same sequence of generic type and region \
-                     parameters that is on the struct/enum definition",
+                    &format!(
+                        "use the same sequence of generic type, lifetime and const parameters \
+                        as the {} definition",
+                        self_descr,
+                    ),
                 )
                 .emit();
                 return Err(ErrorReported);
@@ -143,7 +149,6 @@ fn ensure_drop_params_and_item_params_correspond<'tcx>(
 /// implied by assuming the predicates attached to self_type_did.
 fn ensure_drop_predicates_are_implied_by_item_defn<'tcx>(
     tcx: TyCtxt<'tcx>,
-    drop_impl_did: DefId,
     dtor_predicates: ty::GenericPredicates<'tcx>,
     self_type_did: DefId,
     self_to_impl_substs: SubstsRef<'tcx>,
@@ -187,8 +192,6 @@ fn ensure_drop_predicates_are_implied_by_item_defn<'tcx>(
 
     let self_type_hir_id = tcx.hir().as_local_hir_id(self_type_did).unwrap();
 
-    let drop_impl_span = tcx.def_span(drop_impl_did);
-
     // We can assume the predicates attached to struct/enum definition
     // hold.
     let generic_assumptions = tcx.predicates_of(self_type_did);
@@ -205,7 +208,7 @@ fn ensure_drop_predicates_are_implied_by_item_defn<'tcx>(
     // just to look for all the predicates directly.
 
     assert_eq!(dtor_predicates.parent, None);
-    for (predicate, _) in dtor_predicates.predicates {
+    for (predicate, predicate_sp) in dtor_predicates.predicates {
         // (We do not need to worry about deep analysis of type
         // expressions etc because the Drop impls are already forced
         // to take on a structure that is roughly an alpha-renaming of
@@ -241,18 +244,17 @@ fn ensure_drop_predicates_are_implied_by_item_defn<'tcx>(
 
         if !assumptions_in_impl_context.iter().any(predicate_matches_closure) {
             let item_span = tcx.hir().span(self_type_hir_id);
+            let self_descr =
+                tcx.def_kind(self_type_did).map(|kind| kind.descr(self_type_did)).unwrap_or("type");
             struct_span_err!(
                 tcx.sess,
-                drop_impl_span,
+                *predicate_sp,
                 E0367,
-                "The requirement `{}` is added only by the Drop impl.",
-                predicate
-            )
-            .span_note(
-                item_span,
-                "The same requirement must be part of \
-                 the struct/enum definition",
+                "`Drop` impl requires `{}` but the {} it is implemented for does not",
+                predicate,
+                self_descr,
             )
+            .span_note(item_span, "the implementor must specify the same requirement")
             .emit();
             result = Err(ErrorReported);
         }
diff --git a/src/librustc_typeck/coherence/builtin.rs b/src/librustc_typeck/coherence/builtin.rs
index 7f7e21838d2..7e016cf7e9a 100644
--- a/src/librustc_typeck/coherence/builtin.rs
+++ b/src/librustc_typeck/coherence/builtin.rs
@@ -13,7 +13,6 @@ use rustc::ty::util::CopyImplementationError;
 use rustc::ty::TypeFoldable;
 use rustc::ty::{self, Ty, TyCtxt};
 
-use hir::Node;
 use rustc::hir::def_id::DefId;
 use rustc::hir::{self, ItemKind};
 
@@ -51,35 +50,25 @@ impl<'tcx> Checker<'tcx> {
 }
 
 fn visit_implementation_of_drop(tcx: TyCtxt<'_>, impl_did: DefId) {
-    if let ty::Adt(..) = tcx.type_of(impl_did).kind {
-        /* do nothing */
-    } else {
-        // Destructors only work on nominal types.
-        if let Some(impl_hir_id) = tcx.hir().as_local_hir_id(impl_did) {
-            if let Some(Node::Item(item)) = tcx.hir().find(impl_hir_id) {
-                let span = match item.kind {
-                    ItemKind::Impl(.., ref ty, _) => ty.span,
-                    _ => item.span,
-                };
-                struct_span_err!(
-                    tcx.sess,
-                    span,
-                    E0120,
-                    "the Drop trait may only be implemented on \
-                                  structures"
-                )
-                .span_label(span, "implementing Drop requires a struct")
-                .emit();
-            } else {
-                bug!("didn't find impl in ast map");
-            }
-        } else {
-            bug!(
-                "found external impl of Drop trait on \
-                  something other than a struct"
-            );
-        }
+    // Destructors only work on nominal types.
+    if let ty::Adt(..) | ty::Error = tcx.type_of(impl_did).kind {
+        return;
     }
+
+    let impl_hir_id = tcx.hir().as_local_hir_id(impl_did).expect("foreign Drop impl on non-ADT");
+    let sp = match tcx.hir().expect_item(impl_hir_id).kind {
+        ItemKind::Impl(.., ty, _) => ty.span,
+        _ => bug!("expected Drop impl item"),
+    };
+
+    struct_span_err!(
+        tcx.sess,
+        sp,
+        E0120,
+        "the `Drop` trait may only be implemented for structs, enums, and unions",
+    )
+    .span_label(sp, "must be a struct, enum, or union")
+    .emit();
 }
 
 fn visit_implementation_of_copy(tcx: TyCtxt<'_>, impl_did: DefId) {
diff --git a/src/test/ui/dropck/drop-on-non-struct.rs b/src/test/ui/dropck/drop-on-non-struct.rs
index 259cdf40ae5..ef5e18126dc 100644
--- a/src/test/ui/dropck/drop-on-non-struct.rs
+++ b/src/test/ui/dropck/drop-on-non-struct.rs
@@ -1,10 +1,15 @@
 impl<'a> Drop for &'a mut isize {
-    //~^ ERROR the Drop trait may only be implemented on structures
+    //~^ ERROR the `Drop` trait may only be implemented for structs, enums, and unions
     //~^^ ERROR E0117
     fn drop(&mut self) {
         println!("kaboom");
     }
 }
 
+impl Drop for Nonexistent {
+    //~^ ERROR cannot find type `Nonexistent`
+    fn drop(&mut self) { }
+}
+
 fn main() {
 }
diff --git a/src/test/ui/dropck/drop-on-non-struct.stderr b/src/test/ui/dropck/drop-on-non-struct.stderr
index a374b0d2636..3991c44f2ed 100644
--- a/src/test/ui/dropck/drop-on-non-struct.stderr
+++ b/src/test/ui/dropck/drop-on-non-struct.stderr
@@ -1,8 +1,14 @@
-error[E0120]: the Drop trait may only be implemented on structures
+error[E0412]: cannot find type `Nonexistent` in this scope
+  --> $DIR/drop-on-non-struct.rs:9:15
+   |
+LL | impl Drop for Nonexistent {
+   |               ^^^^^^^^^^^ not found in this scope
+
+error[E0120]: the `Drop` trait may only be implemented for structs, enums, and unions
   --> $DIR/drop-on-non-struct.rs:1:19
    |
 LL | impl<'a> Drop for &'a mut isize {
-   |                   ^^^^^^^^^^^^^ implementing Drop requires a struct
+   |                   ^^^^^^^^^^^^^ must be a struct, enum, or union
 
 error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
   --> $DIR/drop-on-non-struct.rs:1:1
@@ -15,7 +21,7 @@ LL | impl<'a> Drop for &'a mut isize {
    |
    = note: define and implement a trait or new type instead
 
-error: aborting due to 2 previous errors
+error: aborting due to 3 previous errors
 
-Some errors have detailed explanations: E0117, E0120.
+Some errors have detailed explanations: E0117, E0120, E0412.
 For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/error-codes/E0117.rs b/src/test/ui/error-codes/E0117.rs
index 18dd809f3ff..dbbac514801 100644
--- a/src/test/ui/error-codes/E0117.rs
+++ b/src/test/ui/error-codes/E0117.rs
@@ -1,6 +1,5 @@
 impl Drop for u32 {} //~ ERROR E0117
-//~| ERROR the Drop trait may only be implemented on structures
-//~| implementing Drop requires a struct
+//~| ERROR the `Drop` trait may only be implemented for structs, enums, and unions
 
 fn main() {
 }
diff --git a/src/test/ui/error-codes/E0117.stderr b/src/test/ui/error-codes/E0117.stderr
index f0cfc8a2533..b48a1d8e50d 100644
--- a/src/test/ui/error-codes/E0117.stderr
+++ b/src/test/ui/error-codes/E0117.stderr
@@ -1,8 +1,8 @@
-error[E0120]: the Drop trait may only be implemented on structures
+error[E0120]: the `Drop` trait may only be implemented for structs, enums, and unions
   --> $DIR/E0117.rs:1:15
    |
 LL | impl Drop for u32 {}
-   |               ^^^ implementing Drop requires a struct
+   |               ^^^ must be a struct, enum, or union
 
 error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
   --> $DIR/E0117.rs:1:1
diff --git a/src/test/ui/error-codes/E0120.stderr b/src/test/ui/error-codes/E0120.stderr
index 68ca7d800d5..6c306455e42 100644
--- a/src/test/ui/error-codes/E0120.stderr
+++ b/src/test/ui/error-codes/E0120.stderr
@@ -1,8 +1,8 @@
-error[E0120]: the Drop trait may only be implemented on structures
+error[E0120]: the `Drop` trait may only be implemented for structs, enums, and unions
   --> $DIR/E0120.rs:3:15
    |
 LL | impl Drop for dyn MyTrait {
-   |               ^^^^^^^^^^^ implementing Drop requires a struct
+   |               ^^^^^^^^^^^ must be a struct, enum, or union
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/issues/issue-17959.rs b/src/test/ui/issues/issue-17959.rs
index 73865ae2d2e..01416a0d79e 100644
--- a/src/test/ui/issues/issue-17959.rs
+++ b/src/test/ui/issues/issue-17959.rs
@@ -9,7 +9,7 @@ struct G<T: ?Sized> {
 }
 
 impl<T> Drop for G<T> {
-//~^ ERROR: The requirement `T: std::marker::Sized` is added only by the Drop impl. [E0367]
+//~^ ERROR `Drop` impl requires `T: std::marker::Sized`
     fn drop(&mut self) {
         if !self._ptr.is_null() {
         }
diff --git a/src/test/ui/issues/issue-17959.stderr b/src/test/ui/issues/issue-17959.stderr
index de742e48aea..29d32c1f3ce 100644
--- a/src/test/ui/issues/issue-17959.stderr
+++ b/src/test/ui/issues/issue-17959.stderr
@@ -1,16 +1,10 @@
-error[E0367]: The requirement `T: std::marker::Sized` is added only by the Drop impl.
-  --> $DIR/issue-17959.rs:11:1
+error[E0367]: `Drop` impl requires `T: std::marker::Sized` but the struct it is implemented for does not
+  --> $DIR/issue-17959.rs:11:6
    |
-LL | / impl<T> Drop for G<T> {
-LL | |
-LL | |     fn drop(&mut self) {
-LL | |         if !self._ptr.is_null() {
-LL | |         }
-LL | |     }
-LL | | }
-   | |_^
+LL | impl<T> Drop for G<T> {
+   |      ^
    |
-note: The same requirement must be part of the struct/enum definition
+note: the implementor must specify the same requirement
   --> $DIR/issue-17959.rs:7:1
    |
 LL | / struct G<T: ?Sized> {
diff --git a/src/test/ui/issues/issue-38868.stderr b/src/test/ui/issues/issue-38868.stderr
index fe932c744bf..10d1e7c4e66 100644
--- a/src/test/ui/issues/issue-38868.stderr
+++ b/src/test/ui/issues/issue-38868.stderr
@@ -1,4 +1,4 @@
-error[E0366]: Implementations of Drop cannot be specialized
+error[E0366]: `Drop` impls cannot be specialized
   --> $DIR/issue-38868.rs:5:1
    |
 LL | / impl Drop for List<i32> {
@@ -8,7 +8,7 @@ LL | |     }
 LL | | }
    | |_^
    |
-note: Use same sequence of generic type and region parameters that is on the struct/enum definition
+note: use the same sequence of generic type, lifetime and const parameters as the struct definition
   --> $DIR/issue-38868.rs:1:1
    |
 LL | / pub struct List<T> {
diff --git a/src/test/ui/issues/issue-41974.stderr b/src/test/ui/issues/issue-41974.stderr
index 9f164822dea..d082e0a6b5d 100644
--- a/src/test/ui/issues/issue-41974.stderr
+++ b/src/test/ui/issues/issue-41974.stderr
@@ -9,11 +9,11 @@ LL | impl<T> Drop for T where T: A {
              where T: ?Sized;
    = note: downstream crates may implement trait `A` for type `std::boxed::Box<_>`
 
-error[E0120]: the Drop trait may only be implemented on structures
+error[E0120]: the `Drop` trait may only be implemented for structs, enums, and unions
   --> $DIR/issue-41974.rs:7:18
    |
 LL | impl<T> Drop for T where T: A {
-   |                  ^ implementing Drop requires a struct
+   |                  ^ must be a struct, enum, or union
 
 error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
   --> $DIR/issue-41974.rs:7:6
diff --git a/src/test/ui/reject-specialized-drops-8142.rs b/src/test/ui/reject-specialized-drops-8142.rs
index 655b42f5f8f..d7fec8802f0 100644
--- a/src/test/ui/reject-specialized-drops-8142.rs
+++ b/src/test/ui/reject-specialized-drops-8142.rs
@@ -1,5 +1,5 @@
 // Issue 8142: Test that Drop impls cannot be specialized beyond the
-// predicates attached to the struct/enum definition itself.
+// predicates attached to the type definition itself.
 
 trait Bound { fn foo(&self) { } }
 struct K<'l1,'l2> { x: &'l1 i8, y: &'l2 u8 }
@@ -16,12 +16,16 @@ struct U;
 struct V<Tva, Tvb> { x: *const Tva, y: *const Tvb }
 struct W<'l1, 'l2> { x: &'l1 i8, y: &'l2 u8 }
 
+enum Enum<T> { Variant(T) }
+struct TupleStruct<T>(T);
+union Union<T: Copy> { f: T }
+
 impl<'al,'adds_bnd:'al> Drop for K<'al,'adds_bnd> {                        // REJECT
-    //~^ ERROR The requirement `'adds_bnd : 'al` is added only by the Drop impl.
+    //~^ ERROR `Drop` impl requires `'adds_bnd : 'al`
     fn drop(&mut self) { } }
 
 impl<'al,'adds_bnd>     Drop for L<'al,'adds_bnd> where 'adds_bnd:'al {    // REJECT
-    //~^ ERROR The requirement `'adds_bnd : 'al` is added only by the Drop impl.
+    //~^ ERROR `Drop` impl requires `'adds_bnd : 'al`
     fn drop(&mut self) { } }
 
 impl<'ml>               Drop for M<'ml>         { fn drop(&mut self) { } } // ACCEPT
@@ -34,13 +38,13 @@ impl                    Drop for N<'static>     { fn drop(&mut self) { } } // RE
 impl<COkNoBound> Drop for O<COkNoBound> { fn drop(&mut self) { } } // ACCEPT
 
 impl              Drop for P<i8>          { fn drop(&mut self) { } } // REJECT
-//~^ ERROR Implementations of Drop cannot be specialized
+//~^ ERROR `Drop` impls cannot be specialized
 
 impl<AddsBnd:Bound> Drop for Q<AddsBnd> { fn drop(&mut self) { } } // REJECT
-//~^ ERROR The requirement `AddsBnd: Bound` is added only by the Drop impl.
+//~^ ERROR `Drop` impl requires `AddsBnd: Bound`
 
 impl<'rbnd,AddsRBnd:'rbnd> Drop for R<AddsRBnd> { fn drop(&mut self) { } } // REJECT
-//~^ ERROR The requirement `AddsRBnd : 'rbnd` is added only by the Drop impl.
+//~^ ERROR `Drop` impl requires `AddsRBnd : 'rbnd`
 
 impl<Bs:Bound>    Drop for S<Bs>          { fn drop(&mut self) { } } // ACCEPT
 
@@ -49,9 +53,18 @@ impl<'t,Bt:'t>    Drop for T<'t,Bt>       { fn drop(&mut self) { } } // ACCEPT
 impl              Drop for U              { fn drop(&mut self) { } } // ACCEPT
 
 impl<One>         Drop for V<One,One>     { fn drop(&mut self) { } } // REJECT
-//~^ ERROR Implementations of Drop cannot be specialized
+//~^ ERROR `Drop` impls cannot be specialized
 
 impl<'lw>         Drop for W<'lw,'lw>     { fn drop(&mut self) { } } // REJECT
 //~^ ERROR cannot infer an appropriate lifetime for lifetime parameter `'lw`
 
+impl<AddsBnd:Bound> Drop for Enum<AddsBnd> { fn drop(&mut self) { } } // REJECT
+//~^ ERROR `Drop` impl requires `AddsBnd: Bound`
+
+impl<AddsBnd:Bound> Drop for TupleStruct<AddsBnd> { fn drop(&mut self) { } } // REJECT
+//~^ ERROR `Drop` impl requires `AddsBnd: Bound`
+
+impl<AddsBnd:Copy + Bound> Drop for Union<AddsBnd> { fn drop(&mut self) { } } // REJECT
+//~^ ERROR `Drop` impl requires `AddsBnd: Bound`
+
 pub fn main() { }
diff --git a/src/test/ui/reject-specialized-drops-8142.stderr b/src/test/ui/reject-specialized-drops-8142.stderr
index 527babb0120..14618df90cb 100644
--- a/src/test/ui/reject-specialized-drops-8142.stderr
+++ b/src/test/ui/reject-specialized-drops-8142.stderr
@@ -1,33 +1,41 @@
-error[E0367]: The requirement `'adds_bnd : 'al` is added only by the Drop impl.
-  --> $DIR/reject-specialized-drops-8142.rs:19:1
+error[E0367]: `Drop` impl requires `AddsBnd: Bound` but the union it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:67:21
+   |
+LL | impl<AddsBnd:Copy + Bound> Drop for Union<AddsBnd> { fn drop(&mut self) { } } // REJECT
+   |                     ^^^^^
+   |
+note: the implementor must specify the same requirement
+  --> $DIR/reject-specialized-drops-8142.rs:21:1
+   |
+LL | union Union<T: Copy> { f: T }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error[E0367]: `Drop` impl requires `'adds_bnd : 'al` but the struct it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:23:20
    |
-LL | / impl<'al,'adds_bnd:'al> Drop for K<'al,'adds_bnd> {                        // REJECT
-LL | |
-LL | |     fn drop(&mut self) { } }
-   | |____________________________^
+LL | impl<'al,'adds_bnd:'al> Drop for K<'al,'adds_bnd> {                        // REJECT
+   |                    ^^^
    |
-note: The same requirement must be part of the struct/enum definition
+note: the implementor must specify the same requirement
   --> $DIR/reject-specialized-drops-8142.rs:5:1
    |
 LL | struct K<'l1,'l2> { x: &'l1 i8, y: &'l2 u8 }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error[E0367]: The requirement `'adds_bnd : 'al` is added only by the Drop impl.
-  --> $DIR/reject-specialized-drops-8142.rs:23:1
+error[E0367]: `Drop` impl requires `'adds_bnd : 'al` but the struct it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:27:67
    |
-LL | / impl<'al,'adds_bnd>     Drop for L<'al,'adds_bnd> where 'adds_bnd:'al {    // REJECT
-LL | |
-LL | |     fn drop(&mut self) { } }
-   | |____________________________^
+LL | impl<'al,'adds_bnd>     Drop for L<'al,'adds_bnd> where 'adds_bnd:'al {    // REJECT
+   |                                                                   ^^^
    |
-note: The same requirement must be part of the struct/enum definition
+note: the implementor must specify the same requirement
   --> $DIR/reject-specialized-drops-8142.rs:6:1
    |
 LL | struct L<'l1,'l2> { x: &'l1 i8, y: &'l2 u8 }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0308]: mismatched types
-  --> $DIR/reject-specialized-drops-8142.rs:29:1
+  --> $DIR/reject-specialized-drops-8142.rs:33:1
    |
 LL | impl                    Drop for N<'static>     { fn drop(&mut self) { } } // REJECT
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ lifetime mismatch
@@ -41,56 +49,56 @@ LL | struct N<'n> { x: &'n i8 }
    |          ^^
    = note: ...does not necessarily outlive the static lifetime
 
-error[E0366]: Implementations of Drop cannot be specialized
-  --> $DIR/reject-specialized-drops-8142.rs:36:1
+error[E0366]: `Drop` impls cannot be specialized
+  --> $DIR/reject-specialized-drops-8142.rs:40:1
    |
 LL | impl              Drop for P<i8>          { fn drop(&mut self) { } } // REJECT
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
-note: Use same sequence of generic type and region parameters that is on the struct/enum definition
+note: use the same sequence of generic type, lifetime and const parameters as the struct definition
   --> $DIR/reject-specialized-drops-8142.rs:10:1
    |
 LL | struct P<Tp> { x: *const Tp }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error[E0367]: The requirement `AddsBnd: Bound` is added only by the Drop impl.
-  --> $DIR/reject-specialized-drops-8142.rs:39:1
+error[E0367]: `Drop` impl requires `AddsBnd: Bound` but the struct it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:43:14
    |
 LL | impl<AddsBnd:Bound> Drop for Q<AddsBnd> { fn drop(&mut self) { } } // REJECT
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |              ^^^^^
    |
-note: The same requirement must be part of the struct/enum definition
+note: the implementor must specify the same requirement
   --> $DIR/reject-specialized-drops-8142.rs:11:1
    |
 LL | struct Q<Tq> { x: *const Tq }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error[E0367]: The requirement `AddsRBnd : 'rbnd` is added only by the Drop impl.
-  --> $DIR/reject-specialized-drops-8142.rs:42:1
+error[E0367]: `Drop` impl requires `AddsRBnd : 'rbnd` but the struct it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:46:21
    |
 LL | impl<'rbnd,AddsRBnd:'rbnd> Drop for R<AddsRBnd> { fn drop(&mut self) { } } // REJECT
-   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   |                     ^^^^^
    |
-note: The same requirement must be part of the struct/enum definition
+note: the implementor must specify the same requirement
   --> $DIR/reject-specialized-drops-8142.rs:12:1
    |
 LL | struct R<Tr> { x: *const Tr }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error[E0366]: Implementations of Drop cannot be specialized
-  --> $DIR/reject-specialized-drops-8142.rs:51:1
+error[E0366]: `Drop` impls cannot be specialized
+  --> $DIR/reject-specialized-drops-8142.rs:55:1
    |
 LL | impl<One>         Drop for V<One,One>     { fn drop(&mut self) { } } // REJECT
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
-note: Use same sequence of generic type and region parameters that is on the struct/enum definition
+note: use the same sequence of generic type, lifetime and const parameters as the struct definition
   --> $DIR/reject-specialized-drops-8142.rs:16:1
    |
 LL | struct V<Tva, Tvb> { x: *const Tva, y: *const Tvb }
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error[E0495]: cannot infer an appropriate lifetime for lifetime parameter `'lw` due to conflicting requirements
-  --> $DIR/reject-specialized-drops-8142.rs:54:1
+  --> $DIR/reject-specialized-drops-8142.rs:58:1
    |
 LL | impl<'lw>         Drop for W<'lw,'lw>     { fn drop(&mut self) { } } // REJECT
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -106,14 +114,38 @@ note: ...but the lifetime must also be valid for the lifetime `'l2` as defined o
 LL | struct W<'l1, 'l2> { x: &'l1 i8, y: &'l2 u8 }
    |               ^^^
 note: ...so that the types are compatible
-  --> $DIR/reject-specialized-drops-8142.rs:54:1
+  --> $DIR/reject-specialized-drops-8142.rs:58:1
    |
 LL | impl<'lw>         Drop for W<'lw,'lw>     { fn drop(&mut self) { } } // REJECT
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    = note: expected  `W<'l1, 'l2>`
               found  `W<'_, '_>`
 
-error: aborting due to 8 previous errors
+error[E0367]: `Drop` impl requires `AddsBnd: Bound` but the enum it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:61:14
+   |
+LL | impl<AddsBnd:Bound> Drop for Enum<AddsBnd> { fn drop(&mut self) { } } // REJECT
+   |              ^^^^^
+   |
+note: the implementor must specify the same requirement
+  --> $DIR/reject-specialized-drops-8142.rs:19:1
+   |
+LL | enum Enum<T> { Variant(T) }
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error[E0367]: `Drop` impl requires `AddsBnd: Bound` but the struct it is implemented for does not
+  --> $DIR/reject-specialized-drops-8142.rs:64:14
+   |
+LL | impl<AddsBnd:Bound> Drop for TupleStruct<AddsBnd> { fn drop(&mut self) { } } // REJECT
+   |              ^^^^^
+   |
+note: the implementor must specify the same requirement
+  --> $DIR/reject-specialized-drops-8142.rs:20:1
+   |
+LL | struct TupleStruct<T>(T);
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 11 previous errors
 
 Some errors have detailed explanations: E0308, E0366, E0367, E0495.
 For more information about an error, try `rustc --explain E0308`.