Structurally resolve before applying projection in borrowck
As far as I can tell, all other `.normalize` calls in borrowck are noops and can remain that way. This is the only one that actually requires structurally resolving the type.
r? lcnr
Check `xform_ret_ty` for WF in the new solver to improve method winnowing
This is a bit interesting. Method probing in the old solver is stronger than the new solver because eagerly normalizing types causes us to check their corresponding trait goals. This is important because we don't end up checking all of the where clauses of a method when method probing; just the where clauses of the impl. i.e., for:
```
impl Foo
where
WC1,
{
fn method()
where
WC2,
{}
}
```
We only check WC1 and not WC2. This is because at this point in probing the method is instantiated w/ infer vars, and checking the where clauses in WC2 will lead to cycles if we were to check them (at least that's my understanding; I could investigate changing that in general, incl. in the old solver, but I don't have much confidence that it won't lead to really bad overflows.)
This PR chooses to emulate the old solver by just checking that the return type is WF. This is theoretically stronger, but I'm not too worried about it. I think we alternatively have several approaches we can take here, though this one seems the simplest. Thoughts?
r? lcnr
Add `as_array` and `as_mut_array` conversion methods to slices.
Tracking issue: #133508
This PR unstably implements the `as_array` and `as_mut_array` converters to `[T]`, `*const [T]`, and `*mut [T]`.
Actually use placeholder regions for trait method late bound regions in `collect_return_position_impl_trait_in_trait_tys`
So in https://github.com/rust-lang/rust/pull/113182, I introduced a "diagnostics improvement" in the form of 473c88dfb6, which changes which signature we end up instantiating with placeholder regions and which signature we end up instantiating with fresh region vars so that we have placeholders corresponding to the names of the late-bound regions coming from the *impl*.
However, this is not sound, since now we're essentially no longer proving that *all* instantiations of the trait method are compatible with an instantiation of the impl method, but vice versa (which is weaker). Let's look at the example `tests/ui/impl-trait/in-trait/do-not-imply-from-trait-impl.rs`:
```rust
trait MkStatic {
fn mk_static(self) -> &'static str;
}
impl MkStatic for &'static str {
fn mk_static(self) -> &'static str { self }
}
trait Foo {
fn foo<'a: 'static, 'late>(&'late self) -> impl MkStatic;
}
impl Foo for str {
fn foo<'a: 'static>(&'a self) -> impl MkStatic + 'static {
self
}
}
fn call_foo<T: Foo + ?Sized>(t: &T) -> &'static str {
t.foo().mk_static()
}
fn main() {
let s = call_foo(String::from("hello, world").as_str());
println!("> {s}");
}
```
To collect RPITITs, we were previously instantiating the trait signature with infer vars (`fn(&'?0 str) -> ?1t` where `?1t` is the variable we use to infer the RPITIT) and the impl signature with placeholders (there are no late-bound regions in that signature, so we just have `fn(&'a str) -> Opaque`).
Equating the signatures works, since all we do is unify `?1t` with `Opaque` and `'?0` with `'a`. However, conceptually it *shouldn't* hold, since this definition is not valid for *all* instantiations of the trait method but just the one where `'0` (i.e. `'late`) is equal to `'a` :(
## So what
This PR effectively reverts 473c88dfb6 to fix the unsoundness.
Fixes#133427
Also fixes#133425, which is actually coincidentally another instance of this bug (but not one that is weaponized into UB, just one that causes an ICE in refinement checking).
Delay a bug when encountering an impl with unconstrained generics in `codegen_select`
Despite its name, `codegen_select` is what powers `Instance::try_resolve`, which is used in pre-codegen contexts to try to resolve a method where possible. One place that it's used is in the "recursion MIR lint" that detects recursive MIR bodies.
If we encounter an impl in `codegen_select` that contains unconstrained generic parameters, we expect that impl to caused an error to be reported; however, there's no temporal guarantee that this error is reported *before* we call `codegen_select`. This is what a delayed bug is *for*, and this PR makes us use a delayed bug rather than asserting something about errors already having been emitted.
Fixes #126646
Expand std::os::unix::fs::chown() doc with a warning
Include warning about losing setuid/gid when chowning, per POSIX.
It is about the underlying system call but it is rather useful to mention it in the help in case someone accidentally forgets (don't look at me :)).
Recover some lost performence from #132732
This PR reorders some conditions in the `dangling_pointers_from_temporaries` lint to avoid some potentially expensive query call, in particular those who could involve some metadata decoding from disk.
cc https://github.com/rust-lang/rust/pull/132732#issuecomment-2499990683
cc `@Kobzol`
Some minor dyn-related tweaks
Each commit should be self-explanatory, but I'm happy to explain what's going on if not. These are tweaks I pulled out of #133388, but they can be reviewed sooner than that.
r? types
Allow injecting a profiler runtime into `#![no_core]` crates
An alternative to #133300, allowing `-Cinstrument-coverage` to be used with `-Zbuild-std`.
The incompatibility between `profiler_builtins` and `#![no_core]` crates appears to have been caused by profiler_builtins depending on core, and therefore conflicting with core (or minicore).
But that's a false dependency, because the profiler doesn't contain any actual Rust code. So we can just mark the profiler itself as `#![no_core]`, and remove the incompatibility error.
---
For context, the error was originally added by #79958.
do not constrain infer vars in `find_best_leaf_obligation`
This ended up causing an ICE by making the following code path reachable by incorrectly constraining an inference variable while computing the best obligation for a preceding ambiguity. Closes#129444.
f2abf827c1/compiler/rustc_trait_selection/src/solve/fulfill.rs (L312-L314)
I have to be honest, I don't fully understand how that change removes all the additional diagnostics :3
r? `@compiler-errors`
miri: implement `TlsFree`
If the variable does not need a destructor, `std` uses racy initialization for creating TLS keys on Windows. With just the right timing, this can lead to `TlsFree` being called. Unfortunately, with #132654 this is hit quite often, so miri should definitely support `TlsFree` ([documentation](https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-tlsfree)).
I'm filing this here instead of in the miri repo so that #132654 isn't blocked for so long.
Commit license-metadata.json to git and check it's correct in CI
This PR adds `license-metadata.json` to the root of the git repo, and changes `mingw-check` to check that the file is still up-to-date.
By committing this file, we remove the need for developers to a) have reuse installed or b) run an expensive ~90 second analysis of the files on disk when they want generate the COPYRIGHT.html files which depend on this license metadata.
The file will need updating whenever `REUSE.toml` changes, or when git submodules are added, or when git submodules change their license information (as detected by REUSE).
You can now run:
* `./x run collect-license-metadata` to update the `./license-metadata.json` file
* `./x test collect-license-metadata` to test the `./license-metadata.json` file for correctness
The comparison is done with two `serde_json::Value` objects, so the map objects they contain should ignore differences in ordering.
use `--exact` on `--skip` to avoid unintended substring matches
Without the `--exact` flag, using `--skip tests/rustdoc` can unintentionally skip other tests that match as substrings such as `rustdoc-gui`, `rustdoc-js`, etc.
For debugging, run: `./x.py --stage 2 test rustdoc-ui --skip tests/rustdoc` and `./x.py --stage 2 test rustdoc-ui --skip tests/rustdoc -- --exact`
Resolves https://github.com/rust-lang/rust/issues/117721
try-job: x86_64-apple-1
Use edition of `macro_rules` when compiling the macro
This changes the edition assigned to a macro_rules macro when it is compiled to use the edition of where the macro came from instead of the local crate's edition.
This fixes a problem when a macro_rules macro is created by a proc-macro. Previously that macro would be tagged with the local edition, which would cause problems with using the correct edition behavior inside the macro. For example, the check for unsafe attributes would cause errors in 2024 when using proc-macros from older editions.
This is partially related to https://github.com/rust-lang/rust/issues/132906. Unfortunately this is only a half fix for that issue. It fixes the error that happens in 2024, but does not fix the lint firing in 2021. I'm still trying to think of some way to fix that, but I'm running low on ideas.
Fix `Result` and `Option` not getting a jump to def link generated
It was just because we didn't store the "span" in the `PreludeTy` variant.
r? ``@notriddle``
Revert diagnostics hack to fix ICE 132920
This reverts 8a568d9f15 from #128849 to fix the diagnostics ICE in #132920.
The hack mentioned in that commit was supposed to be tailored to E277, but that codepath is used actually shared with other errors, e.g. at least the E283 from the linked issue.
We may have to eat the slightly worse diagnostics until a non-hacky way to make this error less verbose is implemented (or I guess a different hack specializing even more to E277's structure).
Sorry ``@estebank`` 🙏. I can close this if you'd prefer to fix it in a different way.
Since it seems unexpected that #128849 would impact the repro, here's how the error used to look before that PR.
```console
warning: unused import: `minirapier::Ray`
--> src/main.rs:2:5
|
2 | use minirapier::Ray;
| ^^^^^^^^^^^^^^^
|
= note: `#[warn(unused_imports)]` on by default
error[E0283]: type annotations needed
--> src/main.rs:10:5
|
10 | insert_resource(Res.into());
| ^^^^^^^^^^^^^^^ ---------- type must be known at this point
| |
| cannot infer type of the type parameter `R` declared on the function `insert_resource`
|
= note: cannot satisfy `_: Resource`
= help: the trait `Resource` is implemented for `Res`
note: required by a bound in `insert_resource`
--> src/main.rs:4:23
|
4 | fn insert_resource<R: Resource>(_resource: R) {}
| ^^^^^^^^ required by this bound in `insert_resource`
help: consider specifying the generic argument
|
10 | insert_resource::<R>(Res.into());
| +++++
help: consider removing this method call, as the receiver has type `Res` and `Res: Resource` trivially holds
|
10 - insert_resource(Res.into());
10 + insert_resource(Res);
```
And how it looks now without the ICE.
```console
warning: unused import: `minirapier::Ray`
--> src/main.rs:2:5
|
2 | use minirapier::Ray;
| ^^^^^^^^^^^^^^^
|
= note: `#[warn(unused_imports)]` on by default
error[E0283]: type annotations needed
--> src/main.rs:10:5
|
10 | insert_resource(Res.into());
| ^^^^^^^^^^^^^^^ ---------- type must be known at this point
| |
| cannot infer type of the type parameter `R` declared on the function `insert_resource`
|
= note: cannot satisfy `_: Resource`
note: there are multiple different versions of crate `minibevy` in the dependency graph
--> /home/lqd/rust/tmp/minimization/issue-132920/rustc-ice-version-conflict/minibevy_b/src/lib.rs:1:1
|
1 | pub trait Resource {}
| ^^^^^^^^^^^^^^^^^^ this is the required trait
|
::: src/main.rs:1:5
|
1 | use minibevy::Resource;
| -------- one version of crate `minibevy` is used here, as a direct dependency of the current crate
2 | use minirapier::Ray;
| ---------- one version of crate `minibevy` is used here, as a dependency of crate `minirapier`
|
::: /home/lqd/rust/tmp/minimization/issue-132920/rustc-ice-version-conflict/minibevy_a/src/lib.rs:1:1
|
1 | pub trait Resource {}
| ------------------ this is the found trait
= help: you can use `cargo tree` to explore your dependency tree
note: required by a bound in `insert_resource`
--> src/main.rs:4:23
|
4 | fn insert_resource<R: Resource>(_resource: R) {}
| ^^^^^^^^ required by this bound in `insert_resource`
help: consider specifying the generic argument
|
10 | insert_resource::<R>(Res.into());
| +++++
help: consider removing this method call, as the receiver has type `Res` and `Res: Resource` trivially holds
|
10 - insert_resource(Res.into());
10 + insert_resource(Res);
|
```
The improvements from #128849 are still present and the note about the trait coming from the 2 versions of bevy is more explanatory/helpful than before, albeit a bit verbosely.
Fixes#132920.
Remove -Zfuel.
I'm not sure this feature is used. I only found 2 references in a google search, both referring to its introduction.
Meanwhile, it's a global mutable state, untracked by incremental compilation, so incompatible with it.
Bail on more errors in dyn ty lowering
If we have more than one principal trait, or if we have a principal trait with errors in it, then bail with `TyKind::Error` rather than attempting lowering. Lowering a dyn trait with more than one principal just arbitrarily chooses the first one and drops the subsequent ones, and lowering a dyn trait path with errors in it is just kinda useless.
This suppresses unnecessary errors which I think is net-good, but also is important to make sure that we don't end up leaking `{type error}` in https://github.com/rust-lang/rust/issues/133388 error messaging :)
r? types
Simplify array length mismatch error reporting (to not try to turn consts into target usizes)
This changes `TypeError::FixedArrayLen` to use `ExpectedFound<ty::Const<'tcx>>` (instead of `ExpectedFound<u64>`), and renames it to `TypeError::ArrayLen`. This allows us to avoid a `try_to_target_usize` call in the type relation, which ICEs when we have a scalar of the wrong bit length (i.e. u8).
This also makes `structurally_relate_tys` to always use this type error kind any time we have a const mismatch resulting from relating the array-len part of `[T; N]`.
This has the effect of changing the error message we issue for array length mismatches involving non-valtree consts. I actually quite like the change, though, since before:
```
LL | fn test<const N: usize, const M: usize>() -> [u8; M] {
| ------- expected `[u8; M]` because of return type
LL | [0; N]
| ^^^^^^ expected `M`, found `N`
|
= note: expected array `[u8; M]`
found array `[u8; N]`
```
and after, which I think is far less verbose:
```
LL | fn test<const N: usize, const M: usize>() -> [u8; M] {
| ------- expected `[u8; M]` because of return type
LL | [0; N]
| ^^^^^^ expected an array with a size of M, found one with a size of N
```
The only questions I have are:
1. Should we do something about backticks here? Right now we don't backtick either fully evaluated consts like `2`, or rigid consts like `Foo::BAR`.... but maybe we should? It seems kinda verbose to do for numbers -- maybe we could intercept those specifically.
2. I guess we may still run the risk of leaking unevaluated consts into error reporting like `2 + 1`...?
r? ``@BoxyUwU``
Fixes#126359Fixes#131101
No need to re-sort existential preds in relate impl
We already assert that these predicates are in the right ordering in `mk_poly_existential_predicates`.
r? types
Remove the `DefinitelyInitializedPlaces` analysis.
Its only use is in the `tests/ui/mir-dataflow/def_inits-1.rs` where it is tested via `rustc_peek_definite_init`.
Also, it's probably buggy. It's supposed to be the inverse of `MaybeUninitializedPlaces`, and it mostly is, except that `apply_terminator_effect` is a little different, and `apply_switch_int_edge_effects` is missing. Unlike `MaybeUninitializedPlaces`, which is used extensively in borrow checking, any bugs in `DefinitelyInitializedPlaces` are easy to overlook because it is only used in one small test.
This commit removes the analysis. It also removes
`rustc_peek_definite_init`, `Dual` and `MeetSemiLattice`, all of which are no longer needed.
r? ``@cjgillot``
Shorten the `MaybeUninit` `Debug` implementation
Currently the `Debug` implementation for `MaybeUninit` winds up being pretty verbose. This struct:
```rust
#[derive(Debug)]
pub struct Foo {
pub a: u32,
pub b: &'static str,
pub c: MaybeUninit<u32>,
pub d: MaybeUninit<String>,
}
```
Prints as:
Foo {
a: 0,
b: "hello",
c: core::mem::maybe_uninit::MaybeUninit<u32>,
d: core::mem::maybe_uninit::MaybeUninit<alloc::string::String>,
}
The goal is just to be a standin for content so the path prefix doesn't add any useful information. Change the implementation to trim `MaybeUninit`'s leading path, meaning the new result is now:
Foo {
a: 0,
b: "hello",
c: MaybeUninit<u32>,
d: MaybeUninit<alloc::string::String>,
}
Inline ExprPrecedence::order into Expr::precedence
The representation of expression precedence in rustc_ast has been an obstacle to further improvements in the pretty-printer (continuing from #119105 and #119427).
Previously the operation of *"does this expression have lower precedence than that one"* (relevant for parenthesis insertion in macro-generated syntax trees) consisted of 3 steps:
1. Convert `Expr` to `ExprPrecedence` using `.precedence()`
2. Convert `ExprPrecedence` to `i8` using `.order()`
3. Compare using `<`
As far as I can guess, the reason for the separation between `precedence()` and `order()` was so that both `rustc_ast::Expr` and `rustc_hir::Expr` could convert as straightforwardly as possible to the same `ExprPrecedence` enum, and then the more finicky logic performed by `order` could be present just once.
The mapping between `Expr` and `ExprPrecedence` was intended to be as straightforward as possible:
```rust
match self.kind {
ExprKind::Closure(..) => ExprPrecedence::Closure,
...
}
```
although there were exceptions of both many-to-one, and one-to-many:
```rust
ExprKind::Underscore => ExprPrecedence::Path,
ExprKind::Path(..) => ExprPrecedence::Path,
...
ExprKind::Match(_, _, MatchKind::Prefix) => ExprPrecedence::Match,
ExprKind::Match(_, _, MatchKind::Postfix) => ExprPrecedence::PostfixMatch,
```
Where the nature of `ExprPrecedence` becomes problematic is when a single expression kind might be associated with multiple different precedence levels depending on context (outside the expression) and contents (inside the expression). For example consider what is the precedence of an ExprKind::Closure `$closure`. Well, on the left-hand side of a binary operator it would need parentheses in order to avoid the trailing binary operator being absorbed into the closure body: `($closure) + Rhs`, so the precedence is something lower than that of `+`. But on the right-hand side of a binary operator, a closure is just a straightforward prefix expression like a unary op, which is a relatively high precedence level, higher than binops but lower than method calls: `Lhs + $closure` is fine without parens but `($closure).method()` needs them. But as a third case, if the closure contains an explicit return type, then the precedence is an even higher level than that, never needing parenthesization even in a binop left-hand side or method call: `|| -> bool { false } + Rhs` or `|| -> bool { false }.method()`.
You can see that trying to capture all of this resolution about expressions into `ExprPrecedence` violates the intention of `ExprPrecedence` being a straightforward one-to-one correspondence from each AST and HIR `ExprKind` variant. It would be possible to attempt that by doing stuff like `ExprPrecedence::Closure(Side::Leading, ReturnType::No)`, but I don't foresee the original envisioned benefit of the `precedence()`/`order()` distinction being retained in this approach. Instead I want to move toward a model that Syn has been using successfully. In Syn, there is a Precedence enum but it differs from rustc in the following ways:
- There are [relatively few variants](https://github.com/dtolnay/syn/blob/2.0.87/src/precedence.rs#L11-L47) compared to rustc's `ExprPrecedence`. For example there is no distinction at the precedence level between returns and closures, or between loops and method calls.
- We distinguish between [leading](https://github.com/dtolnay/syn/blob/2.0.87/src/fixup.rs#L293) and [trailing](https://github.com/dtolnay/syn/blob/2.0.87/src/fixup.rs#L309) precedence, taking into account an expression's context such as what token follows it (for various syntactic bail-outs in Rust's grammar, like ambiguities around break-with-value) and how it relates to operators from the surrounding syntax tree.
- There are no hardcoded mysterious integer quantities like rustc's `PREC_CLOSURE = -40`. All precedence comparisons are performed via PartialOrd on a C-like enum.
This PR is just a first step in these changes. As you can tell from Syn, I definitely think there is value in having a dedicated type to represent precedence, instead of what `order()` is doing with `i8`. But that is a whole separate adventure because rustc_ast doesn't even agree consistently on `i8` being the type for precedence order; `AssocOp::precedence` instead uses `usize` and there are casts in both directions. It is likely that a type called `ExprPrecedence` will re-appear, but it will look substantially different from the one that existed before this PR.
Support ranges in `<[T]>::get_many_mut()`
As per T-libs-api decision in #104642.
I implemented that with a separate trait and not within `SliceIndex`, because doing that via `SliceIndex` requires adding support for range types that are (almost) always overlapping e.g. `RangeFrom`, and also adding fake support code for `impl SliceIndex<str>`.
An inconvenience that I ran into was that slice indexing takes the index by value, but I only have it by reference. I could change slice indexing to take by ref, but this is pretty much the hottest code ever so I'm afraid to touch it. Instead I added a requirement for `Clone` (which all index types implement anyway) and cloned. This is an internal requirement the user won't see and the clone should always be optimized away.
I also implemented `Clone`, `PartialEq` and `Eq` for the error type, since I noticed it does not do that when writing the tests and other errors in std seem to implement them. I didn't implement `Copy` because maybe we will want to put something non-`Copy` there.
btree: add `{Entry,VacantEntry}::insert_entry`
This matches the recently-stabilized methods on `HashMap` entries. I've
reused tracking issue #65225 for now, but we may want to split it.