7
7
// option. This file may not be copied, modified, or distributed
8
8
// except according to those terms.
9
9
10
- use crate :: utils:: { get_trait_def_id, higher, implements_trait, match_qpath, paths, span_lint} ;
10
+ use crate :: utils:: { get_trait_def_id, higher, implements_trait, match_qpath, match_type , paths, span_lint} ;
11
11
use rustc:: hir:: * ;
12
12
use rustc:: lint:: { LateContext , LateLintPass , LintArray , LintPass } ;
13
13
use rustc:: { declare_tool_lint, lint_array} ;
@@ -200,7 +200,6 @@ static POSSIBLY_COMPLETING_METHODS: &[(&str, usize)] = &[
200
200
/// their iterators
201
201
static COMPLETING_METHODS : & [ ( & str , usize ) ] = & [
202
202
( "count" , 1 ) ,
203
- ( "collect" , 1 ) ,
204
203
( "fold" , 3 ) ,
205
204
( "for_each" , 2 ) ,
206
205
( "partition" , 2 ) ,
@@ -214,6 +213,18 @@ static COMPLETING_METHODS: &[(&str, usize)] = &[
214
213
( "product" , 1 ) ,
215
214
] ;
216
215
216
+ /// the paths of types that are known to be infinitely allocating
217
+ static INFINITE_COLLECTORS : & [ & [ & str ] ] = & [
218
+ & paths:: BINARY_HEAP ,
219
+ & paths:: BTREEMAP ,
220
+ & paths:: BTREESET ,
221
+ & paths:: HASHMAP ,
222
+ & paths:: HASHSET ,
223
+ & paths:: LINKED_LIST ,
224
+ & paths:: VEC ,
225
+ & paths:: VEC_DEQUE ,
226
+ ] ;
227
+
217
228
fn complete_infinite_iter ( cx : & LateContext < ' _ , ' _ > , expr : & Expr ) -> Finiteness {
218
229
match expr. node {
219
230
ExprKind :: MethodCall ( ref method, _, ref args) => {
@@ -233,6 +244,11 @@ fn complete_infinite_iter(cx: &LateContext<'_, '_>, expr: &Expr) -> Finiteness {
233
244
if not_double_ended {
234
245
return is_infinite ( cx, & args[ 0 ] ) ;
235
246
}
247
+ } else if method. ident . name == "collect" {
248
+ let ty = cx. tables . expr_ty ( expr) ;
249
+ if INFINITE_COLLECTORS . iter ( ) . any ( |path| match_type ( cx, ty, path) ) {
250
+ return is_infinite ( cx, & args[ 0 ] ) ;
251
+ }
236
252
}
237
253
} ,
238
254
ExprKind :: Binary ( op, ref l, ref r) => {
0 commit comments