@@ -207,7 +207,13 @@ impl<'tcx> LateLintPass<'tcx> for Ranges {
207207 extract_msrv_attr ! ( LateContext ) ;
208208}
209209
210- fn check_possible_range_contains ( cx : & LateContext < ' _ > , op : BinOpKind , l : & Expr < ' _ > , r : & Expr < ' _ > , expr : & Expr < ' _ > ) {
210+ fn check_possible_range_contains (
211+ cx : & LateContext < ' _ > ,
212+ op : BinOpKind ,
213+ left : & Expr < ' _ > ,
214+ right : & Expr < ' _ > ,
215+ expr : & Expr < ' _ > ,
216+ ) {
211217 if in_constant ( cx, expr. hir_id ) {
212218 return ;
213219 }
@@ -219,23 +225,19 @@ fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'
219225 _ => return ,
220226 } ;
221227 // value, name, order (higher/lower), inclusiveness
222- if let (
223- Some ( ( lval, lexpr, lid, name_span, lval_span, lord, linc) ) ,
224- Some ( ( rval, _, rid, _, rval_span, rord, rinc) ) ,
225- ) = ( check_range_bounds ( cx, l) , check_range_bounds ( cx, r) )
226- {
228+ if let ( Some ( l) , Some ( r) ) = ( check_range_bounds ( cx, left) , check_range_bounds ( cx, right) ) {
227229 // we only lint comparisons on the same name and with different
228230 // direction
229- if lid != rid || lord == rord {
231+ if l . id != r . id || l . ord == r . ord {
230232 return ;
231233 }
232- let ord = Constant :: partial_cmp ( cx. tcx , cx. typeck_results ( ) . expr_ty ( lexpr ) , & lval , & rval ) ;
233- if combine_and && ord == Some ( rord ) {
234+ let ord = Constant :: partial_cmp ( cx. tcx , cx. typeck_results ( ) . expr_ty ( l . expr ) , & l . val , & r . val ) ;
235+ if combine_and && ord == Some ( r . ord ) {
234236 // order lower bound and upper bound
235- let ( l_span, u_span, l_inc, u_inc) = if rord == Ordering :: Less {
236- ( lval_span , rval_span , linc , rinc )
237+ let ( l_span, u_span, l_inc, u_inc) = if r . ord == Ordering :: Less {
238+ ( l . val_span , r . val_span , l . inc , r . inc )
237239 } else {
238- ( rval_span , lval_span , rinc , linc )
240+ ( r . val_span , l . val_span , r . inc , l . inc )
239241 } ;
240242 // we only lint inclusive lower bounds
241243 if !l_inc {
@@ -247,7 +249,7 @@ fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'
247249 ( "Range" , ".." )
248250 } ;
249251 let mut applicability = Applicability :: MachineApplicable ;
250- let name = snippet_with_applicability ( cx, name_span, "_" , & mut applicability) ;
252+ let name = snippet_with_applicability ( cx, l . name_span , "_" , & mut applicability) ;
251253 let lo = snippet_with_applicability ( cx, l_span, "_" , & mut applicability) ;
252254 let hi = snippet_with_applicability ( cx, u_span, "_" , & mut applicability) ;
253255 let space = if lo. ends_with ( '.' ) { " " } else { "" } ;
@@ -260,13 +262,13 @@ fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'
260262 format ! ( "({}{}{}{}).contains(&{})" , lo, space, range_op, hi, name) ,
261263 applicability,
262264 ) ;
263- } else if !combine_and && ord == Some ( lord ) {
265+ } else if !combine_and && ord == Some ( l . ord ) {
264266 // `!_.contains(_)`
265267 // order lower bound and upper bound
266- let ( l_span, u_span, l_inc, u_inc) = if lord == Ordering :: Less {
267- ( lval_span , rval_span , linc , rinc )
268+ let ( l_span, u_span, l_inc, u_inc) = if l . ord == Ordering :: Less {
269+ ( l . val_span , r . val_span , l . inc , r . inc )
268270 } else {
269- ( rval_span , lval_span , rinc , linc )
271+ ( r . val_span , l . val_span , r . inc , l . inc )
270272 } ;
271273 if l_inc {
272274 return ;
@@ -277,7 +279,7 @@ fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'
277279 ( "RangeInclusive" , "..=" )
278280 } ;
279281 let mut applicability = Applicability :: MachineApplicable ;
280- let name = snippet_with_applicability ( cx, name_span, "_" , & mut applicability) ;
282+ let name = snippet_with_applicability ( cx, l . name_span , "_" , & mut applicability) ;
281283 let lo = snippet_with_applicability ( cx, l_span, "_" , & mut applicability) ;
282284 let hi = snippet_with_applicability ( cx, u_span, "_" , & mut applicability) ;
283285 let space = if lo. ends_with ( '.' ) { " " } else { "" } ;
@@ -294,10 +296,20 @@ fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'
294296 }
295297}
296298
297- fn check_range_bounds < ' a > (
298- cx : & ' a LateContext < ' _ > ,
299- ex : & ' a Expr < ' _ > ,
300- ) -> Option < ( Constant , & ' a Expr < ' a > , HirId , Span , Span , Ordering , bool ) > {
299+ struct RangeBounds < ' a > {
300+ val : Constant ,
301+ expr : & ' a Expr < ' a > ,
302+ id : HirId ,
303+ name_span : Span ,
304+ val_span : Span ,
305+ ord : Ordering ,
306+ inc : bool ,
307+ }
308+
309+ // Takes a binary expression such as x <= 2 as input
310+ // Breaks apart into various pieces, such as the value of the number,
311+ // hir id of the variable, and direction/inclusiveness of the operator
312+ fn check_range_bounds < ' a > ( cx : & ' a LateContext < ' _ > , ex : & ' a Expr < ' _ > ) -> Option < RangeBounds < ' a > > {
301313 if let ExprKind :: Binary ( ref op, l, r) = ex. kind {
302314 let ( inclusive, ordering) = match op. node {
303315 BinOpKind :: Gt => ( false , Ordering :: Greater ) ,
@@ -308,11 +320,27 @@ fn check_range_bounds<'a>(
308320 } ;
309321 if let Some ( id) = path_to_local ( l) {
310322 if let Some ( ( c, _) ) = constant ( cx, cx. typeck_results ( ) , r) {
311- return Some ( ( c, r, id, l. span , r. span , ordering, inclusive) ) ;
323+ return Some ( RangeBounds {
324+ val : c,
325+ expr : r,
326+ id,
327+ name_span : l. span ,
328+ val_span : r. span ,
329+ ord : ordering,
330+ inc : inclusive,
331+ } ) ;
312332 }
313333 } else if let Some ( id) = path_to_local ( r) {
314334 if let Some ( ( c, _) ) = constant ( cx, cx. typeck_results ( ) , l) {
315- return Some ( ( c, l, id, r. span , l. span , ordering. reverse ( ) , inclusive) ) ;
335+ return Some ( RangeBounds {
336+ val : c,
337+ expr : l,
338+ id,
339+ name_span : r. span ,
340+ val_span : l. span ,
341+ ord : ordering. reverse ( ) ,
342+ inc : inclusive,
343+ } ) ;
316344 }
317345 }
318346 }
0 commit comments