microsoft / WinObjC

Objective-C for Windows
MIT License
6.24k stars 809 forks source link

Clang >= 6.0.0 emits errors for types templated on Objective-C generics #2862

Open DHowett-MSFT opened 6 years ago

DHowett-MSFT commented 6 years ago

_https://bugs.llvm.org/show_bug.cgi?id=25343_

The following code triggers a spurious error:

__attribute__((objc_root_class))
@interface One
@end
__attribute__((objc_root_class))
@interface Two
@end
__attribute__((objc_root_class))
@interface Root <__covariant Type>
@end

template <typename T>
struct F {
        using TPtr = T*;
        TPtr get() { return nullptr; }
};

void repro() {
        F<Root<One*>> one;
        F<Root<Two*>> two;

        one.get();
        two.get();
}
% & ".\clang.exe" --% -o - -S -emit-llvm .\test.mm
.\test.mm:14:7: error: definition with same mangled name as another definition
        TPtr get() { return nullptr; }
             ^
.\test.mm:14:7: note: previous definition is here
1 error generated.

Since the types Root<One*> and Root<Two*> do not differ in function, they should not result in functionally different template instantiations. However, they do. As they do not differ in mangled name, the compiler has effectively emitted two functions with the same mangled name.

Since the implementation of F<T<X*>>::get does not change based on X, a potential workaround is to fall back to F<T>.

DHowett-MSFT commented 5 years ago

This is still in Clang 7, but it's got a slightly better error message.