about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs7
-rw-r--r--tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr4
-rw-r--r--tests/ui/impl-trait/auto-trait-selection-freeze.old.stderr26
-rw-r--r--tests/ui/impl-trait/auto-trait-selection-freeze.rs3
-rw-r--r--tests/ui/impl-trait/auto-trait-selection.next.stderr4
-rw-r--r--tests/ui/impl-trait/auto-trait-selection.old.stderr26
-rw-r--r--tests/ui/impl-trait/auto-trait-selection.rs3
-rw-r--r--tests/ui/impl-trait/unsized_coercion3.next.stderr4
-rw-r--r--tests/ui/impl-trait/unsized_coercion3.old.stderr16
-rw-r--r--tests/ui/impl-trait/unsized_coercion3.rs1
-rw-r--r--tests/ui/impl-trait/unsized_coercion5.old.stderr16
-rw-r--r--tests/ui/impl-trait/unsized_coercion5.rs3
-rw-r--r--tests/ui/type-alias-impl-trait/in-where-clause.rs1
-rw-r--r--tests/ui/type-alias-impl-trait/in-where-clause.stderr21
-rw-r--r--tests/ui/type-alias-impl-trait/reveal_local.rs2
-rw-r--r--tests/ui/type-alias-impl-trait/reveal_local.stderr10
16 files changed, 93 insertions, 54 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs b/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
index 4c3d833b0f9..06b79ea63ca 100644
--- a/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
+++ b/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
@@ -772,7 +772,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
                     );
                 }
 
