2251 Commits

Author SHA1 Message Date
Matthias Krüger
11d5614a74
Rollup merge of #130013 - jonathan-conder:await_coverage, r=Zalathar
coverage: Count await when the Future is immediately ready

Currently `await` is only counted towards coverage if the containing
function is suspended and resumed at least once. This is because it
expands to code which contains a branch on the discriminant of `Poll`.

By treating it like a branching macro (e.g. `assert!`), these
implementation details will be hidden from the coverage results.

I added a test to ensure the fix works in simple cases, but the heuristic of picking only the first await-related covspan might be unreliable. I plan on testing more thoroughly with a real codebase over the next couple of weeks.

closes #98712
2024-09-06 07:33:59 +02:00
Matthias Krüger
0180b8fff0
Rollup merge of #129969 - GrigorenkoPV:boxed-ty, r=compiler-errors
Make `Ty::boxed_ty` return an `Option`

Looks like a good place to use Rust's type system.

---

Most of 4ac7bcbaad/compiler/rustc_middle/src/ty/sty.rs (L971-L1963) looks like it could be moved to `TyKind` (then I guess  `Ty` should be made to deref to `TyKind`).
2024-09-06 07:33:58 +02:00
Jonathan Conder
25d183057e coverage: Treat await similar to a macro
Currently `await` is only counted towards coverage if the containing
function is suspended and resumed at least once. This is because it
expands to code which contains a branch on the discriminant of `Poll`.

By treating it like a branching macro (e.g. `assert!`), these
implementation details will be hidden from the coverage results.
2024-09-06 17:01:59 +12:00
Pavel Grigorenko
f6e8a84eea Make Ty::boxed_ty return an Option 2024-09-06 00:30:36 +03:00
Matthias Krüger
15e7a67b50
Rollup merge of #129720 - nnethercote:simplify-dest_prop-mm, r=cjgillot
Simplify DestProp memory management

The DestProp MIR pass has some convoluted memory management. This PR simplifies it.

r? ```@davidtwco```
2024-09-05 18:58:55 +02:00
Matthias Krüger
11085aa73a
Rollup merge of #129706 - compiler-errors:scratch, r=estebank
Rename dump of coroutine by-move-body to be more consistent, fix ICE in dump_mir

First, we add a missing match for `DefKind::SyntheticCoroutineBody` in `dump_mir`. Fixes #129703. The second commit (directly below) serves as a test.

Second, we reorder the `dump_mir` in `coroutine_by_move_body_def_id` to be *after* we adjust the body source, and change the disambiguator so it reads more like any other MIR body. This also serves as a test for the ICE, since we're dumping the MIR of a body with `DefKind::SyntheticCoroutineBody`.

Third, we change the parenting of the synthetic MIR body to have the *coroutine-closure* (i.e. async closure) as its parent, so we don't have long strings of `{closure#0}-{closure#0}-{closure#0}`.

try-job: test-various
2024-09-05 18:58:55 +02:00
Michael Goulet
8860008e7f Re-parent the by-move body 2024-09-04 06:28:32 -04:00
Michael Goulet
5525043ac8 Rename dump of coroutine by-move-body to be more consistent, adjust test 2024-09-03 16:22:28 -04:00
Matthias Krüger
4ed0f0d384
Rollup merge of #129926 - nnethercote:mv-SanityCheck-and-MirPass, r=cjgillot
Move `SanityCheck` and `MirPass`

They are currently in `rustc_middle`. This PR moves them to `rustc_mir_transform`, which makes more sense.

r? ``@cjgillot``
2024-09-03 19:13:27 +02:00
Nicholas Nethercote
0b2b03cf70 Clarify a comment. 2024-09-03 16:04:09 +10:00
Nicholas Nethercote
827fa43392 Reduce visibility of MirPass and related things.
They're now all just used within this crate.
2024-09-03 16:04:09 +10:00
Nicholas Nethercote
2aae619edb Move MirPass to rustc_mir_transform.
Because that's now the only crate that uses it.

Moving stuff out of `rustc_middle` is always welcome.

