By assuming that a recursive type is normalizable within the deeper
calls to `is_normalizable_helper()`, more cases can be handled by this
function.
In order to fix stack overflows, a recursion limit has also been added
for recursive generic type instantiations.
Fix#9798Fix#10508Fix#11915
changelog: [`large_enum_variant`]: more precise detection of variants
with large size differences
- `reindent_multiline()` always returns the result of
`reindent_multiline_inner()` which returns a `String`. Make
`reindent_multiline()` return a `String` as well, instead of a
systematically owned `Cow<'_, str>`.
- There is no reason for `reindent_multiline()` to force a caller to
build a `Cow<'_, str>` instead of passing a `&str` directly, especially
considering that a `String` will always be returned.
Also, both the input parameter and return value (of type `Cow<'_, str>`)
shared the same (elided) lifetime for no reason: this worked only
because the result was always the `Cow::Owned` variant which is
compatible with any lifetime.
As a consequence, the signature changes from:
```rust
fn reindent_multiline(s: Cow<'_, str>, …) -> Cow<'_, str> { … }
```
to
```rust
fn reindent_multiline(s: &str, …) -> String { … }
```
changelog: none
Labeled blocks cannot be used as-is in the "then" or "else" part of an
`if` expression. They must be enclosed in an anonymous block.
Fix#14099
changelog: [`match_bool`]: fix suggestion when the rewritten block has a
label
#[contracts::requires(...)] + #[contracts::ensures(...)]
cc https://github.com/rust-lang/rust/issues/128044
Updated contract support: attribute syntax for preconditions and postconditions, implemented via a series of desugarings that culminates in:
1. a compile-time flag (`-Z contract-checks`) that, similar to `-Z ub-checks`, attempts to ensure that the decision of enabling/disabling contract checks is delayed until the end user program is compiled,
2. invocations of lang-items that handle invoking the precondition, building a checker for the post-condition, and invoking that post-condition checker at the return sites for the function, and
3. intrinsics for the actual evaluation of pre- and post-condition predicates that third-party verification tools can intercept and reinterpret for their own purposes (e.g. creating shims of behavior that abstract away the function body and replace it solely with the pre- and post-conditions).
Known issues:
* My original intent, as described in the MCP (https://github.com/rust-lang/compiler-team/issues/759) was to have a rustc-prefixed attribute namespace (like rustc_contracts::requires). But I could not get things working when I tried to do rewriting via a rustc-prefixed builtin attribute-macro. So for now it is called `contracts::requires`.
* Our attribute macro machinery does not provide direct support for attribute arguments that are parsed like rust expressions. I spent some time trying to add that (e.g. something that would parse the attribute arguments as an AST while treating the remainder of the items as a token-tree), but its too big a lift for me to undertake. So instead I hacked in something approximating that goal, by semi-trivially desugaring the token-tree attribute contents into internal AST constucts. This may be too fragile for the long-term.
* (In particular, it *definitely* breaks when you try to add a contract to a function like this: `fn foo1(x: i32) -> S<{ 23 }> { ... }`, because its token-tree based search for where to inject the internal AST constructs cannot immediately see that the `{ 23 }` is within a generics list. I think we can live for this for the short-term, i.e. land the work, and continue working on it while in parallel adding a new attribute variant that takes a token-tree attribute alongside an AST annotation, which would completely resolve the issue here.)
* the *intent* of `-Z contract-checks` is that it behaves like `-Z ub-checks`, in that we do not prematurely commit to including or excluding the contract evaluation in upstream crates (most notably, `core` and `std`). But the current test suite does not actually *check* that this is the case. Ideally the test suite would be extended with a multi-crate test that explores the matrix of enabling/disabling contracts on both the upstream lib and final ("leaf") bin crates.
- `reindent_multiline()` always returns the result of
`reindent_multiline_inner()` which returns a `String`. Make
`reindent_multiline()` return a `String` as well, instead of a
systematically owned `Cow<'_, str>`.
- There is no reason for `reindent_multiline()` to force a caller to
build a `Cow<'_, str>` instead of passing a `&str` directly,
especially considering that a `String` will always be returned.
Also, both the input parameter and return value (of type `Cow<'_, str>`)
shared the same (elided) lifetime for no reason: this worked only because
the result was always the `Cow::Owned` variant which is compatible with
any lifetime.
As a consequence, the signature changes from:
```rust
fn reindent_multiline(s: Cow<'_, str>, …) -> Cow<'_, str> { … }
```
to
```rust
fn reindent_multiline(s: &str, …) -> String { … }
```
Hey folks. It's been a while since I added the `as_slice` method to
`Option`, and I totally forgot about a lint to suggest it. Well, I had
some time around Christmas, so here it is now.
---
changelog: add [`manual_option_as_slice`] lint
includes post-developed commit: do not suggest internal-only keywords as corrections to parse failures.
includes post-developed commit: removed tabs that creeped in into rustfmt tool source code.
includes post-developed commit, placating rustfmt self dogfooding.
includes post-developed commit: add backquotes to prevent markdown checking from trying to treat an attr as a markdown hyperlink/
includes post-developed commit: fix lowering to keep contracts from being erroneously inherited by nested bodies (like closures).
Rebase Conflicts:
- compiler/rustc_parse/src/parser/diagnostics.rs
- compiler/rustc_parse/src/parser/item.rs
- compiler/rustc_span/src/hygiene.rs
Remove contracts keywords from diagnostic messages
Do not consider child bound assumptions for rigid alias
r? lcnr
See first commit for the important details. For second commit, I also stacked a somewhat opinionated name change, though I can separate that if needed.
Fixes https://github.com/rust-lang/trait-system-refactor-initiative/issues/149
Get rid of `mir::Const::from_ty_const`
This function is strange, because it turns valtrees into `mir::Const::Value`, but the rest of the const variants stay as type system consts.
All of the callsites except for one in `instsimplify` (array length simplification of `ptr_metadata` call) just go through the valtree arm of the function, so it's easier to just create a `mir::Const` directly for those.
For the instsimplify case, if we have a type system const we should *keep* having a type system const, rather than turning it into a `mir::Const::Value`; it doesn't really matter in practice, though, bc `usize` has no padding, but it feels more principled.
This lint detects and removes the unnecessary semicolon after a `match`
or `if` statement returning `()`. It seems to be quite a common
"mistake", given the number of hits (88) we had in the Clippy sources
themselves.
The lint doesn't bother about loops, as `rustfmt` already removes the
extra semicolon. It doesn't handle blocks either, as an extra block
level, followed or not by a semicolon, is likely intentional.
I propose to put the lint in `pedantic`, as putting it in `style` seems
quite hazardous given the number of hits.
Note: there exists a `redundant-semicolon` lint in the compiler, but it
is an early lint and cannot check that the expression evaluates to `()`,
so it ignores the cases we're handling here.
----
changelog: [`unnecessary_semicolon`]: new lint
By assuming that a recursive type is normalizable within the deeper
calls to `is_normalizable_helper()`, more cases can be handled by this
function.
In order to fix stack overflows, a recursion limit has also been added
for recursive generic type instantiations.
changelog: [`useless-nonzero-new_unchecked`]: new lint
Close#13991
### What it does
Checks for `NonZero*::new_unchecked(<literal>)` being used in a `const`
context.
### Why is this bad?
Using `NonZero*::new_unchecked()` is an `unsafe` function and requires
an `unsafe` context. When used with an
integer literal in a `const` context, `NonZero*::new().unwrap()` will
provide the same result with identical
runtime performances while not requiring `unsafe`.
### Example
```no_run
const PLAYERS: NonZeroUsize = unsafe { NonZeroUsize::new_unchecked(3) };
```
Use instead:
```no_run
const PLAYERS: NonZeroUsize = NonZeroUsize::new(3).unwrap();
```
Commit 9ef6e2199c introduced a check to
ensure that Clippy doesn't consider a lifetime present in an explicit
self types as being the default for an elided output lifetime. For
example, elision did not work in the case like:
```rust
fn func(self: &Rc<Self>, &str) -> &str { … }
```
Since Rust 1.81.0, the lifetime in the self type is now considered the
default for elision. Elision should then be suggested when appropriate.
changelog: [`needless_lifetimes`]: suggest elision of lifetimes present
in explicit self types as well
r? @Alexendoo
because of #8278
Commit 9ef6e2199c introduced a check to
ensure that Clippy doesn't consider a lifetime present in an explicit
self type as being the default for an elided output lifetime. For
example, elision did not work in the case like:
```rust
fn func(self: &Rc<Self>, &str) -> &str { … }
```
Since Rust 1.81.0, the lifetime in the self type is now considered
the default for elision. Elision should then be suggested when
appropriate.
changelog: [`manual_ok_err`]: new lint
Detect manual implementations of `.ok()` or `.err()`, as in
```rust
let a = match func() {
Ok(v) => Some(v),
Err(_) => None,
};
let b = if let Err(v) = func() {
Some(v)
} else {
None
};
```
which can be replaced by
```rust
let a = func().ok();
let b = func().err();
```
This pattern was detected in the wild in the Rust reimplementation of
coreutils:
https://github.com/uutils/coreutils/pull/6886#pullrequestreview-2465160137