Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit 0e6f834

Browse files
committed
Auto merge of rust-lang#129543 - fmease:obj-lt-def-gat, r=<try>
[WIP] Properly deduce object lifetime defaults in GAT paths FIXME: Proper explainer (several things fall out of this PR) Fixes rust-lang#115379. r? ghost
2 parents b8c54d6 + bb92e56 commit 0e6f834

12 files changed

+294
-133
lines changed

compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs

Lines changed: 193 additions & 127 deletions
Large diffs are not rendered by default.

compiler/rustc_metadata/src/rmeta/encoder.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1476,7 +1476,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
14761476
if let Some(name) = tcx.intrinsic(def_id) {
14771477
record!(self.tables.intrinsic[def_id] <- name);
14781478
}
1479-
if let DefKind::TyParam = def_kind {
1479+
if let DefKind::TyParam | DefKind::Trait = def_kind {
14801480
let default = self.tcx.object_lifetime_default(def_id);
14811481
record!(self.tables.object_lifetime_default[def_id] <- default);
14821482
}

compiler/rustc_passes/src/check_attr.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -717,7 +717,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
717717
let hir::GenericParamKind::Type { .. } = p.kind else { continue };
718718
let default = tcx.object_lifetime_default(p.def_id);
719719
let repr = match default {
720-
ObjectLifetimeDefault::Empty => "BaseDefault".to_owned(),
720+
ObjectLifetimeDefault::Empty => "Empty".to_owned(),
721721
ObjectLifetimeDefault::Static => "'static".to_owned(),
722722
ObjectLifetimeDefault::Param(def_id) => tcx.item_name(def_id).to_string(),
723723
ObjectLifetimeDefault::Ambiguous => "Ambiguous".to_owned(),

src/librustdoc/clean/mod.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1994,6 +1994,8 @@ impl<'tcx> ContainerTy<'_, 'tcx> {
19941994
match self {
19951995
Self::Ref(region) => ObjectLifetimeDefault::Arg(region),
19961996
Self::Regular { ty: container, args, arg: index } => {
1997+
// FIXME: Update this to handle AssocTys.
1998+
19971999
let (DefKind::Struct
19982000
| DefKind::Union
19992001
| DefKind::Enum
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
// FIXME: Explainer.
2+
//@ check-pass
3+
4+
trait Outer { type Ty; }
5+
trait Inner {}
6+
7+
impl<'a> Outer for dyn Inner + 'a { type Ty = &'a (); }
8+
9+
fn f<'r>(x: &'r <dyn Inner as Outer>::Ty) { g(x) }
10+
fn g<'r>(x: &'r <dyn Inner + 'static as Outer>::Ty) {}
11+
12+
fn main() {}
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
// FIXME: Explainer
2+
//@ check-pass
3+
4+
// FIXME: Test both bound and where-clause form
5+
// trait Outer<'a> where Self: 'a { type Ty; }
6+
trait Outer<'a>: 'a { type Ty; }
7+
trait Inner {}
8+
9+
impl<'a> Outer<'a> for dyn Inner + 'a { type Ty = &'a (); }
10+
11+
fn f<'r>(x: <dyn Inner + 'r as Outer<'r>>::Ty) { g(x) }
12+
fn g<'r>(x: <dyn Inner as Outer<'r>>::Ty) {}
13+
14+
fn main() {}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
// Properly deduce the object lifetime default in generic associated type (GAT) *paths*.
2+
// issue: <https://github.com/rust-lang/rust/issues/115379>
3+
//@ check-pass
4+
5+
mod own { // the object lifetime default comes from the own generics
6+
trait Outer {
7+
type Ty<'a, T: ?Sized + 'a>;
8+
}
9+
impl Outer for () {
10+
type Ty<'a, T: ?Sized + 'a> = &'a T;
11+
}
12+
trait Inner {}
13+
14+
fn f<'r>(x: <() as Outer>::Ty<'r, dyn Inner + 'r>) { g(x) }
15+
fn g<'r>(_: <() as Outer>::Ty<'r, dyn Inner>) {}
16+
}
17+
18+
mod parent { // the object lifetime default comes from the parent generics
19+
trait Outer<'a> {
20+
type Ty<T: ?Sized + 'a>;
21+
}
22+
impl<'a> Outer<'a> for () {
23+
type Ty<T: ?Sized + 'a> = &'a T;
24+
}
25+
trait Inner {}
26+
27+
fn f<'r>(x: <() as Outer<'r>>::Ty<dyn Inner + 'r>) { g(x) }
28+
fn g<'r>(_: <() as Outer<'r>>::Ty<dyn Inner>) {}
29+
}
30+
31+
fn main() {}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
// FIXME: Explainer
2+
3+
trait Outer { type Ty<'a, T: 'a + ?Sized>; }
4+
trait Inner {}
5+
6+
fn f<'r, T: Outer>(x: T::Ty<'r, dyn Inner>) {}
7+
//~^ ERROR lifetime bound for this object type cannot be deduced from context
8+
9+
fn main() {}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
error[E0228]: the lifetime bound for this object type cannot be deduced from context; please supply an explicit bound
2+
--> $DIR/object-lifetime-default-gat-type-relative.rs:6:33
3+
|
4+
LL | fn f<'r, T: Outer>(x: T::Ty<'r, dyn Inner>) {}
5+
| ^^^^^^^^^
6+
7+
error: aborting due to 1 previous error
8+
9+
For more information about this error, try `rustc --explain E0228`.
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// FIXME: Explainer (used to fail: "inderminate" due to an off by one :^))
2+
//@ check-pass
3+
4+
trait Inner {}
5+
trait Outer<'a, T: 'a + ?Sized> {}
6+
7+
fn bound0<'r, T>() where T: Outer<'r, dyn Inner + 'r> { bound1::<'r, T>() }
8+
fn bound1<'r, T>() where T: Outer<'r, dyn Inner> {}
9+
10+
fn dyn0<'r>(x: Box<dyn Outer<'r, dyn Inner + 'r>>) { dyn1(x) }
11+
fn dyn1<'r>(_: Box<dyn Outer<'r, dyn Inner>>) {}
12+
13+
fn impl0<'r>(x: impl Outer<'r, dyn Inner + 'r>) { impl1(x) }
14+
fn impl1<'r>(_: impl Outer<'r, dyn Inner>) {}
15+
16+
// FIXME(fmease): However, `<Xxx as Outer<'r, dyn Inner>::Yyy` is still "indeterminate"???
17+
18+
fn main() {}

tests/ui/object-lifetime/object-lifetime-default.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,13 @@
22

33
#[rustc_object_lifetime_default]
44
struct A<
5-
T, //~ ERROR BaseDefault
5+
T, //~ ERROR Empty
66
>(T);
77

88
#[rustc_object_lifetime_default]
99
struct B<
1010
'a,
11-
T, //~ ERROR BaseDefault
11+
T, //~ ERROR Empty
1212
>(&'a (), T);
1313

1414
#[rustc_object_lifetime_default]

tests/ui/object-lifetime/object-lifetime-default.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
1-
error: BaseDefault
1+
error: Empty
22
--> $DIR/object-lifetime-default.rs:5:5
33
|
44
LL | T,
55
| ^
66

7-
error: BaseDefault
7+
error: Empty
88
--> $DIR/object-lifetime-default.rs:11:5
99
|
1010
LL | T,

0 commit comments

Comments
 (0)