Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rollup of 7 pull requests #128719

Closed
wants to merge 30 commits into from

Conversation

matthiaskrgr
Copy link
Member

Successful merges:

r? @ghost
@rustbot modify labels: rollup

Create a similar rollup

Voultapher and others added 30 commits July 27, 2024 16:47
The new sort implementations have the ability to
detect Ord violations in many cases. This commit
improves the message in a way that should help
users realize what went wrong in their program.
…ble*

- Move panic information into # Panics section
- Fix mentions of T: Ord that should be compare
- Add missing information
- Use if the implementation of [`Ord`] for `T`
  language
- Link to total order wiki page
- Rework total order help and examples
- Improve language to be more precise and less
  prone to misunderstandings.
- Fix usage of `sort_unstable_by` in `sort_by`
  example
- Fix missing author mention
- Use more consistent example input for sort
- Use more idiomatic assert_eq! in examples
- Use more natural "comparison function" language
  instead of "comparator function"
Since [1], `Cargo.lock` was split into `Cargo.lock` and
`library/Cargo.lock`. Update Triagebot to give the same warning for both.

[1]: rust-lang#128534
When encountering an E0277, if the type and the trait both come from a crate with the same name but different crate number, we explain that there are multiple crate versions in the dependency tree.

If there's a type that fulfills the bound, and it has the same name as the passed in type and has the same crate name, we explain that the same type in two different versions of the same crate *are different*.

```
error[E0277]: the trait bound `Type: dependency::Trait` is not satisfied
 --> src/main.rs:4:18
  |
4 |     do_something(Type);
  |     ------------ ^^^^ the trait `dependency::Trait` is not implemented for `Type`
  |     |
  |     required by a bound introduced by this call
  |
help: you have multiple different versions of crate `dependency` in your dependency graph
 --> src/main.rs:1:5
  |
1 | use bar::do_something;
  |     ^^^ one version of crate `dependency` is used here, as a dependency of crate `bar`
2 | use dependency::Type;
  |     ^^^^^^^^^^ one version of crate `dependency` is used here, as a direct dependency of the current crate
note: two types coming from two different versions of the same crate are different types even if they look the same
 --> /home/gh-estebank/crate_versions/baz-2/src/lib.rs:1:1
  |
1 | pub struct Type;
  | ^^^^^^^^^^^^^^^ this type doesn't implement the required trait
  |
 ::: /home/gh-estebank/crate_versions/baz/src/lib.rs:1:1
  |
1 | pub struct Type;
  | ^^^^^^^^^^^^^^^ this type implements the required trait
2 | pub trait Trait {}
  | --------------- this is the required trait
note: required by a bound in `bar::do_something`
 --> /home/gh-estebank/crate_versions/baz/src/lib.rs:4:24
  |
4 | pub fn do_something<X: Trait>(_: X) {}
  |                        ^^^^^ required by this bound in `do_something`
```

Address rust-lang#22750.
… r=fee1-dead

Stabilize `min_exhaustive_patterns`

## Stabilisation report

