@@ -737,12 +737,14 @@ pub struct DerefClosure {
737
737
/// such as explicit deref and borrowing cases.
738
738
/// Returns `None` if no such use cases have been triggered in closure body
739
739
///
740
- /// note: this only works on single line immutable closures with one exactly one input parameter.
740
+ /// note: this only works on single line immutable closures with exactly one input parameter.
741
741
pub fn deref_closure_args < ' tcx > ( cx : & LateContext < ' _ > , closure : & ' tcx hir:: Expr < ' _ > ) -> Option < DerefClosure > {
742
742
if let hir:: ExprKind :: Closure ( _, fn_decl, body_id, ..) = closure. kind {
743
743
let closure_body = cx. tcx . hir ( ) . body ( body_id) ;
744
- // is closure arg a double reference (i.e.: `|x: &&i32| ...`)
745
- let closure_arg_is_double_ref = if let TyKind :: Rptr ( _, MutTy { ty, .. } ) = fn_decl. inputs [ 0 ] . kind {
744
+ // is closure arg a type annotated double reference (i.e.: `|x: &&i32| ...`)
745
+ // a type annotation is present if param `kind` is different from `TyKind::Infer`
746
+ let closure_arg_is_type_annotated_double_ref = if let TyKind :: Rptr ( _, MutTy { ty, .. } ) = fn_decl. inputs [ 0 ] . kind
747
+ {
746
748
matches ! ( ty. kind, TyKind :: Rptr ( _, MutTy { .. } ) )
747
749
} else {
748
750
false
@@ -751,7 +753,7 @@ pub fn deref_closure_args<'tcx>(cx: &LateContext<'_>, closure: &'tcx hir::Expr<'
751
753
let mut visitor = DerefDelegate {
752
754
cx,
753
755
closure_span : closure. span ,
754
- closure_arg_is_double_ref ,
756
+ closure_arg_is_type_annotated_double_ref ,
755
757
next_pos : closure. span . lo ( ) ,
756
758
suggestion_start : String :: new ( ) ,
757
759
applicability : Applicability :: MaybeIncorrect ,
@@ -780,8 +782,8 @@ struct DerefDelegate<'a, 'tcx> {
780
782
cx : & ' a LateContext < ' tcx > ,
781
783
/// The span of the input closure to adapt
782
784
closure_span : Span ,
783
- /// Indicates if the arg of the closure is a double reference
784
- closure_arg_is_double_ref : bool ,
785
+ /// Indicates if the arg of the closure is a type annotated double reference
786
+ closure_arg_is_type_annotated_double_ref : bool ,
785
787
/// last position of the span to gradually build the suggestion
786
788
next_pos : BytePos ,
787
789
/// starting part of the gradually built suggestion
@@ -799,7 +801,7 @@ impl DerefDelegate<'_, 'tcx> {
799
801
let end_span = Span :: new ( self . next_pos , self . closure_span . hi ( ) , self . closure_span . ctxt ( ) , None ) ;
800
802
let end_snip = snippet_with_applicability ( self . cx , end_span, ".." , & mut self . applicability ) ;
801
803
let sugg = format ! ( "{}{}" , self . suggestion_start, end_snip) ;
802
- if self . closure_arg_is_double_ref {
804
+ if self . closure_arg_is_type_annotated_double_ref {
803
805
sugg. replacen ( '&' , "" , 1 )
804
806
} else {
805
807
sugg
@@ -889,7 +891,7 @@ impl<'tcx> Delegate<'tcx> for DerefDelegate<'_, 'tcx> {
889
891
// and if the item is already a double ref
890
892
let ident_sugg = if !call_args. is_empty ( )
891
893
&& !takes_arg_by_double_ref
892
- && ( self . closure_arg_is_double_ref || has_field_or_index_projection)
894
+ && ( self . closure_arg_is_type_annotated_double_ref || has_field_or_index_projection)
893
895
{
894
896
let ident = if has_field_or_index_projection {
895
897
ident_str_with_proj
0 commit comments