Skip to content

Commit 50ac0a3

Browse files
committed
Simplify error reporting code, remove await point wording
1 parent e467840 commit 50ac0a3

File tree

10 files changed

+133
-265
lines changed

10 files changed

+133
-265
lines changed

compiler/rustc_infer/src/infer/error_reporting/nice_region_error/different_lifetimes.rs

+33-77
Original file line numberDiff line numberDiff line change
@@ -106,91 +106,47 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
106106
None => String::new(),
107107
};
108108

109-
let (span_1, span_2, main_label, span_label, future_return_type) =
110-
match (sup_is_ret_type, sub_is_ret_type) {
111-
(None, None) => {
112-
let (main_label_1, span_label_1) = if ty_sup.hir_id == ty_sub.hir_id {
113-
(
114-
"this type is declared with multiple lifetimes...".to_owned(),
115-
"...but data with one lifetime flows into the other here".to_owned(),
116-
)
117-
} else {
118-
(
119-
"these two types are declared with different lifetimes...".to_owned(),
120-
format!("...but data{} flows{} here", span_label_var1, span_label_var2),
121-
)
122-
};
123-
(ty_sup.span, ty_sub.span, main_label_1, span_label_1, None)
124-
}
109+
debug!(
110+
"try_report_anon_anon_conflict: sub_is_ret_type={:?} sup_is_ret_type={:?}",
111+
sub_is_ret_type, sup_is_ret_type
112+
);
125113

126-
(Some(ret_span), _) => {
127-
let sup_future = self.future_return_type(scope_def_id_sup);
128-
let (return_type, action) = if sup_future.is_some() {
129-
("returned future", "held across an await point")
130-
} else {
131-
("return type", "returned")
132-
};
114+
let mut err = struct_span_err!(self.tcx().sess, span, E0623, "lifetime mismatch");
133115

134-
(
135-
ty_sub.span,
136-
ret_span,
137-
format!(
138-
"this parameter and the {} are declared with different lifetimes...",
139-
return_type
140-
),
141-
format!("...but data{} is {} here", span_label_var1, action),
142-
sup_future,
143-
)
144-
}
145-
(_, Some(ret_span)) => {
146-
let sub_future = self.future_return_type(scope_def_id_sub);
147-
let (return_type, action) = if sub_future.is_some() {
148-
("returned future", "held across an await point")
149-
} else {
150-
("return type", "returned")
151-
};
116+
match (sup_is_ret_type, sub_is_ret_type) {
117+
(ret_capture @ Some(ret_span), _) | (_, ret_capture @ Some(ret_span)) => {
118+
let param_span =
119+
if sup_is_ret_type == ret_capture { ty_sub.span } else { ty_sup.span };
120+
121+
err.span_label(
122+
param_span,
123+
"this parameter and the return type are declared with different lifetimes...",
124+
);
125+
err.span_label(ret_span, "");
126+
err.span_label(span, format!("...but data{} is returned here", span_label_var1));
127+
}
152128

153-
(
129+
(None, None) => {
130+
if ty_sup.hir_id == ty_sub.hir_id {
131+
err.span_label(ty_sup.span, "this type is declared with multiple lifetimes...");
132+
err.span_label(ty_sub.span, "");
133+
err.span_label(span, "...but data with one lifetime flows into the other here");
134+
} else {
135+
err.span_label(
154136
ty_sup.span,
155-
ret_span,
156-
format!(
157-
"this parameter and the {} are declared with different lifetimes...",
158-
return_type
159-
),
160-
format!("...but data{} is {} here", span_label_var1, action),
161-
sub_future,
162-
)
137+
"these two types are declared with different lifetimes...",
138+
);
139+
err.span_label(ty_sub.span, "");
140+
err.span_label(
141+
span,
142+
format!("...but data{} flows{} here", span_label_var1, span_label_var2),
143+
);
163144
}
164-
};
165-
166-
let mut err = struct_span_err!(self.tcx().sess, span, E0623, "lifetime mismatch");
167-
168-
err.span_label(span_1, main_label);
169-
err.span_label(span_2, String::new());
170-
err.span_label(span, span_label);
145+
}
146+
}
171147

172148
self.suggest_adding_lifetime_params(sub, ty_sup, ty_sub, &mut err);
173149

174-
// TODO: This is only helpful if the lifetime more visible in the impl Future type than in the signature.
175-
if let Some(t) = future_return_type {
176-
let snip = self
177-
.tcx()
178-
.sess
179-
.source_map()
180-
.span_to_snippet(t.span)
181-
.ok()
182-
.and_then(|s| match (&t.kind, s.as_str()) {
183-
(rustc_hir::TyKind::Tup(&[]), "") => Some("()".to_string()),
184-
(_, "") => None,
185-
_ => Some(s),
186-
})
187-
.unwrap_or_else(|| "{unnamed_type}".to_string());
188-
189-
err.span_label(
190-
t.span,
191-
&format!("this `async fn` implicitly returns an `impl Future<Output = {}>`", snip),
192-
);
193-
}
194150
err.emit();
195151
Some(ErrorReported)
196152
}

