@@ -1860,22 +1860,22 @@ where
1860
1860
mod redundant_pattern_match {
1861
1861
use super :: REDUNDANT_PATTERN_MATCHING ;
1862
1862
use clippy_utils:: diagnostics:: span_lint_and_then;
1863
- use clippy_utils:: higher;
1864
1863
use clippy_utils:: source:: snippet;
1865
1864
use clippy_utils:: sugg:: Sugg ;
1866
1865
use clippy_utils:: ty:: { implements_trait, is_type_diagnostic_item, is_type_lang_item, match_type} ;
1867
- use clippy_utils:: { is_lang_ctor, is_qpath_def_path, is_trait_method, paths} ;
1866
+ use clippy_utils:: { higher, match_def_path} ;
1867
+ use clippy_utils:: { is_lang_ctor, is_trait_method, paths} ;
1868
1868
use if_chain:: if_chain;
1869
1869
use rustc_ast:: ast:: LitKind ;
1870
1870
use rustc_data_structures:: fx:: FxHashSet ;
1871
1871
use rustc_errors:: Applicability ;
1872
- use rustc_hir:: LangItem :: { OptionNone , OptionSome , PollPending , PollReady , ResultErr , ResultOk } ;
1872
+ use rustc_hir:: LangItem :: { OptionNone , PollPending } ;
1873
1873
use rustc_hir:: {
1874
1874
intravisit:: { walk_expr, Visitor } ,
1875
1875
Arm , Block , Expr , ExprKind , LangItem , MatchSource , Node , Pat , PatKind , QPath , UnOp ,
1876
1876
} ;
1877
1877
use rustc_lint:: LateContext ;
1878
- use rustc_middle:: ty:: { self , subst:: GenericArgKind , Ty } ;
1878
+ use rustc_middle:: ty:: { self , subst:: GenericArgKind , DefIdTree , Ty } ;
1879
1879
use rustc_span:: sym;
1880
1880
1881
1881
pub fn check < ' tcx > ( cx : & LateContext < ' tcx > , expr : & ' tcx Expr < ' _ > ) {
@@ -2051,28 +2051,31 @@ mod redundant_pattern_match {
2051
2051
has_else : bool ,
2052
2052
) {
2053
2053
// also look inside refs
2054
- let mut kind = & let_pat. kind ;
2055
2054
// if we have &None for example, peel it so we can detect "if let None = x"
2056
- if let PatKind :: Ref ( inner, _mutability) = kind {
2057
- kind = & inner. kind ;
2058
- }
2055
+ let check_pat = match let_pat. kind {
2056
+ PatKind :: Ref ( inner, _mutability) => inner,
2057
+ _ => let_pat,
2058
+ } ;
2059
2059
let op_ty = cx. typeck_results ( ) . expr_ty ( let_expr) ;
2060
2060
// Determine which function should be used, and the type contained by the corresponding
2061
2061
// variant.
2062
- let ( good_method, inner_ty) = match kind {
2063
- PatKind :: TupleStruct ( ref path , [ sub_pat] , _) => {
2062
+ let ( good_method, inner_ty) = match check_pat . kind {
2063
+ PatKind :: TupleStruct ( ref qpath , [ sub_pat] , _) => {
2064
2064
if let PatKind :: Wild = sub_pat. kind {
2065
- if is_lang_ctor ( cx, path, ResultOk ) {
2065
+ let res = cx. typeck_results ( ) . qpath_res ( qpath, check_pat. hir_id ) ;
2066
+ let Some ( id) = res. opt_def_id ( ) . and_then ( |ctor_id| cx. tcx . parent ( ctor_id) ) else { return } ;
2067
+ let lang_items = cx. tcx . lang_items ( ) ;
2068
+ if Some ( id) == lang_items. result_ok_variant ( ) {
2066
2069
( "is_ok()" , try_get_generic_ty ( op_ty, 0 ) . unwrap_or ( op_ty) )
2067
- } else if is_lang_ctor ( cx , path , ResultErr ) {
2070
+ } else if Some ( id ) == lang_items . result_err_variant ( ) {
2068
2071
( "is_err()" , try_get_generic_ty ( op_ty, 1 ) . unwrap_or ( op_ty) )
2069
- } else if is_lang_ctor ( cx , path , OptionSome ) {
2072
+ } else if Some ( id ) == lang_items . option_some_variant ( ) {
2070
2073
( "is_some()" , op_ty)
2071
- } else if is_lang_ctor ( cx , path , PollReady ) {
2074
+ } else if Some ( id ) == lang_items . poll_ready_variant ( ) {
2072
2075
( "is_ready()" , op_ty)
2073
- } else if is_qpath_def_path ( cx, path , sub_pat . hir_id , & paths:: IPADDR_V4 ) {
2076
+ } else if match_def_path ( cx, id , & paths:: IPADDR_V4 ) {
2074
2077
( "is_ipv4()" , op_ty)
2075
- } else if is_qpath_def_path ( cx, path , sub_pat . hir_id , & paths:: IPADDR_V6 ) {
2078
+ } else if match_def_path ( cx, id , & paths:: IPADDR_V6 ) {
2076
2079
( "is_ipv6()" , op_ty)
2077
2080
} else {
2078
2081
return ;
@@ -2272,17 +2275,22 @@ mod redundant_pattern_match {
2272
2275
should_be_left : & ' a str ,
2273
2276
should_be_right : & ' a str ,
2274
2277
) -> Option < & ' a str > {
2275
- let body_node_pair = if is_qpath_def_path ( cx, path_left, arms[ 0 ] . pat . hir_id , expected_left)
2276
- && is_qpath_def_path ( cx, path_right, arms[ 1 ] . pat . hir_id , expected_right)
2277
- {
2278
- ( & ( * arms[ 0 ] . body ) . kind , & ( * arms[ 1 ] . body ) . kind )
2279
- } else if is_qpath_def_path ( cx, path_right, arms[ 1 ] . pat . hir_id , expected_left)
2280
- && is_qpath_def_path ( cx, path_left, arms[ 0 ] . pat . hir_id , expected_right)
2281
- {
2282
- ( & ( * arms[ 1 ] . body ) . kind , & ( * arms[ 0 ] . body ) . kind )
2283
- } else {
2284
- return None ;
2285
- } ;
2278
+ let left_id = cx
2279
+ . typeck_results ( )
2280
+ . qpath_res ( path_left, arms[ 0 ] . pat . hir_id )
2281
+ . opt_def_id ( ) ?;
2282
+ let right_id = cx
2283
+ . typeck_results ( )
2284
+ . qpath_res ( path_right, arms[ 1 ] . pat . hir_id )
2285
+ . opt_def_id ( ) ?;
2286
+ let body_node_pair =
2287
+ if match_def_path ( cx, left_id, expected_left) && match_def_path ( cx, right_id, expected_right) {
2288
+ ( & ( * arms[ 0 ] . body ) . kind , & ( * arms[ 1 ] . body ) . kind )
2289
+ } else if match_def_path ( cx, right_id, expected_left) && match_def_path ( cx, right_id, expected_right) {
2290
+ ( & ( * arms[ 1 ] . body ) . kind , & ( * arms[ 0 ] . body ) . kind )
2291
+ } else {
2292
+ return None ;
2293
+ } ;
2286
2294
2287
2295
match body_node_pair {
2288
2296
( ExprKind :: Lit ( ref lit_left) , ExprKind :: Lit ( ref lit_right) ) => match ( & lit_left. node , & lit_right. node ) {
0 commit comments