diff --git a/compiler/rustc_hir/src/hir.rs b/compiler/rustc_hir/src/hir.rs index 1446c84a3976..ca60b91fae0d 100644 --- a/compiler/rustc_hir/src/hir.rs +++ b/compiler/rustc_hir/src/hir.rs @@ -3228,33 +3228,6 @@ impl<'hir> Node<'hir> { } } - /// Returns `Constness::Const` when this node is a const fn/impl/item. - pub fn constness_for_typeck(&self) -> Constness { - match self { - Node::Item(Item { - kind: ItemKind::Fn(FnSig { header: FnHeader { constness, .. }, .. }, ..), - .. - }) - | Node::TraitItem(TraitItem { - kind: TraitItemKind::Fn(FnSig { header: FnHeader { constness, .. }, .. }, ..), - .. - }) - | Node::ImplItem(ImplItem { - kind: ImplItemKind::Fn(FnSig { header: FnHeader { constness, .. }, .. }, ..), - .. - }) - | Node::Item(Item { kind: ItemKind::Impl(Impl { constness, .. }), .. }) => *constness, - - Node::Item(Item { kind: ItemKind::Const(..), .. }) - | Node::Item(Item { kind: ItemKind::Static(..), .. }) - | Node::TraitItem(TraitItem { kind: TraitItemKind::Const(..), .. }) - | Node::AnonConst(_) - | Node::ImplItem(ImplItem { kind: ImplItemKind::Const(..), .. }) => Constness::Const, - - _ => Constness::NotConst, - } - } - pub fn as_owner(self) -> Option> { match self { Node::Item(i) => Some(OwnerNode::Item(i)), diff --git a/compiler/rustc_ty_utils/src/ty.rs b/compiler/rustc_ty_utils/src/ty.rs index 9a4639b08860..f47f8a562ddf 100644 --- a/compiler/rustc_ty_utils/src/ty.rs +++ b/compiler/rustc_ty_utils/src/ty.rs @@ -287,7 +287,43 @@ fn param_env(tcx: TyCtxt<'_>, def_id: DefId) -> ty::ParamEnv<'_> { let hir_id = local_did.map(|def_id| tcx.hir().local_def_id_to_hir_id(def_id)); let constness = match hir_id { - Some(hir_id) => tcx.hir().get(hir_id).constness_for_typeck(), + Some(hir_id) => match tcx.hir().get(hir_id) { + hir::Node::Item(hir::Item { kind: hir::ItemKind::Const(..), .. }) + | hir::Node::Item(hir::Item { kind: hir::ItemKind::Static(..), .. }) + | hir::Node::TraitItem(hir::TraitItem { kind: hir::TraitItemKind::Const(..), .. }) + | hir::Node::AnonConst(_) + | hir::Node::ImplItem(hir::ImplItem { kind: hir::ImplItemKind::Const(..), .. }) + | hir::Node::ImplItem(hir::ImplItem { + kind: hir::ImplItemKind::Fn(hir::FnSig { header: hir::FnHeader { constness: hir::Constness::Const, .. }, .. }, ..), + .. + }) => hir::Constness::Const, + + hir::Node::ImplItem(hir::ImplItem { + kind: hir::ImplItemKind::TyAlias(..) | hir::ImplItemKind::Fn(..), + .. + }) => { + let parent_hir_id = tcx.hir().get_parent_node(hir_id); + match tcx.hir().get(parent_hir_id) { + hir::Node::Item(hir::Item { kind: hir::ItemKind::Impl(hir::Impl { constness, .. }), .. }) => *constness, + _ => span_bug!( + tcx.def_span(parent_hir_id.owner), + "impl item's parent node is not an impl", + ), + } + } + + hir::Node::Item(hir::Item { + kind: hir::ItemKind::Fn(hir::FnSig { header: hir::FnHeader { constness, .. }, .. }, ..), + .. + }) + | hir::Node::TraitItem(hir::TraitItem { + kind: hir::TraitItemKind::Fn(hir::FnSig { header: hir::FnHeader { constness, .. }, .. }, ..), + .. + }) + | hir::Node::Item(hir::Item { kind: hir::ItemKind::Impl(hir::Impl { constness, .. }), .. }) => *constness, + + _ => hir::Constness::NotConst, + }, None => hir::Constness::NotConst, }; diff --git a/src/test/ui/rfc-2632-const-trait-impl/assoc-type.rs b/src/test/ui/rfc-2632-const-trait-impl/assoc-type.rs index 11334c107754..7b012083c5a3 100644 --- a/src/test/ui/rfc-2632-const-trait-impl/assoc-type.rs +++ b/src/test/ui/rfc-2632-const-trait-impl/assoc-type.rs @@ -1,6 +1,5 @@ // FIXME(fee1-dead): this should have a better error message #![feature(const_trait_impl)] -// check-pass struct NonConstAdd(i32); impl std::ops::Add for NonConstAdd { @@ -17,7 +16,7 @@ trait Foo { impl const Foo for NonConstAdd { type Bar = NonConstAdd; - //TODO: ~^ ERROR + //~^ ERROR } trait Baz { diff --git a/src/test/ui/rfc-2632-const-trait-impl/assoc-type.stderr b/src/test/ui/rfc-2632-const-trait-impl/assoc-type.stderr new file mode 100644 index 000000000000..d1e55e12d6f5 --- /dev/null +++ b/src/test/ui/rfc-2632-const-trait-impl/assoc-type.stderr @@ -0,0 +1,20 @@ +error[E0277]: cannot add `NonConstAdd` to `NonConstAdd` + --> $DIR/assoc-type.rs:18:5 + | +LL | type Bar = NonConstAdd; + | ^^^^^^^^^^^^^^^^^^^^^^^ no implementation for `NonConstAdd + NonConstAdd` + | + = help: the trait `Add` is not implemented for `NonConstAdd` +note: required by a bound in `Foo::Bar` + --> $DIR/assoc-type.rs:14:15 + | +LL | type Bar: ~const std::ops::Add; + | ^^^^^^^^^^^^^^^^^^^^ required by this bound in `Foo::Bar` +help: consider introducing a `where` bound, but there might be an alternative better way to express this requirement + | +LL | impl const Foo for NonConstAdd where NonConstAdd: Add { + | ++++++++++++++++++++++ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`.