-                ty::Alias(ty::Opaque, _) => {
+                ty::Alias(ty::Opaque, alias) => {
                     if candidates.vec.iter().any(|c| matches!(c, ProjectionCandidate(_))) {
                         // We do not generate an auto impl candidate for `impl Trait`s which already
                         // reference our auto trait.
@@ -787,6 +787,11 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
                         // We do not emit auto trait candidates for opaque types in coherence.
                         // Doing so can result in weird dependency cycles.
                         candidates.ambiguous = true;
+                    } else if self.infcx.can_define_opaque_ty(alias.def_id) {
+                        // We do not emit auto trait candidates for opaque types in their defining scope, as
+                        // we need to know the hidden type first, which we can't reliably know within the defining
+                        // scope.
+                        candidates.ambiguous = true;
                     } else {
                         candidates.vec.push(AutoImplCandidate)
                     }
diff --git a/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr b/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr
index d9192e85497..5caf0eb2fd4 100644
--- a/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr
+++ b/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr
@@ -1,5 +1,5 @@
 error[E0283]: type annotations needed
-  --> $DIR/auto-trait-selection-freeze.rs:20:16
+  --> $DIR/auto-trait-selection-freeze.rs:19:16
    |
 LL |     if false { is_trait(foo()) } else { Default::default() }
    |                ^^^^^^^^ ----- type must be known at this point
@@ -8,7 +8,7 @@ LL |     if false { is_trait(foo()) } else { Default::default() }
    |
    = note: cannot satisfy `_: Trait<_>`
 note: required by a bound in `is_trait`
-  --> $DIR/auto-trait-selection-freeze.rs:12:16
+  --> $DIR/auto-trait-selection-freeze.rs:11:16
    |
 LL | fn is_trait<T: Trait<U>, U: Default>(_: T) -> U {
    |                ^^^^^^^^ required by this bound in `is_trait`
diff --git a/tests/ui/impl-trait/auto-trait-selection-freeze.old.stderr b/tests/ui/impl-trait/auto-trait-selection-freeze.old.stderr
new file mode 100644
index 00000000000..b4d2229d408
--- /dev/null
+++ b/tests/ui/impl-trait/auto-trait-selection-freeze.old.stderr
@@ -0,0 +1,26 @@
+error[E0283]: type annotations needed
+  --> $DIR/auto-trait-selection-freeze.rs:19:16
+   |
+LL |     if false { is_trait(foo()) } else { Default::default() }
+   |                ^^^^^^^^ cannot infer type of the type parameter `U` declared on the function `is_trait`
+   |
+note: multiple `impl`s satisfying `impl Sized: Trait<_>` found
+  --> $DIR/auto-trait-selection-freeze.rs:16:1
+   |
+LL | impl<T: Freeze> Trait<u32> for T {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | impl<T> Trait<i32> for T {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^
+note: required by a bound in `is_trait`
+  --> $DIR/auto-trait-selection-freeze.rs:11:16
+   |
+LL | fn is_trait<T: Trait<U>, U: Default>(_: T) -> U {
+   |                ^^^^^^^^ required by this bound in `is_trait`
+help: consider specifying the generic arguments
+   |
+LL |     if false { is_trait::<_, U>(foo()) } else { Default::default() }
+   |                        ++++++++
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0283`.
diff --git a/tests/ui/impl-trait/auto-trait-selection-freeze.rs b/tests/ui/impl-trait/auto-trait-selection-freeze.rs
index 72c24c51962..7306a1c41f7 100644
--- a/tests/ui/impl-trait/auto-trait-selection-freeze.rs
+++ b/tests/ui/impl-trait/auto-trait-selection-freeze.rs
@@ -3,7 +3,6 @@
 
 //@ revisions: next old
 //@[next] compile-flags: -Znext-solver
-//@[old]check-pass
 
 #![feature(freeze)]
 
@@ -18,7 +17,7 @@ impl<T: Freeze> Trait<u32> for T {}
 impl<T> Trait<i32> for T {}
 fn foo() -> impl Sized {
     if false { is_trait(foo()) } else { Default::default() }
-    //[next]~^ ERROR: type annotations needed
+    //~^ ERROR: type annotations needed
 }
 
 fn main() {}
diff --git a/tests/ui/impl-trait/auto-trait-selection.next.stderr b/tests/ui/impl-trait/auto-trait-selection.next.stderr
index 2e8d7ad99b2..d34fdcc4496 100644
--- a/tests/ui/impl-trait/auto-trait-selection.next.stderr
+++ b/tests/ui/impl-trait/auto-trait-selection.next.stderr
@@ -1,5 +1,5 @@
 error[E0283]: type annotations needed
-  --> $DIR/auto-trait-selection.rs:16:16
+  --> $DIR/auto-trait-selection.rs:15:16
    |
 LL |     if false { is_trait(foo()) } else { Default::default() }
    |                ^^^^^^^^ ----- type must be known at this point
@@ -8,7 +8,7 @@ LL |     if false { is_trait(foo()) } else { Default::default() }
    |
    = note: cannot satisfy `_: Trait<_>`
 note: required by a bound in `is_trait`
-  --> $DIR/auto-trait-selection.rs:8:16
+  --> $DIR/auto-trait-selection.rs:7:16
    |
 LL | fn is_trait<T: Trait<U>, U: Default>(_: T) -> U {
    |                ^^^^^^^^ required by this bound in `is_trait`
diff --git a/tests/ui/impl-trait/auto-trait-selection.old.stderr b/tests/ui/impl-trait/auto-trait-selection.old.stderr
new file mode 100644
index 00000000000..1b5fd95fdf9
--- /dev/null
+++ b/tests/ui/impl-trait/auto-trait-selection.old.stderr
@@ -0,0 +1,26 @@
+error[E0283]: type annotations needed
+  --> $DIR/auto-trait-selection.rs:15:16
+   |
+LL |     if false { is_trait(foo()) } else { Default::default() }
+   |                ^^^^^^^^ cannot infer type of the type parameter `U` declared on the function `is_trait`
+   |
+note: multiple `impl`s satisfying `impl Sized: Trait<_>` found
+  --> $DIR/auto-trait-selection.rs:12:1
+   |
+LL | impl<T: Send> Trait<u32> for T {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL | impl<T> Trait<i32> for T {}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^
+note: required by a bound in `is_trait`
+  --> $DIR/auto-trait-selection.rs:7:16
+   |
+LL | fn is_trait<T: Trait<U>, U: Default>(_: T) -> U {
+   |                ^^^^^^^^ required by this bound in `is_trait`
+help: consider specifying the generic arguments
+   |
+LL |     if false { is_trait::<_, U>(foo()) } else { Default::default() }
+   |                        ++++++++
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0283`.
diff --git a/tests/ui/impl-trait/auto-trait-selection.rs b/tests/ui/impl-trait/auto-trait-selection.rs
index beb0b189fd7..ee5612459c2 100644
--- a/tests/ui/impl-trait/auto-trait-selection.rs
+++ b/tests/ui/impl-trait/auto-trait-selection.rs
@@ -3,7 +3,6 @@
 
 //@ revisions: next old
 //@[next] compile-flags: -Znext-solver
-//@[old]check-pass
 
 fn is_trait<T: Trait<U>, U: Default>(_: T) -> U {
     Default::default()
@@ -14,7 +13,7 @@ impl<T: Send> Trait<u32> for T {}
 impl<T> Trait<i32> for T {}
 fn foo() -> impl Sized {
     if false { is_trait(foo()) } else { Default::default() }
-    //[next]~^ ERROR: type annotations needed
+    //~^ ERROR: type annotations needed
 }
 
 fn main() {}
diff --git a/tests/ui/impl-trait/unsized_coercion3.next.stderr b/tests/ui/impl-trait/unsized_coercion3.next.stderr
index bab8d1cd83b..586ae076028 100644
--- a/tests/ui/impl-trait/unsized_coercion3.next.stderr
+++ b/tests/ui/impl-trait/unsized_coercion3.next.stderr
@@ -5,7 +5,7 @@ LL |         let x = hello();
    |                 ^^^^^^^ types differ
 
 error[E0308]: mismatched types
-  --> $DIR/unsized_coercion3.rs:19:14
+  --> $DIR/unsized_coercion3.rs:18:14
    |
 LL | fn hello() -> Box<impl Trait + ?Sized> {
    |                   ------------------- the expected opaque type
@@ -21,7 +21,7 @@ note: associated function defined here
   --> $SRC_DIR/alloc/src/boxed.rs:LL:COL
 
 error[E0277]: the size for values of type `impl Trait + ?Sized` cannot be known at compilation time
-  --> $DIR/unsized_coercion3.rs:19:14
+  --> $DIR/unsized_coercion3.rs:18:14
    |
 LL |     Box::new(1u32)
    |     -------- ^^^^ doesn't have a size known at compile-time
diff --git a/tests/ui/impl-trait/unsized_coercion3.old.stderr b/tests/ui/impl-trait/unsized_coercion3.old.stderr
index 24a302d7007..52a72b84a8d 100644
--- a/tests/ui/impl-trait/unsized_coercion3.old.stderr
+++ b/tests/ui/impl-trait/unsized_coercion3.old.stderr
@@ -1,17 +1,3 @@
-error: cannot check whether the hidden type of opaque type satisfies auto traits
-  --> $DIR/unsized_coercion3.rs:15:32
-   |
-LL |         let y: Box<dyn Send> = x;
-   |                                ^
-   |
-   = note: fetching the hidden types of an opaque inside of the defining scope is not supported. You can try moving the opaque type and the item that actually registers a hidden type into a new submodule
-note: opaque type is declared here
-  --> $DIR/unsized_coercion3.rs:11:19
-   |
-LL | fn hello() -> Box<impl Trait + ?Sized> {
-   |                   ^^^^^^^^^^^^^^^^^^^
-   = note: required for the cast from `Box<impl Trait + ?Sized>` to `Box<dyn Send>`
-
 error[E0277]: the size for values of type `impl Trait + ?Sized` cannot be known at compilation time
   --> $DIR/unsized_coercion3.rs:15:32
    |
@@ -21,6 +7,6 @@ LL |         let y: Box<dyn Send> = x;
    = help: the trait `Sized` is not implemented for `impl Trait + ?Sized`
    = note: required for the cast from `Box<impl Trait + ?Sized>` to `Box<dyn Send>`
 
-error: aborting due to 2 previous errors
+error: aborting due to 1 previous error
 
 For more information about this error, try `rustc --explain E0277`.
diff --git a/tests/ui/impl-trait/unsized_coercion3.rs b/tests/ui/impl-trait/unsized_coercion3.rs
index 85950ac583e..7e862de2157 100644
--- a/tests/ui/impl-trait/unsized_coercion3.rs
+++ b/tests/ui/impl-trait/unsized_coercion3.rs
@@ -14,7 +14,6 @@ fn hello() -> Box<impl Trait + ?Sized> {
         //[next]~^ ERROR: type mismatch resolving `impl Trait + ?Sized <: dyn Send`
         let y: Box<dyn Send> = x;
         //[old]~^ ERROR: the size for values of type `impl Trait + ?Sized` cannot be know
-        //[old]~| ERROR: cannot check whether the hidden type of opaque type satisfies auto traits
     }
     Box::new(1u32)
     //[next]~^ ERROR: mismatched types
diff --git a/tests/ui/impl-trait/unsized_coercion5.old.stderr b/tests/ui/impl-trait/unsized_coercion5.old.stderr
index b6437266f27..06ad54b1f1d 100644
--- a/tests/ui/impl-trait/unsized_coercion5.old.stderr
+++ b/tests/ui/impl-trait/unsized_coercion5.old.stderr
@@ -9,20 +9,6 @@ LL |         let y: Box<dyn Send> = x as Box<dyn Trait + Send>;
    = note: expected struct `Box<dyn Send>`
               found struct `Box<dyn Trait + Send>`
 
-error: cannot check whether the hidden type of opaque type satisfies auto traits
-  --> $DIR/unsized_coercion5.rs:16:32
-   |
-LL |         let y: Box<dyn Send> = x as Box<dyn Trait + Send>;
-   |                                ^
-   |
-   = note: fetching the hidden types of an opaque inside of the defining scope is not supported. You can try moving the opaque type and the item that actually registers a hidden type into a new submodule
-note: opaque type is declared here
-  --> $DIR/unsized_coercion5.rs:13:19
-   |
-LL | fn hello() -> Box<impl Trait + ?Sized> {
-   |                   ^^^^^^^^^^^^^^^^^^^
-   = note: required for the cast from `Box<impl Trait + ?Sized>` to `Box<dyn Trait + Send>`
-
 error[E0277]: the size for values of type `impl Trait + ?Sized` cannot be known at compilation time
   --> $DIR/unsized_coercion5.rs:16:32
    |
@@ -32,7 +18,7 @@ LL |         let y: Box<dyn Send> = x as Box<dyn Trait + Send>;
    = help: the trait `Sized` is not implemented for `impl Trait + ?Sized`
    = note: required for the cast from `Box<impl Trait + ?Sized>` to `Box<dyn Trait + Send>`
 
-error: aborting due to 3 previous errors
+error: aborting due to 2 previous errors
 
 Some errors have detailed explanations: E0277, E0308.
 For more information about an error, try `rustc --explain E0277`.
diff --git a/tests/ui/impl-trait/unsized_coercion5.rs b/tests/ui/impl-trait/unsized_coercion5.rs
index b007267a006..85d313caa13 100644
--- a/tests/ui/impl-trait/unsized_coercion5.rs
+++ b/tests/ui/impl-trait/unsized_coercion5.rs
@@ -15,8 +15,7 @@ fn hello() -> Box<impl Trait + ?Sized> {
         let x = hello();
         let y: Box<dyn Send> = x as Box<dyn Trait + Send>;
         //[old]~^ ERROR: the size for values of type `impl Trait + ?Sized` cannot be know
-        //[old]~| ERROR: cannot check whether the hidden type of opaque type satisfies auto traits
-        //~^^^ ERROR: mismatched types
+        //~^^ ERROR: mismatched types
     }
     Box::new(1u32)
 }
diff --git a/tests/ui/type-alias-impl-trait/in-where-clause.rs b/tests/ui/type-alias-impl-trait/in-where-clause.rs
index 6e104781d84..a089fdc9075 100644
--- a/tests/ui/type-alias-impl-trait/in-where-clause.rs
+++ b/tests/ui/type-alias-impl-trait/in-where-clause.rs
@@ -10,6 +10,7 @@ where
     Bar: Send,
 {
     [0; 1 + 2]
+    //~^ ERROR: type annotations needed: cannot satisfy `Bar: Send`
 }
 
 fn main() {}
diff --git a/tests/ui/type-alias-impl-trait/in-where-clause.stderr b/tests/ui/type-alias-impl-trait/in-where-clause.stderr
index c486013f887..f1361b47c56 100644
--- a/tests/ui/type-alias-impl-trait/in-where-clause.stderr
+++ b/tests/ui/type-alias-impl-trait/in-where-clause.stderr
@@ -25,6 +25,23 @@ LL | type Bar = impl Sized;
    |            ^^^^^^^^^^
    = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information
 
-error: aborting due to 1 previous error
+error[E0283]: type annotations needed: cannot satisfy `Bar: Send`
+  --> $DIR/in-where-clause.rs:12:9
+   |
+LL |     [0; 1 + 2]
+   |         ^^^^^
+   |
+   = note: cannot satisfy `Bar: Send`
+note: required by a bound in `foo`
+  --> $DIR/in-where-clause.rs:10:10
+   |
+LL | fn foo() -> Bar
+   |    --- required by a bound in this function
+LL | where
+LL |     Bar: Send,
+   |          ^^^^ required by this bound in `foo`
+
+error: aborting due to 2 previous errors
 
-For more information about this error, try `rustc --explain E0391`.
+Some errors have detailed explanations: E0283, E0391.
+For more information about an error, try `rustc --explain E0283`.
diff --git a/tests/ui/type-alias-impl-trait/reveal_local.rs b/tests/ui/type-alias-impl-trait/reveal_local.rs
index 07fd989b0fa..34f3788e234 100644
--- a/tests/ui/type-alias-impl-trait/reveal_local.rs
+++ b/tests/ui/type-alias-impl-trait/reveal_local.rs
@@ -20,7 +20,7 @@ fn not_gooder() -> Foo {
     // while we could know this from the hidden type, it would
     // need extra roundabout logic to support it.
     is_send::<Foo>();
-    //~^ ERROR: cannot check whether the hidden type of `reveal_local[9507]::Foo::{opaque#0}` satisfies auto traits
+    //~^ ERROR: type annotations needed: cannot satisfy `Foo: Send`
 
     x
 }
diff --git a/tests/ui/type-alias-impl-trait/reveal_local.stderr b/tests/ui/type-alias-impl-trait/reveal_local.stderr
index e1b320cc38e..9829c58cf73 100644
--- a/tests/ui/type-alias-impl-trait/reveal_local.stderr
+++ b/tests/ui/type-alias-impl-trait/reveal_local.stderr
@@ -16,18 +16,13 @@ note: required by a bound in `is_send`
 LL | fn is_send<T: Send>() {}
    |               ^^^^ required by this bound in `is_send`
 
-error: cannot check whether the hidden type of `reveal_local[9507]::Foo::{opaque#0}` satisfies auto traits
+error[E0283]: type annotations needed: cannot satisfy `Foo: Send`
   --> $DIR/reveal_local.rs:22:15
    |
 LL |     is_send::<Foo>();
    |               ^^^
    |
-   = note: fetching the hidden types of an opaque inside of the defining scope is not supported. You can try moving the opaque type and the item that actually registers a hidden type into a new submodule
-note: opaque type is declared here
-  --> $DIR/reveal_local.rs:5:12
-   |
-LL | type Foo = impl Debug;
-   |            ^^^^^^^^^^
+   = note: cannot satisfy `Foo: Send`
 note: required by a bound in `is_send`
   --> $DIR/reveal_local.rs:7:15
    |
@@ -36,3 +31,4 @@ LL | fn is_send<T: Send>() {}
 
 error: aborting due to 2 previous errors
 
+For more information about this error, try `rustc --explain E0283`.