Skip to content

Commit 36076ec

Browse files
compiler-errorsworkingjubilee
authored andcommitted
Clarify implicit captures for RPITIT
1 parent a7dc987 commit 36076ec

File tree

4 files changed

+30
-11
lines changed

4 files changed

+30
-11
lines changed

Diff for: compiler/rustc_hir_analysis/messages.ftl

+3
Original file line numberDiff line numberDiff line change
@@ -259,6 +259,9 @@ hir_analysis_late_bound_lifetime_in_apit = `impl Trait` can only mention lifetim
259259
hir_analysis_late_bound_type_in_apit = `impl Trait` can only mention type parameters from an fn or impl
260260
.label = type parameter declared here
261261
262+
hir_analysis_lifetime_implicitly_captured = `impl Trait` captures lifetime parameter, but it is not mentioned in `use<...>` precise captures list
263+
.param_label = all lifetime parameters originating from a trait are captured implicitly
264+
262265
hir_analysis_lifetime_must_be_first = lifetime parameter `{$name}` must be listed before non-lifetime parameters
263266
.label = move the lifetime before this parameter
264267

Diff for: compiler/rustc_hir_analysis/src/check/check.rs

+16-9
Original file line numberDiff line numberDiff line change
@@ -589,15 +589,22 @@ fn check_opaque_precise_captures<'tcx>(tcx: TyCtxt<'tcx>, opaque_def_id: LocalDe
589589
param_span: tcx.def_span(def_id),
590590
});
591591
} else {
592-
// If the `use_span` is actually just the param itself, then we must
593-
// have not duplicated the lifetime but captured the original.
594-
// The "effective" `use_span` will be the span of the opaque itself,
595-
// and the param span will be the def span of the param.
596-
tcx.dcx().emit_err(errors::LifetimeNotCaptured {
597-
opaque_span,
598-
use_span: opaque_span,
599-
param_span: use_span,
600-
});
592+
if tcx.def_kind(tcx.parent(param.def_id)) == DefKind::Trait {
593+
tcx.dcx().emit_err(errors::LifetimeImplicitlyCaptured {
594+
opaque_span,
595+
param_span: tcx.def_span(param.def_id),
596+
});
597+
} else {
598+
// If the `use_span` is actually just the param itself, then we must
599+
// have not duplicated the lifetime but captured the original.
600+
// The "effective" `use_span` will be the span of the opaque itself,
601+
// and the param span will be the def span of the param.
602+
tcx.dcx().emit_err(errors::LifetimeNotCaptured {
603+
opaque_span,
604+
use_span: opaque_span,
605+
param_span: use_span,
606+
});
607+
}
601608
}
602609
continue;
603610
}

Diff for: compiler/rustc_hir_analysis/src/errors/precise_captures.rs

+9
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,15 @@ pub(crate) struct LifetimeNotCaptured {
3434
pub opaque_span: Span,
3535
}
3636

37+
#[derive(Diagnostic)]
38+
#[diag(hir_analysis_lifetime_implicitly_captured)]
39+
pub(crate) struct LifetimeImplicitlyCaptured {
40+
#[primary_span]
41+
pub opaque_span: Span,
42+
#[label(hir_analysis_param_label)]
43+
pub param_span: Span,
44+
}
45+
3746
#[derive(Diagnostic)]
3847
#[diag(hir_analysis_bad_precise_capture)]
3948
pub(crate) struct BadPreciseCapture {

Diff for: tests/ui/impl-trait/precise-capturing/rpitit.stderr

+2-2
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ error: `impl Trait` captures lifetime parameter, but it is not mentioned in `use
22
--> $DIR/rpitit.rs:11:19
33
|
44
LL | trait TraitLt<'a: 'a> {
5-
| -- this lifetime parameter is captured
5+
| -- all lifetime parameters originating from a trait are captured implicitly
66
LL | fn hello() -> impl Sized + use<Self>;
7-
| ^^^^^^^^^^^^^^^^^^^^^^ lifetime captured due to being mentioned in the bounds of the `impl Trait`
7+
| ^^^^^^^^^^^^^^^^^^^^^^
88

99
error: lifetime may not live long enough
1010
--> $DIR/rpitit.rs:15:5

0 commit comments

Comments
 (0)