Skip to content

Commit be5a45d

Browse files
committed
fix struct path
1 parent 34329d6 commit be5a45d

File tree

8 files changed

+137
-48
lines changed

8 files changed

+137
-48
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4134,6 +4134,7 @@ dependencies = [
41344134
name = "rustc_hir_typeck"
41354135
version = "0.1.0"
41364136
dependencies = [
4137+
"either",
41374138
"rustc_ast",
41384139
"rustc_data_structures",
41394140
"rustc_errors",

compiler/rustc_hir_typeck/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ edition = "2021"
88
[dependencies]
99
smallvec = { version = "1.8.1", features = ["union", "may_dangle"] }
1010
tracing = "0.1"
11+
either = "1.5.0"
1112
rustc_ast = { path = "../rustc_ast" }
1213
rustc_data_structures = { path = "../rustc_data_structures" }
1314
rustc_errors = { path = "../rustc_errors" }

compiler/rustc_hir_typeck/src/fn_ctxt/checks.rs

Lines changed: 28 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@ use rustc_span::symbol::{kw, Ident};
3232
use rustc_span::{self, sym, Span};
3333
use rustc_trait_selection::traits::{self, ObligationCauseCode, SelectionContext};
3434

35+
use either::Either;
36+
3537
use std::iter;
3638
use std::mem;
3739
use std::ops::ControlFlow;
@@ -1231,28 +1233,44 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
12311233
);
12321234
return None;
12331235
}
1234-
Res::Def(DefKind::Variant, _) => match ty.normalized.kind() {
1235-
ty::Adt(adt, substs) => Some((adt.variant_of_res(def), adt.did(), substs)),
1236+
Res::Def(DefKind::Variant, _) => match (ty.raw.kind(), ty.normalized.kind()) {
1237+
(ty::Adt(adt, substs), _) => {
1238+
Some((adt.variant_of_res(def), adt.did(), substs, Either::Left(substs)))
1239+
}
1240+
(_, ty::Adt(adt, substs)) => {
1241+
Some((adt.variant_of_res(def), adt.did(), substs, Either::Right(ty.raw)))
1242+
}
12361243
_ => bug!("unexpected type: {:?}", ty.normalized),
12371244
},
12381245
Res::Def(DefKind::Struct | DefKind::Union | DefKind::TyAlias | DefKind::AssocTy, _)
12391246
| Res::SelfTyParam { .. }
1240-
| Res::SelfTyAlias { .. } => match ty.normalized.kind() {
1241-
ty::Adt(adt, substs) if !adt.is_enum() => {
1242-
Some((adt.non_enum_variant(), adt.did(), substs))
1247+
| Res::SelfTyAlias { .. } => match (ty.raw.kind(), ty.normalized.kind()) {
1248+
(ty::Adt(adt, substs), _) if !adt.is_enum() => {
1249+
Some((adt.non_enum_variant(), adt.did(), substs, Either::Left(substs)))
1250+
}
1251+
(_, ty::Adt(adt, substs)) if !adt.is_enum() => {
1252+
Some((adt.non_enum_variant(), adt.did(), substs, Either::Right(ty.raw)))
12431253
}
12441254
_ => None,
12451255
},
12461256
_ => bug!("unexpected definition: {:?}", def),
12471257
};
12481258

1249-
if let Some((variant, did, substs)) = variant {
1259+
if let Some((variant, did, substs, user_annotation)) = variant {
12501260
debug!("check_struct_path: did={:?} substs={:?}", did, substs);
12511261

1252-
// FIXME(aliemjay): We're using UserSelfTy unconditionally here because it is the only
1253-
// way to register the raw user ty, because `substs` is normalized.
1254-
let self_ty = ty::UserSelfTy { impl_def_id: did, self_ty: ty.raw };
1255-
self.write_user_type_annotation_from_substs(hir_id, did, substs, Some(self_ty));
1262+
// Register type annotation.
1263+
self.probe(|_| {
1264+
// UserSubsts and UserSelfTy are mutually exclusive here.
1265+
let (user_substs, self_ty) = match user_annotation {
1266+
Either::Left(substs) => (*substs, None),
1267+
Either::Right(self_ty) => {
1268+
(self.fresh_substs_for_item(path_span, did), Some(self_ty))
1269+
}
1270+
};
1271+
let self_ty = self_ty.map(|self_ty| ty::UserSelfTy { impl_def_id: did, self_ty });
1272+
self.write_user_type_annotation_from_substs(hir_id, did, user_substs, self_ty);
1273+
});
12561274

12571275
// Check bounds on type arguments used in the path.
12581276
self.add_required_obligations_for_hir(path_span, did, substs, hir_id);

src/test/ui/const-generics/issue-97007.rs

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,4 @@
1-
//~ ERROR broken MIR
2-
3-
// known-bug
4-
// failure-status: 101
5-
// rustc-env: RUSTC_BACKTRACE=0
1+
// check-pass
62

73
#![feature(adt_const_params, generic_const_exprs)]
84
#![allow(incomplete_features)]

src/test/ui/nll/user-annotations/dump-adt-brace-struct.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,8 @@ struct SomeStruct<T> { t: T }
1111
#[rustc_dump_user_substs]
1212
fn main() {
1313
SomeStruct { t: 22 }; // Nothing given, no annotation.
14-
//~^ ERROR SomeStruct<^0>
1514

1615
SomeStruct::<_> { t: 22 }; // Nothing interesting given, no annotation.
17-
//~^ ERROR SomeStruct<^0>
1816

1917
SomeStruct::<u32> { t: 22 }; // No lifetime bounds given.
2018

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,8 @@
1-
error: user substs: UserSubsts { substs: [^0], user_self_ty: Some(UserSelfTy { impl_def_id: DefId(0:3 ~ dump_adt_brace_struct[4679]::SomeStruct), self_ty: SomeStruct<^0> }) }
2-
--> $DIR/dump-adt-brace-struct.rs:13:5
3-
|
4-
LL | SomeStruct { t: 22 }; // Nothing given, no annotation.
5-
| ^^^^^^^^^^^^^^^^^^^^
6-
7-
error: user substs: UserSubsts { substs: [^0], user_self_ty: Some(UserSelfTy { impl_def_id: DefId(0:3 ~ dump_adt_brace_struct[4679]::SomeStruct), self_ty: SomeStruct<^0> }) }
8-
--> $DIR/dump-adt-brace-struct.rs:16:5
9-
|
10-
LL | SomeStruct::<_> { t: 22 }; // Nothing interesting given, no annotation.
11-
| ^^^^^^^^^^^^^^^^^^^^^^^^^
12-
13-
error: user substs: UserSubsts { substs: [&ReStatic u32], user_self_ty: Some(UserSelfTy { impl_def_id: DefId(0:3 ~ dump_adt_brace_struct[4679]::SomeStruct), self_ty: SomeStruct<&ReStatic u32> }) }
14-
--> $DIR/dump-adt-brace-struct.rs:21:5
1+
error: user substs: UserSubsts { substs: [&ReStatic u32], user_self_ty: None }
2+
--> $DIR/dump-adt-brace-struct.rs:19:5
153
|
164
LL | SomeStruct::<&'static u32> { t: &22 };
175
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
186

19-
error: aborting due to 3 previous errors
7+
error: aborting due to previous error
208

src/test/ui/nll/user-annotations/normalization-2.rs

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ enum MyTy<T> {
2424

2525
impl<T> MyTy<T> {
2626
fn method<X>() {}
27+
fn method2<X>(&self) {}
2728
}
2829

2930
type Ty<'a> = <&'a () as Trait>::Assoc;
@@ -45,6 +46,9 @@ fn test_path<'a, 'b, 'c, 'd>() {
4546
//~^ ERROR lifetime may not live long enough
4647
<Ty<'static>>::method::<Ty<'b>>;
4748
//~^ ERROR lifetime may not live long enough
49+
50+
MyTy::Unit::<Ty<'c>>;
51+
//~^ ERROR lifetime may not live long enough
4852
}
4953

5054
fn test_call<'a, 'b, 'c>() {
@@ -55,14 +59,44 @@ fn test_call<'a, 'b, 'c>() {
5559
}
5660

5761
fn test_variants<'a, 'b, 'c>() {
58-
<Ty<'a>>::Struct {}; //TODO
62+
<Ty<'a>>::Struct {};
5963
//~^ ERROR lifetime may not live long enough
6064
<Ty<'b>>::Tuple();
6165
//~^ ERROR lifetime may not live long enough
6266
<Ty<'c>>::Unit;
6367
//~^ ERROR lifetime may not live long enough
6468
}
6569

70+
fn test_method_call<'a>(x: MyTy<()>) {
71+
// FIXME This should fail.
72+
x.method2::<Ty<'a>>();
73+
}
74+
75+
fn test_struct_path<'a, 'b, 'c, 'd>() {
76+
struct Struct<T> { x: Option<T>, }
77+
78+
trait Project {
79+
type Struct;
80+
type Enum;
81+
}
82+
impl<T> Project for T {
83+
type Struct = Struct<()>;
84+
type Enum = MyTy<()>;
85+
}
86+
87+
// Resolves to enum variant
88+
MyTy::<Ty<'a>>::Struct {}; // without SelfTy
89+
//~^ ERROR lifetime may not live long enough
90+
<Ty<'b> as Project>::Enum::Struct {}; // with SelfTy
91+
//~^ ERROR lifetime may not live long enough
92+
93+
// Resolves to struct and associated type respectively
94+
Struct::<Ty<'c>> { x: None, }; // without SelfTy
95+
//~^ ERROR lifetime may not live long enough
96+
<Ty<'d> as Project>::Struct { x: None, }; // with SelfTy
97+
//~^ ERROR lifetime may not live long enough
98+
}
99+
66100
fn test_pattern<'a, 'b, 'c>() {
67101
use MyTy::*;
68102
match MyTy::Unit {

src/test/ui/nll/user-annotations/normalization-2.stderr

Lines changed: 68 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,21 @@
11
error: lifetime may not live long enough
2-
--> $DIR/normalization-2.rs:32:12
2+
--> $DIR/normalization-2.rs:33:12
33
|
44
LL | fn test_local<'a>() {
55
| -- lifetime `'a` defined here
66
LL | let _: Ty<'a> = MyTy::Unit;
77
| ^^^^^^ requires that `'a` must outlive `'static`
88

99
error: lifetime may not live long enough
10-
--> $DIR/normalization-2.rs:37:6
10+
--> $DIR/normalization-2.rs:38:6
1111
|
1212
LL | fn test_closure_sig<'a, 'b>() {
1313
| -- lifetime `'a` defined here
1414
LL | |_: Ty<'a>| {};
1515
| ^ requires that `'a` must outlive `'static`
1616

1717
error: lifetime may not live long enough
18-
--> $DIR/normalization-2.rs:39:11
18+
--> $DIR/normalization-2.rs:40:11
1919
|
2020
LL | fn test_closure_sig<'a, 'b>() {
2121
| -- lifetime `'b` defined here
@@ -29,37 +29,47 @@ help: the following changes may resolve your lifetime errors
2929
= help: replace `'b` with `'static`
3030

3131
error: lifetime may not live long enough
32-
--> $DIR/normalization-2.rs:44:5
32+
--> $DIR/normalization-2.rs:45:5
3333
|
3434
LL | fn test_path<'a, 'b, 'c, 'd>() {
3535
| -- lifetime `'a` defined here
3636
LL | <Ty<'a>>::method::<Ty<'static>>;
3737
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'a` must outlive `'static`
3838

3939
error: lifetime may not live long enough
40-
--> $DIR/normalization-2.rs:46:5
40+
--> $DIR/normalization-2.rs:47:5
4141
|
4242
LL | fn test_path<'a, 'b, 'c, 'd>() {
4343
| -- lifetime `'b` defined here
4444
...
4545
LL | <Ty<'static>>::method::<Ty<'b>>;
4646
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'b` must outlive `'static`
4747

48+
error: lifetime may not live long enough
49+
--> $DIR/normalization-2.rs:50:5
50+
|
51+
LL | fn test_path<'a, 'b, 'c, 'd>() {
52+
| -- lifetime `'c` defined here
53+
...
54+
LL | MyTy::Unit::<Ty<'c>>;
55+
| ^^^^^^^^^^^^^^^^^^^^ requires that `'c` must outlive `'static`
56+
4857
help: the following changes may resolve your lifetime errors
4958
|
5059
= help: replace `'a` with `'static`
5160
= help: replace `'b` with `'static`
61+
= help: replace `'c` with `'static`
5262

5363
error: lifetime may not live long enough
54-
--> $DIR/normalization-2.rs:51:5
64+
--> $DIR/normalization-2.rs:55:5
5565
|
5666
LL | fn test_call<'a, 'b, 'c>() {
5767
| -- lifetime `'a` defined here
5868
LL | <Ty<'a>>::method::<Ty<'static>>();
5969
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'a` must outlive `'static`
6070

6171
error: lifetime may not live long enough
62-
--> $DIR/normalization-2.rs:53:5
72+
--> $DIR/normalization-2.rs:57:5
6373
|
6474
LL | fn test_call<'a, 'b, 'c>() {
6575
| -- lifetime `'b` defined here
@@ -73,15 +83,15 @@ help: the following changes may resolve your lifetime errors
7383
= help: replace `'b` with `'static`
7484

7585
error: lifetime may not live long enough
76-
--> $DIR/normalization-2.rs:58:5
86+
--> $DIR/normalization-2.rs:62:5
7787
|
7888
LL | fn test_variants<'a, 'b, 'c>() {
7989
| -- lifetime `'a` defined here
80-
LL | <Ty<'a>>::Struct {}; //TODO
90+
LL | <Ty<'a>>::Struct {};
8191
| ^^^^^^^^^^^^^^^^^^^ requires that `'a` must outlive `'static`
8292

8393
error: lifetime may not live long enough
84-
--> $DIR/normalization-2.rs:60:5
94+
--> $DIR/normalization-2.rs:64:5
8595
|
8696
LL | fn test_variants<'a, 'b, 'c>() {
8797
| -- lifetime `'b` defined here
@@ -90,7 +100,7 @@ LL | <Ty<'b>>::Tuple();
90100
| ^^^^^^^^^^^^^^^ requires that `'b` must outlive `'static`
91101

92102
error: lifetime may not live long enough
93-
--> $DIR/normalization-2.rs:62:5
103+
--> $DIR/normalization-2.rs:66:5
94104
|
95105
LL | fn test_variants<'a, 'b, 'c>() {
96106
| -- lifetime `'c` defined here
@@ -105,7 +115,50 @@ help: the following changes may resolve your lifetime errors
105115
= help: replace `'c` with `'static`
106116

107117
error: lifetime may not live long enough
108-
--> $DIR/normalization-2.rs:69:9
118+
--> $DIR/normalization-2.rs:88:5
119+
|
120+
LL | fn test_struct_path<'a, 'b, 'c, 'd>() {
121+
| -- lifetime `'a` defined here
122+
...
123+
LL | MyTy::<Ty<'a>>::Struct {}; // without SelfTy
124+
| ^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'a` must outlive `'static`
125+
126+
error: lifetime may not live long enough
127+
--> $DIR/normalization-2.rs:90:5
128+
|
129+
LL | fn test_struct_path<'a, 'b, 'c, 'd>() {
130+
| -- lifetime `'b` defined here
131+
...
132+
LL | <Ty<'b> as Project>::Enum::Struct {}; // with SelfTy
133+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'b` must outlive `'static`
134+
135+
error: lifetime may not live long enough
136+
--> $DIR/normalization-2.rs:94:5
137+
|
138+
LL | fn test_struct_path<'a, 'b, 'c, 'd>() {
139+
| -- lifetime `'c` defined here
140+
...
141+
LL | Struct::<Ty<'c>> { x: None, }; // without SelfTy
142+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'c` must outlive `'static`
143+
144+
error: lifetime may not live long enough
145+
--> $DIR/normalization-2.rs:96:5
146+
|
147+
LL | fn test_struct_path<'a, 'b, 'c, 'd>() {
148+
| -- lifetime `'d` defined here
149+
...
150+
LL | <Ty<'d> as Project>::Struct { x: None, }; // with SelfTy
151+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ requires that `'d` must outlive `'static`
152+
153+
help: the following changes may resolve your lifetime errors
154+
|
155+
= help: replace `'a` with `'static`
156+
= help: replace `'b` with `'static`
157+
= help: replace `'c` with `'static`
158+
= help: replace `'d` with `'static`
159+
160+
error: lifetime may not live long enough
161+
--> $DIR/normalization-2.rs:103:9
109162
|
110163
LL | fn test_pattern<'a, 'b, 'c>() {
111164
| -- lifetime `'a` defined here
@@ -114,7 +167,7 @@ LL | Struct::<Ty<'a>> {..} => {},
114167
| ^^^^^^^^^^^^^^^^^^^^^ requires that `'a` must outlive `'static`
115168

116169
error: lifetime may not live long enough
117-
--> $DIR/normalization-2.rs:71:9
170+
--> $DIR/normalization-2.rs:105:9
118171
|
119172
LL | fn test_pattern<'a, 'b, 'c>() {
120173
| -- lifetime `'b` defined here
@@ -123,7 +176,7 @@ LL | Tuple::<Ty<'b>> (..) => {},
123176
| ^^^^^^^^^^^^^^^^^^^^ requires that `'b` must outlive `'static`
124177

125178
error: lifetime may not live long enough
126-
--> $DIR/normalization-2.rs:73:9
179+
--> $DIR/normalization-2.rs:107:9
127180
|
128181
LL | fn test_pattern<'a, 'b, 'c>() {
129182
| -- lifetime `'c` defined here
@@ -137,5 +190,5 @@ help: the following changes may resolve your lifetime errors
137190
= help: replace `'b` with `'static`
138191
= help: replace `'c` with `'static`
139192

140-
error: aborting due to 13 previous errors
193+
error: aborting due to 18 previous errors
141194

0 commit comments

Comments
 (0)