I chose to use `impl crate::MirPass`/`impl crate::MirLint` (with
explicit `crate::`) everywhere because that's the only mention of
`MirPass`/`MirLint` used in all of these files. (Prior to this change,
`MirPass` was mostly imported via `use rustc_middle::mir::*` items.)
2024-09-03 16:03:46 +10:00
Nicholas Nethercote
5410900aaa Adjust SanityCheck.
The actual implementation remains in `rustc_mir_dataflow`, but this
commit moves the `MirPass` impl to `rustc_mir_transform` and changes it
to a `MirLint` (fixing a `FIXME` comment).

(I originally tried moving the full implementation from
`rustc_mir_dataflow` but I had some trait problems with `HasMoveData`
and `RustcPeekAt` and `MaybeLiveLocals`. This commit was much smaller
and simpler, but still will allow some follow-up cleanups.)
2024-09-03 15:18:30 +10:00
Matthias Krüger
1d9eb9df7f
Rollup merge of #129877 - Sajjon:sajjon_fix_typos_batch_2, r=fee1-dead
chore: Fix typos in 'compiler' (batch 2)

Batch 2/3: Fixes typos in `compiler`

(See [issue](https://github.com/rust-lang/rust/issues/129874) tracking all PRs with typos fixes)
2024-09-02 22:35:21 +02:00
Alexander Cyon
00de006f22
chore: Fix typos in 'compiler' (batch 2) 2024-09-02 07:50:22 +02:00
Matthias Krüger
dce26656ea
Rollup merge of #129738 - nnethercote:rustc_mir_transform-cleanups, r=cjgillot
`rustc_mir_transform` cleanups

A bunch of small improvements I made while looking closely at this code.

r? `@saethlin`
2024-09-02 04:19:28 +02:00
Matthias Krüger
830b1deaee
Rollup merge of #129812 - RalfJung:box-custom-alloc, r=compiler-errors
interpret, codegen: tweak some comments and checks regarding Box with custom allocator

Cc https://github.com/rust-lang/rust/issues/95453
2024-08-31 14:46:14 +02:00
Matthias Krüger
7d025bb63d
Rollup merge of #129767 - nnethercote:rm-extern-crate-tracing-4, r=jieyouxu
Remove `#[macro_use] extern crate tracing`, round 4

Because explicit importing of macros via use items is nicer (more standard and readable) than implicit importing via #[macro_use]. Continuing the work from #124511, #124914, and #125434. After this PR no `rustc_*` crates use `#[macro_use] extern crate tracing` except for `rustc_codegen_gcc` which is a special case and I will do separately.

r? ```@jieyouxu```
2024-08-31 14:46:11 +02:00
Ralf Jung
d0aedfbb90 interpret, codegen: tweak some comments and checks regarding Box with custom allocator 2024-08-31 11:29:02 +02:00
Matthias Krüger
44185520cf
Rollup merge of #129724 - nnethercote:rm-Option-bang, r=fee1-dead
Remove `Option<!>` return types.

Several compiler functions have `Option<!>` for their return type. That's odd. The only valid return value is `None`, so why is this type used?

Because it lets you write certain patterns slightly more concisely. E.g. if you have these common patterns:
```
    let Some(a) = f() else { return };
    let Ok(b) = g() else { return };
```
you can shorten them to these:
```
    let a = f()?;
    let b = g().ok()?;
```
Huh.

An `Option` return type typically designates success/failure. How should I interpret the type signature of a function that always returns (i.e. doesn't panic), does useful work (modifying `&mut` arguments), and yet only ever fails? This idiom subverts the type system for a cute syntactic trick.

Furthermore, returning `Option<!>` from a function F makes things syntactically more convenient within F, but makes things worse at F's callsites. The callsites can themselves use `?` with F but should not, because they will get an unconditional early return, which is almost certainly not desirable. Instead the return value should be ignored. (Note that some of callsites of `process_operand`, `process_immedate`, `process_assign` actually do use `?`, though the early return doesn't matter in these cases because nothing of significance comes after those calls. Ugh.)

When I first saw this pattern I had no idea how to interpret it, and it took me several minutes of close reading to understand everything I've written above. I even started a Zulip thread about it to make sure I understood it properly. "Save a few characters by introducing types so weird that compiler devs have to discuss it on Zulip" feels like a bad trade-off to me. This commit replaces all the `Option<!>` return values and uses `else`/`return` (or something similar) to replace the relevant `?` uses. The result is slightly more verbose but much easier to understand.

r? ``````@cjgillot``````
2024-08-31 10:08:56 +02:00
Nicholas Nethercote
ac7a293336 Avoid repeated interning in SelfArgVisitor. 2024-08-30 13:35:41 +10:00
Nicholas Nethercote
8541b0f1f3 Use let/else to reduce some indentation. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
243109e006 Remove an unnecessary continue. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
590a02173b Factor out some repetitive code. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
408481f4d8 Remove some unnecessary constants.
These are just renamings of `CoroutineArgs` constants.
2024-08-30 10:30:57 +10:00
Nicholas Nethercote
d7cb1181dc Merge DerefArgVisitor and PinArgVisitor.
They are almost identical, differing only in the `ProjectionElem` they
insert. This commit merges them into a new type `SelfArgVisitor`.
2024-08-30 10:30:57 +10:00
Nicholas Nethercote
5331280a2b Merge some ifs.
For more concise code.
2024-08-30 10:30:57 +10:00
Nicholas Nethercote
3b6af9a451 Use a local variable. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
66b3585145 Simplify a pattern. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
2932e097f4 Simplify creation of a set. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
fda52b8f63 Simplify a provider definition. 2024-08-30 10:30:57 +10:00
Nicholas Nethercote
016a709b24 Condense use rustc_* declarations.
No reason to have two of them listed separately, after modules.
2024-08-30 10:30:56 +10:00
Nicholas Nethercote
016a2e30a9 Remove unused features. 2024-08-30 10:30:56 +10:00
Nicholas Nethercote
ed5161c5ac Remove #[macro_use] extern crate tracing from rustc_mir_transform. 2024-08-30 10:01:34 +10:00
Nicholas Nethercote
fa4f8925f1 Remove Option<!> return types.
Several compiler functions have `Option<!>` for their return type.
That's odd. The only valid return value is `None`, so why is this type
used?

Because it lets you write certain patterns slightly more concisely. E.g.
if you have these common patterns:
```
    let Some(a) = f() else { return };
    let Ok(b) = g() else { return };
```
you can shorten them to these:
```
    let a = f()?;
    let b = g().ok()?;
```
Huh.

An `Option` return type typically designates success/failure. How should
I interpret the type signature of a function that always returns (i.e.
doesn't panic), does useful work (modifying `&mut` arguments), and yet
only ever fails? This idiom subverts the type system for a cute
syntactic trick.

Furthermore, returning `Option<!>` from a function F makes things
syntactically more convenient within F, but makes things worse at F's
callsites. The callsites can themselves use `?` with F but should not,
because they will get an unconditional early return, which is almost
certainly not desirable. Instead the return value should be ignored.
(Note that some of callsites of `process_operand`, `process_immedate`,
`process_assign` actually do use `?`, though the early return doesn't
matter in these cases because nothing of significance comes after those
calls. Ugh.)

When I first saw this pattern I had no idea how to interpret it, and it
took me several minutes of close reading to understand everything I've
written above. I even started a Zulip thread about it to make sure I
understood it properly. "Save a few characters by introducing types so
weird that compiler devs have to discuss it on Zulip" feels like a bad
trade-off to me. This commit replaces all the `Option<!>` return values
and uses `else`/`return` (or something similar) to replace the relevant
`?` uses. The result is slightly more verbose but much easier to
understand.
2024-08-30 08:18:41 +10:00
Nicholas Nethercote
1be2204363 Simplify Candidate.
By making it own the index maps, instead of holding references to them.
This requires moving the free function `find_candidate` into
`Candidate::reset_and_find`. It lets the `'alloc` lifetime be removed
everywhere that still has it.
2024-08-29 12:13:22 +10:00
Nicholas Nethercote
ad5a6e11c7 Remove Allocations.
It's not necessary, and just complicates things.
2024-08-29 12:00:40 +10:00
Nicholas Nethercote
0a282ea717 Move WriteInfo out of Allocations.
It doesn't need to be in there, and the move simplifies lifetimes.
2024-08-29 12:00:40 +10:00
Nicholas Nethercote
c6111c0e80 Remove the 'body lifetime on FilterInformation.
It's not needed.
2024-08-29 12:00:40 +10:00
Ben Kimock
950437a035 Use a reduced recursion limit in the MIR inliner's cycle breaker 2024-08-28 19:52:23 -04:00
Zalathar
46e1b5b6dd coverage: Rename CodeRegion to SourceRegion
LLVM uses the word "code" to refer to a particular kind of coverage mapping.
This unrelated usage of the word is confusing, and makes it harder to introduce
types whose names correspond to the LLVM classification of coverage kinds.
2024-08-28 22:17:42 +10:00
Zalathar
5e162a8f48 coverage: Simplify some debug logging 2024-08-28 22:07:57 +10:00
Michael Goulet
4609841c07 Stop using a special inner body for the coroutine by-move body for async closures 2024-08-26 18:44:19 -04:00
Michael Goulet
0b2525c787 Simplify some redundant field names 2024-08-21 01:31:42 -04:00
Trevor Gross
5044b20028
Rollup merge of #128628 - khuey:simply-cfg-erase-source-info, r=nnethercote
When deduplicating unreachable blocks, erase the source information.

After deduplication the block conceptually belongs to multiple locations in the source. Although these blocks are unreachable, in #123341 we did come across a real side effect, an unreachable block that survives into the compiled code can cause a debugger to set a breakpoint on the wrong instruction. Erasing the source information ensures that a debugger will never be misled into thinking that the unreachable block is worth setting a breakpoint on, especially after #128627.

Technically we don't need to erase the source information if all the deduplicated blocks have identical source information, but tracking that seems like more effort than it's worth.

I'll let njn redirect this one too. r? `@nnethercote`
2024-08-18 23:41:47 -05:00
Ralf Jung
35709be02d rename AddressOf -> RawBorrow inside the compiler 2024-08-18 19:46:53 +02:00
Matthias Krüger
6c898d2b03
Rollup merge of #129101 - compiler-errors:deref-on-parent-by-ref, r=lcnr
Fix projections when parent capture is by-ref but child capture is by-value in the `ByMoveBody` pass

This fixes a somewhat strange bug where we build the incorrect MIR in #129074. This one is weird, but I don't expect it to actually matter in practice since it almost certainly results in a move error in borrowck. However, let's not ICE.

Given the code:

```
#![feature(async_closure)]

// NOT copy.
struct Ty;

fn hello(x: &Ty) {
    let c = async || {
        *x;
        //~^ ERROR cannot move out of `*x` which is behind a shared reference
    };
}

fn main() {}
```

The parent coroutine-closure captures `x: &Ty` by-ref, resulting in an upvar of `&&Ty`. The child coroutine captures `x` by-value, resulting in an upvar of `&Ty`. When constructing the by-move body for the coroutine-closure, we weren't applying an additional deref projection to convert the parent capture into the child capture, resulting in an type error in assignment, which is a validation ICE.

As I said above, this only occurs (AFAICT) in code that eventually results in an error, because it is only triggered by HIR that attempts to move a non-copy value out of a ref. This doesn't occur if `Ty` is `Copy`, since we'd instead capture `x` by-ref in the child coroutine.

Fixes #129074
2024-08-15 19:32:37 +02:00
Matthias Krüger
c582c0c137
Rollup merge of #129067 - cuviper:append, r=wesleywiser
Use `append` instead of `extend(drain(..))`

The first commit adds `IndexVec::append` that forwards to `Vec::append`, and uses it in a couple places.

The second commit updates `indexmap` for its new `IndexMap::append`, and also uses that in a couple places.

These changes are similar to what [`clippy::extend_with_drain`](https://rust-lang.github.io/rust-clippy/master/index.html#/extend_with_drain) would suggest, just for other collection types.
2024-08-15 00:02:27 +02:00
Michael Goulet
1e1d839388 Fix projections when parent capture is by-ref 2024-08-14 13:24:07 -04:00
bors
e9c965df7b Auto merge of #128812 - nnethercote:shrink-TyKind-FnPtr, r=compiler-errors
Shrink `TyKind::FnPtr`.

By splitting the `FnSig` within `TyKind::FnPtr` into `FnSigTys` and `FnHeader`, which can be packed more efficiently. This reduces the size of the hot `TyKind` type from 32 bytes to 24 bytes on 64-bit platforms. This reduces peak memory usage by a few percent on some benchmarks. It also reduces cache misses and page faults similarly, though this doesn't translate to clear cycles or wall-time improvements on CI.

r? `@compiler-errors`
2024-08-14 00:56:53 +00:00