66 lines · cpp
1// RUN: %clang_cc1 %s -std=c++17 -fsyntax-only -fcxx-exceptions -verify2 3struct S1 {4 void f() [[clang::annotate_type("foo")]];5 [[clang::annotate_type("foo")]] void g(); // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}6};7 8template <typename T1, typename T2> struct is_same {9 static constexpr bool value = false;10};11 12template <typename T1> struct is_same<T1, T1> {13 static constexpr bool value = true;14};15 16static_assert(is_same<int, int [[clang::annotate_type("foo")]]>::value);17static_assert(is_same<int [[clang::annotate_type("foo")]],18 int [[clang::annotate_type("bar")]]>::value);19static_assert(is_same<int *, int *[[clang::annotate_type("foo")]]>::value);20 21// Cannot overload on types that only differ by `annotate_type` attribute.22void f(int) {} // expected-note {{previous definition is here}}23void f(int [[clang::annotate_type("foo")]]) {} // expected-error {{redefinition of 'f'}}24 25// Cannot specialize on types that only differ by `annotate_type` attribute.26template <class T> struct S2 {};27 28template <> struct S2<int> {}; // expected-note {{previous definition is here}}29 30template <>31struct S2<int [[clang::annotate_type("foo")]]> {}; // expected-error {{redefinition of 'S2<int>'}}32 33// Test that the attribute supports parameter pack expansion.34template <int... Is> void variadic_func_template() {35 int [[clang::annotate_type("foo", Is...)]] val;36}37int f2() { variadic_func_template<1, 2, 3>(); }38 39// Make sure we correctly diagnose wrong number of arguments for40// [[clang::annotate_type]] inside a template argument.41template <typename Ty> void func_template();42void f3() {43 func_template<int [[clang::annotate_type()]]>(); // expected-error {{'clang::annotate_type' attribute takes at least 1 argument}}44}45 46// More error cases: Prohibit adding the attribute to declarations.47// Different declarations hit different code paths, so they need separate tests.48namespace [[clang::annotate_type("foo")]] my_namespace {} // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}49struct [[clang::annotate_type("foo")]] S3; // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}50struct [[clang::annotate_type("foo")]] S3{ // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}51 [[clang::annotate_type("foo")]] int member; // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}52};53void f4() {54 for ([[clang::annotate_type("foo")]] int i = 0; i < 42; ++i) {} // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}55 for (; [[clang::annotate_type("foo")]] bool b = false;) {} // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}56 while ([[clang::annotate_type("foo")]] bool b = false) {} // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}57 if ([[clang::annotate_type("foo")]] bool b = false) {} // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}58 try {59 } catch ([[clang::annotate_type("foo")]] int i) { // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}60 }61}62template <class T>63[[clang::annotate_type("foo")]] T var_template; // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}64[[clang::annotate_type("foo")]] extern "C" int extern_c_func(); // expected-error {{an attribute list cannot appear here}}65extern "C" [[clang::annotate_type("foo")]] int extern_c_func(); // expected-error {{'clang::annotate_type' attribute cannot be applied to a declaration}}66