about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMichael Goulet <michael@errs.io>2023-02-27 20:47:06 +0000
committerMichael Goulet <michael@errs.io>2023-03-23 06:19:52 +0000
commite5189cc7e45991e1c6e9a4218c80d54441b346a9 (patch)
treeaa9ebe077c366e31fe2393bde73f44895748953e
parent1c771fec3329ef1d8c66697daf9517501d0c129a (diff)
downloadrust-e5189cc7e45991e1c6e9a4218c80d54441b346a9.tar.gz
rust-e5189cc7e45991e1c6e9a4218c80d54441b346a9.zip
Nested impl traits trigger opaque_hidden_inferred_bound too much
-rw-r--r--compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs21
-rw-r--r--tests/ui/impl-trait/nested-return-type2.rs1
-rw-r--r--tests/ui/impl-trait/nested-return-type2.stderr17
-rw-r--r--tests/ui/impl-trait/nested-return-type3.rs1
-rw-r--r--tests/ui/impl-trait/nested-return-type3.stderr17
5 files changed, 18 insertions, 39 deletions
diff --git a/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs b/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs
index 883a56cb3ce..f9d43fe2200 100644
--- a/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs
+++ b/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs
@@ -27,6 +27,8 @@ declare_lint! {
     /// ### Example
     ///
     /// ```rust
+    /// #![feature(type_alias_impl_trait)]
+    ///
     /// trait Duh {}
     ///
     /// impl Duh for i32 {}
@@ -41,7 +43,9 @@ declare_lint! {
     ///     type Assoc = F;
     /// }
     ///
-    /// fn test() -> impl Trait<Assoc = impl Sized> {
+    /// type Tait = impl Sized;
+    ///
+    /// fn test() -> impl Trait<Assoc = Tait> {
     ///     42
     /// }
     /// ```
@@ -54,7 +58,7 @@ declare_lint! {
     ///
     /// Although the hidden type, `i32` does satisfy this bound, we do not
     /// consider the return type to be well-formed with this lint. It can be
-    /// fixed by changing `impl Sized` into `impl Sized + Send`.
+    /// fixed by changing `Tait = impl Sized` into `Tait = impl Sized + Send`.
     pub OPAQUE_HIDDEN_INFERRED_BOUND,
     Warn,
     "detects the use of nested `impl Trait` types in associated type bounds that are not general enough"
@@ -64,7 +68,7 @@ declare_lint_pass!(OpaqueHiddenInferredBound => [OPAQUE_HIDDEN_INFERRED_BOUND]);
 
 impl<'tcx> LateLintPass<'tcx> for OpaqueHiddenInferredBound {
     fn check_item(&mut self, cx: &LateContext<'tcx>, item: &'tcx hir::Item<'tcx>) {
-        let hir::ItemKind::OpaqueTy(_) = &item.kind else { return; };
+        let hir::ItemKind::OpaqueTy(opaque) = &item.kind else { return; };
         let def_id = item.owner_id.def_id.to_def_id();
         let infcx = &cx.tcx.infer_ctxt().build();
         // For every projection predicate in the opaque type's explicit bounds,
@@ -81,6 +85,17 @@ impl<'tcx> LateLintPass<'tcx> for OpaqueHiddenInferredBound {
             // have opaques in them anyways.
             let Some(proj_term) = proj.term.ty() else { continue };
 
+            // HACK: `impl Trait<Assoc = impl Trait2>` from an RPIT is "ok"...
+            if let ty::Alias(ty::Opaque, opaque_ty) = *proj_term.kind()
+                && cx.tcx.parent(opaque_ty.def_id) == def_id
+                && matches!(
+                    opaque.origin,
+                    hir::OpaqueTyOrigin::FnReturn(_) | hir::OpaqueTyOrigin::AsyncFn(_)
+                )
+            {
+                continue;
+            }
+
             let proj_ty =
                 cx.tcx.mk_projection(proj.projection_ty.def_id, proj.projection_ty.substs);
             // For every instance of the projection type in the bounds,
diff --git a/tests/ui/impl-trait/nested-return-type2.rs b/tests/ui/impl-trait/nested-return-type2.rs
index fe883ce6fc8..e1d5511379e 100644
--- a/tests/ui/impl-trait/nested-return-type2.rs
+++ b/tests/ui/impl-trait/nested-return-type2.rs
@@ -26,7 +26,6 @@ impl<R: Duh, F: FnMut() -> R> Trait for F {
 // Lazy TAIT would error out, but we inserted a hack to make it work again,
 // keeping backwards compatibility.
 fn foo() -> impl Trait<Assoc = impl Send> {
-    //~^ WARN opaque type `impl Trait<Assoc = impl Send>` does not satisfy its associated type bounds
     || 42
 }
 
diff --git a/tests/ui/impl-trait/nested-return-type2.stderr b/tests/ui/impl-trait/nested-return-type2.stderr
deleted file mode 100644
index 09ad3bd05c1..00000000000
--- a/tests/ui/impl-trait/nested-return-type2.stderr
+++ /dev/null
@@ -1,17 +0,0 @@
-warning: opaque type `impl Trait<Assoc = impl Send>` does not satisfy its associated type bounds
-  --> $DIR/nested-return-type2.rs:28:24
-   |
-LL |     type Assoc: Duh;
-   |                 --- this associated type bound is unsatisfied for `impl Send`
-...
-LL | fn foo() -> impl Trait<Assoc = impl Send> {
-   |                        ^^^^^^^^^^^^^^^^^
-   |
-   = note: `#[warn(opaque_hidden_inferred_bound)]` on by default
-help: add this bound
-   |
-LL | fn foo() -> impl Trait<Assoc = impl Send + Duh> {
-   |                                          +++++
-
-warning: 1 warning emitted
-
diff --git a/tests/ui/impl-trait/nested-return-type3.rs b/tests/ui/impl-trait/nested-return-type3.rs
index 5a764fc4c28..74b4dae22eb 100644
--- a/tests/ui/impl-trait/nested-return-type3.rs
+++ b/tests/ui/impl-trait/nested-return-type3.rs
@@ -13,7 +13,6 @@ impl<F: Duh> Trait for F {
 }
 
 fn foo() -> impl Trait<Assoc = impl Send> {
-    //~^ WARN opaque type `impl Trait<Assoc = impl Send>` does not satisfy its associated type bounds
     42
 }
 
diff --git a/tests/ui/impl-trait/nested-return-type3.stderr b/tests/ui/impl-trait/nested-return-type3.stderr
deleted file mode 100644
index 632de71aa4c..00000000000
--- a/tests/ui/impl-trait/nested-return-type3.stderr
+++ /dev/null
@@ -1,17 +0,0 @@
-warning: opaque type `impl Trait<Assoc = impl Send>` does not satisfy its associated type bounds
-  --> $DIR/nested-return-type3.rs:15:24
-   |
-LL |     type Assoc: Duh;
-   |                 --- this associated type bound is unsatisfied for `impl Send`
-...
-LL | fn foo() -> impl Trait<Assoc = impl Send> {
-   |                        ^^^^^^^^^^^^^^^^^
-   |
-   = note: `#[warn(opaque_hidden_inferred_bound)]` on by default
-help: add this bound
-   |
-LL | fn foo() -> impl Trait<Assoc = impl Send + Duh> {
-   |                                          +++++
-
-warning: 1 warning emitted
-