Skip to content

Commit

Permalink
Deny ~const trait bounds in inherent impl headers
Browse files Browse the repository at this point in the history
  • Loading branch information
fmease committed Dec 18, 2023
1 parent 3ad8e2d commit 4a5dd16
Show file tree
Hide file tree
Showing 7 changed files with 36 additions and 20 deletions.
3 changes: 2 additions & 1 deletion compiler/rustc_ast_passes/messages.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,8 @@ ast_passes_tilde_const_disallowed = `~const` is not allowed here
.closure = closures cannot have `~const` trait bounds
.function = this function is not `const`, so it cannot have `~const` trait bounds
.trait = this trait is not a `#[const_trait]`, so it cannot have `~const` trait bounds
.impl = this impl is not `const`, so it cannot have `~const` trait bounds
.trait_impl = this impl is not `const`, so it cannot have `~const` trait bounds
.impl = inherent impls cannot have `~const` trait bounds
.object = trait objects cannot have `~const` trait bounds
.item = this item cannot have `~const` trait bounds
Expand Down
12 changes: 10 additions & 2 deletions compiler/rustc_ast_passes/src/ast_validation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ enum DisallowTildeConstContext<'a> {
TraitObject,
Fn(FnKind<'a>),
Trait(Span),
TraitImpl(Span),
Impl(Span),
Item,
}
Expand Down Expand Up @@ -837,7 +838,7 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
this.visit_vis(&item.vis);
this.visit_ident(item.ident);
let disallowed = matches!(constness, Const::No)
.then(|| DisallowTildeConstContext::Impl(item.span));
.then(|| DisallowTildeConstContext::TraitImpl(item.span));
this.with_tilde_const(disallowed, |this| this.visit_generics(generics));
this.visit_trait_ref(t);
this.visit_ty(self_ty);
Expand Down Expand Up @@ -890,7 +891,9 @@ impl<'a> Visitor<'a> for AstValidator<'a> {

self.visit_vis(&item.vis);
self.visit_ident(item.ident);
self.with_tilde_const(None, |this| this.visit_generics(generics));
self.with_tilde_const(Some(DisallowTildeConstContext::Impl(item.span)), |this| {
this.visit_generics(generics)
});
self.visit_ty(self_ty);
walk_list!(self, visit_assoc_item, items, AssocCtxt::Impl);
walk_list!(self, visit_attribute, &item.attrs);
Expand Down Expand Up @@ -1216,7 +1219,12 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
&DisallowTildeConstContext::Trait(span) => {
errors::TildeConstReason::Trait { span }
}
&DisallowTildeConstContext::TraitImpl(span) => {
errors::TildeConstReason::TraitImpl { span }
}
&DisallowTildeConstContext::Impl(span) => {
// FIXME(effects): Consider providing a help message or even a structured
// suggestion for moving such bounds to the assoc const fns if available.
errors::TildeConstReason::Impl { span }
}
DisallowTildeConstContext::TraitObject => {
Expand Down
5 changes: 5 additions & 0 deletions compiler/rustc_ast_passes/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -563,6 +563,11 @@ pub enum TildeConstReason {
#[primary_span]
span: Span,
},
#[note(ast_passes_trait_impl)]
TraitImpl {
#[primary_span]
span: Span,
},
#[note(ast_passes_impl)]
Impl {
#[primary_span]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,4 +52,7 @@ trait Child1 where Self: ~const Trait {} //~ ERROR `~const` is not allowed
// non-const impl
impl<T: ~const Trait> Trait for T {} //~ ERROR `~const` is not allowed

// inherent impl (regression test for issue #117004)
impl<T: ~const Trait> Struct<T> {} //~ ERROR `~const` is not allowed

fn main() {}
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,18 @@ note: this impl is not `const`, so it cannot have `~const` trait bounds
LL | impl<T: ~const Trait> Trait for T {}
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error: `~const` is not allowed here
--> $DIR/tilde-const-invalid-places.rs:56:9
|
LL | impl<T: ~const Trait> Struct<T> {}
| ^^^^^^
|
note: inherent impls cannot have `~const` trait bounds
--> $DIR/tilde-const-invalid-places.rs:56:1
|
LL | impl<T: ~const Trait> Struct<T> {}
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

error[E0658]: generic const items are experimental
--> $DIR/tilde-const-invalid-places.rs:19:15
|
Expand Down Expand Up @@ -239,6 +251,6 @@ LL | type Type<T: ~const Trait> = ();
= note: see issue #8995 <https://github.com/rust-lang/rust/issues/8995> for more information
= help: add `#![feature(inherent_associated_types)]` to the crate attributes to enable

error: aborting due to 26 previous errors
error: aborting due to 27 previous errors

For more information about this error, try `rustc --explain E0658`.
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
// known-bug: #110395
// FIXME check-pass
// check-pass
#![feature(const_trait_impl, effects)]

#[const_trait]
Expand All @@ -9,8 +8,8 @@ trait Foo {

struct Bar<T>(T);

impl<T: ~const Foo> Bar<T> {
const fn foo(&self) {
impl<T> Bar<T> {
const fn foo(&self) where T: ~const Foo {
self.0.foo()
}
}
Expand Down

This file was deleted.

0 comments on commit 4a5dd16

Please sign in to comment.