xref: /minix3/external/bsd/llvm/dist/clang/test/SemaTemplate/ms-delayed-default-template-args.cpp (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1*0a6a1f1dSLionel Sambuc // RUN: %clang_cc1 -fms-compatibility -std=c++11 %s -verify
2*0a6a1f1dSLionel Sambuc 
3*0a6a1f1dSLionel Sambuc // MSVC should compile this file without errors.
4*0a6a1f1dSLionel Sambuc 
5*0a6a1f1dSLionel Sambuc namespace test_basic {
6*0a6a1f1dSLionel Sambuc template <typename T = Baz> // expected-warning {{using the undeclared type 'Baz' as a default template argument is a Microsoft extension}}
7*0a6a1f1dSLionel Sambuc struct Foo { T x; };
8*0a6a1f1dSLionel Sambuc typedef int Baz;
9*0a6a1f1dSLionel Sambuc template struct Foo<>;
10*0a6a1f1dSLionel Sambuc }
11*0a6a1f1dSLionel Sambuc 
12*0a6a1f1dSLionel Sambuc namespace test_namespace {
13*0a6a1f1dSLionel Sambuc namespace nested {
14*0a6a1f1dSLionel Sambuc template <typename T = Baz> // expected-warning {{using the undeclared type 'Baz' as a default template argument is a Microsoft extension}}
15*0a6a1f1dSLionel Sambuc struct Foo {
16*0a6a1f1dSLionel Sambuc   static_assert(sizeof(T) == 4, "should get int, not double");
17*0a6a1f1dSLionel Sambuc };
18*0a6a1f1dSLionel Sambuc typedef int Baz;
19*0a6a1f1dSLionel Sambuc }
20*0a6a1f1dSLionel Sambuc typedef double Baz;
21*0a6a1f1dSLionel Sambuc template struct nested::Foo<>;
22*0a6a1f1dSLionel Sambuc }
23*0a6a1f1dSLionel Sambuc 
24*0a6a1f1dSLionel Sambuc namespace test_inner_class_template {
25*0a6a1f1dSLionel Sambuc struct Outer {
26*0a6a1f1dSLionel Sambuc   template <typename T = Baz> // expected-warning {{using the undeclared type 'Baz' as a default template argument is a Microsoft extension}}
27*0a6a1f1dSLionel Sambuc   struct Foo {
28*0a6a1f1dSLionel Sambuc     static_assert(sizeof(T) == 4, "should get int, not double");
29*0a6a1f1dSLionel Sambuc   };
30*0a6a1f1dSLionel Sambuc   typedef int Baz;
31*0a6a1f1dSLionel Sambuc };
32*0a6a1f1dSLionel Sambuc typedef double Baz;
33*0a6a1f1dSLionel Sambuc template struct Outer::Foo<>;
34*0a6a1f1dSLionel Sambuc }
35*0a6a1f1dSLionel Sambuc 
36*0a6a1f1dSLionel Sambuc namespace test_nontype_param {
37*0a6a1f1dSLionel Sambuc template <typename T> struct Bar { T x; };
38*0a6a1f1dSLionel Sambuc typedef int Qux;
39*0a6a1f1dSLionel Sambuc template <Bar<Qux> *P>
40*0a6a1f1dSLionel Sambuc struct Foo {
41*0a6a1f1dSLionel Sambuc };
42*0a6a1f1dSLionel Sambuc Bar<int> g;
43*0a6a1f1dSLionel Sambuc template struct Foo<&g>;
44*0a6a1f1dSLionel Sambuc }
45*0a6a1f1dSLionel Sambuc 
46*0a6a1f1dSLionel Sambuc // MSVC accepts this, but Clang doesn't.
47*0a6a1f1dSLionel Sambuc namespace test_template_instantiation_arg {
48*0a6a1f1dSLionel Sambuc template <typename T> struct Bar { T x; };
49*0a6a1f1dSLionel Sambuc template <typename T = Bar<Weber>>  // expected-error {{use of undeclared identifier 'Weber'}}
50*0a6a1f1dSLionel Sambuc struct Foo {
51*0a6a1f1dSLionel Sambuc   static_assert(sizeof(T) == 4, "Bar should have gotten int");
52*0a6a1f1dSLionel Sambuc   // FIXME: These diagnostics are bad.
53*0a6a1f1dSLionel Sambuc }; // expected-error {{expected ',' or '>' in template-parameter-list}}
54*0a6a1f1dSLionel Sambuc // expected-warning@-1 {{does not declare anything}}
55*0a6a1f1dSLionel Sambuc typedef int Weber;
56*0a6a1f1dSLionel Sambuc }
57*0a6a1f1dSLionel Sambuc 
58*0a6a1f1dSLionel Sambuc #ifdef __clang__
59*0a6a1f1dSLionel Sambuc // These are negative test cases that MSVC doesn't compile either.  Try to use
60*0a6a1f1dSLionel Sambuc // unique undeclared identifiers so typo correction doesn't find types declared
61*0a6a1f1dSLionel Sambuc // above.
62*0a6a1f1dSLionel Sambuc 
63*0a6a1f1dSLionel Sambuc namespace test_undeclared_nontype_parm_type {
64*0a6a1f1dSLionel Sambuc template <Zargon N> // expected-error {{unknown type name 'Zargon'}}
65*0a6a1f1dSLionel Sambuc struct Foo { int x[N]; };
66*0a6a1f1dSLionel Sambuc typedef int Zargon;
67*0a6a1f1dSLionel Sambuc template struct Foo<4>;
68*0a6a1f1dSLionel Sambuc }
69*0a6a1f1dSLionel Sambuc 
70*0a6a1f1dSLionel Sambuc namespace test_undeclared_nontype_parm_type_no_name {
71*0a6a1f1dSLionel Sambuc template <typename T, Asdf> // expected-error {{unknown type name 'Asdf'}}
72*0a6a1f1dSLionel Sambuc struct Foo { T x; };
73*0a6a1f1dSLionel Sambuc template struct Foo<int, 0>;
74*0a6a1f1dSLionel Sambuc }
75*0a6a1f1dSLionel Sambuc 
76*0a6a1f1dSLionel Sambuc namespace test_undeclared_type_arg {
77*0a6a1f1dSLionel Sambuc template <typename T>
78*0a6a1f1dSLionel Sambuc struct Foo { T x; };
79*0a6a1f1dSLionel Sambuc template struct Foo<Yodel>; // expected-error {{use of undeclared identifier 'Yodel'}}
80*0a6a1f1dSLionel Sambuc }
81*0a6a1f1dSLionel Sambuc 
82*0a6a1f1dSLionel Sambuc namespace test_undeclared_nontype_parm_arg {
83*0a6a1f1dSLionel Sambuc // Bury an undeclared type as a template argument to the type of a non-type
84*0a6a1f1dSLionel Sambuc // template parameter.
85*0a6a1f1dSLionel Sambuc template <typename T> struct Bar { T x; };
86*0a6a1f1dSLionel Sambuc 
87*0a6a1f1dSLionel Sambuc template <Bar<Xylophone> *P> // expected-error {{use of undeclared identifier 'Xylophone'}}
88*0a6a1f1dSLionel Sambuc // expected-note@-1 {{template parameter is declared here}}
89*0a6a1f1dSLionel Sambuc struct Foo { };
90*0a6a1f1dSLionel Sambuc 
91*0a6a1f1dSLionel Sambuc typedef int Xylophone;
92*0a6a1f1dSLionel Sambuc Bar<Xylophone> g;
93*0a6a1f1dSLionel Sambuc template struct Foo<&g>; // expected-error {{cannot be converted}}
94*0a6a1f1dSLionel Sambuc }
95*0a6a1f1dSLionel Sambuc 
96*0a6a1f1dSLionel Sambuc #endif
97