Remove the distinction between LifetimeName::Implicit and LifetimeName::Underscore.
This commit is contained in:
parent
a2254d5d7c
commit
ab63591f00
7 changed files with 21 additions and 63 deletions
|
@ -1883,7 +1883,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
}
|
}
|
||||||
hir::LifetimeName::Param(param, ParamName::Fresh)
|
hir::LifetimeName::Param(param, ParamName::Fresh)
|
||||||
}
|
}
|
||||||
LifetimeRes::Anonymous { binder, elided } => {
|
LifetimeRes::Anonymous { binder } => {
|
||||||
let mut l_name = None;
|
let mut l_name = None;
|
||||||
if let Some(mut captured_lifetimes) = self.captured_lifetimes.take() {
|
if let Some(mut captured_lifetimes) = self.captured_lifetimes.take() {
|
||||||
if !captured_lifetimes.binders_to_ignore.contains(&binder) {
|
if !captured_lifetimes.binders_to_ignore.contains(&binder) {
|
||||||
|
@ -1900,11 +1900,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
}
|
}
|
||||||
self.captured_lifetimes = Some(captured_lifetimes);
|
self.captured_lifetimes = Some(captured_lifetimes);
|
||||||
};
|
};
|
||||||
l_name.unwrap_or(if elided {
|
l_name.unwrap_or(hir::LifetimeName::Underscore)
|
||||||
hir::LifetimeName::Implicit
|
|
||||||
} else {
|
|
||||||
hir::LifetimeName::Underscore
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
LifetimeRes::Static => hir::LifetimeName::Static,
|
LifetimeRes::Static => hir::LifetimeName::Static,
|
||||||
LifetimeRes::Error => hir::LifetimeName::Error,
|
LifetimeRes::Error => hir::LifetimeName::Error,
|
||||||
|
|
|
@ -589,7 +589,6 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
|
||||||
|
|
||||||
hir::LifetimeName::Param(_, hir::ParamName::Fresh)
|
hir::LifetimeName::Param(_, hir::ParamName::Fresh)
|
||||||
| hir::LifetimeName::ImplicitObjectLifetimeDefault
|
| hir::LifetimeName::ImplicitObjectLifetimeDefault
|
||||||
| hir::LifetimeName::Implicit
|
|
||||||
| hir::LifetimeName::Underscore => {
|
| hir::LifetimeName::Underscore => {
|
||||||
// In this case, the user left off the lifetime; so
|
// In this case, the user left off the lifetime; so
|
||||||
// they wrote something like:
|
// they wrote something like:
|
||||||
|
|
|
@ -742,8 +742,6 @@ pub enum LifetimeRes {
|
||||||
Anonymous {
|
Anonymous {
|
||||||
/// Id of the introducing place. See `Param`.
|
/// Id of the introducing place. See `Param`.
|
||||||
binder: NodeId,
|
binder: NodeId,
|
||||||
/// Whether this lifetime was spelled or elided.
|
|
||||||
elided: bool,
|
|
||||||
},
|
},
|
||||||
/// Explicit `'static` lifetime.
|
/// Explicit `'static` lifetime.
|
||||||
Static,
|
Static,
|
||||||
|
|
|
@ -90,9 +90,6 @@ pub enum LifetimeName {
|
||||||
/// User-given names or fresh (synthetic) names.
|
/// User-given names or fresh (synthetic) names.
|
||||||
Param(LocalDefId, ParamName),
|
Param(LocalDefId, ParamName),
|
||||||
|
|
||||||
/// User wrote nothing (e.g., the lifetime in `&u32`).
|
|
||||||
Implicit,
|
|
||||||
|
|
||||||
/// Implicit lifetime in a context like `dyn Foo`. This is
|
/// Implicit lifetime in a context like `dyn Foo`. This is
|
||||||
/// distinguished from implicit lifetimes elsewhere because the
|
/// distinguished from implicit lifetimes elsewhere because the
|
||||||
/// lifetime that they default to must appear elsewhere within the
|
/// lifetime that they default to must appear elsewhere within the
|
||||||
|
@ -110,7 +107,7 @@ pub enum LifetimeName {
|
||||||
/// that was already reported.
|
/// that was already reported.
|
||||||
Error,
|
Error,
|
||||||
|
|
||||||
/// User wrote specifies `'_`.
|
/// User wrote an anonymous lifetime, either `'_` or nothing.
|
||||||
Underscore,
|
Underscore,
|
||||||
|
|
||||||
/// User wrote `'static`.
|
/// User wrote `'static`.
|
||||||
|
@ -120,9 +117,7 @@ pub enum LifetimeName {
|
||||||
impl LifetimeName {
|
impl LifetimeName {
|
||||||
pub fn ident(&self) -> Ident {
|
pub fn ident(&self) -> Ident {
|
||||||
match *self {
|
match *self {
|
||||||
LifetimeName::ImplicitObjectLifetimeDefault
|
LifetimeName::ImplicitObjectLifetimeDefault | LifetimeName::Error => Ident::empty(),
|
||||||
| LifetimeName::Implicit
|
|
||||||
| LifetimeName::Error => Ident::empty(),
|
|
||||||
LifetimeName::Underscore => Ident::with_dummy_span(kw::UnderscoreLifetime),
|
LifetimeName::Underscore => Ident::with_dummy_span(kw::UnderscoreLifetime),
|
||||||
LifetimeName::Static => Ident::with_dummy_span(kw::StaticLifetime),
|
LifetimeName::Static => Ident::with_dummy_span(kw::StaticLifetime),
|
||||||
LifetimeName::Param(_, param_name) => param_name.ident(),
|
LifetimeName::Param(_, param_name) => param_name.ident(),
|
||||||
|
@ -132,7 +127,6 @@ impl LifetimeName {
|
||||||
pub fn is_anonymous(&self) -> bool {
|
pub fn is_anonymous(&self) -> bool {
|
||||||
match *self {
|
match *self {
|
||||||
LifetimeName::ImplicitObjectLifetimeDefault
|
LifetimeName::ImplicitObjectLifetimeDefault
|
||||||
| LifetimeName::Implicit
|
|
||||||
| LifetimeName::Underscore
|
| LifetimeName::Underscore
|
||||||
| LifetimeName::Param(_, ParamName::Fresh)
|
| LifetimeName::Param(_, ParamName::Fresh)
|
||||||
| LifetimeName::Error => true,
|
| LifetimeName::Error => true,
|
||||||
|
@ -142,9 +136,7 @@ impl LifetimeName {
|
||||||
|
|
||||||
pub fn is_elided(&self) -> bool {
|
pub fn is_elided(&self) -> bool {
|
||||||
match self {
|
match self {
|
||||||
LifetimeName::ImplicitObjectLifetimeDefault
|
LifetimeName::ImplicitObjectLifetimeDefault | LifetimeName::Underscore => true,
|
||||||
| LifetimeName::Implicit
|
|
||||||
| LifetimeName::Underscore => true,
|
|
||||||
|
|
||||||
// It might seem surprising that `Fresh` counts as
|
// It might seem surprising that `Fresh` counts as
|
||||||
// *not* elided -- but this is because, as far as the code
|
// *not* elided -- but this is because, as far as the code
|
||||||
|
|
|
@ -496,7 +496,6 @@ pub fn walk_lifetime<'v, V: Visitor<'v>>(visitor: &mut V, lifetime: &'v Lifetime
|
||||||
| LifetimeName::Param(_, ParamName::Error)
|
| LifetimeName::Param(_, ParamName::Error)
|
||||||
| LifetimeName::Static
|
| LifetimeName::Static
|
||||||
| LifetimeName::Error
|
| LifetimeName::Error
|
||||||
| LifetimeName::Implicit
|
|
||||||
| LifetimeName::ImplicitObjectLifetimeDefault
|
| LifetimeName::ImplicitObjectLifetimeDefault
|
||||||
| LifetimeName::Underscore => {}
|
| LifetimeName::Underscore => {}
|
||||||
}
|
}
|
||||||
|
|
|
@ -262,9 +262,6 @@ enum LifetimeRibKind {
|
||||||
/// error on default object bounds (e.g., `Box<dyn Foo>`).
|
/// error on default object bounds (e.g., `Box<dyn Foo>`).
|
||||||
AnonymousReportError,
|
AnonymousReportError,
|
||||||
|
|
||||||
/// Pass responsibility to `resolve_lifetime` code for all cases.
|
|
||||||
AnonymousPassThrough(NodeId),
|
|
||||||
|
|
||||||
/// Replace all anonymous lifetimes by provided lifetime.
|
/// Replace all anonymous lifetimes by provided lifetime.
|
||||||
Elided(LifetimeRes),
|
Elided(LifetimeRes),
|
||||||
|
|
||||||
|
@ -868,7 +865,7 @@ impl<'a: 'ast, 'ast> Visitor<'ast> for LateResolutionVisitor<'a, '_, 'ast> {
|
||||||
let previous_state = replace(&mut this.in_func_body, true);
|
let previous_state = replace(&mut this.in_func_body, true);
|
||||||
// Resolve the function body, potentially inside the body of an async closure
|
// Resolve the function body, potentially inside the body of an async closure
|
||||||
this.with_lifetime_rib(
|
this.with_lifetime_rib(
|
||||||
LifetimeRibKind::AnonymousPassThrough(fn_id),
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous { binder: fn_id }),
|
||||||
|this| this.visit_block(body),
|
|this| this.visit_block(body),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -896,7 +893,9 @@ impl<'a: 'ast, 'ast> Visitor<'ast> for LateResolutionVisitor<'a, '_, 'ast> {
|
||||||
this.with_lifetime_rib(
|
this.with_lifetime_rib(
|
||||||
match binder {
|
match binder {
|
||||||
ClosureBinder::NotPresent => {
|
ClosureBinder::NotPresent => {
|
||||||
LifetimeRibKind::AnonymousPassThrough(fn_id)
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous {
|
||||||
|
binder: fn_id,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
ClosureBinder::For { .. } => LifetimeRibKind::AnonymousReportError,
|
ClosureBinder::For { .. } => LifetimeRibKind::AnonymousReportError,
|
||||||
},
|
},
|
||||||
|
@ -908,7 +907,7 @@ impl<'a: 'ast, 'ast> Visitor<'ast> for LateResolutionVisitor<'a, '_, 'ast> {
|
||||||
let previous_state = replace(&mut this.in_func_body, true);
|
let previous_state = replace(&mut this.in_func_body, true);
|
||||||
// Resolve the function body, potentially inside the body of an async closure
|
// Resolve the function body, potentially inside the body of an async closure
|
||||||
this.with_lifetime_rib(
|
this.with_lifetime_rib(
|
||||||
LifetimeRibKind::AnonymousPassThrough(fn_id),
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous { binder: fn_id }),
|
||||||
|this| this.visit_expr(body),
|
|this| this.visit_expr(body),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -1053,8 +1052,7 @@ impl<'a: 'ast, 'ast> Visitor<'ast> for LateResolutionVisitor<'a, '_, 'ast> {
|
||||||
visit::walk_generic_args(self, path_span, args);
|
visit::walk_generic_args(self, path_span, args);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
LifetimeRibKind::AnonymousPassThrough(..)
|
LifetimeRibKind::AnonymousCreateParameter { .. }
|
||||||
| LifetimeRibKind::AnonymousCreateParameter { .. }
|
|
||||||
| LifetimeRibKind::AnonymousReportError
|
| LifetimeRibKind::AnonymousReportError
|
||||||
| LifetimeRibKind::Elided(_)
|
| LifetimeRibKind::Elided(_)
|
||||||
| LifetimeRibKind::ElisionFailure
|
| LifetimeRibKind::ElisionFailure
|
||||||
|
@ -1415,8 +1413,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
| LifetimeRibKind::AnonymousReportError
|
| LifetimeRibKind::AnonymousReportError
|
||||||
| LifetimeRibKind::ElisionFailure => Some(LifetimeUseSet::Many),
|
| LifetimeRibKind::ElisionFailure => Some(LifetimeUseSet::Many),
|
||||||
// An anonymous lifetime is legal here, go ahead.
|
// An anonymous lifetime is legal here, go ahead.
|
||||||
LifetimeRibKind::AnonymousPassThrough(_)
|
LifetimeRibKind::AnonymousCreateParameter { .. } => {
|
||||||
| LifetimeRibKind::AnonymousCreateParameter { .. } => {
|
|
||||||
Some(LifetimeUseSet::One { use_span: ident.span, use_ctxt })
|
Some(LifetimeUseSet::One { use_span: ident.span, use_ctxt })
|
||||||
}
|
}
|
||||||
// Only report if eliding the lifetime would have the same
|
// Only report if eliding the lifetime would have the same
|
||||||
|
@ -1527,14 +1524,6 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
self.record_lifetime_res(lifetime.id, LifetimeRes::Error, elision_candidate);
|
self.record_lifetime_res(lifetime.id, LifetimeRes::Error, elision_candidate);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
LifetimeRibKind::AnonymousPassThrough(node_id) => {
|
|
||||||
self.record_lifetime_res(
|
|
||||||
lifetime.id,
|
|
||||||
LifetimeRes::Anonymous { binder: node_id, elided },
|
|
||||||
elision_candidate,
|
|
||||||
);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
LifetimeRibKind::Elided(res) => {
|
LifetimeRibKind::Elided(res) => {
|
||||||
self.record_lifetime_res(lifetime.id, res, elision_candidate);
|
self.record_lifetime_res(lifetime.id, res, elision_candidate);
|
||||||
return;
|
return;
|
||||||
|
@ -1658,8 +1647,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
// Do not create a parameter for patterns and expressions.
|
// Do not create a parameter for patterns and expressions.
|
||||||
for rib in self.lifetime_ribs.iter().rev() {
|
for rib in self.lifetime_ribs.iter().rev() {
|
||||||
match rib.kind {
|
match rib.kind {
|
||||||
LifetimeRibKind::AnonymousPassThrough(binder) => {
|
LifetimeRibKind::Elided(res @ LifetimeRes::Anonymous { .. }) => {
|
||||||
let res = LifetimeRes::Anonymous { binder, elided: true };
|
|
||||||
for id in node_ids {
|
for id in node_ids {
|
||||||
self.record_lifetime_res(id, res, LifetimeElisionCandidate::Named);
|
self.record_lifetime_res(id, res, LifetimeElisionCandidate::Named);
|
||||||
}
|
}
|
||||||
|
@ -1673,8 +1661,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
// FIXME(cjgillot) This resolution is wrong, but this does not matter
|
// FIXME(cjgillot) This resolution is wrong, but this does not matter
|
||||||
// since these cases are erroneous anyway. Lifetime resolution should
|
// since these cases are erroneous anyway. Lifetime resolution should
|
||||||
// emit a "missing lifetime specifier" diagnostic.
|
// emit a "missing lifetime specifier" diagnostic.
|
||||||
let res =
|
let res = LifetimeRes::Anonymous { binder: DUMMY_NODE_ID };
|
||||||
LifetimeRes::Anonymous { binder: DUMMY_NODE_ID, elided: true };
|
|
||||||
for id in node_ids {
|
for id in node_ids {
|
||||||
self.record_lifetime_res(id, res, LifetimeElisionCandidate::Named);
|
self.record_lifetime_res(id, res, LifetimeElisionCandidate::Named);
|
||||||
}
|
}
|
||||||
|
@ -1753,19 +1740,6 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// `PassThrough` is the normal case.
|
|
||||||
LifetimeRibKind::AnonymousPassThrough(binder) => {
|
|
||||||
let res = LifetimeRes::Anonymous { binder, elided: true };
|
|
||||||
let mut candidate = LifetimeElisionCandidate::Missing(missing_lifetime);
|
|
||||||
for id in node_ids {
|
|
||||||
self.record_lifetime_res(
|
|
||||||
id,
|
|
||||||
res,
|
|
||||||
replace(&mut candidate, LifetimeElisionCandidate::Ignore),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
LifetimeRibKind::Elided(res) => {
|
LifetimeRibKind::Elided(res) => {
|
||||||
let mut candidate = LifetimeElisionCandidate::Missing(missing_lifetime);
|
let mut candidate = LifetimeElisionCandidate::Missing(missing_lifetime);
|
||||||
for id in node_ids {
|
for id in node_ids {
|
||||||
|
@ -2272,7 +2246,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
this.visit_ty(ty);
|
this.visit_ty(ty);
|
||||||
});
|
});
|
||||||
this.with_lifetime_rib(
|
this.with_lifetime_rib(
|
||||||
LifetimeRibKind::AnonymousPassThrough(item.id),
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous { binder: item.id }),
|
||||||
|this| {
|
|this| {
|
||||||
if let Some(expr) = expr {
|
if let Some(expr) = expr {
|
||||||
let constant_item_kind = match item.kind {
|
let constant_item_kind = match item.kind {
|
||||||
|
@ -2547,7 +2521,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
// Type parameters can already be used and as associated consts are
|
// Type parameters can already be used and as associated consts are
|
||||||
// not used as part of the type system, this is far less surprising.
|
// not used as part of the type system, this is far less surprising.
|
||||||
self.with_lifetime_rib(
|
self.with_lifetime_rib(
|
||||||
LifetimeRibKind::AnonymousPassThrough(item.id),
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous { binder: item.id }),
|
||||||
|this| {
|
|this| {
|
||||||
this.with_constant_rib(
|
this.with_constant_rib(
|
||||||
IsRepeatExpr::No,
|
IsRepeatExpr::No,
|
||||||
|
@ -2721,7 +2695,7 @@ impl<'a: 'ast, 'b, 'ast> LateResolutionVisitor<'a, 'b, 'ast> {
|
||||||
// Type parameters can already be used and as associated consts are
|
// Type parameters can already be used and as associated consts are
|
||||||
// not used as part of the type system, this is far less surprising.
|
// not used as part of the type system, this is far less surprising.
|
||||||
self.with_lifetime_rib(
|
self.with_lifetime_rib(
|
||||||
LifetimeRibKind::AnonymousPassThrough(item.id),
|
LifetimeRibKind::Elided(LifetimeRes::Anonymous { binder: item.id }),
|
||||||
|this| {
|
|this| {
|
||||||
this.with_constant_rib(
|
this.with_constant_rib(
|
||||||
IsRepeatExpr::No,
|
IsRepeatExpr::No,
|
||||||
|
|
|
@ -819,7 +819,7 @@ impl<'a, 'tcx> Visitor<'tcx> for LifetimeContext<'a, 'tcx> {
|
||||||
// `Box<dyn Debug + 'static>`.
|
// `Box<dyn Debug + 'static>`.
|
||||||
self.resolve_object_lifetime_default(lifetime)
|
self.resolve_object_lifetime_default(lifetime)
|
||||||
}
|
}
|
||||||
LifetimeName::Implicit | LifetimeName::Underscore => {
|
LifetimeName::Underscore => {
|
||||||
// If the user writes `'_`, we use the *ordinary* elision
|
// If the user writes `'_`, we use the *ordinary* elision
|
||||||
// rules. So the `'_` in e.g., `Box<dyn Debug + '_>` will be
|
// rules. So the `'_` in e.g., `Box<dyn Debug + '_>` will be
|
||||||
// resolved the same as the `'_` in `&'_ Foo`.
|
// resolved the same as the `'_` in `&'_ Foo`.
|
||||||
|
@ -1135,9 +1135,9 @@ impl<'a, 'tcx> Visitor<'tcx> for LifetimeContext<'a, 'tcx> {
|
||||||
#[tracing::instrument(level = "debug", skip(self))]
|
#[tracing::instrument(level = "debug", skip(self))]
|
||||||
fn visit_lifetime(&mut self, lifetime_ref: &'tcx hir::Lifetime) {
|
fn visit_lifetime(&mut self, lifetime_ref: &'tcx hir::Lifetime) {
|
||||||
match lifetime_ref.name {
|
match lifetime_ref.name {
|
||||||
hir::LifetimeName::ImplicitObjectLifetimeDefault
|
hir::LifetimeName::ImplicitObjectLifetimeDefault | hir::LifetimeName::Underscore => {
|
||||||
| hir::LifetimeName::Implicit
|
self.resolve_elided_lifetimes(&[lifetime_ref])
|
||||||
| hir::LifetimeName::Underscore => self.resolve_elided_lifetimes(&[lifetime_ref]),
|
}
|
||||||
hir::LifetimeName::Static => self.insert_lifetime(lifetime_ref, Region::Static),
|
hir::LifetimeName::Static => self.insert_lifetime(lifetime_ref, Region::Static),
|
||||||
hir::LifetimeName::Param(param_def_id, _) => {
|
hir::LifetimeName::Param(param_def_id, _) => {
|
||||||
self.resolve_lifetime_ref(param_def_id, lifetime_ref)
|
self.resolve_lifetime_ref(param_def_id, lifetime_ref)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue