Skip to content

Commit e9cc540

Browse files
GrzegorzManishearth
authored andcommitted
do not trigger redundant_closure when there is a difference in borrow level between closure parameter and "self"
1 parent 5d7c24f commit e9cc540

File tree

2 files changed

+22
-9
lines changed

2 files changed

+22
-9
lines changed

clippy_lints/src/eta_reduction.rs

Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -129,25 +129,30 @@ fn get_ufcs_type_name(
129129
let actual_type_of_self = &cx.tables.node_type(self_arg.hir_id).sty;
130130

131131
if let Some(trait_id) = cx.tcx.trait_of_item(method_def_id) {
132-
//if the method expectes &self, ufcs requires explicit borrowing so closure can't be removed
133-
return match (expected_type_of_self, actual_type_of_self) {
134-
(ty::Ref(_, _, _), ty::Ref(_, _, _)) => Some(cx.tcx.item_path_str(trait_id)),
135-
(l, r) => match (l, r) {
136-
(ty::Ref(_, _, _), _) | (_, ty::Ref(_, _, _)) => None,
137-
(_, _) => Some(cx.tcx.item_path_str(trait_id)),
138-
},
139-
};
132+
if match_borrow_depth(expected_type_of_self, actual_type_of_self) {
133+
return Some(cx.tcx.item_path_str(trait_id));
134+
}
140135
}
141136

142137
cx.tcx.impl_of_method(method_def_id).and_then(|_| {
143-
//a type may implicitly implement other types methods (e.g. Deref)
138+
//a type may implicitly implement other type's methods (e.g. Deref)
144139
if match_types(expected_type_of_self, actual_type_of_self) {
145140
return Some(get_type_name(cx, &actual_type_of_self));
146141
}
147142
None
148143
})
149144
}
150145

146+
fn match_borrow_depth(lhs: &ty::TyKind<'_>, rhs: &ty::TyKind<'_>) -> bool {
147+
match (lhs, rhs) {
148+
(ty::Ref(_, t1, _), ty::Ref(_, t2, _)) => match_borrow_depth(&t1.sty, &t2.sty),
149+
(l, r) => match (l, r) {
150+
(ty::Ref(_, _, _), _) | (_, ty::Ref(_, _, _)) => false,
151+
(_, _) => true,
152+
},
153+
}
154+
}
155+
151156
fn match_types(lhs: &ty::TyKind<'_>, rhs: &ty::TyKind<'_>) -> bool {
152157
match (lhs, rhs) {
153158
(ty::Bool, ty::Bool)

tests/ui/eta.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,14 @@ fn test_redundant_closures_containing_method_calls() {
8888
let c = Some(TestStruct { some_ref: &i })
8989
.as_ref()
9090
.map(|c| c.to_ascii_uppercase());
91+
92+
fn test_different_borrow_levels<T>(t: &[&T])
93+
where
94+
T: TestTrait,
95+
{
96+
t.iter().filter(|x| x.trait_foo_ref());
97+
t.iter().map(|x| x.trait_foo_ref());
98+
}
9199
}
92100

93101
fn meta<F>(f: F)

0 commit comments

Comments
 (0)