Skip to content

Commit

Permalink
Rollup merge of rust-lang#124219 - gurry:122989-ice-unexpected-anon-c…
Browse files Browse the repository at this point in the history
…onst, r=compiler-errors

Do not ICE on `AnonConst`s in `diagnostic_hir_wf_check`

Fixes rust-lang#122989

Below is the snippet from rust-lang#122989 that ICEs:
```rust
trait Traitor<const N: N<2> = 1, const N: N<2> = N> {
    fn N(&N) -> N<2> {
        M
    }
}

trait N<const N: Traitor<2> = 12> {}
```

The `AnonConst` that triggers the ICE is the `2` in the param `const N: N<2> = 1`. The currently existing code in `diagnostic_hir_wf_check` deals only with `AnonConst`s that are default values of some param, but  the `2` is not a default value. It is just an `AnonConst` HIR node inside a `TraitRef` HIR node corresponding to `N<2>`. Therefore the existing code cannot handle it and this PR ensures that it does.
  • Loading branch information
matthiaskrgr committed May 7, 2024
2 parents b923ea4 + 446f78d commit 5b80aff
Show file tree
Hide file tree
Showing 4 changed files with 208 additions and 14 deletions.
14 changes: 8 additions & 6 deletions compiler/rustc_hir_analysis/src/hir_wf_check.rs
Original file line number Diff line number Diff line change
Expand Up @@ -163,15 +163,17 @@ fn diagnostic_hir_wf_check<'tcx>(
kind: hir::GenericParamKind::Type { default: Some(ty), .. },
..
}) => vec![*ty],
hir::Node::AnonConst(_)
if let Some(const_param_id) =
tcx.hir().opt_const_param_default_param_def_id(hir_id)
hir::Node::AnonConst(_) => {
if let Some(const_param_id) = tcx.hir().opt_const_param_default_param_def_id(hir_id)
&& let hir::Node::GenericParam(hir::GenericParam {
kind: hir::GenericParamKind::Const { ty, .. },
..
}) = tcx.hir_node_by_def_id(const_param_id) =>
{
vec![*ty]
}) = tcx.hir_node_by_def_id(const_param_id)
{
vec![*ty]
} else {
vec![]
}
}
ref node => bug!("Unexpected node {:?}", node),
},
Expand Down
8 changes: 0 additions & 8 deletions tests/crashes/122989.rs

This file was deleted.

21 changes: 21 additions & 0 deletions tests/ui/wf/ice-hir-wf-check-anon-const-issue-122989.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
// Regression test for ICE #122989
trait Foo<const N: Bar<2>> {
//~^ WARN trait objects without an explicit `dyn` are deprecated
//~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
//~| ERROR cycle detected when computing type of `Foo::N`
//~| ERROR cycle detected when computing type of `Foo::N`
//~| ERROR the trait `Foo` cannot be made into an object
//~| ERROR the trait `Foo` cannot be made into an object
//~| ERROR the trait `Foo` cannot be made into an object
//~| ERROR `(dyn Bar<2> + 'static)` is forbidden as the type of a const generic parameter
fn func() {
}
}

trait Bar<const M: Foo<2>> {}
//~^ WARN trait objects without an explicit `dyn` are deprecated
//~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
//~| ERROR the trait `Foo` cannot be made into an object
//~| ERROR `(dyn Foo<2> + 'static)` is forbidden as the type of a const generic parameter

