xref: /minix3/external/bsd/llvm/dist/clang/test/SemaTemplate/lookup-dependent-bases.cpp (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f4a2713aSLionel Sambuc // RUN: %clang_cc1 -fms-compatibility -fsyntax-only -verify %s
2f4a2713aSLionel Sambuc 
3*0a6a1f1dSLionel Sambuc namespace basic {
4*0a6a1f1dSLionel Sambuc struct C {
foo2basic::C5f4a2713aSLionel Sambuc   static void foo2() {}
6f4a2713aSLionel Sambuc };
7*0a6a1f1dSLionel Sambuc template <typename T>
8*0a6a1f1dSLionel Sambuc struct A {
9f4a2713aSLionel Sambuc   typedef C D;
10f4a2713aSLionel Sambuc };
11f4a2713aSLionel Sambuc 
12*0a6a1f1dSLionel Sambuc template <typename T>
13*0a6a1f1dSLionel Sambuc struct B : A<T> {
foobasic::B14f4a2713aSLionel Sambuc   void foo() {
15*0a6a1f1dSLionel Sambuc     D::foo2(); // expected-warning {{use of undeclared identifier 'D'; unqualified lookup into dependent bases of class template 'B' is a Microsoft extension}}
16f4a2713aSLionel Sambuc   }
17f4a2713aSLionel Sambuc };
18*0a6a1f1dSLionel Sambuc 
19*0a6a1f1dSLionel Sambuc template struct B<int>; // Instantiation has no warnings.
20*0a6a1f1dSLionel Sambuc }
21*0a6a1f1dSLionel Sambuc 
22*0a6a1f1dSLionel Sambuc namespace nested_nodep_base {
23*0a6a1f1dSLionel Sambuc // There are limits to our hacks, MSVC accepts this, but we don't.
24*0a6a1f1dSLionel Sambuc struct A {
25*0a6a1f1dSLionel Sambuc   struct D { static void foo2(); };
26*0a6a1f1dSLionel Sambuc };
27*0a6a1f1dSLionel Sambuc template <typename T>
28*0a6a1f1dSLionel Sambuc struct B : T {
29*0a6a1f1dSLionel Sambuc   struct C {
foonested_nodep_base::B::C30*0a6a1f1dSLionel Sambuc     void foo() {
31*0a6a1f1dSLionel Sambuc       D::foo2(); // expected-error {{use of undeclared identifier 'D'}}
32*0a6a1f1dSLionel Sambuc     }
33*0a6a1f1dSLionel Sambuc   };
34*0a6a1f1dSLionel Sambuc };
35*0a6a1f1dSLionel Sambuc 
36*0a6a1f1dSLionel Sambuc template struct B<A>; // Instantiation has no warnings.
37*0a6a1f1dSLionel Sambuc }
38*0a6a1f1dSLionel Sambuc 
39*0a6a1f1dSLionel Sambuc namespace nested_dep_base {
40*0a6a1f1dSLionel Sambuc // We actually accept this because the inner class has a dependent base even
41*0a6a1f1dSLionel Sambuc // though it isn't a template.
42*0a6a1f1dSLionel Sambuc struct A {
43*0a6a1f1dSLionel Sambuc   struct D { static void foo2(); };
44*0a6a1f1dSLionel Sambuc };
45*0a6a1f1dSLionel Sambuc template <typename T>
46*0a6a1f1dSLionel Sambuc struct B {
47*0a6a1f1dSLionel Sambuc   struct C : T {
foonested_dep_base::B::C48*0a6a1f1dSLionel Sambuc     void foo() {
49*0a6a1f1dSLionel Sambuc       D::foo2(); // expected-warning {{use of undeclared identifier 'D'; unqualified lookup into dependent bases of class template 'C' is a Microsoft extension}}
50*0a6a1f1dSLionel Sambuc     }
51*0a6a1f1dSLionel Sambuc   };
52*0a6a1f1dSLionel Sambuc };
53*0a6a1f1dSLionel Sambuc 
54*0a6a1f1dSLionel Sambuc template struct B<A>; // Instantiation has no warnings.
55*0a6a1f1dSLionel Sambuc }
56