@@ -46,7 +46,7 @@ struct TopInfo<'tcx> {
46
46
/// Was the origin of the `span` from a scrutinee expression?
47
47
///
48
48
/// Otherwise there is no scrutinee and it could be e.g. from the type of a formal parameter.
49
- origin_expr : bool ,
49
+ origin_expr : Option < & ' tcx hir :: Expr < ' tcx > > ,
50
50
/// The span giving rise to the `expected` type, if one could be provided.
51
51
///
52
52
/// If `origin_expr` is `true`, then this is the span of the scrutinee as in:
@@ -74,7 +74,8 @@ struct TopInfo<'tcx> {
74
74
75
75
impl < ' tcx > FnCtxt < ' _ , ' tcx > {
76
76
fn pattern_cause ( & self , ti : TopInfo < ' tcx > , cause_span : Span ) -> ObligationCause < ' tcx > {
77
- let code = Pattern { span : ti. span , root_ty : ti. expected , origin_expr : ti. origin_expr } ;
77
+ let code =
78
+ Pattern { span : ti. span , root_ty : ti. expected , origin_expr : ti. origin_expr . is_some ( ) } ;
78
79
self . cause ( cause_span, code)
79
80
}
80
81
@@ -85,7 +86,14 @@ impl<'tcx> FnCtxt<'_, 'tcx> {
85
86
actual : Ty < ' tcx > ,
86
87
ti : TopInfo < ' tcx > ,
87
88
) -> Option < DiagnosticBuilder < ' tcx , ErrorGuaranteed > > {
88
- self . demand_eqtype_with_origin ( & self . pattern_cause ( ti, cause_span) , expected, actual)
89
+ let mut diag =
90
+ self . demand_eqtype_with_origin ( & self . pattern_cause ( ti, cause_span) , expected, actual) ?;
91
+ if let Some ( expr) = ti. origin_expr {
92
+ self . suggest_fn_call ( & mut diag, expr, expected, |output| {
93
+ self . can_eq ( self . param_env , output, actual) . is_ok ( )
94
+ } ) ;
95
+ }
96
+ Some ( diag)
89
97
}
90
98
91
99
fn demand_eqtype_pat (
@@ -127,7 +135,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
127
135
pat : & ' tcx Pat < ' tcx > ,
128
136
expected : Ty < ' tcx > ,
129
137
span : Option < Span > ,
130
- origin_expr : bool ,
138
+ origin_expr : Option < & ' tcx hir :: Expr < ' tcx > > ,
131
139
) {
132
140
let info = TopInfo { expected, origin_expr, span } ;
133
141
self . check_pat ( pat, expected, INITIAL_BM , info) ;
@@ -2146,7 +2154,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
2146
2154
err. help ( "the semantics of slice patterns changed recently; see issue #62254" ) ;
2147
2155
} else if self . autoderef ( span, expected_ty)
2148
2156
. any ( |( ty, _) | matches ! ( ty. kind( ) , ty:: Slice ( ..) | ty:: Array ( ..) ) )
2149
- && let ( Some ( span) , true ) = ( ti. span , ti. origin_expr )
2157
+ && let Some ( span) = ti. span
2158
+ && let Some ( _) = ti. origin_expr
2150
2159
&& let Ok ( snippet) = self . tcx . sess . source_map ( ) . span_to_snippet ( span)
2151
2160
{
2152
2161
let ty = self . resolve_vars_if_possible ( ti. expected ) ;
0 commit comments