fn main() {}
179 changes: 179 additions & 0 deletions tests/ui/wf/ice-hir-wf-check-anon-const-issue-122989.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
warning: trait objects without an explicit `dyn` are deprecated
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:20
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^
|
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
= note: for more information, see <https://doc.rust-lang.org/nightly/edition-guide/rust-2021/warnings-promoted-to-error.html>
= note: `#[warn(bare_trait_objects)]` on by default
help: if this is an object-safe trait, use `dyn`
|
LL | trait Foo<const N: dyn Bar<2>> {
| +++

warning: trait objects without an explicit `dyn` are deprecated
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:15:20
|
LL | trait Bar<const M: Foo<2>> {}
| ^^^^^^
|
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021!
= note: for more information, see <https://doc.rust-lang.org/nightly/edition-guide/rust-2021/warnings-promoted-to-error.html>
help: if this is an object-safe trait, use `dyn`
|
LL | trait Bar<const M: dyn Foo<2>> {}
| +++

error[E0391]: cycle detected when computing type of `Foo::N`
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:11
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^
|
note: ...which requires computing type of `Bar::M`...
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:15:11
|
LL | trait Bar<const M: Foo<2>> {}
| ^^^^^^^^^^^^^^^
= note: ...which again requires computing type of `Foo::N`, completing the cycle
note: cycle used when computing explicit predicates of trait `Foo`
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:1
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
= note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information

error[E0391]: cycle detected when computing type of `Foo::N`
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:11
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^
|
note: ...which requires computing type of `Bar::M`...
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:15:11
|
LL | trait Bar<const M: Foo<2>> {}
| ^^^^^^^^^^^^^^^
= note: ...which again requires computing type of `Foo::N`, completing the cycle
note: cycle used when computing explicit predicates of trait `Foo`
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:1
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
= note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information
= note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`

error[E0038]: the trait `Foo` cannot be made into an object
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:24
|
LL | trait Foo<const N: Bar<2>> {
| ^ `Foo` cannot be made into an object
|
note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit <https://doc.rust-lang.org/reference/items/traits.html#object-safety>
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:11:8
|
LL | trait Foo<const N: Bar<2>> {
| --- this trait cannot be made into an object...
...
LL | fn func() {
| ^^^^ ...because associated function `func` has no `self` parameter
help: consider turning `func` into a method by giving it a `&self` argument
|
LL | fn func(&self) {
| +++++
help: alternatively, consider constraining `func` so it does not apply to trait objects
|
LL | fn func() where Self: Sized {
| +++++++++++++++++

error[E0038]: the trait `Foo` cannot be made into an object
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:11
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^ `Foo` cannot be made into an object
|
note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit <https://doc.rust-lang.org/reference/items/traits.html#object-safety>
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:11:8
|
LL | trait Foo<const N: Bar<2>> {
| --- this trait cannot be made into an object...
...
LL | fn func() {
| ^^^^ ...because associated function `func` has no `self` parameter
help: consider turning `func` into a method by giving it a `&self` argument
|
LL | fn func(&self) {
| +++++
help: alternatively, consider constraining `func` so it does not apply to trait objects
|
LL | fn func() where Self: Sized {
| +++++++++++++++++

error: `(dyn Bar<2> + 'static)` is forbidden as the type of a const generic parameter
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:20
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^
|
= note: the only supported types are integers, `bool` and `char`

error[E0038]: the trait `Foo` cannot be made into an object
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:15:11
|
LL | trait Bar<const M: Foo<2>> {}
| ^^^^^^^^^^^^^^^ `Foo` cannot be made into an object
|
note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit <https://doc.rust-lang.org/reference/items/traits.html#object-safety>
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:11:8
|
LL | trait Foo<const N: Bar<2>> {
| --- this trait cannot be made into an object...
...
LL | fn func() {
| ^^^^ ...because associated function `func` has no `self` parameter
help: consider turning `func` into a method by giving it a `&self` argument
|
LL | fn func(&self) {
| +++++
help: alternatively, consider constraining `func` so it does not apply to trait objects
|
LL | fn func() where Self: Sized {
| +++++++++++++++++

error: `(dyn Foo<2> + 'static)` is forbidden as the type of a const generic parameter
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:15:20
|
LL | trait Bar<const M: Foo<2>> {}
| ^^^^^^
|
= note: the only supported types are integers, `bool` and `char`

error[E0038]: the trait `Foo` cannot be made into an object
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:2:11
|
LL | trait Foo<const N: Bar<2>> {
| ^^^^^^^^^^^^^^^ `Foo` cannot be made into an object
|
note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit <https://doc.rust-lang.org/reference/items/traits.html#object-safety>
--> $DIR/ice-hir-wf-check-anon-const-issue-122989.rs:11:8
|
LL | trait Foo<const N: Bar<2>> {
| --- this trait cannot be made into an object...
...
LL | fn func() {
| ^^^^ ...because associated function `func` has no `self` parameter
= note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
help: consider turning `func` into a method by giving it a `&self` argument
|
LL | fn func(&self) {
| +++++
help: alternatively, consider constraining `func` so it does not apply to trait objects
|
LL | fn func() where Self: Sized {
| +++++++++++++++++

error: aborting due to 8 previous errors; 2 warnings emitted

Some errors have detailed explanations: E0038, E0391.
For more information about an error, try `rustc --explain E0038`.

0 comments on commit 5b80aff

Please sign in to comment.