compiler/rustc_infer/src/infer/error_reporting/nice_region_error/util.rs

-53
Original file line numberDiff line numberDiff line change
@@ -94,59 +94,6 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> {
9494
})
9595
}
9696

97-
pub(super) fn future_return_type(
98-
&self,
99-
local_def_id: LocalDefId,
100-
) -> Option<&rustc_hir::Ty<'_>> {
101-
if let Some(hir::IsAsync::Async) = self.asyncness(local_def_id) {
102-
if let rustc_middle::ty::Opaque(def_id, _) =
103-
self.tcx().type_of(local_def_id).fn_sig(self.tcx()).output().skip_binder().kind()
104-
{
105-
match self.tcx().hir().get_if_local(*def_id) {
106-
Some(hir::Node::Item(hir::Item {
107-
kind:
108-
hir::ItemKind::OpaqueTy(hir::OpaqueTy {
109-
bounds,
110-
origin: hir::OpaqueTyOrigin::AsyncFn(..),
111-
..
112-
}),
113-
..
114-
})) => {
115-
for b in bounds.iter() {
116-
if let hir::GenericBound::LangItemTrait(
117-
hir::LangItem::Future,
118-
_span,
119-
_hir_id,
120-
generic_args,
121-
) = b
122-
{
123-
for type_binding in generic_args.bindings.iter() {
124-
if type_binding.ident.name == rustc_span::sym::Output {
125-
if let hir::TypeBindingKind::Equality { ty } =
126-
type_binding.kind
127-
{
128-
return Some(ty);
129-
}
130-
}
131-
}
132-
}
133-
}
134-
}
135-
_ => {}
136-
}
137-
}
138-
}
139-
None
140-
}
141-
142-
pub(super) fn asyncness(&self, local_def_id: LocalDefId) -> Option<hir::IsAsync> {
143-
// similar to the asyncness fn in rustc_ty_utils::ty
144-
let hir_id = self.tcx().hir().local_def_id_to_hir_id(local_def_id);
145-
let node = self.tcx().hir().get(hir_id);
146-
let fn_kind = node.fn_kind()?;
147-
Some(fn_kind.asyncness())
148-
}
149-
15097
// Here, we check for the case where the anonymous region
15198
// is in the return type as written by the user.
15299
// FIXME(#42703) - Need to handle certain cases here.

src/test/ui/async-await/issues/issue-63388-1.stderr

