Skip to content

Possible regression on use of Self in generics ("mismatched types") #69611

Closed

Description

@rye

The following code (also on playground) compiles fine on Stable and Beta rustc, but has started no longer compiling on latest nightly (2020-02-28, 2020-02-29 both have this issue).

pub struct Container<V>(pub V);

impl<T, V> core::ops::Mul<T> for Container<V>
where
    T: From<V> + core::ops::Mul<T, Output = T>,
{
    type Output = Container<T>;

    fn mul(self, scalar: T) -> Self::Output {
        Self(scalar * self.0.into())
    }
}

I would expect this code snippet to compile with no errors as it currently does in stable and beta Rust.

Instead, on recent nightlies (02-28 and 02-29 were tested), an error is produced:

  --> src/lib.rs:10:14
   |
3  | impl<T, V> core::ops::Mul<T> for Container<V>
   |      -  - expected type parameter
   |      |
   |      found type parameter
...
10 |         Self(scalar * self.0.into())
   |              ^^^^^^^^^^^^^^^^^^^^^^ expected type parameter `V`, found type parameter `T`
   |
   = note: expected type parameter `V`
              found type parameter `T`
   = note: a type parameter was expected, but a different one was found; you might be missing a type parameter or trait bound
   = note: for more information, visit https://doc.rust-lang.org/book/ch10-02-traits.html#traits-as-parameters

For what it's worth, the substitution

 pub struct Container<V>(pub V);

 impl<T, V> core::ops::Mul<T> for Container<V>
 where
     T: From<V> + core::ops::Mul<T, Output = T>,
 {
     type Output = Container<T>;
 
     fn mul(self, scalar: T) -> Self::Output {
-        Self(scalar * self.0.into())
+        Container(scalar * self.0.into())
     }
 }

resolves the error.

I believe this is because rustc is erroneously picking Self to be Container<V> (the type for which the impl is being specified) instead of using Container and inferring the (formerly correct) output type of Container<T>.

Meta

rustc --version --verbose:

rustc 1.43.0-nightly (d3c79346a 2020-02-29)
binary: rustc
commit-hash: d3c79346a3e7ddbb5fb417810f226ac5a9209007
commit-date: 2020-02-29
host: x86_64-apple-darwin
release: 1.43.0-nightly
LLVM version: 9.0

Activity

  1. added
    C-bugCategory: This is a bug.
    on Mar 1, 2020
  2. rye commented on Mar 1, 2020

    @rye
    ContributorAuthor

    Sure enough, this seems related to #69306, which was marked resolved by PR #69340. I guess I'm one of the lucky people affected by those changes. 😄

  3. Centril commented on Mar 1, 2020

    @Centril
    Contributor

    Yeah, this was caused by a bug fix to type checking of Self paths, which would previously wrongly introduce inference variables for type parameters in the impl. Using Self should always refer to the Self type, just as using Self {...} would. In other words, your code should never have compiled.

  4. Centril commented on Mar 18, 2020

    @Centril
    Contributor

    Closing as expected breakage and "wontfix".

  5. added a commit that references this issue on Mar 20, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions