Add new `PatKind::Missing` variants
To avoid some ugly uses of `kw::Empty` when handling "missing" patterns, e.g. in bare fn tys. Helps with #137978. Details in the individual commits.
r? ``@oli-obk``
Misc query tweaks
Remove some redundant work around `cache_on_disk` and `ensure_ok`, since `Result<(), ErrorGuaranteed>` queries don't need to cache or recompute their "value" if they are only used for their result.
In the AST, currently we use `BinOpKind` within `ExprKind::AssignOp` and
`AssocOp::AssignOp`, even though this allows some nonsensical
combinations. E.g. there is no `&&=` operator. Likewise for HIR and
THIR.
This commit introduces `AssignOpKind` which only includes the ten
assignable operators, and uses it in `ExprKind::AssignOp` and
`AssocOp::AssignOp`. (And does similar things for `hir::ExprKind` and
`thir::ExprKind`.) This avoids the possibility of nonsensical
combinations, as seen by the removal of the `bug!` case in
`lang_item_for_binop`.
The commit is mostly plumbing, including:
- Adds an `impl From<AssignOpKind> for BinOpKind` (AST) and `impl
From<AssignOp> for BinOp` (MIR/THIR).
- `BinOpCategory` can now be created from both `BinOpKind` and
`AssignOpKind`.
- Replaces the `IsAssign` type with `Op`, which has more information and
a few methods.
- `suggest_swapping_lhs_and_rhs`: moves the condition to the call site,
it's easier that way.
- `check_expr_inner`: had to factor out some code into a separate
method.
I'm on the fence about whether avoiding the nonsensical combinations is
worth the extra code.
Rollup of 6 pull requests
Successful merges:
- #138992 (literal pattern lowering: use the pattern's type instead of the literal's in `const_to_pat`)
- #139211 (interpret: add a version of run_for_validation for &self)
- #139235 (`AstValidator` tweaks)
- #139237 (Add a dep kind for use of the anon node with zero dependencies)
- #139260 (Add dianqk to codegen reviewers)
- #139264 (Fix two incorrect turbofish suggestions)
r? `@ghost`
`@rustbot` modify labels: rollup
literal pattern lowering: use the pattern's type instead of the literal's in `const_to_pat`
This has two purposes:
- First, it enables removing the `treat_byte_string_as_slice` fields from `TypeckResults` and `ConstToPat`. A byte string pattern's type will be `&[u8]` when matching on a slice reference, so `const_to_pat` will lower it to a slice ref pattern. I believe this is tested by `tests/ui/match/pattern-deref-miscompile.rs`.
- Second, it will simplify the implementation of byte string literals in deref patterns. If byte string patterns can be given the type `[u8; N]` or `[u8]` during HIR typeck, then nothing needs to be changed in `const_to_pat` in order to lower the patterns `deref!(b"..."): Vec<u8>` and `deref!(b"..."): Box<[u8; 3]>`.
Implementation-wise, this uses `lit_to_const` to make a const with the pattern's type and the literal's valtree; that feels to me like the best way to make sure that the valtree representations of the pattern type and literal are the same. Though it may necessitate later changes to `lit_to_const` to accommodate giving byte string literal patterns non-reference types—would that be reasonable?
This unfortunately doesn't work for the `string_deref_patterns` feature (since that gives string literal patterns the `String` type), so I added a workaround for that. However, once `deref_patterns` supports string literals, it may be able to replace `string_deref_patterns`; the special case for `String` can removed at that point.
r? ``@oli-obk``
"Missing" patterns are possible in bare fn types (`fn f(u32)`) and
similar places. Currently these are represented in the AST with
`ast::PatKind::Ident` with no `by_ref`, no `mut`, an empty ident, and no
sub-pattern. This flows through to `{hir,thir}::PatKind::Binding` for
HIR and THIR.
This is a bit nasty. It's very non-obvious, and easy to forget to check
for the exceptional empty identifier case.
This commit adds a new variant, `PatKind::Missing`, to do it properly.
The process I followed:
- Add a `Missing` variant to `{ast,hir,thir}::PatKind`.
- Chang `parse_param_general` to produce `ast::PatKind::Missing`
instead of `ast::PatKind::Missing`.
- Look through `kw::Empty` occurrences to find functions where an
existing empty ident check needs replacing with a `PatKind::Missing`
check: `print_param`, `check_trait_item`, `is_named_param`.
- Add a `PatKind::Missing => unreachable!(),` arm to every exhaustive
match identified by the compiler.
- Find which arms are actually reachable by running the test suite,
changing them to something appropriate, usually by looking at what
would happen to a `PatKind::Ident`/`PatKind::Binding` with no ref, no
`mut`, an empty ident, and no subpattern.
Quite a few of the `unreachable!()` arms were never reached. This makes
sense because `PatKind::Missing` can't happen in every pattern, only
in places like bare fn tys and trait fn decls.
I also tried an alternative approach: modifying `ast::Param::pat` to
hold an `Option<P<Pat>>` instead of a `P<Pat>`, but that quickly turned
into a very large and painful change. Adding `PatKind::Missing` is much
easier.
This allows us to remove the field `treat_byte_string_as_slice` from
`TypeckResults`, since the pattern's type contains everything necessary
to get the correct lowering for byte string literal patterns.
This leaves the implementation of `string_deref_patterns` broken, to be
fixed in the next commit.
Don't produce debug information for compiler-introduced-vars when desugaring assignments.
An assignment such as
(a, b) = (b, c);
desugars to the HIR
{ let (lhs, lhs) = (b, c); a = lhs; b = lhs; };
The repeated `lhs` leads to multiple Locals assigned to the same DILocalVariable. Rather than attempting to fix that, get rid of the debug info for these bindings that don't even exist in the program to begin with.
Fixes#138198
r? `@jieyouxu`
match lowering cleanup: remove unused unsizing logic from `non_scalar_compare`
Since array and slice constants are now translated to array and slice patterns, `non_scalar_compare` is only used for string comparisons. This specializes it to strings, renames it, and removes the unused array-unsizing logic.
This also updates the doc comments for `thir::PatKind::Constant` and `TestKind::Eq`, which referred to them being used for slice references.
r? ````@oli-obk````
Since array and slice constants are now lowered to array and slice
patterns, `non_scalar_compare` was only called for string comparisons.
This specializes it to strings, renames it, and removes the unused
array-unsizing logic.
This also updates some outdated doc comments.
An assignment such as
(a, b) = (b, c);
desugars to the HIR
{ let (lhs, lhs) = (b, c); a = lhs; b = lhs; };
The repeated `lhs` leads to multiple Locals assigned to the same DILocalVariable. Rather than
attempting to fix that, get rid of the debug info for these bindings that don't even exist
in the program to begin with.
Fixes#138198
It's very useful. There are some false positives involving integration
tests in `rustc_pattern_analysis` and `rustc_serialize`. There is also a
false positive involving `rustc_driver_impl`'s
`rustc_randomized_layouts` feature. And I removed a `rustc_span` mention
in a doc comment in `rustc_log` because it wasn't integral to the
comment but caused a dev-dependency.
mir_build: consider privacy when checking for irrefutable patterns
This PR fixes#137999.
Note that, since this makes the compiler reject code that was previously accepted, it will probably need a crater run.
I include a commit that factors out a common code pattern into a helper function, purely because the fact that this was repeated all over the place was bothering me. Let me know if I should split that into a separate PR instead.
Rollup of 7 pull requests
Successful merges:
- #138384 (Move `hir::Item::ident` into `hir::ItemKind`.)
- #138508 (Clarify "owned data" in E0515.md)
- #138531 (Store test diffs in job summaries and improve analysis formatting)
- #138533 (Only use `DIST_TRY_BUILD` for try jobs that were not selected explicitly)
- #138556 (Fix ICE: attempted to remap an already remapped filename)
- #138608 (rustc_target: Add target feature constraints for LoongArch)
- #138619 (Flatten `if`s in `rustc_codegen_ssa`)
r? `@ghost`
`@rustbot` modify labels: rollup
`hir::Item` has an `ident` field.
- It's always non-empty for these item kinds: `ExternCrate`, `Static`,
`Const`, `Fn`, `Macro`, `Mod`, `TyAlias`, `Enum`, `Struct`, `Union`,
Trait`, TraitAalis`.
- It's always empty for these item kinds: `ForeignMod`, `GlobalAsm`,
`Impl`.
- For `Use`, it is non-empty for `UseKind::Single` and empty for
`UseKind::{Glob,ListStem}`.
All of this is quite non-obvious; the only documentation is a single
comment saying "The name might be a dummy name in case of anonymous
items". Some sites that handle items check for an empty ident, some
don't. This is a very C-like way of doing things, but this is Rust, we
have sum types, we can do this properly and never forget to check for
the exceptional case and never YOLO possibly empty identifiers (or
possibly dummy spans) around and hope that things will work out.
The commit is large but it's mostly obvious plumbing work. Some notable
things.
- A similar transformation makes sense for `ast::Item`, but this is
already a big change. That can be done later.
- Lots of assertions are added to item lowering to ensure that
identifiers are empty/non-empty as expected. These will be removable
when `ast::Item` is done later.
- `ItemKind::Use` doesn't get an `Ident`, but `UseKind::Single` does.
- `lower_use_tree` is significantly simpler. No more confusing `&mut
Ident` to deal with.
- `ItemKind::ident` is a new method, it returns an `Option<Ident>`. It's
used with `unwrap` in a few places; sometimes it's hard to tell
exactly which item kinds might occur. None of these unwraps fail on
the test suite. It's conceivable that some might fail on alternative
input. We can deal with those if/when they happen.
- In `trait_path` the `find_map`/`if let` is replaced with a loop, and
things end up much clearer that way.
- `named_span` no longer checks for an empty name; instead the call site
now checks for a missing identifier if necessary.
- `maybe_inline_local` doesn't need the `glob` argument, it can be
computed in-function from the `renamed` argument.
- `arbitrary_source_item_ordering::check_mod` had a big `if` statement
that was just getting the ident from the item kinds that had one. It
could be mostly replaced by a single call to the new `ItemKind::ident`
method.
- `ItemKind` grows from 56 to 64 bytes, but `Item` stays the same size,
and that's what matters, because `ItemKind` only occurs within `Item`.
The existing method does some non-obvious extra work to collect user types and
build user-type projections, which is specifically needed by `declare_bindings`
and not by the other two callers.
Continuing the work from #137350.
Removes the unused methods: `expect_variant`, `expect_field`,
`expect_foreign_item`.
Every method gains a `hir_` prefix.
Do not write user type annotation for const param value path
As I noted in the code comment, `DefKind::ConstParam` isn't actually *generic* over its own args, we just use the identity args from the body when lowering the value path so we have something to plug into the `EarlyBinder` we get back from `type_of` for the const param. So skip over it in `write_user_type_annotation_from_args`.
Somewhat unrelated, but I left an explanation for a somewhat mysterious quirk in the THIR lowering of user type annotations for patterns having to do with ctors and their `type_of` not actually being the type of the pattern node it's ascribing.
Fixes#138048
r? ``@BoxyUwU``
Allow int literals for pattern types with int base types
r? ``@BoxyUwU``
I also added an error at layout computation time for layouts that contain wrapping ranges (happens at monomorphization time). This is obviously hacky, but at least prevents such types from making it to codegen for now. It made writing the tests for int literals easier as I didn't have to think about that edge case
Basically this PR allows you to stop using transmutes for creating pattern types and instead just use literals:
```rust
let x: pattern_type!(u32 is 5..10) = 7;
```
works, and if the literal is out of range you get a type mismatch because it just stays at the base type and the base type can't be coerced to the pattern type.
cc ``@joshtriplett`` ``@scottmcm``
Revert <https://github.com/rust-lang/rust/pull/138084> to buy time to
consider options that avoids breaking downstream usages of cargo on
distributed `rustc-src` artifacts, where such cargo invocations fail due
to inability to inherit `lints` from workspace root manifest's
`workspace.lints` (this is only valid for the source rust-lang/rust
workspace, but not really the distributed `rustc-src` artifacts).
This breakage was reported in
<https://github.com/rust-lang/rust/issues/138304>.
This reverts commit 48caf81484, reversing
changes made to c6662879b2.
Don't include global asm in `mir_keys`, fix error body synthesis
r? oli-obk
Fixes#137470Fixes#137471Fixes#137472Fixes#137473
try-job: test-various
try-job: x86_64-apple-2