I propose we stabilize the [`min_exhaustive_patterns`](rust-lang#119612) language feature.

With this feature, patterns of empty types are considered unreachable when matched by-value. This allows:
```rust
enum Void {}
fn foo() -> Result<u32, Void>;

fn main() {
  let Ok(x) = foo();
  // also
  match foo() {
    Ok(x) => ...,
  }
}
```

This is a subset of the long-unstable [`exhaustive_patterns`](rust-lang#51085) feature. That feature is blocked because omitting empty patterns is tricky when *not* matched by-value. This PR stabilizes the by-value case, which is not tricky.

The not-by-value cases (behind references, pointers, and unions) stay as they are today, e.g.
```rust
enum Void {}
fn foo() -> Result<u32, &Void>;

fn main() {
  let Ok(x) = foo(); // ERROR: missing `Err(_)`
}
```

The consequence on existing code is some extra "unreachable pattern" warnings. This is fully backwards-compatible.

### Comparison with today's rust

This proposal only affects match checking of empty types (i.e. types with no valid values). Non-empty types behave the same with or without this feature. Note that everything below is phrased in terms of `match` but applies equallly to `if let` and other pattern-matching expressions.

To be precise, a visibly empty type is:
- an enum with no variants;
- the never type `!`;
- a struct with a *visible* field of a visibly empty type (and no #[non_exhaustive] annotation);
- a tuple where one of the types is visibly empty;
- en enum with all variants visibly empty (and no `#[non_exhaustive]` annotation);
- a `[T; N]` with `N != 0` and `T` visibly empty;
- all other types are nonempty.

(An extra change was proposed below: that we ignore #[non_exhaustive] for structs since adding fields cannot turn an empty struct into a non-empty one)

For normal types, exhaustiveness checking requires that we list all variants (or use a wildcard). For empty types it's more subtle: in some cases we require a `_` pattern even though there are no valid values that can match it. This is where the difference lies regarding this feature.

#### Today's rust

Under today's rust, a `_` is required for all empty types, except specifically: if the matched expression is of type `!` (the never type) or `EmptyEnum` (where `EmptyEnum` is an enum with no variants), then the `_` is not required.

```rust
let foo: Result<u32, !> = ...;
match foo {
    Ok(x) => ...,
    Err(_) => ..., // required
}
let foo: Result<u32, &!> = ...;
match foo {
    Ok(x) => ...,
    Err(_) => ..., // required
}
let foo: &! = ...;
match foo {
    _ => ..., // required
}
fn blah(foo: (u32, !)) {
    match foo {
        _ => ..., // required
    }
}
unsafe {
    let ptr: *const ! = ...;
    match *ptr {} // allowed
    let ptr: *const (u32, !) = ...;
    match *ptr {
        (x, _) => { ... } // required
    }
    let ptr: *const Result<u32, !> = ...;
    match *ptr {
        Ok(x) => { ... }
        Err(_) => { ... } // required
    }
}
```

#### After this PR

After this PR, a pattern of an empty type can be omitted if (and only if):
- the match scrutinee expression has type  `!` or `EmptyEnum` (like before);
- *or* the empty type is matched by value (that's the new behavior).

In all other cases, a `_` is required to match on an empty type.

```rust
let foo: Result<u32, !> = ...;
match foo {
    Ok(x) => ..., // `Err` not required
}
let foo: Result<u32, &!> = ...;
match foo {
    Ok(x) => ...,
    Err(_) => ..., // required because `!` is under a dereference
}
let foo: &! = ...;
match foo {
    _ => ..., // required because `!` is under a dereference
}
fn blah(foo: (u32, !)) {
    match foo {} // allowed
}
unsafe {
    let ptr: *const ! = ...;
    match *ptr {} // allowed
    let ptr: *const (u32, !) = ...;
    match *ptr {
        (x, _) => { ... } // required because the matched place is under a (pointer) dereference
    }
    let ptr: *const Result<u32, !> = ...;
    match *ptr {
        Ok(x) => { ... }
        Err(_) => { ... } // required because the matched place is under a (pointer) dereference
    }
}
```

### Documentation

The reference does not say anything specific about exhaustiveness checking, hence there is nothing to update there. The nomicon does, I opened rust-lang/nomicon#445 to reflect the changes.

### Tests

The relevant tests are in `tests/ui/pattern/usefulness/empty-types.rs`.

### Unresolved Questions

None that I know of.
…r=fee1-dead

On trait bound mismatch, detect multiple crate versions in dep tree

When encountering an E0277, if the type and the trait both come from a crate with the same name but different crate number, we explain that there are multiple crate versions in the dependency tree.

If there's a type that fulfills the bound, and it has the same name as the passed in type and has the same crate name, we explain that the same type in two different versions of the same crate *are different*.

```
error[E0277]: the trait bound `Type: dependency::Trait` is not satisfied
 --> src/main.rs:4:18
  |
4 |     do_something(Type);
  |     ------------ ^^^^ the trait `dependency::Trait` is not implemented for `Type`
  |     |
  |     required by a bound introduced by this call
  |
help: you have multiple different versions of crate `dependency` in your dependency graph
 --> src/main.rs:1:5
  |
1 | use bar::do_something;
  |     ^^^ one version of crate `dependency` is used here, as a dependency of crate `bar`
2 | use dependency::Type;
  |     ^^^^^^^^^^ one version of crate `dependency` is used here, as a direct dependency of the current crate
note: two types coming from two different versions of the same crate are different types even if they look the same
 --> /home/gh-estebank/crate_versions/baz-2/src/lib.rs:1:1
  |
1 | pub struct Type;
  | ^^^^^^^^^^^^^^^ this type doesn't implement the required trait
  |
 ::: /home/gh-estebank/crate_versions/baz/src/lib.rs:1:1
  |
1 | pub struct Type;
  | ^^^^^^^^^^^^^^^ this type implements the required trait
2 | pub trait Trait {}
  | --------------- this is the required trait
note: required by a bound in `bar::do_something`
 --> /home/gh-estebank/crate_versions/baz/src/lib.rs:4:24
  |
4 | pub fn do_something<X: Trait>(_: X) {}
  |                        ^^^^^ required by this bound in `do_something`
```

Address rust-lang#22750.
…elp, r=workingjubilee

Improve `Ord` violation help

Recent experience in rust-lang#128083 showed that the panic message when an Ord violation is detected by the new sort implementations can be confusing. So this PR aims to improve it, together with minor bug fixes in the doc comments for sort*, sort_unstable* and select_nth_unstable*.

Is it possible to get these changes into the 1.81 release? It doesn't change behavior and would greatly help when users encounter this panic for the first time, which they may after upgrading to 1.81.

Tagging `@orlp`
Forbid unused unsafe in vxworks-specific std modules

Tracking issue rust-lang#127747
Adding deny(unsafe_op_in_unsafe_fn) in VxWorks specific files did not cause any error.
Most of VxWorks falls back on Unix libraries. So we'll have to wait for Unix changes.

r? `@workingjubilee`
…Simulacrum

Add a triagebot mention for `library/Cargo.lock`

Since [1], `Cargo.lock` was split into `Cargo.lock` and `library/Cargo.lock`. Update Triagebot to give the same warning for both.

[1]: rust-lang#128534
Don't ICE when getting an input file name's stem fails

Fixes rust-lang#128681

The file stem is only used as a user-friendly prefix on intermediary files. While nice to have, it's not the end of the world if it fails so there's no real reason to emit an error here. We can continue with a fixed name as we do when an anonymous string is used.
@rustbot rustbot added A-meta Area: Issues & PRs about the rust-lang/rust repository itself A-run-make Area: port run-make Makefiles to rmake.rs O-unix Operating system: Unix-like S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-libs Relevant to the library team, which will review and decide on the PR/issue. rollup A PR which is a rollup labels Aug 6, 2024
@matthiaskrgr
Copy link
Member Author

@bors r+ rollup=never p=7

@bors
Copy link
Contributor

bors commented Aug 6, 2024

📌 Commit db95a01 has been approved by matthiaskrgr

It is now in the queue for this repository.

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Aug 6, 2024
bors added a commit to rust-lang-ci/rust that referenced this pull request Aug 6, 2024
…iaskrgr

Rollup of 7 pull requests

Successful merges:

 - rust-lang#122792 (Stabilize `min_exhaustive_patterns`)
 - rust-lang#124944 (On trait bound mismatch, detect multiple crate versions in dep tree)
 - rust-lang#128273 (Improve `Ord` violation help)
 - rust-lang#128406 (implement BufReader::peek)
 - rust-lang#128539 (Forbid unused unsafe in vxworks-specific std modules)
 - rust-lang#128692 (Add a triagebot mention for `library/Cargo.lock`)
 - rust-lang#128710 (Don't ICE when getting an input file name's stem fails)

r? `@ghost`
`@rustbot` modify labels: rollup
@bors
Copy link
Contributor

bors commented Aug 6, 2024

⌛ Testing commit db95a01 with merge a357411...

@rust-log-analyzer
Copy link
Collaborator

The job dist-aarch64-apple failed! Check out the build log: (web) (plain)

Click to see the possible cause of the failure (guessed by this bot)
   Compiling hir-ty v0.0.0 (/Users/runner/work/rust/rust/src/tools/rust-analyzer/crates/hir-ty)
error: unreachable pattern
   --> crates/hir-ty/src/mir/eval/shim.rs:30:13
    |
26  | / macro_rules! from_bytes {
27  | |     ($ty:tt, $value:expr) => {
28  | |         ($ty::from_le_bytes(match ($value).try_into() {
29  | |             Ok(it) => it,
30  | |             Err(_) => return Err(MirEvalError::InternalError("mismatched size".into())),
31  | |         }))
32  | |     };
33  | | }
    | |_- in this expansion of `from_bytes!`
    | |_- in this expansion of `from_bytes!`
...
535 |                   let value = from_bytes!(u128, pad16(arg1.get(self)?, false));
    |
    = note: this pattern matches no values because `Infallible` is uninhabited
    = note: `-D unreachable-patterns` implied by `-D warnings`
    = help: to override `-D warnings` add `#[allow(unreachable_patterns)]`

@bors
Copy link
Contributor

bors commented Aug 6, 2024

💔 Test failed - checks-actions

@bors bors added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. and removed S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. labels Aug 6, 2024
@bors
Copy link
Contributor

bors commented Aug 6, 2024

☔ The latest upstream changes (presumably #126804) made this pull request unmergeable. Please resolve the merge conflicts.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-meta Area: Issues & PRs about the rust-lang/rust repository itself A-run-make Area: port run-make Makefiles to rmake.rs O-unix Operating system: Unix-like rollup A PR which is a rollup S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-libs Relevant to the library team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

10 participants