instantiate-expr-2.cpp revision 260059cab5bab4960880bc9155b32618201d7994
1ffd408a50adb01ae9c0ad92fb5f0981e1ca72df5Daniel Dunbar// RUN: clang-cc -fsyntax-only %s
20760636d458c860beeb77a63049e91e614b4be31Douglas Gregortypedef char one_byte;
30760636d458c860beeb77a63049e91e614b4be31Douglas Gregortypedef char (&two_bytes)[2];
40760636d458c860beeb77a63049e91e614b4be31Douglas Gregortypedef char (&four_bytes)[4];
50760636d458c860beeb77a63049e91e614b4be31Douglas Gregortypedef char (&eight_bytes)[8];
60760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
70760636d458c860beeb77a63049e91e614b4be31Douglas Gregortemplate<int N> struct A { };
80760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
90760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N1 {
100760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  struct X { };
110760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
120760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
130760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N2 {
140760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  struct Y { };
150760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
160760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  two_bytes operator+(Y, Y);
170760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
180760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
190760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N3 {
200760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  struct Z { };
210760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
220760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  eight_bytes operator+(Z, Z);
230760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
240760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
250760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N4 {
260760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  one_byte operator+(N1::X, N2::Y);
270760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
280760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  template<typename T, typename U>
290760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  struct BinOpOverload {
300760636d458c860beeb77a63049e91e614b4be31Douglas Gregor    typedef A<sizeof(T() + U())> type;
310760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  };
320760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
330760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
340760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N1 {
350760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  four_bytes operator+(X, X);
360760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
370760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
380760636d458c860beeb77a63049e91e614b4be31Douglas Gregornamespace N3 {
390760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  eight_bytes operator+(Z, Z); // redeclaration
400760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
410760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
420760636d458c860beeb77a63049e91e614b4be31Douglas Gregorvoid test_bin_op_overload(A<1> *a1, A<2> *a2, A<4> *a4, A<8> *a8) {
430760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  typedef N4::BinOpOverload<N1::X, N2::Y>::type XY;
440760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  XY *xy = a1;
450760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  typedef N4::BinOpOverload<N1::X, N1::X>::type XX;
460760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  XX *xx = a4;
470760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  typedef N4::BinOpOverload<N2::Y, N2::Y>::type YY;
480760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  YY *yy = a2;
490760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  typedef N4::BinOpOverload<N3::Z, N3::Z>::type ZZ;
500760636d458c860beeb77a63049e91e614b4be31Douglas Gregor  ZZ *zz = a8;
510760636d458c860beeb77a63049e91e614b4be31Douglas Gregor}
520760636d458c860beeb77a63049e91e614b4be31Douglas Gregor
53c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregornamespace N3 {
54c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  eight_bytes operator-(::N3::Z);
55c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor}
56c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor
57c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregornamespace N4 {
58c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  template<typename T>
59c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  struct UnaryOpOverload {
60c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor    typedef A<sizeof(-T())> type;
61c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  };
62c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor}
63c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor
64c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregorvoid test_unary_op_overload(A<8> *a8) {
65c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  typedef N4::UnaryOpOverload<N3::Z>::type UZ;
66c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor  UZ *uz = a8;
67c78182dea4396fba411d2526a1386ca994eee6c0Douglas Gregor}
688a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
698a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif/*
708a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greifnamespace N5 {
718a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  template<int I>
728a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  struct Lookup {
738a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif    enum { val = I, more = val + 1 };
748a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  };
758a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
768a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  template<bool B>
778a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  struct Cond {
788a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif    enum Junk { is = B ? Lookup<B>::more : Lookup<Lookup<B+1>::more>::val };
798a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  };
808a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
818a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  enum { resultT = Cond<true>::is,
828a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif         resultF = Cond<false>::is };
838a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif}
848a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif*/
858a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
868a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greifnamespace N6 {
87b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  // non-typedependent
888a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  template<int I>
89b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  struct Lookup {};
908a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
918a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  template<bool B, typename T, typename E>
928a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  struct Cond {
938a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif    typedef Lookup<B ? sizeof(T) : sizeof(E)> True;
948a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif    typedef Lookup<!B ? sizeof(T) : sizeof(E)> False;
958a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  };
968a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
978a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif  typedef Cond<true, int, char>::True True;
9876368bbd3f5a8433a863798727e41af9afbf598dGabor Greif  typedef Cond<true, int, char>::False False;
9976368bbd3f5a8433a863798727e41af9afbf598dGabor Greif
10076368bbd3f5a8433a863798727e41af9afbf598dGabor Greif  // check that we have the right types
10176368bbd3f5a8433a863798727e41af9afbf598dGabor Greif  Lookup<1> const &L1(False());
10276368bbd3f5a8433a863798727e41af9afbf598dGabor Greif  Lookup<sizeof(int)> const &L2(True());
1038a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif}
1048a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
1058a0659c213ac62a4dcaa7d25c7c3825212bc763dGabor Greif
106b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greifnamespace N7 {
107b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  // type dependent
108b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  template<int I>
109b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  struct Lookup {};
110b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif
111b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  template<bool B, typename T, typename E>
112b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  struct Cond {
113b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif    T foo() { return B ? T() : E(); }
114b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif    typedef Lookup<sizeof(B ? T() : E())> Type;
115b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  };
116b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif
117b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  //Cond<true, int*, double> C; // Errors
118b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  //int V(C.foo()); // Errors
119b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  //typedef Cond<true, int*, double>::Type Type; // Errors + CRASHES!
120b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif  typedef Cond<true, int, double>::Type Type;
121b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif}
122b4f9090cc19ca3502fd895def9769d9c5a5a06c2Gabor Greif
123260059cab5bab4960880bc9155b32618201d7994Douglas Gregor#if 0
124260059cab5bab4960880bc9155b32618201d7994Douglas Gregor// FIXME: Unable to handle general declaration references at this point.
125260059cab5bab4960880bc9155b32618201d7994Douglas Gregortemplate<typename T, unsigned long N> struct IntegralConstant { };
126260059cab5bab4960880bc9155b32618201d7994Douglas Gregor
127260059cab5bab4960880bc9155b32618201d7994Douglas Gregortemplate<typename T>
128260059cab5bab4960880bc9155b32618201d7994Douglas Gregorstruct X0 {
129260059cab5bab4960880bc9155b32618201d7994Douglas Gregor  void f(T x, IntegralConstant<T, sizeof(x)>);
130260059cab5bab4960880bc9155b32618201d7994Douglas Gregor};
131260059cab5bab4960880bc9155b32618201d7994Douglas Gregor
132260059cab5bab4960880bc9155b32618201d7994Douglas Gregorvoid test_X0(X0<int> x, IntegralConstant<int, sizeof(int)> ic) {
133260059cab5bab4960880bc9155b32618201d7994Douglas Gregor  x.f(ic);
134260059cab5bab4960880bc9155b32618201d7994Douglas Gregor}
135260059cab5bab4960880bc9155b32618201d7994Douglas Gregor#endif
136