@@ -2024,6 +2024,25 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
2024
2024
Ty :: new_ref ( self . tcx , region, mt)
2025
2025
}
2026
2026
2027
+ fn try_resolve_slice_ty_to_array_ty (
2028
+ & self ,
2029
+ before : & ' tcx [ Pat < ' tcx > ] ,
2030
+ slice : Option < & ' tcx Pat < ' tcx > > ,
2031
+ span : Span ,
2032
+ ) -> Option < Ty < ' tcx > > {
2033
+ if !slice. is_none ( ) {
2034
+ return None ;
2035
+ }
2036
+
2037
+ let tcx = self . tcx ;
2038
+ let len = before. len ( ) ;
2039
+ let ty_var_origin =
2040
+ TypeVariableOrigin { kind : TypeVariableOriginKind :: TypeInference , span } ;
2041
+ let inner_ty = self . next_ty_var ( ty_var_origin) ;
2042
+
2043
+ Some ( tcx. mk_array ( inner_ty, len. try_into ( ) . unwrap ( ) ) )
2044
+ }
2045
+
2027
2046
/// Type check a slice pattern.
2028
2047
///
2029
2048
/// Syntactically, these look like `[pat_0, ..., pat_n]`.
@@ -2044,6 +2063,13 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
2044
2063
def_bm : BindingMode ,
2045
2064
ti : TopInfo < ' tcx > ,
2046
2065
) -> Ty < ' tcx > {
2066
+ // If `expected` is an infer ty, we try to equate it to an array if the given pattern
2067
+ // allows it. See issue #76342
2068
+ if let Some ( resolved_arr_ty) = self . try_resolve_slice_ty_to_array_ty ( before, slice, span) && expected. is_ty_var ( ) {
2069
+ debug ! ( ?resolved_arr_ty) ;
2070
+ self . demand_eqtype ( span, expected, resolved_arr_ty) ;
2071
+ }
2072
+
2047
2073
let expected = self . structurally_resolve_type ( span, expected) ;
2048
2074
let ( element_ty, opt_slice_ty, inferred) = match * expected. kind ( ) {
2049
2075
// An array, so we might have something like `let [a, b, c] = [0, 1, 2];`.
0 commit comments