Author: rtrieu Date: Wed Feb 21 21:50:29 2018 New Revision: 325742 URL: http://llvm.org/viewvc/llvm-project?rev=325742&view=rev Log: [ODRHash] Fix hashing for friend functions.
When hashing a templated function, use the hash of the function it was instantiated from. Added: cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Bad.h cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Good.h Modified: cfe/trunk/lib/AST/Decl.cpp cfe/trunk/lib/AST/ODRHash.cpp cfe/trunk/test/Modules/Inputs/odr_hash-Friend/module.modulemap cfe/trunk/test/Modules/odr_hash-Friend.cpp Modified: cfe/trunk/lib/AST/Decl.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Decl.cpp?rev=325742&r1=325741&r2=325742&view=diff ============================================================================== --- cfe/trunk/lib/AST/Decl.cpp (original) +++ cfe/trunk/lib/AST/Decl.cpp Wed Feb 21 21:50:29 2018 @@ -3625,6 +3625,12 @@ unsigned FunctionDecl::getODRHash() { } } + if (auto *FT = getInstantiatedFromMemberFunction()) { + HasODRHash = true; + ODRHash = FT->getODRHash(); + return ODRHash; + } + class ODRHash Hash; Hash.AddFunctionDecl(this); HasODRHash = true; Modified: cfe/trunk/lib/AST/ODRHash.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ODRHash.cpp?rev=325742&r1=325741&r2=325742&view=diff ============================================================================== --- cfe/trunk/lib/AST/ODRHash.cpp (original) +++ cfe/trunk/lib/AST/ODRHash.cpp Wed Feb 21 21:50:29 2018 @@ -484,9 +484,6 @@ void ODRHash::AddFunctionDecl(const Func if (!Function->hasBody()) return; if (!Function->getBody()) return; - // TODO: Fix hashing friend functions. - if (Function->getFriendObjectKind()) return; - // Skip functions that are specializations or in specialization context. const DeclContext *DC = Function; while (DC) { Added: cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Bad.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Bad.h?rev=325742&view=auto ============================================================================== --- cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Bad.h (added) +++ cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Bad.h Wed Feb 21 21:50:29 2018 @@ -0,0 +1,17 @@ +template <class T> +struct iterator { + void Compare(const iterator &x) { return; } + friend void Check(iterator) { return; } +}; + +template <class T = int> struct Box { + iterator<T> I; + + void test() { + Check(I); + I.Compare(I); + } +}; + +// Force instantiation of Box<int> +Box<> B; Added: cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Good.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Good.h?rev=325742&view=auto ============================================================================== --- cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Good.h (added) +++ cfe/trunk/test/Modules/Inputs/odr_hash-Friend/Good.h Wed Feb 21 21:50:29 2018 @@ -0,0 +1,17 @@ +template <class T> +struct iterator { + void Compare(const iterator &x) { } + friend void Check(iterator) {} +}; + +template <class T = int> struct Box { + iterator<T> I; + + void test() { + Check(I); + I.Compare(I); + } +}; + +// Force instantiation of Box<int> +Box<> B; Modified: cfe/trunk/test/Modules/Inputs/odr_hash-Friend/module.modulemap URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Modules/Inputs/odr_hash-Friend/module.modulemap?rev=325742&r1=325741&r2=325742&view=diff ============================================================================== --- cfe/trunk/test/Modules/Inputs/odr_hash-Friend/module.modulemap (original) +++ cfe/trunk/test/Modules/Inputs/odr_hash-Friend/module.modulemap Wed Feb 21 21:50:29 2018 @@ -13,3 +13,11 @@ module Module2 { module Module3 { header "M3.h" } + +module Good { + header "Good.h" +} + +module Bad { + header "Bad.h" +} Modified: cfe/trunk/test/Modules/odr_hash-Friend.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Modules/odr_hash-Friend.cpp?rev=325742&r1=325741&r2=325742&view=diff ============================================================================== --- cfe/trunk/test/Modules/odr_hash-Friend.cpp (original) +++ cfe/trunk/test/Modules/odr_hash-Friend.cpp Wed Feb 21 21:50:29 2018 @@ -1,21 +1,89 @@ // RUN: rm -rf %t -// RUN: %clang_cc1 -fmodules -fmodules-cache-path=%t/modules.cache \ +// PR35939: MicrosoftMangle.cpp triggers an assertion failure on this test. +// UNSUPPORTED: system-windows + +// RUN: %clang_cc1 \ // RUN: -I %S/Inputs/odr_hash-Friend \ // RUN: -emit-obj -o /dev/null \ // RUN: -fmodules \ // RUN: -fimplicit-module-maps \ // RUN: -fmodules-cache-path=%t/modules.cache \ -// RUN: -std=c++11 -x c++ %s -verify +// RUN: -std=c++11 -x c++ %s -verify -DTEST1 -fcolor-diagnostics -// PR35939: MicrosoftMangle.cpp triggers an assertion failure on this test. -// UNSUPPORTED: system-windows +// RUN: %clang_cc1 \ +// RUN: -I %S/Inputs/odr_hash-Friend \ +// RUN: -emit-obj -o /dev/null \ +// RUN: -fmodules \ +// RUN: -fimplicit-module-maps \ +// RUN: -fmodules-cache-path=%t/modules.cache \ +// RUN: -std=c++11 -x c++ %s -verify -DTEST2 -fcolor-diagnostics + +// RUN: %clang_cc1 \ +// RUN: -I %S/Inputs/odr_hash-Friend \ +// RUN: -emit-obj -o /dev/null \ +// RUN: -fmodules \ +// RUN: -fimplicit-module-maps \ +// RUN: -fmodules-cache-path=%t/modules.cache \ +// RUN: -std=c++11 -x c++ %s -verify -DTEST3 -fcolor-diagnostics + +// RUN: %clang_cc1 \ +// RUN: -I %S/Inputs/odr_hash-Friend \ +// RUN: -emit-obj -o /dev/null \ +// RUN: -fmodules \ +// RUN: -fimplicit-module-maps \ +// RUN: -fmodules-cache-path=%t/modules.cache \ +// RUN: -std=c++11 -x c++ %s -verify -DTEST3 -fcolor-diagnostics + +// RUN: %clang_cc1 \ +// RUN: -I %S/Inputs/odr_hash-Friend \ +// RUN: -emit-obj -o /dev/null \ +// RUN: -fmodules \ +// RUN: -fimplicit-module-maps \ +// RUN: -fmodules-cache-path=%t/modules.cache \ +// RUN: -std=c++11 -x c++ %s -verify -DTEST3 -fcolor-diagnostics +#if defined(TEST1) +#include "Box.h" +#include "M1.h" +#include "M3.h" // expected-no-diagnostics +#endif +#if defined(TEST2) #include "Box.h" #include "M1.h" #include "M3.h" +#include "Good.h" +// expected-no-diagnostics +#endif + +#if defined(TEST3) +#include "Good.h" +#include "Box.h" +#include "M1.h" +#include "M3.h" +// expected-no-diagnostics +#endif + +#if defined(TEST4) +#include "Box.h" +#include "M1.h" +#include "M3.h" +#include "Bad.h" +// expected-error@Bad.h:* {{'Check' has different definitions in different modules; definition in module 'Bad' first difference is function body}} +// expected-note@Box.h:* {{but in 'Box' found a different body}} +#endif + +#if defined(TEST5) +#include "Bad.h" +#include "Box.h" +#include "M1.h" +#include "M3.h" +// expected-error@Bad.h:* {{'Check' has different definitions in different modules; definition in module 'Bad' first difference is function body}} +// expected-note@Box.h:* {{but in 'Box' found a different body}} +#endif + void Run() { Box<> Present; _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits