@@ -112,9 +112,9 @@ pub struct ItemCtxt<'tcx> {
112
112
///////////////////////////////////////////////////////////////////////////
113
113
114
114
#[ derive( Default ) ]
115
- crate struct PlaceholderHirTyCollector ( crate Vec < Span > ) ;
115
+ crate struct HirPlaceholderCollector ( crate Vec < Span > ) ;
116
116
117
- impl < ' v > Visitor < ' v > for PlaceholderHirTyCollector {
117
+ impl < ' v > Visitor < ' v > for HirPlaceholderCollector {
118
118
fn visit_ty ( & mut self , t : & ' v hir:: Ty < ' v > ) {
119
119
if let hir:: TyKind :: Infer = t. kind {
120
120
self . 0 . push ( t. span ) ;
@@ -131,6 +131,12 @@ impl<'v> Visitor<'v> for PlaceholderHirTyCollector {
131
131
_ => { }
132
132
}
133
133
}
134
+ fn visit_array_length ( & mut self , length : & ' v hir:: ArrayLen ) {
135
+ if let & hir:: ArrayLen :: Infer ( _, span) = length {
136
+ self . 0 . push ( span) ;
137
+ }
138
+ intravisit:: walk_array_len ( self , length)
139
+ }
134
140
}
135
141
136
142
struct CollectItemTypesVisitor < ' tcx > {
@@ -175,7 +181,7 @@ crate fn placeholder_type_error<'tcx>(
175
181
sugg. push ( ( span, format ! ( ", {}" , type_name) ) ) ;
176
182
}
177
183
178
- let mut err = bad_placeholder ( tcx, "type" , placeholder_types, kind) ;
184
+ let mut err = bad_placeholder ( tcx, placeholder_types, kind) ;
179
185
180
186
// Suggest, but only if it is not a function in const or static
181
187
if suggest {
@@ -233,7 +239,7 @@ fn reject_placeholder_type_signatures_in_item<'tcx>(
233
239
_ => return ,
234
240
} ;
235
241
236
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
242
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
237
243
visitor. visit_item ( item) ;
238
244
239
245
placeholder_type_error (
@@ -311,7 +317,6 @@ impl<'tcx> Visitor<'tcx> for CollectItemTypesVisitor<'tcx> {
311
317
312
318
fn bad_placeholder < ' tcx > (
313
319
tcx : TyCtxt < ' tcx > ,
314
- placeholder_kind : & ' static str ,
315
320
mut spans : Vec < Span > ,
316
321
kind : & ' static str ,
317
322
) -> rustc_errors:: DiagnosticBuilder < ' tcx > {
@@ -322,8 +327,7 @@ fn bad_placeholder<'tcx>(
322
327
tcx. sess,
323
328
spans. clone( ) ,
324
329
E0121 ,
325
- "the {} placeholder `_` is not allowed within types on item signatures for {}" ,
326
- placeholder_kind,
330
+ "the placeholder `_` is not allowed within types on item signatures for {}" ,
327
331
kind
328
332
) ;
329
333
for span in spans {
@@ -381,7 +385,7 @@ impl<'tcx> AstConv<'tcx> for ItemCtxt<'tcx> {
381
385
}
382
386
383
387
fn ty_infer ( & self , _: Option < & ty:: GenericParamDef > , span : Span ) -> Ty < ' tcx > {
384
- self . tcx ( ) . ty_error_with_message ( span, "bad_placeholder_type " )
388
+ self . tcx ( ) . ty_error_with_message ( span, "bad placeholder type " )
385
389
}
386
390
387
391
fn ct_infer (
@@ -390,13 +394,11 @@ impl<'tcx> AstConv<'tcx> for ItemCtxt<'tcx> {
390
394
_: Option < & ty:: GenericParamDef > ,
391
395
span : Span ,
392
396
) -> & ' tcx Const < ' tcx > {
393
- bad_placeholder ( self . tcx ( ) , "const" , vec ! [ span] , "generic" ) . emit ( ) ;
394
- // Typeck doesn't expect erased regions to be returned from `type_of`.
395
397
let ty = self . tcx . fold_regions ( ty, & mut false , |r, _| match r {
396
398
ty:: ReErased => self . tcx . lifetimes . re_static ,
397
399
_ => r,
398
400
} ) ;
399
- self . tcx ( ) . const_error ( ty)
401
+ self . tcx ( ) . const_error_with_message ( ty, span , "bad placeholder constant" )
400
402
}
401
403
402
404
fn projected_ty_from_poly_trait_ref (
@@ -743,7 +745,7 @@ fn convert_item(tcx: TyCtxt<'_>, item_id: hir::ItemId) {
743
745
match item. kind {
744
746
hir:: ForeignItemKind :: Fn ( ..) => tcx. ensure ( ) . fn_sig ( item. def_id ) ,
745
747
hir:: ForeignItemKind :: Static ( ..) => {
746
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
748
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
747
749
visitor. visit_foreign_item ( item) ;
748
750
placeholder_type_error (
749
751
tcx,
@@ -826,7 +828,7 @@ fn convert_item(tcx: TyCtxt<'_>, item_id: hir::ItemId) {
826
828
hir:: ItemKind :: Const ( ty, ..) | hir:: ItemKind :: Static ( ty, ..) => {
827
829
// (#75889): Account for `const C: dyn Fn() -> _ = "";`
828
830
if let hir:: TyKind :: TraitObject ( ..) = ty. kind {
829
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
831
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
830
832
visitor. visit_item ( it) ;
831
833
placeholder_type_error (
832
834
tcx,
@@ -862,7 +864,7 @@ fn convert_trait_item(tcx: TyCtxt<'_>, trait_item_id: hir::TraitItemId) {
862
864
hir:: TraitItemKind :: Const ( ..) => {
863
865
tcx. ensure ( ) . type_of ( trait_item_id. def_id ) ;
864
866
// Account for `const C: _;`.
865
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
867
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
866
868
visitor. visit_trait_item ( trait_item) ;
867
869
placeholder_type_error ( tcx, None , & [ ] , visitor. 0 , false , None , "constant" ) ;
868
870
}
@@ -871,7 +873,7 @@ fn convert_trait_item(tcx: TyCtxt<'_>, trait_item_id: hir::TraitItemId) {
871
873
tcx. ensure ( ) . item_bounds ( trait_item_id. def_id ) ;
872
874
tcx. ensure ( ) . type_of ( trait_item_id. def_id ) ;
873
875
// Account for `type T = _;`.
874
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
876
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
875
877
visitor. visit_trait_item ( trait_item) ;
876
878
placeholder_type_error ( tcx, None , & [ ] , visitor. 0 , false , None , "associated type" ) ;
877
879
}
@@ -880,7 +882,7 @@ fn convert_trait_item(tcx: TyCtxt<'_>, trait_item_id: hir::TraitItemId) {
880
882
tcx. ensure ( ) . item_bounds ( trait_item_id. def_id ) ;
881
883
// #74612: Visit and try to find bad placeholders
882
884
// even if there is no concrete type.
883
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
885
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
884
886
visitor. visit_trait_item ( trait_item) ;
885
887
886
888
placeholder_type_error ( tcx, None , & [ ] , visitor. 0 , false , None , "associated type" ) ;
@@ -902,7 +904,7 @@ fn convert_impl_item(tcx: TyCtxt<'_>, impl_item_id: hir::ImplItemId) {
902
904
}
903
905
hir:: ImplItemKind :: TyAlias ( _) => {
904
906
// Account for `type T = _;`
905
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
907
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
906
908
visitor. visit_impl_item ( impl_item) ;
907
909
908
910
placeholder_type_error ( tcx, None , & [ ] , visitor. 0 , false , None , "associated type" ) ;
@@ -1822,10 +1824,14 @@ fn are_suggestable_generic_args(generic_args: &[hir::GenericArg<'_>]) -> bool {
1822
1824
/// Whether `ty` is a type with `_` placeholders that can be inferred. Used in diagnostics only to
1823
1825
/// use inference to provide suggestions for the appropriate type if possible.
1824
1826
fn is_suggestable_infer_ty ( ty : & hir:: Ty < ' _ > ) -> bool {
1827
+ debug ! ( ?ty) ;
1825
1828
use hir:: TyKind :: * ;
1826
1829
match & ty. kind {
1827
1830
Infer => true ,
1828
- Slice ( ty) | Array ( ty, _) => is_suggestable_infer_ty ( ty) ,
1831
+ Slice ( ty) => is_suggestable_infer_ty ( ty) ,
1832
+ Array ( ty, length) => {
1833
+ is_suggestable_infer_ty ( ty) || matches ! ( length, hir:: ArrayLen :: Infer ( _, _) )
1834
+ }
1829
1835
Tup ( tys) => tys. iter ( ) . any ( is_suggestable_infer_ty) ,
1830
1836
Ptr ( mut_ty) | Rptr ( _, mut_ty) => is_suggestable_infer_ty ( mut_ty. ty ) ,
1831
1837
OpaqueDef ( _, generic_args) => are_suggestable_generic_args ( generic_args) ,
@@ -1877,9 +1883,9 @@ fn fn_sig(tcx: TyCtxt<'_>, def_id: DefId) -> ty::PolyFnSig<'_> {
1877
1883
} ) ;
1878
1884
let fn_sig = ty:: Binder :: dummy ( fn_sig) ;
1879
1885
1880
- let mut visitor = PlaceholderHirTyCollector :: default ( ) ;
1886
+ let mut visitor = HirPlaceholderCollector :: default ( ) ;
1881
1887
visitor. visit_ty ( ty) ;
1882
- let mut diag = bad_placeholder ( tcx, "type" , visitor. 0 , "return type" ) ;
1888
+ let mut diag = bad_placeholder ( tcx, visitor. 0 , "return type" ) ;
1883
1889
let ret_ty = fn_sig. skip_binder ( ) . output ( ) ;
1884
1890
if !ret_ty. references_error ( ) {
1885
1891
if !ret_ty. is_closure ( ) {
0 commit comments