Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Associated const equality conflicts with associated type equality #112560

Closed
mversic opened this issue Jun 12, 2023 · 4 comments · Fixed by #118668
Closed

Associated const equality conflicts with associated type equality #112560

mversic opened this issue Jun 12, 2023 · 4 comments · Fixed by #118668
Assignees
Labels
A-const-generics Area: const generics (parameters and arguments) C-bug Category: This is a bug. F-associated_const_equality `#![feature(associated_const_equality)]` T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-lang Relevant to the language team, which will review and decide on the PR/issue.

Comments

@mversic
Copy link

mversic commented Jun 12, 2023

I tried this code and it compiled:

trait Trait2 {}

trait Trait1 {
    const A: u32;
    type A;
}

impl<T: Trait1<A = u32>, const N: usize> Trait2 for [T; N] {}

fn main() {}

Then I tried this code and it didn't compile:

#![feature(associated_const_equality)]

trait Trait2 {}

trait Trait1 {
    const A: u32;
    type A;
}

impl<T: Trait1<A = 12>, const N: usize> Trait2 for [T; N] {}

fn main() {}

Meta

rustc --version --verbose:

rustc 1.72.0-nightly (37998ab50 2023-06-11)
binary: rustc
commit-hash: 37998ab508d5d9fa0d465d7b535dc673087dda8f
commit-date: 2023-06-11
host: aarch64-apple-darwin
release: 1.72.0-nightly
LLVM version: 16.0.5
Backtrace

error: expected associated type bound, found constant
  --> src/main.rs:10:16
   |
10 | impl<T: Trait1<A = 12>, const N: usize> Trait2 for [T; N] {}
   |                ^^^^^^
   |
note: associated type defined here
  --> src/main.rs:5:5
   |
5  |     type A;
   |     ^^^^^^

error: could not compile `proba2` (bin "proba2") due to previous error

Explanation

Rust allows for associated const parameter and associated type parameter to have the same name. So, I expected there would be some way to disambiguate which one I'm referring to when setting the equality constraint but haven't found a way to do so.

This problem is related to Associated Const Equality

@mversic mversic added the C-bug Category: This is a bug. label Jun 12, 2023
@BoxyUwU BoxyUwU added A-const-generics Area: const generics (parameters and arguments) F-associated_const_equality `#![feature(associated_const_equality)]` labels Jun 12, 2023
@fmease fmease added T-lang Relevant to the language team, which will review and decide on the PR/issue. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Nov 15, 2023
@fmease
Copy link
Member

fmease commented Nov 15, 2023

Added T-compiler since this particular code could be accepted by making the AssocKind passed to trait_defines_associated_item_named dependent on the term kind (type or constant) of the binding in <dyn AstConv<'_>>::add_predicates_for_ast_type_binding. Edit: That's not quite correct but close.

Added T-lang since in the future, we might want to allow Trait<Const = path::to::Const> (i.e., allowing the user to omit the curly braces and allowing paths to resolve to either type or const) in which case, it would very much become ambiguous.

@Jules-Bertholet
Copy link
Contributor

Perhaps a const prefix could be required to disambiguate? (T: Trait1<A = u32, const A = 16>)

@mversic
Copy link
Author

mversic commented Nov 20, 2023

IMHO I would disallow types and consts to have the same name as in this example:

trait Trait1 {
    const N: u32;
    type N;
}

since this is not allowed:

trait Trait1<N, const N: usize> {}

but that would be a breaking change

@fmease
Copy link
Member

fmease commented Nov 20, 2023

That could be left for a future t-lang discussion. I've already got a fix locally since we can always continue to require curly braces for paths
&co as the RHS of assoc const bindings to rule out ambiguities.

Forbidding assoc consts & types if they're identically named would be pretty inconsistent, they live in different namespaces after all. Further, assoc const equality bounds are pretty niche, no reason to add special cases just for them. What's more, while identically named assoc consts & types are relatively rare, the following code involving supertraits could come up in practice I'd argue:

trait A: B { type X;  }
trait B { const X: (); }

// A<X = { () }>

My patch is going to handle the case above as well.

bors added a commit to rust-lang-ci/rust that referenced this issue Dec 8, 2023
…y-namespace, r=compiler-errors

Resolve associated item bindings by namespace

This is the 3rd commit split off from rust-lang#118360 with tests reblessed (they no longer contain duplicated diags which were caused by 4c0addc) & slightly adapted (removed supertraits from a UI test, cc rust-lang#118040).

> * Resolve all assoc item bindings (type, const, fn (feature `return_type_notation`)) by namespace instead of trying to resolve a type first (in the non-RTN case) and falling back to consts afterwards. This is consistent with RTN. E.g., for `Tr<K = {…}>` we now always try to look up assoc consts (this extends to supertrait bounds). This gets rid of assoc tys shadowing assoc consts in assoc item bindings which is undesirable & inconsistent (types and consts live in different namespaces after all)
> * Consolidate the resolution of assoc {ty, const} bindings and RTN (dedup, better diags for RTN)
> * Fix assoc consts being labeled as assoc *types* in several diagnostics
> * Make a bunch of diagnostics translatable

Fixes rust-lang#112560 (error → pass).

As discussed
r? `@compiler-errors`

---

**Addendum**: What I call “associated item bindings” are commonly referred to as “type bindings” for historical reasons. Nowadays, “type bindings” include assoc type bindings, assoc const bindings and RTN (return type notation) which is why I prefer not to use this outdated term.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-const-generics Area: const generics (parameters and arguments) C-bug Category: This is a bug. F-associated_const_equality `#![feature(associated_const_equality)]` T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. T-lang Relevant to the language team, which will review and decide on the PR/issue.
Projects
None yet
4 participants