Basically calling _.iter() in the while let expression will lead to an infinite loop (except the collection is empty).
I'd love to contribute to Clippy. Since this is a good first issue I was hoping I could start working on it. Could I get some pointers on where in the code to get started?
Cool! I usually start by writing a test case (create a new .rs file in tests/ui, see the other files there for examples). Then I look into where the lint fits in, for example clippy_lints/src/loops.rs might be a good fit. There you first need to add the lint declaration and add the lint to the LintPass. Finally you need some code to check for iter calls whose expr_ty implements Iterator.
I'm a little late, but this doc gives you step by step instructions on how to write a new lint. For this lint the Author lint chapter is probably interesting for you.
Hi all, if @pop is not going to tackle this issue, I'd like to take it. I've already taken a look at the resources, thanks @llogiq and @flip1995.
I think a LateLintPass fits here because we need the type information of the match arm.
From what I've seen this is the place where we should detect this condition and emit the lint message:
This "desugars" the while let into a loop match, which in our case would be:
while let Some(&x) = a.iter().next() {
println!("{:?}", x);
}
into
loop {
match a.iter().next() {
Some(&x) => { println!("{:?}", x); },
_ => (),
}
}
}
Afterwards it decomposes the first arm using the pattern kind and the match_expre using the expression kind as well,
So that, roughly speaking:
pat is Some(&x) => { println!("{:?}", x); },
match_expr is a Method call => a.iter().next()
Where I get lost is how to get the type information from the qpath, and method_path.
I've looked into match_type in utils, but it seems it expects a different type, than qpath, which is a hir::QPath or in method_path case it is hir::PathSegment.
I'll keep looking into it, but if you have any useful pointers into what I should look into (HIR, MIR, Ty) or examples I would greatly appreciate it, specially since I'm new to clippy and rustc internals.
You seem primed and ready to take this one, so go for it @chibby0ne.
From what I've seen this is the place where we should detect this condition and emit the lint message:
Seems good to me
So that, roughly speaking:
pat is Some(&x) => { println!("{:?}", x); },
match_expr is a Method call => a.iter().next()
Exactly, you should only have to look at the match_expr though.
how to get the type information from the qpath
You should be able to use the function
https://github.com/rust-lang/rust-clippy/blob/737f0a6bb508706b75e21194e3010aa3865e779a/clippy_lints/src/utils/mod.rs#L178-L187
You can grep the repo for match_qpath on how to use it.
You seem primed and ready to take this one, so go for it @chibby0ne.
Thanks @pop I appreciate! :smile:
How did you fare with this one, @chibby0ne? :)