• N
    Fix orphan checking (cc #19470). (This is not a complete fix of #19470 because... · c61a0092
    Niko Matsakis 提交于
    Fix orphan checking (cc #19470). (This is not a complete fix of #19470 because of the backwards compatibility feature gate.)
    
    This is a [breaking-change]. The new rules require that, for an impl of a trait defined
    in some other crate, two conditions must hold:
    
    1. Some type must be local.
    2. Every type parameter must appear "under" some local type.
    
    Here are some examples that are legal:
    
    ```rust
    struct MyStruct<T> { ... }
    
    // Here `T` appears "under' `MyStruct`.
    impl<T> Clone for MyStruct<T> { }
    
    // Here `T` appears "under' `MyStruct` as well. Note that it also appears
    // elsewhere.
    impl<T> Iterator<T> for MyStruct<T> { }
    ```
    
    Here is an illegal example:
    
    ```rust
    // Here `U` does not appear "under" `MyStruct` or any other local type.
    // We call `U` "uncovered".
    impl<T,U> Iterator<U> for MyStruct<T> { }
    ```
    
    There are a couple of ways to rewrite this last example so that it is
    legal:
    
    1. In some cases, the uncovered type parameter (here, `U`) should be converted
       into an associated type. This is however a non-local change that requires access
       to the original trait. Also, associated types are not fully baked.
    2. Add `U` as a type parameter of `MyStruct`:
       ```rust
       struct MyStruct<T,U> { ... }
       impl<T,U> Iterator<U> for MyStruct<T,U> { }
       ```
    3. Create a newtype wrapper for `U`
       ```rust
       impl<T,U> Iterator<Wrapper<U>> for MyStruct<T,U> { }
       ```
    
    Because associated types are not fully baked, which in the case of the
    `Hash` trait makes adhering to this rule impossible, you can
    temporarily disable this rule in your crate by using
    `#![feature(old_orphan_check)]`. Note that the `old_orphan_check`
    feature will be removed before 1.0 is released.
    c61a0092
lib.rs 61.3 KB