Extend `if_then_some_else_none` to also suggest `bool::then_some`
Closes#9094.
changelog: Extend `if_then_some_else_none` to also suggest `bool::then_some`
Add partialeq_to_none lint
Initial implementation of #9275, adding lint `partialeq_to_none`. This is my first time working on `clippy`, so please review carefully.
I'm unsure especially about the `Sugg`, as it covers the entire `BinOp`, instead of just covering one of the sides and the operator (see the multi-line example). I was unsure if pinpointing the suggestion wouldn't be brittle...
changelog: [`PARTIALEQ_TO_NONE`]: Initial commit
`explicit_auto_deref` changes
fixes#9123fixes#9109fixes#9143fixes#9101
This avoid suggesting code which hits a rustc bug. Basically `&{x}` won't use auto-deref if the target type is `Sized`.
changelog: Don't suggest using auto deref for block expressions when the target type is `Sized`
changelog: Include the borrow in the suggestion for `explicit_auto_deref`
changelog: Don't lint `explicit_auto_deref` on `dyn Trait` return
changelog: Don't lint `explicit_auto_deref` when other adjustments are required
changelog: Lint `explicit_auto_deref` in implicit return positions for closures
More proc-macro detection
fixes#6514fixes#8683fixes#6858fixes#6594
This is a more general way of checking if an expression comes from a macro and could be trivially applied to other lints. Ideally this would be fixed in rustc's proc-macro api, but I don't see that happening any time soon.
changelog: FPs: [`unit_arg`] [`default_trait_access`] [`missing_docs_in_private_items`]: No longer trigger in code generated from proc-macros.
move [`assertions_on_result_states`] to restriction
"Backports" the first commit of https://github.com/rust-lang/rust-clippy/pull/9273, so that the lint doesn't go into beta as a warn-by-default lint.
The other changes in the linked PR can ride the train as usual.
r? ``@xFrednet`` (only Clippy changes, so we don't need to bother compiler people)
---
For Clippy:
changelog: none
Always include a position span in `rustc_parse_format::Argument`
Moves the spans from the `Position` enum to always be included in the `Argument` struct. Doesn't make any changes to use it in rustc, but it will be useful for some upcoming Clippy lints
Fix suggestions for `async` closures in redundant_closure_call
Fixes#9052
changelog: Fix suggestions given by [`redundant_closure_call`] for async closures
- only compare where predicates to trait bounds when generating where
clause specific message to fix#9151
- use comparable_trait_ref to account for trait bound generics to fix#8757
Move [`assertions_on_result_states`] to restriction
Close#9263
This lint causes regression on readability of code and log output. And printing runtime values is not particularly useful for majority of tests which should be reproducible.
changelog: Move [`assertions_on_result_states`] to restriction and don't lint it for unit type
Signed-off-by: tabokie <xy.tao@outlook.com>
unwrap_used: Don't recommend using `expect` when the `expect_used` lint is not allowed
Fixes#9222
```
changelog: [`unwrap_used`]: Don't recommend using `expect` when the `expect_used` lint is not allowed
```
From 72 bytes to 12 bytes (on x86-64).
There are two parts to this:
- Changing various source code offsets from 64-bit to 32-bit. This is
not a problem because the rest of rustc also uses 32-bit source code
offsets. This means `Token` is no longer `Copy` but this causes no
problems.
- Removing the `RawStrError` from `LiteralKind`. Raw string literal
invalidity is now indicated by a `None` value within
`RawStr`/`RawByteStr`, and the new `validate_raw_str` function can be
used to re-lex an invalid raw string literal to get the `RawStrError`.
There is one very small change in behaviour. Previously, if a raw string
literal matched both the `InvalidStarter` and `TooManyHashes` cases,
the latter would override the former. This has now changed, because
`raw_double_quoted_string` now uses `?` and so returns immediately upon
detecting the `InvalidStarter` case. I think this is a slight
improvement to report the earlier-detected error, and it explains the
change in the `test_too_many_hashes` test.
The commit also removes a couple of comments that refer to #77629 and
say that the size of these types don't affect performance. These
comments are wrong, though the performance effect is small.
Rollup of 5 pull requests
Successful merges:
- #99311 (change maybe_body_owned_by to take local def id)
- #99862 (Improve type mismatch w/ function signatures)
- #99895 (don't call type ascription "cast")
- #99900 (remove some manual hash stable impls)
- #99903 (Add diagnostic when using public instead of pub)
Failed merges:
r? `@ghost`
`@rustbot` modify labels: rollup
Remove `TreeAndSpacing`.
A `TokenStream` contains a `Lrc<Vec<(TokenTree, Spacing)>>`. But this is
not quite right. `Spacing` makes sense for `TokenTree::Token`, but does
not make sense for `TokenTree::Delimited`, because a
`TokenTree::Delimited` cannot be joined with another `TokenTree`.
This commit fixes this problem, by adding `Spacing` to `TokenTree::Token`,
changing `TokenStream` to contain a `Lrc<Vec<TokenTree>>`, and removing the
`TreeAndSpacing` typedef.
The commit removes these two impls:
- `impl From<TokenTree> for TokenStream`
- `impl From<TokenTree> for TreeAndSpacing`
These were useful, but also resulted in code with many `.into()` calls
that was hard to read, particularly for anyone not highly familiar with
the relevant types. This commit makes some other changes to compensate:
- `TokenTree::token()` becomes `TokenTree::token_{alone,joint}()`.
- `TokenStream::token_{alone,joint}()` are added.
- `TokenStream::delimited` is added.
This results in things like this:
```rust
TokenTree::token(token::Semi, stmt.span).into()
```
changing to this:
```rust
TokenStream::token_alone(token::Semi, stmt.span)
```
This makes the type of the result, and its spacing, clearer.
These changes also simplifies `Cursor` and `CursorRef`, because they no longer
need to distinguish between `next` and `next_with_spacing`.
r? `@petrochenkov`
The expect_used lint is allow-by-default, so it would be better to show the case where this is enabled.
Co-authored-by: Takayuki Nakata <f.seasons017@gmail.com>
A `TokenStream` contains a `Lrc<Vec<(TokenTree, Spacing)>>`. But this is
not quite right. `Spacing` makes sense for `TokenTree::Token`, but does
not make sense for `TokenTree::Delimited`, because a
`TokenTree::Delimited` cannot be joined with another `TokenTree`.
This commit fixes this problem, by adding `Spacing` to `TokenTree::Token`,
changing `TokenStream` to contain a `Lrc<Vec<TokenTree>>`, and removing the
`TreeAndSpacing` typedef.
The commit removes these two impls:
- `impl From<TokenTree> for TokenStream`
- `impl From<TokenTree> for TreeAndSpacing`
These were useful, but also resulted in code with many `.into()` calls
that was hard to read, particularly for anyone not highly familiar with
the relevant types. This commit makes some other changes to compensate:
- `TokenTree::token()` becomes `TokenTree::token_{alone,joint}()`.
- `TokenStream::token_{alone,joint}()` are added.
- `TokenStream::delimited` is added.
This results in things like this:
```rust
TokenTree::token(token::Semi, stmt.span).into()
```
changing to this:
```rust
TokenStream::token_alone(token::Semi, stmt.span)
```
This makes the type of the result, and its spacing, clearer.
These changes also simplifies `Cursor` and `CursorRef`, because they no longer
need to distinguish between `next` and `next_with_spacing`.
Generate correct suggestion with named arguments used positionally
Address issue #99265 by checking each positionally used argument
to see if the argument is named and adding a lint to use the name
instead. This way, when named arguments are used positionally in a
different order than their argument order, the suggested lint is
correct.
For example:
```
println!("{b} {}", a=1, b=2);
```
This will now generate the suggestion:
```
println!("{b} {a}", a=1, b=2);
```
Additionally, this check now also correctly replaces or inserts
only where the positional argument is (or would be if implicit).
Also, width and precision are replaced with their argument names
when they exists.
Since the issues were so closely related, this fix for issue #99265
also fixes issue #99266.
Fixes#99265Fixes#99266
Read and use deprecated configuration (as well as emitting a warning)
Original change written by `@flip1995` I've simply rebased to master and fixed up the formatting/tests. This change teaches the configuration parser which config key replaced a deprecated key and attempts to populate the latter from the former. If both keys are provided this fails with a duplicate key error (rather than attempting to guess which the user intended).
Currently this on affects `cyclomatic-complexity-threshold` -> `cognitive-complexity-threshold` but will also be used in #8974 to handle `blacklisted-names` -> `disallowed-names`.
```
changelog: deprecated configuration keys are still applied as if they were provided as their non-deprecated name.
```
- [x] `cargo test` passes locally
- [x] Run `cargo dev fmt`
Address issue #99265 by checking each positionally used argument
to see if the argument is named and adding a lint to use the name
instead. This way, when named arguments are used positionally in a
different order than their argument order, the suggested lint is
correct.
For example:
```
println!("{b} {}", a=1, b=2);
```
This will now generate the suggestion:
```
println!("{b} {a}", a=1, b=2);
```
Additionally, this check now also correctly replaces or inserts
only where the positional argument is (or would be if implicit).
Also, width and precision are replaced with their argument names
when they exists.
Since the issues were so closely related, this fix for issue #99265
also fixes issue #99266.
Fixes#99265Fixes#99266
Add new lint `obfuscated_if_else`
part of #9100, additional commits could make it work with `then` and `unwrap_or_else` as well
changelog: Add new lint `obfuscated_if_else`
unused_self: respect avoid-breaking-exported-api
```
changelog: [`unused_self`]: Now respects the `avoid-breaking-exported-api` config option
```
Fixes#9195.
I mostly copied the implementation from `unnecessary_wraps`, since I don't have much understanding of rustc internals.
[`box_collection`]: raise warn for all std collections
So far, only [`Vec`, `String`, `HashMap`] were considered.
Extend collection checklist for this lint with:
- `HashSet`
- `VecDeque`
- `LinkedList`
- `BTreeMap`
- `BTreeSet`
- `BinaryHeap`
changelog: [`box_collection`]: raise warn for all std collections
Move format_push_string to restriction
Fixes#9077 (kinda) by moving the lint to the restriction group. As I noted in that issue, I think the suggested change is too much and as the OP of the issue points out, the ramifications of the change are not necessarily easily understood. As such I don't think the lint should be enabled by default.
changelog: [`format_push_string`]: moved to restriction (see #9077).
Implement `for<>` lifetime binder for closures
This PR implements RFC 3216 ([TI](https://github.com/rust-lang/rust/issues/97362)) and allows code like the following:
```rust
let _f = for<'a, 'b> |a: &'a A, b: &'b B| -> &'b C { b.c(a) };
// ^^^^^^^^^^^--- new!
```
cc ``@Aaron1011`` ``@cjgillot``
Always create elided lifetime parameters for functions
Anonymous and elided lifetimes in functions are sometimes (async fns) --and sometimes not (regular fns)-- desugared to implicit generic parameters.
This difference of treatment makes it some downstream analyses more complicated to handle. This step is a pre-requisite to perform lifetime elision resolution on AST.
There is currently an inconsistency in the treatment of argument-position impl-trait for functions and async fns:
```rust
trait Foo<'a> {}
fn foo(t: impl Foo<'_>) {} //~ ERROR missing lifetime specifier
async fn async_foo(t: impl Foo<'_>) {} //~ OK
fn bar(t: impl Iterator<Item = &'_ u8>) {} //~ ERROR missing lifetime specifier
async fn async_bar(t: impl Iterator<Item = &'_ u8>) {} //~ OK
```
The current implementation reports "missing lifetime specifier" on `foo`, but **accepts it** in `async_foo`.
This PR **proposes to accept** the anonymous lifetime in both cases as an extra generic lifetime parameter.
This change would be insta-stable, so let's ping t-lang.
Anonymous lifetimes in GAT bindings keep being forbidden:
```rust
fn foo(t: impl Foo<Assoc<'_> = Bar<'_>>) {}
^^ ^^
forbidden ok
```
I started a discussion here: https://rust-lang.zulipchat.com/#narrow/stream/213817-t-lang/topic/Anonymous.20lifetimes.20in.20universal.20impl-trait/near/284968606
r? ``@petrochenkov``
fix [`manual_flatten`] help texts order
fixes #8948
Whenever suggestion for this lint does not fit in one line,
legacy solution has some unexpected/unhandled behavior:
lint will then generate two help messages which seem to be shown in the wrong order.
The second help message in that case will contain the suggestion.
The first help message always refers to a suggestion message,
and **it should adapt** depending on the location of the suggestion:
- inline suggestion within the error/warning message
- suggestion separated into a second help text
This is my first contribution here, so I hope I didn't miss anything for creating this PR.
changelog: fix [`manual_flatten`] help texts order
Whenever suggestion for this lint does not fit in one line,
lint will generate two help messages. The second help message
will always contain the suggestion.
The first help message refers to suggestion message,
and it should adapt depending on the location of the suggestion:
- inline suggestion within the error/warning message
- suggestion separated into second help text
Add `repeated_where_clause_or_trait_bound` lint
I thought I would try and scratch my own itch for #8674.
1. Is comparing the `Res` the correct way for ensuring we have the same trait?
2. Is there a way to get the spans for the bounds and clauses for suggestions?
I tried to use `GenericParam::bounds_span_for_suggestions` but it only gave me an empty span at the end of the spans.
I tried `WhereClause::span_for_predicates_or_empty_place` and it included the comma.
3. Is there a simpler way to get the trait names? I have used the spans of the traits because I didn't see a way to get it off the `Res` or `Def`.
changelog: Add ``[`repeated_where_clause_or_trait_bound`]`` lint.
change applicability type to MaybeIncorrect in `explicit_counter_loop`
close#9013
This PR changes applicability type to `MaybeIncorrect`, because the suggestion is not `MachineApplicable`.
changelog: change applicability type to MaybeIncorrect in `explicit_counter_loop`
Fixes for `branches_sharing_code`
fixes#7198fixes#7452fixes#7555fixes#7589
changelog: Don't suggest moving modifications to locals used in any of the condition expressions in `branches_sharing_code`
changelog: Don't suggest moving anything after a local with a significant drop in `branches_sharing_code`
Fix span for or_fun_call
Closes#9033
changelog: [`or_fun_call`]: span points to the `unwrap_or` only instead of through the entire method chain expression
* Don't suggest moving modifications to locals used in any of the condition expressions
* Don't suggest moving anything after a local with a significant drop
Simplify if let statements
fixes: #8288
---
changelog: Allowing [`qustion_mark`] lint to check `if let` expressions that immediatly return unwrapped value
Lint simple expressions in `manual_filter_map`, `manual_find_map`
changelog: Lint simple expressions in [`manual_filter_map`], [`manual_find_map`]
The current comparison rules out `.find(|a| a.is_some()).map(|b| b.unwrap())` because `a` being a reference can effect more complicated expressions, this adds a simple check for that case and adds the necessary derefs
There's some overlap with `option_filter_map` so `lint_filter_some_map_unwrap` now returns a `bool` to indicate it linted
Make MIR basic blocks field public
This makes it possible to mutably borrow different fields of the MIR
body without resorting to methods like `basic_blocks_local_decls_mut_and_var_debug_info`.
To preserve validity of control flow graph caches in the presence of
modifications, a new struct `BasicBlocks` wraps together basic blocks
and control flow graph caches.
The `BasicBlocks` dereferences to `IndexVec<BasicBlock, BasicBlockData>`.
On the other hand a mutable access requires explicit `as_mut()` call.
Finishing touches for `#[expect]` (RFC 2383)
This PR adds documentation and some functionality to rustc's lint passes, to manually fulfill expectations. This is needed for some lints in Clippy. Hopefully, it should be one of the last things before we can move forward with stabilizing this feature.
As part of this PR, I've also updated `clippy::duplicate_mod` to showcase how this new functionality can be used and to ensure that it works correctly.
---
changelog: [`duplicate_mod`]: Fixed lint attribute interaction
r? `@wesleywiser`
cc: https://github.com/rust-lang/rust/issues/97660, https://github.com/rust-lang/rust/issues/85549
And I guess that's it. Here have a magical unicorn 🦄
the two loops did practically the same, only the type were different (&&
vs &), so I used `copied` to convert `&&` and chained them together.
Instead of parsing the trait info manually, I use the already provided
method `get_trait_info_from_bound`.
Also, instead of using manual string writing, I used `join` by
`itertools`.
Fix `undocumented_unsafe_blocks` in closures
fixes#9114
changelog: Fix `undocumented_unsafe_blocks` not checking for comments before the start of a closure
Add `invalid_utf8_in_unchecked`
changelog: Add [`invalid_utf8_in_unchecked`]
closes: #629
Don't know how useful of a lint this is, just saw this was a really old issue 😄.
Correct lint version for `format_push_string`
Closes#9081
changelog: none
IDK what else to say. Look I can draw an ascii penguin =D:
```
(^v^)
<( )>
w w
```
Add details about how significant drop in match scrutinees can cause deadlocks
Adds more details about how a significant drop in a match scrutinee can cause a deadlock and include link to documentation.
changelog: Add more details to significant drop lint to explicitly show how temporaries in match scrutinees can cause deadlocks.
Fix `#[expect]` for most clippy lints
This PR fixes most `#[expect]` - lint interactions listed in rust-lang/rust#97660. [My comment in the issue](https://github.com/rust-lang/rust/issues/97660#issuecomment-1147269504) shows the current progress (Once this is merged). I plan to work on `duplicate_mod` and `multiple_inherent_impl` and leave the rest for later. I feel like stabilizing the feature is more important than fixing the last few nits, which currently also don't work with `#[allow]`.
---
changelog: none
r? `@Jarcho`
cc: rust-lang/rust#97660
Add lint `explicit_auto_deref` take 2
fixes: #234fixes: #8367fixes: #8380
Still things to do:
* ~~This currently only lints `&*<expr>` when it doesn't trigger `needless_borrow`.~~
* ~~This requires a borrow after a deref to trigger. So `*<expr>` changing `&&T` to `&T` won't be caught.~~
* The `deref` and `deref_mut` trait methods aren't linted.
* Neither ~~field accesses~~, nor method receivers are linted.
* ~~This probably shouldn't lint reborrowing.~~
* Full slicing to deref should probably be handled here as well. e.g. `&vec[..]` when just `&vec` would do
changelog: new lint `explicit_auto_deref`
try reading rust-version from Cargo.toml
Cargo.toml can contain a field `rust-version`, that acts like a MSRV of
clippy.toml file: https://doc.rust-lang.org/cargo/reference/manifest.html#the-rust-version-field
This will try to read that field and use it, if the clippy.toml config
has no `msrv` entry
changelog: respect `rust-version` from `Cargo.toml`
closes#8746closes#7765
`trivially_copy_pass_by_ref` fixes
fixes#5953fixes#2961
The fix for #5953 is overly aggressive, but the suggestion is so bad that it's worth the false negatives. Basically three things together:
* It's not obviously wrong
* It compiles
* It may actually work when tested
changelog: Don't lint `trivially_copy_pass_by_ref` when unsafe pointers are used.
changelog: Better track lifetimes when linting `trivially_copy_pass_by_ref`.
add [`manual_find`] lint for function return case
part of the implementation discussed in #7143
changelog: add [`manual_find`] lint for function return case
feat(new lint): new lint `manual_retain`
close#8097
This PR is a new lint implementation.
This lint checks if the `retain` method is available.
Thank you in advance.
changelog: add new ``[`manual_retain`]`` lint
Suggest `pointer::cast` when possible in `transmute_ptr_to_ref`
fixes#8924
changelog: Suggest casting the pointer for any type containing lifetimes in `transmute_ptr_to_ref`.
changelog: Suggest `pointer::cast` when possible in `transmute_ptr_to_ref`.
enum_variant_names should ignore when all prefixes are _
close#9018
When Enum prefix is only an underscore, we should not issue warnings.
changelog: fix false positive in enum_variant_names
Lint `[single_match]` on `Option` matches
fixes#8928
changelog: did some cleanup of the logic for ``[`single_match`]`` and ``[`single_match_else`]`` which fixes the bug where `Option` matches were not linted unless a wildcard was used for one of the arms.
ignore item in `thread_local!` macro
close#8493
This PR ignores `thread_local` macro in `declare_interior_mutable_const`.
changelog: ignore `thread_local!` macro in `declare_interior_mutable_const`
Fix `extra_unused_lifetimes` false positive
This PR fixes#9014.
I confirmed the FP on the `crates.io` source as `@JohnTitor` mentioned, and confirmed that the FP is no longer present following this change.
I did not include a test in this PR because I think constructing one would be complicated, and the fix is pretty simple. But please let me know if this is unacceptable.
changelog: fix `extra_unused_lifetimes` FP
add vec.capacity() to [`slow_vec_initialization`] detection
fix#8800
for example
```rust
let mut vec1 = Vec::with_capacity(len);
vec1.resize(vec1.capacity(), 0);
let mut vec2 = Vec::with_capacity(len);
vec2.extend(repeat(0).take(vec2.capacity()));
```
will trigger the lint
---
changelog: add `vec.capacity()` to [`slow_vec_initialization`] detection
confirm using chain in collapsible_span_lint_calls
close#8798
This PR fixes false positive when using chain in `collapsible_span_lint_calls`.
changelog: None
put parentheses around neg_multiply suggestion if needed
*Please write a short comment explaining your change (or "none" for internal only changes)*
changelog: [`neg_multiply`]: put parentheses around suggestion if needed