Erase regions from CallArgument, add test + bless

This commit is contained in:
Michael Goulet 2022-10-27 16:22:06 +00:00
parent dce44faf5b
commit 4e0c27bbfd
5 changed files with 73 additions and 7 deletions

View File

@ -1630,7 +1630,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
let op_arg_ty = self.normalize(op_arg_ty, term_location);
let category = if from_hir_call {
ConstraintCategory::CallArgument(func_ty)
ConstraintCategory::CallArgument(self.infcx.tcx.erase_regions(func_ty))
} else {
ConstraintCategory::Boring
};

View File

@ -15,19 +15,19 @@ LL | let a = bar(f, x);
= help: see <https://doc.rust-lang.org/nomicon/subtyping.html> for more information about variance
error: lifetime may not live long enough
--> $DIR/project-fn-ret-invariant.rs:40:13
--> $DIR/project-fn-ret-invariant.rs:42:13
|
LL | fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
| -- -- lifetime `'b` defined here
| |
| lifetime `'a` defined here
LL | let f = foo; // <-- No consistent type can be inferred for `f` here.
LL | let a = bar(f, x);
...
LL | let b = bar(f, y);
| ^^^^^^^^^ argument requires that `'b` must outlive `'a`
|
= help: consider adding the following bound: `'b: 'a`
= note: requirement occurs because of a function pointer to `foo`
= note: the function `foo` is invariant over the parameter `'a`
= note: requirement occurs because of the type `Type<'_>`, which makes the generic argument `'_` invariant
= note: the struct `Type<'a>` is invariant over the parameter `'a`
= help: see <https://doc.rust-lang.org/nomicon/subtyping.html> for more information about variance
help: `'a` and `'b` must be the same: replace one with the other

View File

@ -39,8 +39,8 @@ fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
let f = foo; // <-- No consistent type can be inferred for `f` here.
let a = bar(f, x);
//[oneuse]~^ ERROR lifetime may not live long enough
//[oneuse]~| ERROR lifetime may not live long enough
let b = bar(f, y);
//[oneuse]~^ ERROR lifetime may not live long enough
(a, b)
}

View File

@ -0,0 +1,31 @@
// edition:2021
struct StructA {
b: StructB,
}
async fn spawn_blocking<T>(f: impl (Fn() -> T) + Send + Sync + 'static) -> T {
todo!()
}
impl StructA {
async fn foo(&self) {
let bar = self.b.bar().await;
spawn_blocking(move || {
//~^ ERROR borrowed data escapes outside of associated function
self.b;
//~^ ERROR cannot move out of `self.b`, as `self` is a captured variable in an `Fn` closure
})
.await;
}
}
struct StructB {}
impl StructB {
async fn bar(&self) -> Option<u8> {
None
}
}
fn main() {}

View File

@ -0,0 +1,35 @@
error[E0507]: cannot move out of `self.b`, as `self` is a captured variable in an `Fn` closure
--> $DIR/issue-103624.rs:16:13
|
LL | async fn foo(&self) {
| ----- captured outer variable
LL | let bar = self.b.bar().await;
LL | spawn_blocking(move || {
| ------- captured by this `Fn` closure
LL |
LL | self.b;
| ^^^^^^ move occurs because `self.b` has type `StructB`, which does not implement the `Copy` trait
error[E0521]: borrowed data escapes outside of associated function
--> $DIR/issue-103624.rs:14:9
|
LL | async fn foo(&self) {
| -----
| |
| `self` is a reference that is only valid in the associated function body
| let's call the lifetime of this reference `'1`
LL | let bar = self.b.bar().await;
LL | / spawn_blocking(move || {
LL | |
LL | | self.b;
LL | |
LL | | })
| | ^
| | |
| |__________`self` escapes the associated function body here
| argument requires that `'1` must outlive `'static`
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0507, E0521.
For more information about an error, try `rustc --explain E0507`.