Fix missing syntax context in lifetime hygiene debug output
`-Zunpretty=expanded,hygiene` was not printing the syntax context for lifetimes. For example, two macro-generated lifetimes `'a` with different hygiene would both print as `/* 2538 */` instead of `/* 2538#0 */` and `/* 2538#1 */`, making it impossible to distinguish them.
This was fixed by changing `print_lifetime` to call `ann_post()` with the full `Ident`, matching how regular identifiers are handled in `print_ident`.
Closes: rust-lang/rust#151797
privacy: Fix privacy lints in RPITITs
Visit RPITITs and report `private_interfaces`, `private_bounds` and `exported_private_dependencies` in them (these are regular, non-deprecation lints).
New hard errors are not reported, https://github.com/rust-lang/rust/pull/146470 is for hard errors.
So this PR doesn't contain any breakage or language changes.
Fix accidental type inference in array coercion
Fixesrust-lang/rust#136420.
If the expectation of array element is a type variable, we should avoid resolving it to the first element's type and wait until LUB coercion is completed.
We create a free type variable instead which is only used in this `CoerceMany`.
[`check_expr_match`](847e3ee6b0/compiler/rustc_hir_typeck/src/_match.rs (L72)) and [`check_expr_if`](847e3ee6b0/compiler/rustc_hir_typeck/src/expr.rs (L1329)) where `CoerceMany` is also used do the [same](847e3ee6b0/compiler/rustc_hir_typeck/src/expectation.rs (L50)).
### [FCP Proposal](https://github.com/rust-lang/rust/pull/140283#issuecomment-2933771068):
> Array expressions normally lub their element expressions' types to ensure that things like `[5, 5_u8]` work and don't result in type mismatches. When invoking a generic function `fn foo<T>(_: [T; N])` with an array expression, we end up with an infer var for the element type of the array in the signature. So when typecking the first array element we compare its type with the infer var and thus subsequently require all other elements to be the same type.
>
> This PR changes that to instead fall back to "not knowing" that the argument type is array of infer var, but just having an infer var for the entire argument. Thus we typeck the array expression normally, lubbing the element expressions, and then in the end comparing the array expression's type with the array of infer var type.
>
> Things like
>
> ```rust
> fn foo() {}
> fn bar() {}
> fn f<T>(_: [T; 2]) {}
>
> f([foo, bar]);
> ```
>
> and
>
> ```rust
> struct Foo;
> struct Bar;
> trait Trait {}
> impl Trait for Foo {}
> impl Trait for Bar {}
> fn f<T>(_: [T; 2]) {}
>
> f([&Foo, &Bar as &dyn Trait]);
> ```
### Remaining inconsistency with `if` and `match`(rust-lang/rust#145048):
The typeck of array always uses the element coercion target type as the expectation of element exprs while `if` and `match` use `NoExpectation` if the expected type is an infer var.
This causes that array doesn't support nested coercion.
```rust
fn foo() {}
fn bar() {}
fn main() {
let _ = [foo, if false { bar } else { foo }]; // type mismatch when trying to coerce `bar` into `foo` in if-then branch coercion.
}
```
But we can't simply change this behavior to be the same as `if` and `match` since [many code](https://github.com/rust-lang/rust/pull/140283#issuecomment-3190564399) depends on using the first element's type as expectation.
Suggest ignore returning value inside macro for unused_must_use lint
Fixesrust-lang/rust#151269
The first commit fix the original issue,
the second commit is a code refactoring in this lint.
`-Zunpretty=expanded,hygiene` was not printing the syntax context for
lifetimes. For example, two macro-generated lifetimes `'a` with different
hygiene would both print as `/* 2538 */` instead of `/* 2538#0 */` and
`/* 2538#1 */`, making it impossible to distinguish them.
This was fixed by changing `print_lifetime` to call `ann_post()` with
the full `Ident`, matching how regular identifiers are handled in
`print_ident`.
Cleanup of `#[derive(Diagnostic)]` attribute parsers
This PR does a lot of refactoring on the implementation of `#[derive(Diagnostic)]`. It should have no observable effect other than error messages for incorrect usage of the attributes. In general, I think the error messages got better.
This PR can be reviewed commit by commit, each commit passes the tests.
- [Convert parse_nested_meta to parse_args_with for #[diagnostic]](https://github.com/rust-lang/rust/pull/151657/changes/9e61014a8a0bb1f1d7911511c303a7ae2a9c2a7d)
Start parsing `#[diagnostic]` using `syn`'s `parse_args_with` function instead of `parse_nested_meta`. This improves error messages and prepares for the new syntax needed for https://github.com/rust-lang/rust/issues/151366 which cannot be parsed using `parse_args_with`.
- [Convert parse_nested_meta to parse_args_with for #[subdiagnostic]](https://github.com/rust-lang/rust/pull/151657/changes/5d21a21695d56b74ea249f269ee10195251008b7)
Same as above but for `#[subdiagnostic]`
- [Remove unused no_span option](https://github.com/rust-lang/rust/pull/151657/changes/0bf3f5d51cb853884240792818d81e70daec6ab7)
Removes the `no_span` option of `#[suggestion]`, which there were no tests for and which seems to have been unused. If needed again in the future, this can be re-added pretty easily, but I find that unlikely.
- [Remove HasFieldMap trait in favour of passing FieldMap directly](https://github.com/rust-lang/rust/pull/151657/changes/2e8347abf4147d2bffe4d7989a21b17ae04cdb57)
Removes the `HasFieldMap` trait, because I don't really see the point of having a trait "has a field map" if we can just pass the fieldmap itself instead.
r? @Kivooeo
(Thanks for reviewing my PRs so far :3)
fix(parser): Disallow CR in frontmatter
T-lang came back on the stabilization PR (rust-lang/rust#148051) asking for CR to be disallowed
to leave room for all stray CRs to be rejected in the future.
At that point, the test can remain but the implementation can be
removed.
If that plan does not go through, we'll need to re-evaluate
- whether this is more lint-like and should defer to the calling tool
that is managing the frontmatter
- how much Rust should treat the frontmatter as Rust and apply the same
grammar restrictions of "no stray CR" (like raw string literals)
Part of rust-lang/rust#136889
[rustdoc] Add a marker to tell users that there are hidden (deprecated) items in the search results
Someone on mastodon rightfully pointed out that having a visual indication that some search results were hidden would be a good idea if the "hide deprecated items" setting is enabled. In particular if no results are displayed.
It looks like this:
<img width="861" height="228" alt="Screenshot From 2026-01-24 00-26-33" src="https://github.com/user-attachments/assets/93aeef11-a550-47dc-9c78-219ea4fd822c" />
r? @lolbinarycat
Improve move error diagnostic for `AsyncFn` closures
When an async closure captures a variable by move but is constrained to `AsyncFn` or `AsyncFnMut`, the error message now explains that the closure kind is the issue and points to the trait bound, similar to the existing diagnostic for `Fn`/`FnMut` closures.
**Before:**
```
error[E0507]: cannot move out of `foos` which is behind a shared reference
--> src/lib.rs:12:20
|
11 | async fn foo(foos: &mut [&mut Foo]) -> Result<(), ()> {
| ---- move occurs because `foos` has type...
12 | in_transaction(async || -> Result<(), ()> {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ `foos` is moved here
13 | for foo in foos {
| ---- variable moved due to use in coroutine
```
**After:**
```
error[E0507]: cannot move out of `y`, a captured variable in an `AsyncFn` closure
--> src/lib.rs:9:10
|
LL | let y = vec![format!("World")];
| - captured outer variable
LL | call(async || {
| ^^^^^^^^ captured by this `AsyncFn` closure
...
help: `AsyncFn` and `AsyncFnMut` closures require captured values to be able
to be consumed multiple times, but `AsyncFnOnce` closures may consume
them only once
--> src/lib.rs:5:27
|
LL | fn call<F>(_: F) where F: AsyncFn() {}
| ^^^^^^^^^
```
Fixesrust-lang/rust#150174
Tidy: detect ui tests subdirectory changes so `tests/ui/README.md` stays in sync
close: rust-lang/rust#150399
There's an issue where `tests/ui/README.md` isn't updated whenever the ui subdirectory changes.
I've added subdirectory change detection to tidy ~~added a new mention to `triage.toml` to notify `tests/ui/README.md` to also be updated~~.
r? @Urgau
Do not suggest `derive` if there is already an impl
This PR fixes an issue where the compiler would suggest adding `#[derive(Trait)]` even if the struct or enum already implements that trait manually.
Fixes [#146515](https://github.com/rust-lang/rust/issues/146515)
T-lang came back on the stabilization PR asking for CR to be disallowed
to leave room for all stray CRs to be rejected in the future.
At that point, the test can remain but the implementation can be
removed.
If that plan does not go through, we'll need to re-evaluate
- whether this is more lint-like and should defer to the calling tool
that is managing the frontmatter
- how much Rust should treat the frontmatter as Rust and apply the same
grammar restrictions of "no stray CR" (like raw string literals)
resolve: Replace `Macros20NormalizedIdent` with `IdentKey`
This is a continuation of https://github.com/rust-lang/rust/pull/150741 and https://github.com/rust-lang/rust/pull/150982 based on the ideas from https://github.com/rust-lang/rust/pull/151491#issuecomment-3784421866.
Before this PR `Macros20NormalizedIdent` was used as a key in various "identifier -> its resolution" maps in `rustc_resolve`.
`Macros20NormalizedIdent` is a newtype around `Ident` in which `SyntaxContext` (packed inside `Span`) is guaranteed to be normalized using `normalize_to_macros_2_0`.
This type is also used in a number of functions looking up identifiers in those maps.
`Macros20NormalizedIdent` still contains span locations, which are useless and ignored during hash map lookups and comparisons due to `Ident`'s special `PartialEq` and `Hash` impls.
This PR replaces `Macros20NormalizedIdent` with a new type called `IdentKey`, which contains only a symbol and a normalized unpacked syntax context. (E.g. `IdentKey` == `Macros20NormalizedIdent` minus span locations.)
So we avoid keeping additional data and doing some syntax context packing/unpacking.
Along with `IdentKey` you can often see `orig_ident_span: Span` being passed around.
This is an unnormalized span of the original `Ident` from which `IdentKey` was obtained.
It is not used in map keys, but it is used in a number of other scenarios:
- diagnostics
- edition checks
- `allow_unstable` checks
This is because `normalize_to_macros_2_0` normalization is lossy and the normalized spans / syntax contexts no longer contain parts of macro backtraces, while the original span contains everything.
When an async closure captures a variable by move but is constrained to
`AsyncFn` or `AsyncFnMut`, the error message now explains that the
closure kind is the issue and points to the trait bound, similar to the
existing diagnostic for `Fn`/`FnMut` closures.
Tweak `SlicePartialEq` to allow MIR-inlining the `compare_bytes` call
rust-lang/rust#150265 disabled this because it was a net perf win, but let's see if we can tweak the structure of this to allow more inlining on this side while still not MIR-inlining the loop when it's not just `memcmp` and thus hopefully preserving the perf win.
This should also allow MIR-inlining the length check, which was previously blocked, and thus might allow some obvious non-matches to optimize away as well.