Skip to content

[clang] Migrate DR tests to static_assert #88611

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Apr 16, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 9 additions & 5 deletions clang/test/CXX/drs/dr0xx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,11 @@
// RUN: %clang_cc1 -std=c++20 %s -verify=expected,since-cxx11,since-cxx17 -fexceptions -fcxx-exceptions -pedantic-errors -triple %itanium_abi_triple
// RUN: %clang_cc1 -std=c++23 %s -verify=expected,since-cxx11,since-cxx17 -fexceptions -fcxx-exceptions -pedantic-errors -triple %itanium_abi_triple

#if __cplusplus == 199711L
#define static_assert(...) __extension__ _Static_assert(__VA_ARGS__)
// cxx98-error@-1 {{variadic macros are a C99 feature}}
#endif

namespace cwg1 { // cwg1: no
namespace X { extern "C" void cwg1_f(int a = 1); }
namespace Y { extern "C" void cwg1_f(int a = 1); }
Expand Down Expand Up @@ -897,7 +902,7 @@ namespace cwg54 { // cwg54: 2.8

namespace cwg55 { // cwg55: yes
enum E { e = 5 };
int test[(e + 1 == 6) ? 1 : -1];
static_assert(e + 1 == 6, "");
}

namespace cwg56 { // cwg56: yes
Expand Down Expand Up @@ -1163,10 +1168,9 @@ namespace cwg75 { // cwg75: yes

namespace cwg76 { // cwg76: yes
const volatile int n = 1;
int arr[n]; // #cwg76-vla
// expected-error@#cwg76-vla {{variable length arrays in C++ are a Clang extension}}
// expected-note@#cwg76-vla {{read of volatile-qualified type 'const volatile int' is not allowed in a constant expression}}
// expected-error@#cwg76-vla {{variable length array declaration not allowed at file scope}}
static_assert(n, "");
// expected-error@-1 {{static assertion expression is not an integral constant expression}}
// expected-note@-2 {{read of volatile-qualified type 'const volatile int' is not allowed in a constant expression}}
}

namespace cwg77 { // cwg77: yes
Expand Down
5 changes: 2 additions & 3 deletions clang/test/CXX/drs/dr16xx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -153,10 +153,9 @@ namespace cwg1645 { // cwg1645: 3.9

namespace cwg1652 { // cwg1652: 3.6
int a, b;
int arr[&a + 1 == &b ? 1 : 2];
// expected-error@-1 {{variable length arrays in C++ are a Clang extension}}
static_assert(&a + 1 == &b, "");
// expected-error@-1 {{static assertion expression is not an integral constant expression}}
// expected-note@-2 {{comparison against pointer '&a + 1' that points past the end of a complete object has unspecified value}}
// expected-error@-3 {{variable length array declaration not allowed at file scope}}
}

namespace cwg1653 { // cwg1653: 4 c++17
Expand Down
61 changes: 33 additions & 28 deletions clang/test/CXX/drs/dr1xx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,17 @@
// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-unknown %s -verify=expected,since-cxx11,since-cxx17 -fexceptions -fcxx-exceptions -pedantic-errors
// RUN: %clang_cc1 -std=c++23 -triple x86_64-unknown-unknown %s -verify=expected,since-cxx11,since-cxx17 -fexceptions -fcxx-exceptions -pedantic-errors

#if __cplusplus == 199711L
#define static_assert(...) __extension__ _Static_assert(__VA_ARGS__)
// cxx98-error@-1 {{variadic macros are a C99 feature}}
#endif

#if __cplusplus == 199711L
#define __enable_constant_folding(x) (__builtin_constant_p(x) ? (x) : (x))
#else
#define __enable_constant_folding
#endif

namespace cwg100 { // cwg100: yes
template<const char (*)[4]> struct A {}; // #cwg100-A
template<const char (&)[4]> struct B {}; // #cwg100-B
Expand Down Expand Up @@ -736,22 +747,16 @@ namespace cwg147 { // cwg147: yes

namespace cwg148 { // cwg148: yes
struct A { int A::*p; };
int check1[__is_pod(int(A::*)) ? 1 : -1];
int check2[__is_pod(A) ? 1 : -1];
static_assert(__is_pod(int(A::*)), "");
static_assert(__is_pod(A), "");
}

// cwg149: na

namespace cwg151 { // cwg151: 3.1
struct X {};
typedef int X::*p;
#if __cplusplus < 201103L
#define fold(x) (__builtin_constant_p(0) ? (x) : (x))
#else
#define fold
#endif
int check[fold(p() == 0) ? 1 : -1];
#undef fold
static_assert(__enable_constant_folding(p() == 0), "");
}

namespace cwg152 { // cwg152: yes
Expand Down Expand Up @@ -956,42 +961,42 @@ namespace cwg171 {

namespace cwg172 { // cwg172: yes
enum { zero };
int check1[-1 < zero ? 1 : -1];
static_assert(-1 < zero, "");

enum { x = -1, y = (unsigned int)-1 };
int check2[sizeof(x) > sizeof(int) ? 1 : -1];
static_assert(sizeof(x) > sizeof(int), "");

enum { a = (unsigned int)-1 / 2 };
int check3a[sizeof(a) == sizeof(int) ? 1 : -1];
int check3b[-a < 0 ? 1 : -1];
static_assert(sizeof(a) == sizeof(int), "");
static_assert(-a < 0, "");

enum { b = (unsigned int)-1 / 2 + 1 };
int check4a[sizeof(b) == sizeof(unsigned int) ? 1 : -1];
int check4b[-b > 0 ? 1 : -1];
static_assert(sizeof(b) == sizeof(unsigned int), "");
static_assert(-b > 0, "");

enum { c = (unsigned long)-1 / 2 };
int check5a[sizeof(c) == sizeof(long) ? 1 : -1];
int check5b[-c < 0 ? 1 : -1];
static_assert(sizeof(c) == sizeof(long), "");
static_assert(-c < 0, "");

enum { d = (unsigned long)-1 / 2 + 1 };
int check6a[sizeof(d) == sizeof(unsigned long) ? 1 : -1];
int check6b[-d > 0 ? 1 : -1];
static_assert(sizeof(d) == sizeof(unsigned long), "");
static_assert(-d > 0, "");

enum { e = (unsigned long long)-1 / 2 };
// cxx98-error@-1 {{'long long' is a C++11 extension}}
int check7a[sizeof(e) == sizeof(long) ? 1 : -1];
int check7b[-e < 0 ? 1 : -1];
static_assert(sizeof(e) == sizeof(long), "");
static_assert(-e < 0, "");

enum { f = (unsigned long long)-1 / 2 + 1 };
// cxx98-error@-1 {{'long long' is a C++11 extension}}
int check8a[sizeof(f) == sizeof(unsigned long) ? 1 : -1];
int check8b[-f > 0 ? 1 : -1];
static_assert(sizeof(f) == sizeof(unsigned long), "");
static_assert(-f > 0, "");
}

namespace cwg173 { // cwg173: yes
int check[('0' + 1 == '1' && '0' + 2 == '2' && '0' + 3 == '3' &&
'0' + 4 == '4' && '0' + 5 == '5' && '0' + 6 == '6' &&
'0' + 7 == '7' && '0' + 8 == '8' && '0' + 9 == '9') ? 1 : -1];
static_assert('0' + 1 == '1' && '0' + 2 == '2' && '0' + 3 == '3' &&
'0' + 4 == '4' && '0' + 5 == '5' && '0' + 6 == '6' &&
'0' + 7 == '7' && '0' + 8 == '8' && '0' + 9 == '9', "");
}

// cwg174: sup 1012
Expand Down Expand Up @@ -1070,7 +1075,7 @@ namespace cwg177 { // cwg177: yes
}

namespace cwg178 { // cwg178: yes
int check[int() == 0 ? 1 : -1];
static_assert(int() == 0, "");
#if __cplusplus >= 201103L
static_assert(int{} == 0, "");
struct S { int a, b; };
Expand Down Expand Up @@ -1180,7 +1185,7 @@ namespace cwg187 { // cwg187: sup 481

namespace cwg188 { // cwg188: yes
char c[10];
int check[sizeof(0, c) == 10 ? 1 : -1];
static_assert(sizeof(0, c) == 10, "");
}

// cwg190 FIXME: add codegen test for tbaa
Expand Down
15 changes: 10 additions & 5 deletions clang/test/CXX/drs/dr2xx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,10 +10,15 @@
typedef __SIZE_TYPE__ size_t;
// cxx98-error@-1 0-1 {{'long long' is a C++11 extension}}

#if __cplusplus < 201103L
#define fold(x) (__builtin_constant_p(x) ? (x) : (x))
#if __cplusplus == 199711L
#define static_assert(...) __extension__ _Static_assert(__VA_ARGS__)
// cxx98-error@-1 {{variadic macros are a C99 feature}}
#endif

#if __cplusplus == 199711L
#define __enable_constant_folding(x) (__builtin_constant_p(x) ? (x) : (x))
#else
#define fold
#define __enable_constant_folding
#endif

namespace cwg200 { // cwg200: dup 214
Expand All @@ -31,7 +36,7 @@ namespace cwg200 { // cwg200: dup 214
namespace cwg202 { // cwg202: 3.1
template<typename T> T f();
template<int (*g)()> struct X {
int arr[fold(g == &f<int>) ? 1 : -1];
static_assert(__enable_constant_folding(g == &f<int>), "");
};
template struct X<f>;
}
Expand Down Expand Up @@ -1024,7 +1029,7 @@ namespace cwg275 { // cwg275: no
namespace cwg277 { // cwg277: 3.1
typedef int *intp;
int *p = intp();
int a[fold(intp() ? -1 : 1)];
static_assert(__enable_constant_folding(!intp()), "");
}

namespace cwg280 { // cwg280: 2.9
Expand Down
38 changes: 21 additions & 17 deletions clang/test/CXX/drs/dr3xx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,17 @@
// RUN: %clang_cc1 -std=c++11 -verify=expected,cxx98-14,cxx98-17,cxx98-20,cxx11-14,since-cxx11 -triple %itanium_abi_triple %s -fexceptions -fcxx-exceptions -pedantic-errors
// RUN: %clang_cc1 -std=c++98 -verify=expected,cxx98-14,cxx98-17,cxx98-20,cxx98 -triple %itanium_abi_triple %s -fexceptions -fcxx-exceptions -pedantic-errors

#if __cplusplus == 199711L
#define static_assert(...) __extension__ _Static_assert(__VA_ARGS__)
// cxx98-error@-1 {{variadic macros are a C99 feature}}
#endif

#if __cplusplus == 199711L
#define __enable_constant_folding(x) (__builtin_constant_p(x) ? (x) : (x))
#else
#define __enable_constant_folding
#endif
Comment on lines +8 to +17
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don’t think we normally do that too often for tests, but this is the third file or so that I’ve seen so far that uses these macros, so I’d maybe suggest moving them into a header that the tests can include (especially considering you said you’re going to refactor more tests than just these) if that doesn’t cause any problems.

Copy link
Contributor Author

@Endilll Endilll Apr 13, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're correct that having a very thin standard/backporting library would be beneficial. There have been efforts last year to improve testing infrastructure, and this particular detail was a part of the plan, but those efforts have been stalled for months. I'd keep things as is until the time comes.

I've put up an RFC a year ago if you're interested in the context: https://discourse.llvm.org/t/rfc-opt-in-way-to-make-verifydiagnosticconsumer-slightly-less-strict/70747


namespace cwg300 { // cwg300: yes
template<typename R, typename A> void f(R (&)(A)) {}
int g(int);
Expand Down Expand Up @@ -396,7 +407,7 @@ namespace cwg324 { // cwg324: 3.6

namespace cwg326 { // cwg326: 3.1
struct S {};
int test[__is_trivially_constructible(S, const S&) ? 1 : -1];
static_assert(__is_trivially_constructible(S, const S&), "");
}

namespace cwg327 { // cwg327: dup 538
Expand Down Expand Up @@ -653,7 +664,7 @@ namespace cwg339 { // cwg339: 2.8

template<typename T> A<sizeof(f(T()))> make_A();

int a[conv_int<char>::value ? 1 : -1];
static_assert(conv_int<char>::value, "");
bool b = conv_int2<char>(A<1>());
A<1> c = make_A<char>();
}
Expand Down Expand Up @@ -1099,21 +1110,14 @@ namespace cwg364 { // cwg364: yes
#endif

namespace cwg367 { // cwg367: yes
// FIXME: These diagnostics are terrible. Don't diagnose an ill-formed global
// array as being a VLA!
int a[true ? throw 0 : 4];
// expected-error@-1 {{variable length arrays in C++ are a Clang extension}}
// expected-error@-2 {{variable length array declaration not allowed at file scope}}
int b[true ? 4 : throw 0];
// cxx98-error@-1 {{variable length arrays in C++ are a Clang extension}}
// cxx98-error@-2 {{variable length array folded to constant array as an extension}}
int c[true ? *new int : 4];
// expected-error@-1 {{variable length arrays in C++ are a Clang extension}}
static_assert(__enable_constant_folding(true ? throw 0 : 4), "");
// expected-error@-1 {{expression is not an integral constant expression}}
static_assert(__enable_constant_folding(true ? 4 : throw 0), "");
static_assert(__enable_constant_folding(true ? *new int : 4), "");
// expected-error@-1 {{expression is not an integral constant expression}}
// expected-note@-2 {{read of uninitialized object is not allowed in a constant expression}}
// expected-error@-3 {{variable length array declaration not allowed at file scope}}
int d[true ? 4 : *new int];
// cxx98-error@-1 {{variable length arrays in C++ are a Clang extension}}
// cxx98-error@-2 {{variable length array folded to constant array as an extension}}
static_assert(__enable_constant_folding(true ? 4 : *new int), "");

}

namespace cwg368 { // cwg368: 3.6
Expand Down Expand Up @@ -1325,7 +1329,7 @@ namespace cwg383 { // cwg383: yes
struct B { ~B(); };
union C { C &operator=(const C&); };
union D { ~D(); };
int check[(__is_pod(A) || __is_pod(B) || __is_pod(C) || __is_pod(D)) ? -1 : 1];
static_assert(!__is_pod(A) && !__is_pod(B) && !__is_pod(C) && !__is_pod(D), "");
}

namespace cwg384 { // cwg384: yes
Expand Down
Loading