@@ -221,27 +221,19 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
221
221
let slice = match ctor {
222
222
Struct | Variant ( _) | UnionField => match ty. kind ( ) {
223
223
ty:: Tuple ( fs) => reveal_and_alloc ( cx, fs. iter ( ) ) ,
224
- ty:: Adt ( adt, args) => {
225
- if adt. is_box ( ) {
226
- // The only legal patterns of type `Box` (outside `std`) are `_` and box
227
- // patterns. If we're here we can assume this is a box pattern.
228
- reveal_and_alloc ( cx, once ( args. type_at ( 0 ) ) )
229
- } else {
230
- let variant =
231
- & adt. variant ( RustcPatCtxt :: variant_index_for_adt ( & ctor, * adt) ) ;
232
- let tys = cx. variant_sub_tys ( ty, variant) . map ( |( field, ty) | {
233
- let is_visible =
234
- adt. is_enum ( ) || field. vis . is_accessible_from ( cx. module , cx. tcx ) ;
235
- let is_uninhabited = cx. is_uninhabited ( * ty) ;
236
- let is_unstable =
237
- cx. tcx . lookup_stability ( field. did ) . is_some_and ( |stab| {
238
- stab. is_unstable ( ) && stab. feature != sym:: rustc_private
239
- } ) ;
240
- let skip = is_uninhabited && ( !is_visible || is_unstable) ;
241
- ( ty, PrivateUninhabitedField ( skip) )
224
+ ty:: Adt ( adt, _) => {
225
+ let variant = & adt. variant ( RustcPatCtxt :: variant_index_for_adt ( & ctor, * adt) ) ;
226
+ let tys = cx. variant_sub_tys ( ty, variant) . map ( |( field, ty) | {
227
+ let is_visible =
228
+ adt. is_enum ( ) || field. vis . is_accessible_from ( cx. module , cx. tcx ) ;
229
+ let is_uninhabited = cx. is_uninhabited ( * ty) ;
230
+ let is_unstable = cx. tcx . lookup_stability ( field. did ) . is_some_and ( |stab| {
231
+ stab. is_unstable ( ) && stab. feature != sym:: rustc_private
242
232
} ) ;
243
- cx. dropless_arena . alloc_from_iter ( tys)
244
- }
233
+ let skip = is_uninhabited && ( !is_visible || is_unstable) ;
234
+ ( ty, PrivateUninhabitedField ( skip) )
235
+ } ) ;
236
+ cx. dropless_arena . alloc_from_iter ( tys)
245
237
}
246
238
_ => bug ! ( "Unexpected type for constructor `{ctor:?}`: {ty:?}" ) ,
247
239
} ,
@@ -273,14 +265,8 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
273
265
Struct | Variant ( _) | UnionField => match ty. kind ( ) {
274
266
ty:: Tuple ( fs) => fs. len ( ) ,
275
267
ty:: Adt ( adt, ..) => {
276
- if adt. is_box ( ) {
277
- // The only legal patterns of type `Box` (outside `std`) are `_` and box
278
- // patterns. If we're here we can assume this is a box pattern.
279
- 1
280
- } else {
281
- let variant_idx = RustcPatCtxt :: variant_index_for_adt ( & ctor, * adt) ;
282
- adt. variant ( variant_idx) . fields . len ( )
283
- }
268
+ let variant_idx = RustcPatCtxt :: variant_index_for_adt ( & ctor, * adt) ;
269
+ adt. variant ( variant_idx) . fields . len ( )
284
270
}
285
271
_ => bug ! ( "Unexpected type for constructor `{ctor:?}`: {ty:?}" ) ,
286
272
} ,
@@ -470,8 +456,6 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
470
456
fields = vec ! [ self . lower_pat( subpattern) . at_index( 0 ) ] ;
471
457
arity = 1 ;
472
458
ctor = match ty. kind ( ) {
473
- // This is a box pattern.
474
- ty:: Adt ( adt, ..) if adt. is_box ( ) => Struct ,
475
459
ty:: Ref ( ..) => Ref ,
476
460
_ => span_bug ! (
477
461
pat. span,
@@ -501,28 +485,6 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
501
485
. map ( |ipat| self . lower_pat ( & ipat. pattern ) . at_index ( ipat. field . index ( ) ) )
502
486
. collect ( ) ;
503
487
}
504
- ty:: Adt ( adt, _) if adt. is_box ( ) => {
505
- // The only legal patterns of type `Box` (outside `std`) are `_` and box
506
- // patterns. If we're here we can assume this is a box pattern.
507
- // FIXME(Nadrieril): A `Box` can in theory be matched either with `Box(_,
508
- // _)` or a box pattern. As a hack to avoid an ICE with the former, we
509
- // ignore other fields than the first one. This will trigger an error later
510
- // anyway.
511
- // See https://github.com/rust-lang/rust/issues/82772,
512
- // explanation: https://github.com/rust-lang/rust/pull/82789#issuecomment-796921977
513
- // The problem is that we can't know from the type whether we'll match
514
- // normally or through box-patterns. We'll have to figure out a proper
515
- // solution when we introduce generalized deref patterns. Also need to
516
- // prevent mixing of those two options.
517
- let pattern = subpatterns. into_iter ( ) . find ( |pat| pat. field . index ( ) == 0 ) ;
518
- if let Some ( pat) = pattern {
519
- fields = vec ! [ self . lower_pat( & pat. pattern) . at_index( 0 ) ] ;
520
- } else {
521
- fields = vec ! [ ] ;
522
- }
523
- ctor = Struct ;
524
- arity = 1 ;
525
- }
526
488
ty:: Adt ( adt, _) => {
527
489
ctor = match pat. kind {
528
490
PatKind :: Leaf { .. } if adt. is_union ( ) => UnionField ,
@@ -825,11 +787,6 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
825
787
Bool ( b) => b. to_string ( ) ,
826
788
Str ( s) => s. to_string ( ) ,
827
789
IntRange ( range) => return self . print_pat_range ( range, * pat. ty ( ) ) ,
828
- Struct if pat. ty ( ) . is_box ( ) => {
829
- // Outside of the `alloc` crate, the only way to create a struct pattern
830
- // of type `Box` is to use a `box` pattern via #[feature(box_patterns)].
831
- format ! ( "box {}" , print( & pat. fields[ 0 ] ) )
832
- }
833
790
Struct | Variant ( _) | UnionField => {
834
791
let enum_info = match * pat. ty ( ) . kind ( ) {
835
792
ty:: Adt ( adt_def, _) if adt_def. is_enum ( ) => EnumInfo :: Enum {
@@ -866,6 +823,14 @@ impl<'p, 'tcx: 'p> RustcPatCtxt<'p, 'tcx> {
866
823
print:: write_ref_like ( & mut s, pat. ty ( ) . inner ( ) , & print ( & pat. fields [ 0 ] ) ) . unwrap ( ) ;
867
824
s
868
825
}
826
+ DerefPattern ( _) if pat. ty ( ) . is_box ( ) && !self . tcx . features ( ) . deref_patterns ( ) => {
827
+ // FIXME(deref_patterns): Remove this special handling once `box_patterns` is gone.
828
+ // HACK(@dianne): `box _` syntax is exposed on stable in diagnostics, e.g. to
829
+ // witness non-exhaustiveness of `match Box::new(0) { Box { .. } if false => {} }`.
830
+ // To avoid changing diagnostics before deref pattern syntax is finalized, let's use
831
+ // `box _` syntax unless `deref_patterns` is enabled.
832
+ format ! ( "box {}" , print( & pat. fields[ 0 ] ) )
833
+ }
869
834
DerefPattern ( _) => format ! ( "deref!({})" , print( & pat. fields[ 0 ] ) ) ,
870
835
Slice ( slice) => {
871
836
let ( prefix_len, has_dot_dot) = match slice. kind {
@@ -964,12 +929,8 @@ impl<'p, 'tcx: 'p> PatCx for RustcPatCtxt<'p, 'tcx> {
964
929
ty : & Self :: Ty ,
965
930
) -> fmt:: Result {
966
931
if let ty:: Adt ( adt, _) = ty. kind ( ) {
967
- if adt. is_box ( ) {
968
- write ! ( f, "Box" ) ?
969
- } else {
970
- let variant = adt. variant ( Self :: variant_index_for_adt ( ctor, * adt) ) ;
971
- write ! ( f, "{}" , variant. name) ?;
972
- }
932
+ let variant = adt. variant ( Self :: variant_index_for_adt ( ctor, * adt) ) ;
933
+ write ! ( f, "{}" , variant. name) ?;
973
934
}
974
935
Ok ( ( ) )
975
936
}
0 commit comments