Rework `Bounds` collection
I think it's weird for the `Bounds` struct in astconv to store its predicates *almost* converted into real predicates... so we do this eagerly, instead of lazily.
We delay projection normalization to further stages in order to
register user type annotations before normalization in HIR typeck.
There are two consumers of astconv: ItemCtxt and FnCtxt.
The former already expects unnormalized types from astconv, see its
AstConv trait impl.
The latter needs `RawTy` for a cleaner interface.
Unfortunately astconv still needs the normalization machinery in
order to resolve enum variants that have projections in the self type,
e.g. `<<T as Trait>::Assoc>::StructVariant {}`.
This is why `AstConv::normalize_ty_2` is necessary.
Add help diag. for `const = Enum` missing braces around `Enum`
Previously it was not clear why this errored or if it was even supported, as there was no diagnostic that suggested wrapping it in braces.
Thus, add a simple diagnostic that suggests wrapping enum variants in braces.
Fixes#105927
Previously it was not clear why this errored or if it was even supported, as there was no
diagnostic that suggested wrapping it in braces.
Thus, add a simple diagnostic that suggests wrapping enum variants in braces.
Avoid some `InferCtxt::build` calls
Either because we're inside of an `InferCtxt` already, or because we're not in a place where we'd ever see inference vars.
r? types
Prefer doc comments over `//`-comments in compiler
Doc comments are generally nicer: they show up in the documentation, they are shown in IDEs when you hover other mentions of items, etc. Thus it makes sense to use them instead of `//`-comments.
Separate lifetime ident from lifetime resolution in HIR
Drive-by: change how suggested generic args are computed.
Fixes https://github.com/rust-lang/rust/issues/103815
I recommend reviewing commit-by-commit.
Rollup of 9 pull requests
Successful merges:
- #104420 (Fix doc example for `wrapping_abs`)
- #104499 (rustdoc JSON: Use `Function` everywhere and remove `Method`)
- #104500 (`rustc_ast`: remove `ref` patterns)
- #104511 (Mark functions created for `raw-dylib` on x86 with DllImport storage class)
- #104595 (Add `PolyExistentialPredicate` type alias)
- #104605 (deduplicate constant evaluation in cranelift backend)
- #104628 (Revert "Update CI to use Android NDK r25b")
- #104662 (Streamline deriving on packed structs.)
- #104667 (Revert formatting changes of a test)
Failed merges:
r? `@ghost`
`@rustbot` modify labels: rollup
Add `PolyExistentialPredicate` type alias
Wrapping `ExistentialPredicate`s in a binder is very common, and this alias already exists for the `PolyExistential{TraitRef,Projection}` types.
Support using `Self` or projections inside an RPIT/async fn
I reuse the same idea as https://github.com/rust-lang/rust/pull/103449 to use variances to encode whether a lifetime parameter is captured by impl-trait.
The current implementation of async and RPIT replace all lifetimes from the parent generics by `'static`. This PR changes the scheme
```rust
impl<'a> Foo<'a> {
fn foo<'b, T>() -> impl Into<Self> + 'b { ... }
}
opaque Foo::<'_a>::foo::<'_b, T>::opaque<'b>: Into<Foo<'_a>> + 'b;
impl<'a> Foo<'a> {
// OLD
fn foo<'b, T>() -> Foo::<'static>::foo::<'static, T>::opaque::<'b> { ... }
^^^^^^^ the `Self` becomes `Foo<'static>`
// NEW
fn foo<'b, T>() -> Foo::<'a>::foo::<'b, T>::opaque::<'b> { ... }
^^ the `Self` stays `Foo<'a>`
}
```
There is the same issue with projections. In the example, substitute `Self` by `<T as Trait<'b>>::Assoc` in the sugared version, and `Foo<'_a>` by `<T as Trait<'_b>>::Assoc` in the desugared one.
This allows to support `Self` in impl-trait, since we do not replace lifetimes by `'static` any more. The same trick allows to use projections like `T::Assoc` where `Self` is allowed. The feature is gated behind a `impl_trait_projections` feature gate.
The implementation relies on 2 tweaking rules for opaques in 2 places:
- we only relate substs that correspond to captured lifetimes during TypeRelation;
- we only list captured lifetimes in choice region computation.
For simplicity, I encoded the "capturedness" of lifetimes as a variance, `Bivariant` vs `Invariant` for unused vs captured lifetimes. The `variances_of` query used to ICE for opaques.
Impl-trait that do not reference `Self` or projections will have their variances as:
- `o` (invariant) for each parent type or const;
- `*` (bivariant) for each parent lifetime --> will not participate in borrowck;
- `o` (invariant) for each own lifetime.
Impl-trait that does reference `Self` and/or projections will have some parent lifetimes marked as `o` (as the example above), and participate in type relation and borrowck. In the example above, `variances_of(opaque) = ['_a: o, '_b: *, T: o, 'b: o]`.
r? types
cc `@compiler-errors` , as you asked about the issue with `Self` and projections.
Record `LocalDefId` in HIR nodes instead of a side table
This is part of an attempt to remove the `HirId -> LocalDefId` table from HIR.
This attempt is a prerequisite to creation of `LocalDefId` after HIR lowering (https://github.com/rust-lang/rust/pull/96840), by controlling how `def_id` information is accessed.
This first part adds the information to HIR nodes themselves instead of a table.
The second part is https://github.com/rust-lang/rust/pull/103902
The third part will be to make `hir::Visitor::visit_fn` take a `LocalDefId` as last parameter.
The fourth part will be to completely remove the side table.
Better error for HRTB error from generator interior
cc #100013
This is just a first pass at an error. It could be better, and shouldn't really be emitted in the first place. But this is better than what was being emitted before.
spastorino noticed some silly expressions like `item_id.def_id.def_id`.
This commit renames several `def_id: OwnerId` fields as `owner_id`, so
those expressions become `item_id.owner_id.def_id`.
`item_id.owner_id.local_def_id` would be even clearer, but the use of
`def_id` for values of type `LocalDefId` is *very* widespread, so I left
that alone.
Rollup of 6 pull requests
Successful merges:
- #102287 (Elaborate supertrait bounds when triggering `unused_must_use` on `impl Trait`)
- #102922 (Filtering spans when emitting json)
- #103051 (translation: doc comments with derives, subdiagnostic-less enum variants, more derive use)
- #103111 (Account for hygiene in typo suggestions, and use them to point to shadowed names)
- #103260 (Fixup a few tests needing asm support)
- #103321 (rustdoc: improve appearance of source page navigation bar)
Failed merges:
- #103209 (Diagnostic derives: allow specifying multiple alternative suggestions)
r? `@ghost`
`@rustbot` modify labels: rollup
Move lint level source explanation to the bottom
So, uhhhhh
r? `@estebank`
## User-facing change
"note: `#[warn(...)]` on by default" and such are moved to the bottom of the diagnostic:
```diff
- = note: `#[warn(unsupported_calling_conventions)]` on by default
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
= note: for more information, see issue #87678 <https://github.com/rust-lang/rust/issues/87678>
+ = note: `#[warn(unsupported_calling_conventions)]` on by default
```
Why warning is enabled is the least important thing, so it shouldn't be the first note the user reads, IMO.
## Developer-facing change
`struct_span_lint` and similar methods have a different signature.
Before: `..., impl for<'a> FnOnce(LintDiagnosticBuilder<'a, ()>)`
After: `..., impl Into<DiagnosticMessage>, impl for<'a, 'b> FnOnce(&'b mut DiagnosticBuilder<'a, ()>) -> &'b mut DiagnosticBuilder<'a, ()>`
The reason for this is that `struct_span_lint` needs to edit the diagnostic _after_ `decorate` closure is called. This also makes lint code a little bit nicer in my opinion.
Another option is to use `impl for<'a> FnOnce(LintDiagnosticBuilder<'a, ()>) -> DiagnosticBuilder<'a, ()>` altough I don't _really_ see reasons to do `let lint = lint.build(message)` everywhere.
## Subtle problem
By moving the message outside of the closure (that may not be called if the lint is disabled) `format!(...)` is executed earlier, possibly formatting `Ty` which may call a query that trims paths that crashes the compiler if there were no warnings...
I don't think it's that big of a deal, considering that we move from `format!(...)` to `fluent` (which is lazy by-default) anyway, however this required adding a workaround which is unfortunate.
## P.S.
I'm sorry, I do not how to make this PR smaller/easier to review. Changes to the lint API affect SO MUCH 😢
`Res::SelfTy` currently has two `Option`s. When the second one is `Some`
the first one is never consulted. So we can split it into two variants,
`Res::SelfTyParam` and `Res::SelfTyAlias`, reducing the size of `Res`
from 24 bytes to 12. This then shrinks `hir::Path` and
`hir::PathSegment`, which are the HIR types that take up the most space.