+2-4
Original file line numberDiff line numberDiff line change
@@ -2,14 +2,12 @@ error[E0623]: lifetime mismatch
22
--> $DIR/issue-63388-1.rs:14:9
33
|
44
LL | &'a self, foo: &dyn Foo
5-
| -------- this parameter and the returned future are declared with different lifetimes...
5+
| -------- this parameter and the return type are declared with different lifetimes...
66
LL | ) -> &dyn Foo
77
| --------
8-
| |
9-
| this `async fn` implicitly returns an `impl Future<Output = &dyn Foo>`
108
LL | {
119
LL | foo
12-
| ^^^ ...but data from `foo` is held across an await point here
10+
| ^^^ ...but data from `foo` is returned here
1311

1412
error: aborting due to previous error
1513

src/test/ui/async-await/multiple-lifetimes/ret-impl-trait-one.stderr

+2-3
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,8 @@ error[E0623]: lifetime mismatch
44
LL | async fn async_ret_impl_trait3<'a, 'b>(a: &'a u8, b: &'b u8) -> impl Trait<'a> + 'b {
55
| ------ ^^^^^^^^^^^^^^^^^^^
66
| | |
7-
| | ...but data from `a` is held across an await point here
8-
| | this `async fn` implicitly returns an `impl Future<Output = impl Trait<'a> + 'b>`
9-
| this parameter and the returned future are declared with different lifetimes...
7+
| | ...but data from `a` is returned here
8+
| this parameter and the return type are declared with different lifetimes...
109

1110
error[E0700]: hidden type for `impl Trait` captures lifetime that does not appear in bounds
1211
--> $DIR/ret-impl-trait-one.rs:16:65

src/test/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr

+9-12
Original file line numberDiff line numberDiff line change
@@ -2,28 +2,25 @@ error[E0623]: lifetime mismatch
22
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch-async.rs:8:52
33
|
44
LL | async fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { f }
5-
| ---- ---- ^ ...but data from `f` is held across an await point here
6-
| | |
7-
| | this `async fn` implicitly returns an `impl Future<Output = &Foo>`
8-
| this parameter and the returned future are declared with different lifetimes...
5+
| ---- ---- ^ ...but data from `f` is returned here
6+
| |
7+
| this parameter and the return type are declared with different lifetimes...
98

109
error[E0623]: lifetime mismatch
1110
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch-async.rs:11:82
1211
|
1312
LL | async fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { (self, f) }
14-
| ---- ----------------- ^ ...but data from `f` is held across an await point here
15-
| | |
16-
| | this `async fn` implicitly returns an `impl Future<Output = (Pin<&Foo>, &Foo)>`
17-
| this parameter and the returned future are declared with different lifetimes...
13+
| ---- ----------------- ^ ...but data from `f` is returned here
14+
| |
15+
| this parameter and the return type are declared with different lifetimes...
1816

1917
error[E0623]: lifetime mismatch
2018
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch-async.rs:17:64
2119
|
2220
LL | async fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg }
23-
| ------ --- ^^^ ...but data from `arg` is held across an await point here
24-
| | |
25-
| | this `async fn` implicitly returns an `impl Future<Output = &()>`
26-
| this parameter and the returned future are declared with different lifetimes...
21+
| ------ --- ^^^ ...but data from `arg` is returned here
22+
| |
23+
| this parameter and the return type are declared with different lifetimes...
2724

2825
error: aborting due to 3 previous errors
2926

src/test/ui/self/elision/lt-ref-self-async.stderr

+18-24
Original file line numberDiff line numberDiff line change
@@ -3,66 +3,60 @@ error[E0623]: lifetime mismatch
33
|
44
LL | async fn ref_self(&self, f: &u32) -> &u32 {
55
| ---- ----
6-
| | |
7-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
8-
| this parameter and the returned future are declared with different lifetimes...
6+
| |
7+
| this parameter and the return type are declared with different lifetimes...
98
LL | f
10-
| ^ ...but data from `f` is held across an await point here
9+
| ^ ...but data from `f` is returned here
1110

1211
error[E0623]: lifetime mismatch
1312
--> $DIR/lt-ref-self-async.rs:19:9
1413
|
1514
LL | async fn ref_Self(self: &Self, f: &u32) -> &u32 {
1615
| ---- ----
17-
| | |
18-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
19-
| this parameter and the returned future are declared with different lifetimes...
16+
| |
17+
| this parameter and the return type are declared with different lifetimes...
2018
LL | f
21-
| ^ ...but data from `f` is held across an await point here
19+
| ^ ...but data from `f` is returned here
2220

2321
error[E0623]: lifetime mismatch
2422
--> $DIR/lt-ref-self-async.rs:23:9
2523
|
2624
LL | async fn box_ref_Self(self: Box<&Self>, f: &u32) -> &u32 {
2725
| ---- ----
28-
| | |
29-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
30-
| this parameter and the returned future are declared with different lifetimes...
26+
| |
27+
| this parameter and the return type are declared with different lifetimes...
3128
LL | f
32-
| ^ ...but data from `f` is held across an await point here
29+
| ^ ...but data from `f` is returned here
3330

3431
error[E0623]: lifetime mismatch
3532
--> $DIR/lt-ref-self-async.rs:27:9
3633
|
3734
LL | async fn pin_ref_Self(self: Pin<&Self>, f: &u32) -> &u32 {
3835
| ---- ----
39-
| | |
40-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
41-
| this parameter and the returned future are declared with different lifetimes...
36+
| |
37+
| this parameter and the return type are declared with different lifetimes...
4238
LL | f
43-
| ^ ...but data from `f` is held across an await point here
39+
| ^ ...but data from `f` is returned here
4440

4541
error[E0623]: lifetime mismatch
4642
--> $DIR/lt-ref-self-async.rs:31:9
4743
|
4844
LL | async fn box_box_ref_Self(self: Box<Box<&Self>>, f: &u32) -> &u32 {
4945
| ---- ----
50-
| | |
51-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
52-
| this parameter and the returned future are declared with different lifetimes...
46+
| |
47+
| this parameter and the return type are declared with different lifetimes...
5348
LL | f
54-
| ^ ...but data from `f` is held across an await point here
49+
| ^ ...but data from `f` is returned here
5550

5651
error[E0623]: lifetime mismatch
5752
--> $DIR/lt-ref-self-async.rs:35:9
5853
|
5954
LL | async fn box_pin_Self(self: Box<Pin<&Self>>, f: &u32) -> &u32 {
6055
| ---- ----
61-
| | |
62-
| | this `async fn` implicitly returns an `impl Future<Output = &u32>`
63-
| this parameter and the returned future are declared with different lifetimes...
56+
| |
57+
| this parameter and the return type are declared with different lifetimes...
6458
LL | f
65-
| ^ ...but data from `f` is held across an await point here
59+
| ^ ...but data from `f` is returned here
6660

6761
error: aborting due to 6 previous errors
6862

0 commit comments

Comments
 (0)