Skip to content

Commit eb3feb3

Browse files
Also note for fields
1 parent 4755f36 commit eb3feb3

File tree

4 files changed

+53
-9
lines changed

4 files changed

+53
-9
lines changed

compiler/rustc_hir_typeck/src/expr.rs

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,8 @@ use rustc_data_structures::stack::ensure_sufficient_stack;
1010
use rustc_data_structures::unord::UnordMap;
1111
use rustc_errors::codes::*;
1212
use rustc_errors::{
13-
Applicability, Diag, ErrorGuaranteed, StashKey, Subdiagnostic, pluralize, struct_span_code_err,
13+
Applicability, Diag, ErrorGuaranteed, MultiSpan, StashKey, Subdiagnostic, pluralize,
14+
struct_span_code_err,
1415
};
1516
use rustc_hir::def::{CtorKind, DefKind, Res};
1617
use rustc_hir::def_id::DefId;
@@ -2796,12 +2797,25 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
27962797
field_ident.span,
27972798
"field not available in `impl Future`, but it is available in its `Output`",
27982799
);
2799-
err.span_suggestion_verbose(
2800-
base.span.shrink_to_hi(),
2801-
"consider `await`ing on the `Future` and access the field of its `Output`",
2802-
".await",
2803-
Applicability::MaybeIncorrect,
2804-
);
2800+
match self.tcx.coroutine_kind(self.body_id) {
2801+
Some(hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::Async, _)) => {
2802+
err.span_suggestion_verbose(
2803+
base.span.shrink_to_hi(),
2804+
"consider `await`ing on the `Future` to access the field",
2805+
".await",
2806+
Applicability::MaybeIncorrect,
2807+
);
2808+
}
2809+
_ => {
2810+
let mut span: MultiSpan = base.span.into();
2811+
span.push_span_label(self.tcx.def_span(self.body_id), "this is not `async`");
2812+
err.span_note(
2813+
span,
2814+
"this implements `Future` and its output type has the field, \
2815+
but the future cannot be awaited in a synchronous function",
2816+
);
2817+
}
2818+
}
28052819
}
28062820

28072821
fn ban_nonexisting_field(

tests/ui/async-await/field-in-sync.rs

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
//@ edition: 2021
2+
3+
struct S {
4+
field: (),
5+
}
6+
7+
async fn foo() -> S { todo!() }
8+
9+
fn main() -> Result<(), ()> {
10+
foo().field;
11+
//~^ ERROR no field `field` on type `impl Future<Output = S>`
12+
Ok(())
13+
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
error[E0609]: no field `field` on type `impl Future<Output = S>`
2+
--> $DIR/field-in-sync.rs:10:11
3+
|
4+
LL | foo().field;
5+
| ^^^^^ field not available in `impl Future`, but it is available in its `Output`
6+
|
7+
note: this implements `Future` and its output type has the field, but the future cannot be awaited in a synchronous function
8+
--> $DIR/field-in-sync.rs:10:5
9+
|
10+
LL | fn main() -> Result<(), ()> {
11+
| --------------------------- this is not `async`
12+
LL | foo().field;
13+
| ^^^^^
14+
15+
error: aborting due to 1 previous error
16+
17+
For more information about this error, try `rustc --explain E0609`.

tests/ui/async-await/issue-61076.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ error[E0609]: no field `0` on type `impl Future<Output = Tuple>`
2828
LL | let _: i32 = tuple().0;
2929
| ^ field not available in `impl Future`, but it is available in its `Output`
3030
|
31-
help: consider `await`ing on the `Future` and access the field of its `Output`
31+
help: consider `await`ing on the `Future` to access the field
3232
|
3333
LL | let _: i32 = tuple().await.0;
3434
| ++++++
@@ -39,7 +39,7 @@ error[E0609]: no field `a` on type `impl Future<Output = Struct>`
3939
LL | let _: i32 = struct_().a;
4040
| ^ field not available in `impl Future`, but it is available in its `Output`
4141
|
42-
help: consider `await`ing on the `Future` and access the field of its `Output`
42+
help: consider `await`ing on the `Future` to access the field
4343
|
4444
LL | let _: i32 = struct_().await.a;
4545
| ++++++

0 commit comments

Comments
 (0)