about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMichael Goulet <michael@errs.io>2022-02-06 15:57:29 -0800
committerMichael Goulet <michael@errs.io>2022-02-24 08:40:59 -0800
commitee98dc8b3bdff99591630ca225f4769201100603 (patch)
tree08bc11972a98af3d1a60eb655fc2cafe27cf9079
parent8ba74369c210a0cdb1b1440c47f19f2145e1640f (diff)
downloadrust-ee98dc8b3bdff99591630ca225f4769201100603.tar.gz
rust-ee98dc8b3bdff99591630ca225f4769201100603.zip
restore spans for issue-50480
-rw-r--r--compiler/rustc_trait_selection/src/traits/misc.rs15
-rw-r--r--src/test/ui/issues/issue-50480.rs4
-rw-r--r--src/test/ui/issues/issue-50480.stderr30
3 files changed, 30 insertions, 19 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/misc.rs b/compiler/rustc_trait_selection/src/traits/misc.rs
index dc72945af24..c293708dcc9 100644
--- a/compiler/rustc_trait_selection/src/traits/misc.rs
+++ b/compiler/rustc_trait_selection/src/traits/misc.rs
@@ -50,8 +50,21 @@ pub fn can_type_implement_copy<'tcx>(
                     continue;
                 }
                 let span = tcx.def_span(field.did);
+                // FIXME(compiler-errors): This gives us better spans for bad
+                // projection types like in issue-50480.
+                // If the ADT has substs, point to the cause we are given.
+                // If it does not, then this field probably doesn't normalize
+                // to begin with, and point to the bad field's span instead.
+                let cause = if field
+                    .ty(tcx, traits::InternalSubsts::identity_for_item(tcx, adt.did))
+                    .has_param_types_or_consts()
+                {
+                    cause.clone()
+                } else {
+                    ObligationCause::dummy_with_span(span)
+                };
                 let ctx = traits::FulfillmentContext::new();
