Show more information when multiple `impl`s apply
- When there are `impl`s without type params, show only those (to avoid showing overly generic `impl`s).
```
error[E0283]: type annotations needed
--> $DIR/multiple-impl-apply.rs:34:9
|
LL | let y = x.into();
| ^ ---- type must be known at this point
|
note: multiple `impl`s satisfying `_: From<Baz>` found
--> $DIR/multiple-impl-apply.rs:14:1
|
LL | impl From<Baz> for Bar {
| ^^^^^^^^^^^^^^^^^^^^^^
...
LL | impl From<Baz> for Foo {
| ^^^^^^^^^^^^^^^^^^^^^^
= note: required for `Baz` to implement `Into<_>`
help: consider giving `y` an explicit type
|
LL | let y: /* Type */ = x.into();
| ++++++++++++
```
- Lower the importance of `T: Sized`, `T: WellFormed` and coercion errors, to prioritize more relevant errors. The pre-existing deduplication logic deals with hiding redundant errors better that way, and we show errors with more metadata that is useful to the user.
- Show `<SelfTy as Trait>::assoc_fn` suggestion in more cases.
```
error[E0790]: cannot call associated function on trait without specifying the corresponding `impl` type
--> $DIR/cross-return-site-inference.rs:38:16
|
LL | return Err(From::from("foo"));
| ^^^^^^^^^^ cannot call associated function of trait
|
help: use a fully-qualified path to a specific available implementation
|
LL | return Err(</* self type */ as From>::from("foo"));
| +++++++++++++++++++ +
```
Fix#88284.
In `report_fullfillment_errors` push back `T: Sized`, `T: WellFormed`
and coercion errors to the end of the list. The pre-existing
deduplication logic eliminates redundant errors better that way, keeping
the resulting output with fewer errors than before, while also having
more detail.
Don't store lazyness in `DefKind::TyAlias`
1. Don't store lazyness of a type alias in its `DefKind`, but instead via a query.
2. This allows us to treat type aliases as lazy if `#[feature(lazy_type_alias)]` *OR* if the alias contains a TAIT, rather than having checks for both in separate parts of the codebase.
r? `@oli-obk` cc `@fmease`
rename mir::Constant -> mir::ConstOperand, mir::ConstKind -> mir::Const
Also, be more consistent with the `to/eval_bits` methods... we had some that take a type and some that take a size, and then sometimes the one that takes a type is called `bits_for_ty`.
Turns out that `ty::Const`/`mir::ConstKind` carry their type with them, so we don't need to even pass the type to those `eval_bits` functions at all.
However this is not properly consistent yet: in `ty` we have most of the methods on `ty::Const`, but in `mir` we have them on `mir::ConstKind`. And indeed those two types are the ones that correspond to each other. So `mir::ConstantKind` should actually be renamed to `mir::Const`. But what to do with `mir::Constant`? It carries around a span, that's really more like a constant operand that appears as a MIR operand... it's more suited for `syntax.rs` than `consts.rs`, but the bigger question is, which name should it get if we want to align the `mir` and `ty` types? `ConstOperand`? `ConstOp`? `Literal`? It's not a literal but it has a field called `literal` so it would at least be consistently wrong-ish...
``@oli-obk`` any ideas?
It's easier to pass it in to the one method that needs it
(`highlighting_region_vid`) than to store it in the type. This means
`RegionHighlightMode` can impl `Default`.
Bubble up opaque <eq> opaque operations instead of picking an order
In case we are in `Bubble` mode (meaning every opaque type that is defined in the current crate is treated as if it were in its defining scope), we don't try to register an opaque type as the hidden type of another opaque type, but instead bubble up an obligation to equate them at the query caller site. Usually that means we have a `DefiningAnchor::Bind` and thus can reliably figure out whether an opaque type is in its defining scope. Where we can't, we'll error out, so the default is sound.
With this change we start using `AliasTyEq` predicates in the old solver, too.
fixes https://github.com/rust-lang/rust/issues/108498
But also regresses `tests/ui/impl-trait/anon_scope_creep.rs`. Our use of `Bubble` for `check_opaque_type_well_formed` is going to keep biting us.
r? `@lcnr` `@compiler-errors`
Fix incorrect mutable suggestion information for binding in ref pattern like: `let &b = a;`
fixes#114896
I find we have to get pat_span but not local_decl.source_info.span for suggestion. In `let &b = a;` pat_span is &b. I think check `let &b = a` in hir to make sure it is hir::Node::Local(hir::Local {pat: hir::Pat{kind: hir::PatKind::Ref(....... can distinguish it from other situation, but I'm not sure.
If my processing method is not accurate, please guide me to modify it, thank you.
r? `@davidtwco`
The `Debug` impl for `Ty` just calls the `Display` impl for `Ty`. This
is surprising and annoying. In particular, it means `Debug` doesn't show
as much information as `Debug` for `TyKind` does. And `Debug` is used in
some user-facing error messages, which seems bad.
This commit changes the `Debug` impl for `Ty` to call the `Debug` impl
for `TyKind`. It also does a number of follow-up changes to preserve
existing output, many of which involve inserting
`with_no_trimmed_paths!` calls. It also adds `Display` impls for
`UserType` and `Canonical`.
Some tests have changes to expected output:
- Those that use the `rustc_abi(debug)` attribute.
- Those that use the `EMIT_MIR` annotation.
In each case the output is slightly uglier than before. This isn't
ideal, but it's pretty weird (particularly for the attribute) that the
output is using `Debug` in the first place. They're fairly obscure
attributes (I hadn't heard of them) so I'm not worried by this.
For `async-is-unwindsafe.stderr`, there is one line that now lacks a
full path. This is a consistency improvement, because all the other
mentions of `Context` in this test lack a path.
Don't report any errors in `lower_intrinsics`.
Intrinsics should have been type checked earlier.
This is part of moving all mir-opt diagnostics early enough so that they are reliably emitted even in check builds: https://github.com/rust-lang/rust/issues/49292#issuecomment-1692212095
This was backfilling causes for new universes that may have been created
by an op, when there was no error info to use for improved
diagnostics. We don't need to do that anymore: `other()` is the default when
there is no registered universe cause.
This was pre-filling causes for universes that could already exist in
the InferCtxt. We don't need to do that anymore: `other()` is the default when
there is no registered universe cause.
This was backfilling causes for the new universes that can be created by
the InferCtxt. We don't need to do that anymore: `other()` is the default when
there is no registered universe cause.
Suggest mutable borrow on read only for-loop that should be mutable
```
error[E0596]: cannot borrow `*test` as mutable, as it is behind a `&` reference
--> $DIR/suggest-mut-iterator.rs:22:9
|
LL | for test in &tests {
| ------ this iterator yields `&` references
LL | test.add(2);
| ^^^^ `test` is a `&` reference, so the data it refers to cannot be borrowed as mutable
|
help: use a mutable iterator instead
|
LL | for test in &mut tests {
| +++
```
Fix#114311.
```
error[E0596]: cannot borrow `*test` as mutable, as it is behind a `&` reference
--> $DIR/suggest-mut-iterator.rs:22:9
|
LL | for test in &tests {
| ------ this iterator yields `&` references
LL | test.add(2);
| ^^^^ `test` is a `&` reference, so the data it refers to cannot be borrowed as mutable
|
help: use a mutable iterator instead
|
LL | for test in &mut tests {
| +++
```
Address #114311.
Store the laziness of type aliases in their `DefKind`
Previously, we would treat paths referring to type aliases as *lazy* type aliases if the current crate had lazy type aliases enabled independently of whether the crate which the alias was defined in had the feature enabled or not.
With this PR, the laziness of a type alias depends on the crate it is defined in. This generally makes more sense to me especially if / once lazy type aliases become the default in a new edition and we need to think about *edition interoperability*:
Consider the hypothetical case where the dependency crate has an older edition (and thus eager type aliases), it exports a type alias with bounds & a where-clause (which are void but technically valid), the dependent crate has the latest edition (and thus lazy type aliases) and it uses that type alias. Arguably, the bounds should *not* be checked since at any time, the dependency crate should be allowed to change the bounds at will with a *non*-major version bump & without negatively affecting downstream crates.
As for the reverse case (dependency: lazy type aliases, dependent: eager type aliases), I guess it rules out anything from slight confusion to mild annoyance from upstream crate authors that would be caused by the compiler ignoring the bounds of their type aliases in downstream crates with older editions.
---
This fixes#114468 since before, my assumption that the type alias associated with a given weak projection was lazy (and therefore had its variances computed) did not necessarily hold in cross-crate scenarios (which [I kinda had a hunch about](https://github.com/rust-lang/rust/pull/114253#discussion_r1278608099)) as outlined above. Now it does hold.
`@rustbot` label F-lazy_type_alias
r? `@oli-obk`