Home | History | Annotate | Download | only in namespace.def
      1 // RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s
      2 
      3 // Fun things you can do with inline namespaces:
      4 
      5 inline namespace X {
      6   void f1();
      7 
      8   inline namespace Y {
      9     void f2();
     10 
     11     template <typename T> class C {};
     12   }
     13 
     14   // Specialize and partially specialize somewhere else.
     15   template <> class C<int> {};
     16   template <typename T> class C<T*> {};
     17 }
     18 
     19 // Qualified and unqualified lookup as if member of enclosing NS.
     20 void foo1() {
     21   f1();
     22   ::f1();
     23   X::f1();
     24   Y::f1(); // expected-error {{no member named 'f1' in namespace 'X::Y'}}
     25 
     26   f2();
     27   ::f2();
     28   X::f2();
     29   Y::f2();
     30 }
     31 
     32 template <> class C<float> {};
     33 template <typename T> class C<T&> {};
     34 
     35 template class C<double>;
     36 
     37 
     38 // As well as all the fun with ADL.
     39 
     40 namespace ADL {
     41   struct Outer {};
     42 
     43   inline namespace IL {
     44     struct Inner {};
     45 
     46     void fo(Outer);
     47   }
     48 
     49   void fi(Inner);
     50 
     51   inline namespace IL2 {
     52     void fi2(Inner);
     53   }
     54 }
     55 
     56 void foo2() {
     57   ADL::Outer o;
     58   ADL::Inner i;
     59   fo(o);
     60   fi(i);
     61   fi2(i);
     62 }
     63 
     64 // Let's not forget overload sets.
     65 struct Distinct {};
     66 inline namespace Over {
     67   void over(Distinct);
     68 }
     69 void over(int);
     70 
     71 void foo3() {
     72   Distinct d;
     73   ::over(d);
     74 }
     75 
     76 // Don't forget to do correct lookup for redeclarations.
     77 namespace redecl { inline namespace n1 {
     78 
     79   template <class Tp> class allocator;
     80 
     81   template <>
     82   class allocator<void>
     83   {
     84   public:
     85       typedef const void* const_pointer;
     86   };
     87 
     88   template <class Tp>
     89   class allocator
     90   {
     91   public:
     92       typedef Tp& reference;
     93 
     94       void allocate(allocator<void>::const_pointer = 0);
     95   };
     96 
     97 } }
     98 
     99 // Normal redeclarations (not for explicit instantiations or
    100 // specializations) are distinct in an inline namespace vs. not in an
    101 // inline namespace.
    102 namespace redecl2 {
    103   inline namespace n1 {
    104     void f(int) { }
    105     struct X1 { };
    106     template<typename T> void f(T) { }
    107     template<typename T> struct X2 { };
    108     int i = 71;
    109     enum E { e };
    110   }
    111 
    112   void f(int) { }
    113   struct X1 { };
    114   template<typename T> void f(T) { }
    115   template<typename T> struct X2 { };
    116   int i = 71;
    117   enum E { e };
    118 }
    119