Skip to content

Commit d554385

Browse files
authored
Rollup merge of #83935 - SNCPlay42:param-default-impl-trait, r=varkor
forbid `impl Trait` in generic param defaults Fixes #83929 Forbid using `impl Trait` in the default types of generic parameters, e.g. `struct Foo<T = impl Trait>`. I assume this was never supposed to be allowed - it seems no UI test used it. Note that using `impl Trait` in this position did not hit a feature gate error; however, this *shouldn't* be a breaking change as any attempt to use it should have hit the ICE in #83929 and/or failed to provide a defining use of the `impl Trait`.
2 parents b81c6cd + ee79f83 commit d554385

File tree

5 files changed

+134
-66
lines changed

5 files changed

+134
-66
lines changed

compiler/rustc_ast_lowering/src/lib.rs

+1-7
Original file line numberDiff line numberDiff line change
@@ -2259,13 +2259,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
22592259

22602260
let kind = hir::GenericParamKind::Type {
22612261
default: default.as_ref().map(|x| {
2262-
self.lower_ty(
2263-
x,
2264-
ImplTraitContext::OtherOpaqueTy {
2265-
capturable_lifetimes: &mut FxHashSet::default(),
2266-
origin: hir::OpaqueTyOrigin::Misc,
2267-
},
2268-
)
2262+
self.lower_ty(x, ImplTraitContext::Disallowed(ImplTraitPosition::Other))
22692263
}),
22702264
synthetic: param
22712265
.attrs
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
struct Foo<T = impl Copy>(T);
2+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
3+
4+
type Result<T, E = impl std::error::Error> = std::result::Result<T, E>;
5+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
6+
7+
// should not cause ICE
8+
fn x() -> Foo {
9+
Foo(0)
10+
}
11+
12+
fn main() -> Result<()> {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
2+
--> $DIR/issue-83929-impl-trait-in-generic-default.rs:1:16
3+
|
4+
LL | struct Foo<T = impl Copy>(T);
5+
| ^^^^^^^^^
6+
7+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
8+
--> $DIR/issue-83929-impl-trait-in-generic-default.rs:4:20
9+
|
10+
LL | type Result<T, E = impl std::error::Error> = std::result::Result<T, E>;
11+
| ^^^^^^^^^^^^^^^^^^^^^^
12+
13+
error: aborting due to 2 previous errors
14+
15+
For more information about this error, try `rustc --explain E0562`.

src/test/ui/impl-trait/where-allowed.rs

+28-4
Original file line numberDiff line numberDiff line change
@@ -56,12 +56,10 @@ fn in_impl_Fn_return_in_parameters(_: &impl Fn() -> impl Debug) { panic!() }
5656
fn in_impl_Fn_parameter_in_return() -> &'static impl Fn(impl Debug) { panic!() }
5757
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
5858
//~| ERROR nested `impl Trait` is not allowed
59-
//~| ERROR cannot resolve opaque type
6059

6160
// Disallowed
6261
fn in_impl_Fn_return_in_return() -> &'static impl Fn() -> impl Debug { panic!() }
6362
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
64-
//~| ERROR cannot resolve opaque type
6563

6664
// Disallowed
6765
fn in_Fn_parameter_in_generics<F: Fn(impl Debug)> (_: F) { panic!() }
@@ -120,7 +118,6 @@ trait DummyTrait {
120118
impl DummyTrait for () {
121119
type Out = impl Debug;
122120
//~^ ERROR `impl Trait` in type aliases is unstable
123-
//~^^ ERROR could not find defining uses
124121

125122
fn in_trait_impl_parameter(_: impl Debug) { }
126123
// Allowed
@@ -156,7 +153,6 @@ extern "C" fn in_extern_fn_return() -> impl Debug {
156153

157154
type InTypeAlias<R> = impl Debug;
158155
//~^ ERROR `impl Trait` in type aliases is unstable
159-
//~^^ ERROR could not find defining uses
160156

161157
type InReturnInTypeAlias<R> = fn() -> impl Debug;
162158
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
@@ -218,6 +214,34 @@ fn in_Fn_return_in_fn_where_clause<T>()
218214
{
219215
}
220216

217+
// Disallowed
218+
struct InStructGenericParamDefault<T = impl Debug>(T);
219+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
220+
221+
// Disallowed
222+
enum InEnumGenericParamDefault<T = impl Debug> { Variant(T) }
223+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
224+
225+
// Disallowed
226+
trait InTraitGenericParamDefault<T = impl Debug> {}
227+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
228+
229+
// Disallowed
230+
type InTypeAliasGenericParamDefault<T = impl Debug> = T;
231+
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types
232+
233+
// Disallowed
234+
impl <T = impl Debug> T {}
235+
//~^ ERROR defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
236+
//~| WARNING this was previously accepted by the compiler but is being phased out
237+
//~| ERROR `impl Trait` not allowed outside of function and inherent method return types
238+
239+
// Disallowed
240+
fn in_method_generic_param_default<T = impl Debug>(_: T) {}
241+
//~^ ERROR defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
242+
//~| WARNING this was previously accepted by the compiler but is being phased out
243+
//~| ERROR `impl Trait` not allowed outside of function and inherent method return types
244+
221245
fn main() {
222246
let _in_local_variable: impl Fn() = || {};
223247
//~^ ERROR `impl Trait` not allowed outside of function and inherent method return types

src/test/ui/impl-trait/where-allowed.stderr

+78-55
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ LL | fn in_impl_Fn_parameter_in_return() -> &'static impl Fn(impl Debug) { panic
1717
| outer `impl Trait`
1818

1919
error[E0658]: `impl Trait` in type aliases is unstable
20-
--> $DIR/where-allowed.rs:121:16
20+
--> $DIR/where-allowed.rs:119:16
2121
|
2222
LL | type Out = impl Debug;
2323
| ^^^^^^^^^^
@@ -26,7 +26,7 @@ LL | type Out = impl Debug;
2626
= help: add `#![feature(min_type_alias_impl_trait)]` to the crate attributes to enable
2727

2828
error[E0658]: `impl Trait` in type aliases is unstable
29-
--> $DIR/where-allowed.rs:157:23
29+
--> $DIR/where-allowed.rs:154:23
3030
|
3131
LL | type InTypeAlias<R> = impl Debug;
3232
| ^^^^^^^^^^
@@ -35,7 +35,7 @@ LL | type InTypeAlias<R> = impl Debug;
3535
= help: add `#![feature(min_type_alias_impl_trait)]` to the crate attributes to enable
3636

3737
error[E0658]: `impl Trait` in type aliases is unstable
38-
--> $DIR/where-allowed.rs:161:39
38+
--> $DIR/where-allowed.rs:157:39
3939
|
4040
LL | type InReturnInTypeAlias<R> = fn() -> impl Debug;
4141
| ^^^^^^^^^^
@@ -110,184 +110,207 @@ LL | fn in_impl_Fn_parameter_in_return() -> &'static impl Fn(impl Debug) { panic
110110
| ^^^^^^^^^^
111111

112112
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
113-
--> $DIR/where-allowed.rs:62:59
113+
--> $DIR/where-allowed.rs:61:59
114114
|
115115
LL | fn in_impl_Fn_return_in_return() -> &'static impl Fn() -> impl Debug { panic!() }
116116
| ^^^^^^^^^^
117117

118118
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
119-
--> $DIR/where-allowed.rs:67:38
119+
--> $DIR/where-allowed.rs:65:38
120120
|
121121
LL | fn in_Fn_parameter_in_generics<F: Fn(impl Debug)> (_: F) { panic!() }
122122
| ^^^^^^^^^^
123123

124124
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
125-
--> $DIR/where-allowed.rs:71:40
125+
--> $DIR/where-allowed.rs:69:40
126126
|
127127
LL | fn in_Fn_return_in_generics<F: Fn() -> impl Debug> (_: F) { panic!() }
128128
| ^^^^^^^^^^
129129

130130
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
131-
--> $DIR/where-allowed.rs:84:32
131+
--> $DIR/where-allowed.rs:82:32
132132
|
133133
LL | struct InBraceStructField { x: impl Debug }
134134
| ^^^^^^^^^^
135135

136136
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
137-
--> $DIR/where-allowed.rs:88:41
137+
--> $DIR/where-allowed.rs:86:41
138138
|
139139
LL | struct InAdtInBraceStructField { x: Vec<impl Debug> }
140140
| ^^^^^^^^^^
141141

142142
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
143-
--> $DIR/where-allowed.rs:92:27
143+
--> $DIR/where-allowed.rs:90:27
144144
|
145145
LL | struct InTupleStructField(impl Debug);
146146
| ^^^^^^^^^^
147147

148148
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
149-
--> $DIR/where-allowed.rs:97:25
149+
--> $DIR/where-allowed.rs:95:25
150150
|
151151
LL | InBraceVariant { x: impl Debug },
152152
| ^^^^^^^^^^
153153

154154
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
155-
--> $DIR/where-allowed.rs:99:20
155+
--> $DIR/where-allowed.rs:97:20
156156
|
157157
LL | InTupleVariant(impl Debug),
158158
| ^^^^^^^^^^
159159

160160
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
161-
--> $DIR/where-allowed.rs:110:23
161+
--> $DIR/where-allowed.rs:108:23
162162
|
163163
LL | fn in_return() -> impl Debug;
164164
| ^^^^^^^^^^
165165

166166
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
167-
--> $DIR/where-allowed.rs:128:34
167+
--> $DIR/where-allowed.rs:125:34
168168
|
169169
LL | fn in_trait_impl_return() -> impl Debug { () }
170170
| ^^^^^^^^^^
171171

172172
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
173-
--> $DIR/where-allowed.rs:141:33
173+
--> $DIR/where-allowed.rs:138:33
174174
|
175175
LL | fn in_foreign_parameters(_: impl Debug);
176176
| ^^^^^^^^^^
177177

178178
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
179-
--> $DIR/where-allowed.rs:144:31
179+
--> $DIR/where-allowed.rs:141:31
180180
|
181181
LL | fn in_foreign_return() -> impl Debug;
182182
| ^^^^^^^^^^
183183

184184
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
185-
--> $DIR/where-allowed.rs:161:39
185+
--> $DIR/where-allowed.rs:157:39
186186
|
187187
LL | type InReturnInTypeAlias<R> = fn() -> impl Debug;
188188
| ^^^^^^^^^^
189189

190190
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
191-
--> $DIR/where-allowed.rs:166:16
191+
--> $DIR/where-allowed.rs:162:16
192192
|
193193
LL | impl PartialEq<impl Debug> for () {
194194
| ^^^^^^^^^^
195195

196196
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
197-
--> $DIR/where-allowed.rs:171:24
197+
--> $DIR/where-allowed.rs:167:24
198198
|
199199
LL | impl PartialEq<()> for impl Debug {
200200
| ^^^^^^^^^^
201201

202202
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
203-
--> $DIR/where-allowed.rs:176:6
203+
--> $DIR/where-allowed.rs:172:6
204204
|
205205
LL | impl impl Debug {
206206
| ^^^^^^^^^^
207207

208208
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
209-
--> $DIR/where-allowed.rs:182:24
209+
--> $DIR/where-allowed.rs:178:24
210210
|
211211
LL | impl InInherentImplAdt<impl Debug> {
212212
| ^^^^^^^^^^
213213

214214
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
215-
--> $DIR/where-allowed.rs:188:11
215+
--> $DIR/where-allowed.rs:184:11
216216
|
217217
LL | where impl Debug: Debug
218218
| ^^^^^^^^^^
219219

220220
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
221-
--> $DIR/where-allowed.rs:195:15
221+
--> $DIR/where-allowed.rs:191:15
222222
|
223223
LL | where Vec<impl Debug>: Debug
224224
| ^^^^^^^^^^
225225

226226
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
227-
--> $DIR/where-allowed.rs:202:24
227+
--> $DIR/where-allowed.rs:198:24
228228
|
229229
LL | where T: PartialEq<impl Debug>
230230
| ^^^^^^^^^^
231231

232232
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
233-
--> $DIR/where-allowed.rs:209:17
233+
--> $DIR/where-allowed.rs:205:17
234234
|
235235
LL | where T: Fn(impl Debug)
236236
| ^^^^^^^^^^
237237

238238
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
239-
--> $DIR/where-allowed.rs:216:22
239+
--> $DIR/where-allowed.rs:212:22
240240
|
241241
LL | where T: Fn() -> impl Debug
242242
| ^^^^^^^^^^
243243

244244
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
245-
--> $DIR/where-allowed.rs:222:29
245+
--> $DIR/where-allowed.rs:218:40
246+
|
247+
LL | struct InStructGenericParamDefault<T = impl Debug>(T);
248+
| ^^^^^^^^^^
249+
250+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
251+
--> $DIR/where-allowed.rs:222:36
252+
|
253+
LL | enum InEnumGenericParamDefault<T = impl Debug> { Variant(T) }
254+
| ^^^^^^^^^^
255+
256+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
257+
--> $DIR/where-allowed.rs:226:38
258+
|
259+
LL | trait InTraitGenericParamDefault<T = impl Debug> {}
260+
| ^^^^^^^^^^
261+
262+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
263+
--> $DIR/where-allowed.rs:230:41
264+
|
265+
LL | type InTypeAliasGenericParamDefault<T = impl Debug> = T;
266+
| ^^^^^^^^^^
267+
268+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
269+
--> $DIR/where-allowed.rs:234:11
270+
|
271+
LL | impl <T = impl Debug> T {}
272+
| ^^^^^^^^^^
273+
274+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
275+
--> $DIR/where-allowed.rs:240:40
276+
|
277+
LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
278+
| ^^^^^^^^^^
279+
280+
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
281+
--> $DIR/where-allowed.rs:246:29
246282
|
247283
LL | let _in_local_variable: impl Fn() = || {};
248284
| ^^^^^^^^^
249285
|
250286
= help: add `#![feature(impl_trait_in_bindings)]` to the crate attributes to enable
251287

252288
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
253-
--> $DIR/where-allowed.rs:224:46
289+
--> $DIR/where-allowed.rs:248:46
254290
|
255291
LL | let _in_return_in_local_variable = || -> impl Fn() { || {} };
256292
| ^^^^^^^^^
257293

258-
error[E0720]: cannot resolve opaque type
259-
--> $DIR/where-allowed.rs:56:49
260-
|
261-
LL | fn in_impl_Fn_parameter_in_return() -> &'static impl Fn(impl Debug) { panic!() }
262-
| ^^^^^^^^^^^^^^^^^^^ -------- this returned value is of `!` type
263-
| |
264-
| cannot resolve opaque type
265-
|
266-
= help: this error will resolve once the item's body returns a concrete type
267-
268-
error[E0720]: cannot resolve opaque type
269-
--> $DIR/where-allowed.rs:62:46
294+
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
295+
--> $DIR/where-allowed.rs:234:7
270296
|
271-
LL | fn in_impl_Fn_return_in_return() -> &'static impl Fn() -> impl Debug { panic!() }
272-
| ^^^^^^^^^^^^^^^^^^^^^^^ -------- this returned value is of `!` type
273-
| |
274-
| cannot resolve opaque type
297+
LL | impl <T = impl Debug> T {}
298+
| ^
275299
|
276-
= help: this error will resolve once the item's body returns a concrete type
300+
= note: `#[deny(invalid_type_param_default)]` on by default
301+
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
302+
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
277303

278-
error: could not find defining uses
279-
--> $DIR/where-allowed.rs:121:16
304+
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
305+
--> $DIR/where-allowed.rs:240:36
280306
|
281-
LL | type Out = impl Debug;
282-
| ^^^^^^^^^^
283-
284-
error: could not find defining uses
285-
--> $DIR/where-allowed.rs:157:23
307+
LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
308+
| ^
286309
|
287-
LL | type InTypeAlias<R> = impl Debug;
288-
| ^^^^^^^^^^
310+
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
311+
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
289312

290-
error: aborting due to 44 previous errors
313+
error: aborting due to 48 previous errors
291314

292-
Some errors have detailed explanations: E0562, E0658, E0666, E0720.
315+
Some errors have detailed explanations: E0562, E0658, E0666.
293316
For more information about an error, try `rustc --explain E0562`.

0 commit comments

Comments
 (0)