summaryrefslogtreecommitdiffstats
path: root/clang/test/CodeGenCXX/template-instantiation.cpp
diff options
context:
space:
mode:
authorChandler Carruth <chandlerc@gmail.com>2011-08-18 09:09:59 +0000
committerChandler Carruth <chandlerc@gmail.com>2011-08-18 09:09:59 +0000
commit48b2831d8ade9f30bf6e82f584e840d7dc9d7ec7 (patch)
tree4da7db76edb4b235f5568067383cb650bf26d9a9 /clang/test/CodeGenCXX/template-instantiation.cpp
parent2f2e9c5057619b6ba90568bc2533f10f931a2b7e (diff)
downloadbcm5719-llvm-48b2831d8ade9f30bf6e82f584e840d7dc9d7ec7.tar.gz
bcm5719-llvm-48b2831d8ade9f30bf6e82f584e840d7dc9d7ec7.zip
Always mark friend function declarations in class templates as
implicitly instantiable, even if we don't see a body on the friend function declaration. The body may simply have not yet been attached. This fixes PR10666. There may be an alternate, preferred implementation strategy, see my FIXME. Review would definitely be appreciated Doug. =D llvm-svn: 137934
Diffstat (limited to 'clang/test/CodeGenCXX/template-instantiation.cpp')
-rw-r--r--clang/test/CodeGenCXX/template-instantiation.cpp36
1 files changed, 36 insertions, 0 deletions
diff --git a/clang/test/CodeGenCXX/template-instantiation.cpp b/clang/test/CodeGenCXX/template-instantiation.cpp
index cc30af0aba4..09b3a4fcc54 100644
--- a/clang/test/CodeGenCXX/template-instantiation.cpp
+++ b/clang/test/CodeGenCXX/template-instantiation.cpp
@@ -17,6 +17,19 @@
// CHECK: define linkonce_odr void @_ZN5test21CIiE6foobarIdEEvT_(
// CHECK: define available_externally void @_ZN5test21CIiE6zedbarEd(
+// CHECK: define linkonce_odr void @_ZN7PR106662g1ENS_1SILi1EEE()
+// CHECK: define linkonce_odr void @_ZN7PR106662g1ENS_1SILi2EEE()
+// CHECK: define linkonce_odr void @_ZN7PR106662g1ENS_1SILi3EEE()
+// CHECK: define linkonce_odr void @_ZN7PR106662g2ENS_1SILi1EEE()
+// CHECK: define linkonce_odr void @_ZN7PR106662g2ENS_1SILi2EEE()
+// CHECK: define linkonce_odr void @_ZN7PR106662g2ENS_1SILi3EEE()
+// CHECK: declare void @_ZN7PR106662h1ENS_1SILi1EEE()
+// CHECK: declare void @_ZN7PR106662h1ENS_1SILi2EEE()
+// CHECK: declare void @_ZN7PR106662h1ENS_1SILi3EEE()
+// CHECK: declare void @_ZN7PR106662h2ENS_1SILi1EEE()
+// CHECK: declare void @_ZN7PR106662h2ENS_1SILi2EEE()
+// CHECK: declare void @_ZN7PR106662h2ENS_1SILi3EEE()
+
namespace test0 {
struct basic_streambuf {
virtual ~basic_streambuf();
@@ -152,3 +165,26 @@ namespace PR10001 {
int x = S<int>::f();
}
+
+// Ensure that definitions are emitted for all friend functions defined within
+// class templates. Order of declaration is extremely important here. Different
+// instantiations of the class happen at different points during the deferred
+// method body parsing and afterward. Those different points of instantiation
+// change the exact form the class template appears to have.
+namespace PR10666 {
+ template <int N> struct S {
+ void f1() { S<1> s; }
+ friend void g1(S s) {}
+ friend void h1(S s);
+ void f2() { S<2> s; }
+ friend void g2(S s) {}
+ friend void h2(S s);
+ void f3() { S<3> s; }
+ };
+ void test(S<1> s1, S<2> s2, S<3> s3) {
+ g1(s1); g1(s2); g1(s3);
+ g2(s1); g2(s2); g2(s3);
+ h1(s1); h1(s2); h1(s3);
+ h2(s1); h2(s2); h2(s3);
+ }
+}
OpenPOWER on IntegriCloud