-                match traits::fully_normalize(&infcx, ctx, cause.clone(), param_env, ty) {
+                match traits::fully_normalize(&infcx, ctx, cause, param_env, ty) {
                     Ok(ty) => {
                         if !infcx.type_is_copy_modulo_regions(param_env, ty, span) {
                             infringing.push(field);
diff --git a/src/test/ui/issues/issue-50480.rs b/src/test/ui/issues/issue-50480.rs
index ca81db023ec..10597caf5b2 100644
--- a/src/test/ui/issues/issue-50480.rs
+++ b/src/test/ui/issues/issue-50480.rs
@@ -1,17 +1,17 @@
 #[derive(Clone, Copy)]
 //~^ ERROR the trait `Copy` may not be implemented for this type
-//~| ERROR `i32` is not an iterator
 struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
 //~^ ERROR cannot find type `NotDefined` in this scope
 //~| ERROR cannot find type `NotDefined` in this scope
 //~| ERROR cannot find type `N` in this scope
 //~| ERROR cannot find type `N` in this scope
+//~| ERROR `i32` is not an iterator
 
 #[derive(Clone, Copy)]
 //~^ ERROR the trait `Copy` may not be implemented for this type
-//~| ERROR `i32` is not an iterator
 struct Bar<T>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
 //~^ ERROR cannot find type `NotDefined` in this scope
 //~| ERROR cannot find type `N` in this scope
+//~| ERROR `i32` is not an iterator
 
 fn main() {}
diff --git a/src/test/ui/issues/issue-50480.stderr b/src/test/ui/issues/issue-50480.stderr
index 48ec4aa434c..0bb1f9ae035 100644
--- a/src/test/ui/issues/issue-50480.stderr
+++ b/src/test/ui/issues/issue-50480.stderr
@@ -1,5 +1,5 @@
 error[E0412]: cannot find type `N` in this scope
-  --> $DIR/issue-50480.rs:4:12
+  --> $DIR/issue-50480.rs:3:12
    |
 LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           -^ not found in this scope
@@ -7,13 +7,13 @@ LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           help: you might be missing a type parameter: `<N>`
 
 error[E0412]: cannot find type `NotDefined` in this scope
-  --> $DIR/issue-50480.rs:4:15
+  --> $DIR/issue-50480.rs:3:15
    |
 LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |               ^^^^^^^^^^ not found in this scope
 
 error[E0412]: cannot find type `N` in this scope
-  --> $DIR/issue-50480.rs:4:12
+  --> $DIR/issue-50480.rs:3:12
    |
 LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           -^ not found in this scope
@@ -21,7 +21,7 @@ LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           help: you might be missing a type parameter: `<N>`
 
 error[E0412]: cannot find type `NotDefined` in this scope
-  --> $DIR/issue-50480.rs:4:15
+  --> $DIR/issue-50480.rs:3:15
    |
 LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           -   ^^^^^^^^^^ not found in this scope
@@ -29,7 +29,7 @@ LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |           help: you might be missing a type parameter: `<NotDefined>`
 
 error[E0412]: cannot find type `N` in this scope
-  --> $DIR/issue-50480.rs:13:18
+  --> $DIR/issue-50480.rs:12:18
    |
 LL | struct Bar<T>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |            -     ^
@@ -46,27 +46,26 @@ LL | struct Bar<T, N>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, Strin
    |             +++
 
 error[E0412]: cannot find type `NotDefined` in this scope
-  --> $DIR/issue-50480.rs:13:21
+  --> $DIR/issue-50480.rs:12:21
    |
 LL | struct Bar<T>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |                     ^^^^^^^^^^ not found in this scope
 
 error[E0277]: `i32` is not an iterator
-  --> $DIR/issue-50480.rs:1:17
+  --> $DIR/issue-50480.rs:3:27
    |
-LL | #[derive(Clone, Copy)]
-   |                 ^^^^ `i32` is not an iterator
+LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
+   |                           ^^^^^^^^^^^^^^^^^^^^^^^ `i32` is not an iterator
    |
    = help: the trait `Iterator` is not implemented for `i32`
    = note: if you want to iterate between `start` until a value `end`, use the exclusive range syntax `start..end` or the inclusive range syntax `start..=end`
-   = note: this error originates in the derive macro `Copy` (in Nightly builds, run with -Z macro-backtrace for more info)
 
 error[E0204]: the trait `Copy` may not be implemented for this type
   --> $DIR/issue-50480.rs:1:17
    |
 LL | #[derive(Clone, Copy)]
    |                 ^^^^
-...
+LL |
 LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |                                                    --------  ------ this field does not implement `Copy`
    |                                                    |
@@ -75,21 +74,20 @@ LL | struct Foo(N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    = note: this error originates in the derive macro `Copy` (in Nightly builds, run with -Z macro-backtrace for more info)
 
 error[E0277]: `i32` is not an iterator
-  --> $DIR/issue-50480.rs:10:17
+  --> $DIR/issue-50480.rs:12:33
    |
-LL | #[derive(Clone, Copy)]
-   |                 ^^^^ `i32` is not an iterator
+LL | struct Bar<T>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
+   |                                 ^^^^^^^^^^^^^^^^^^^^^^^ `i32` is not an iterator
    |
    = help: the trait `Iterator` is not implemented for `i32`
    = note: if you want to iterate between `start` until a value `end`, use the exclusive range syntax `start..end` or the inclusive range syntax `start..=end`
-   = note: this error originates in the derive macro `Copy` (in Nightly builds, run with -Z macro-backtrace for more info)
 
 error[E0204]: the trait `Copy` may not be implemented for this type
   --> $DIR/issue-50480.rs:10:17
    |
 LL | #[derive(Clone, Copy)]
    |                 ^^^^
-...
+LL |
 LL | struct Bar<T>(T, N, NotDefined, <i32 as Iterator>::Item, Vec<i32>, String);
    |                                                          --------  ------ this field does not implement `Copy`
    |                                                          |