351 lines · cpp
1// RUN: %clang_cc1 -fexperimental-new-constant-interpreter -fms-extensions -std=c++11 -verify=expected,both %s2// RUN: %clang_cc1 -fexperimental-new-constant-interpreter -fms-extensions -std=c++20 -verify=expected,both %s3// RUN: %clang_cc1 -std=c++11 -fms-extensions -verify=ref,both %s4// RUN: %clang_cc1 -std=c++20 -fms-extensions -verify=ref,both %s5 6 7using MaxBitInt = _BitInt(128);8#define INT_MIN (~__INT_MAX__)9 10constexpr _BitInt(2) A = 0;11constexpr _BitInt(2) B = A + 1;12constexpr _BitInt(2) C = B + 1; // both-warning {{from 2 to -2}}13static_assert(C == -2, "");14static_assert(C - B == A, ""); // both-error {{not an integral constant expression}} \15 // both-note {{value -3 is outside the range of representable values}}16 17static_assert(B - 1 == 0, "");18 19constexpr MaxBitInt A_ = 0;20constexpr MaxBitInt B_ = A_ + 1;21static_assert(B_ == 1, "");22 23constexpr MaxBitInt BitIntZero{};24static_assert(BitIntZero == 0, "");25constexpr unsigned _BitInt(128) UBitIntZero{};26static_assert(UBitIntZero == 0, "");27 28constexpr _BitInt(2) BitIntZero2{};29static_assert(BitIntZero2 == 0, "");30constexpr unsigned _BitInt(1) UBitIntZero1{};31static_assert(UBitIntZero1 == 0, "");32 33constexpr unsigned _BitInt(2) BI1 = 3u;34static_assert(BI1 == 3, "");35 36constexpr _BitInt(4) MulA = 5;37constexpr _BitInt(4) MulB = 7;38static_assert(MulA * MulB == 50, ""); // both-error {{not an integral constant expression}} \39 // both-note {{value 35 is outside the range of representable values of type '_BitInt(4)'}}40static_assert(MulA * 5 == 25, "");41static_assert(-1 * MulB == -7, "");42 43 44constexpr _BitInt(4) DivA = 2;45constexpr _BitInt(2) DivB = 1;46static_assert(DivA / DivB == 2, "");47 48constexpr _BitInt(4) DivC = DivA / 0; // both-error {{must be initialized by a constant expression}} \49 // both-note {{division by zero}}50 51#ifdef __SIZEOF_INT128__52constexpr __int128 isMinDiv() {53 return __int128{0} / __int128{-1};54}55static_assert(isMinDiv() == 0, "");56#endif57 58 59constexpr _BitInt(7) RemA = 47;60constexpr _BitInt(6) RemB = 9;61static_assert(RemA % RemB == 2, "");62static_assert(RemA % 0 == 1, ""); // both-error {{not an integral constant expression}} \63 // both-note {{division by zero}}64 65constexpr _BitInt(32) bottom = -1;66constexpr _BitInt(32) top = INT_MIN;67constexpr _BitInt(32) nope = top / bottom; // both-error {{must be initialized by a constant expression}} \68 // both-note {{value 2147483648 is outside the range}}69constexpr _BitInt(32) noooo = top % bottom; // both-error {{must be initialized by a constant expression}} \70 // both-note {{value 2147483648 is outside the range}}71 72namespace APCast {73 constexpr _BitInt(10) A = 1;74 constexpr _BitInt(11) B = A;75 static_assert(B == 1, "");76 constexpr _BitInt(16) B2 = A;77 static_assert(B2 == 1, "");78 constexpr _BitInt(32) B3 = A;79 static_assert(B3 == 1, "");80 constexpr unsigned _BitInt(32) B4 = A;81 static_assert(B4 == 1, "");82}83 84#ifdef __SIZEOF_INT128__85typedef __int128 int128_t;86typedef unsigned __int128 uint128_t;87static const __uint128_t UINT128_MAX =__uint128_t(__int128_t(-1L));88static_assert(UINT128_MAX == -1, "");89static_assert(UINT128_MAX == 1, ""); // both-error {{static assertion failed}} \90 // both-note {{'340282366920938463463374607431768211455 == 1'}}91 92static const __int128_t INT128_MAX = UINT128_MAX >> (__int128_t)1;93static_assert(INT128_MAX != 0, "");94static_assert(INT128_MAX == 0, ""); // both-error {{failed}} \95 // both-note {{evaluates to '170141183460469231731687303715884105727 == 0'}}96static const __int128_t INT128_MIN = -INT128_MAX - 1;97 98 99namespace PointerArithmeticOverflow {100 int n;101 constexpr int *p = (&n + 1) + (unsigned __int128)-1; // both-error {{constant expression}} \102 // both-note {{cannot refer to element 3402}}103}104 105namespace i128 {106 107 constexpr int128_t I128_1 = 12;108 static_assert(I128_1 == 12, "");109 static_assert(I128_1 != 10, "");110 static_assert(I128_1 != 12, ""); // both-error{{failed}} \111 // both-note{{evaluates to}}112 113 static const __uint128_t UINT128_MAX =__uint128_t(__int128_t(-1L));114 static_assert(UINT128_MAX == -1, "");115 static_assert(UINT128_MAX == 1, ""); // both-error {{static assertion failed}} \116 // both-note {{'340282366920938463463374607431768211455 == 1'}}117 118 constexpr uint128_t TooMuch = UINT128_MAX * 2;119 120 static const __int128_t INT128_MAX = UINT128_MAX >> (__int128_t)1;121 static_assert(INT128_MAX != 0, "");122 static_assert(INT128_MAX == 0, ""); // both-error {{failed}} \123 // both-note {{evaluates to '170141183460469231731687303715884105727 == 0'}}124 125 constexpr int128_t TooMuch2 = INT128_MAX * INT128_MAX; // both-error {{must be initialized by a constant expression}} \126 // both-note {{value 28948022309329048855892746252171976962977213799489202546401021394546514198529 is outside the range of representable}}127 128 static const __int128_t INT128_MIN = -INT128_MAX - 1;129 constexpr __int128 A = INT128_MAX + 1; // both-error {{must be initialized by a constant expression}} \130 // both-note {{value 170141183460469231731687303715884105728 is outside the range}}131 constexpr int128_t Two = (int128_t)1 << 1ul;132 static_assert(Two == 2, "");133 static_assert(Two, "");134 constexpr bool CastedToBool = Two;135 static_assert(CastedToBool, "");136 137 constexpr uint128_t AllOnes = ~static_cast<uint128_t>(0);138 static_assert(AllOnes == UINT128_MAX, "");139 140 constexpr uint128_t i128Zero{};141 static_assert(i128Zero == 0, "");142 constexpr uint128_t ui128Zero{};143 static_assert(ui128Zero == 0, "");144 145 146 enum LargeEnum : signed __int128 {147 LV = (signed __int128)1 << 127,148 };149 150 constexpr LargeEnum F = LV;151 static_assert(F == (signed __int128)1 << 127, "");152 constexpr LargeEnum getLargeEnum() {153 return LV;154 }155 static_assert(getLargeEnum() == (signed __int128)1 << 127, "");156 157 158 159#if __cplusplus >= 201402L160 template <typename T>161 constexpr T CastFrom(__int128_t A) {162 T B = (T)A;163 return B;164 }165 static_assert(CastFrom<char>(12) == 12, "");166 static_assert(CastFrom<unsigned char>(12) == 12, "");167 static_assert(CastFrom<long>(12) == 12, "");168 static_assert(CastFrom<unsigned short>(12) == 12, "");169 static_assert(CastFrom<int128_t>(12) == 12, "");170 static_assert(CastFrom<float>(12) == 12, "");171 static_assert(CastFrom<double>(12) == 12, "");172 static_assert(CastFrom<long double>(12) == 12, "");173 174 static_assert(CastFrom<char>(AllOnes) == -1, "");175 static_assert(CastFrom<unsigned char>(AllOnes) == 0xFF, "");176 static_assert(CastFrom<long>(AllOnes) == -1, "");177 static_assert(CastFrom<unsigned short>(AllOnes) == 0xFFFF, "");178 static_assert(CastFrom<int>(AllOnes) == -1, "");179 static_assert(CastFrom<int128_t>(AllOnes) == -1, "");180 static_assert(CastFrom<uint128_t>(AllOnes) == AllOnes, "");181 182 template <typename T>183 constexpr __int128 CastTo(T A) {184 int128_t B = (int128_t)A;185 return B;186 }187 static_assert(CastTo<char>(12) == 12, "");188 static_assert(CastTo<unsigned char>(12) == 12, "");189 static_assert(CastTo<long>(12) == 12, "");190 static_assert(CastTo<unsigned long long>(12) == 12, "");191 static_assert(CastTo<float>(12) == 12, "");192 static_assert(CastTo<double>(12) == 12, "");193 static_assert(CastTo<long double>(12) == 12, "");194#endif195 196 constexpr int128_t Error = __LDBL_MAX__; // both-warning {{implicit conversion of out of range value}} \197 // both-error {{must be initialized by a constant expression}} \198 // both-note {{is outside the range of representable values of type}}199 200 constexpr uint128_t Zero = 0;201 static_assert((Zero -1) == -1, "");202 constexpr int128_t Five = 5;203 static_assert(Five - Zero == Five, "");204 205 constexpr int128_t Sub1 = INT128_MIN - 1; // both-error {{must be initialized by a constant expression}} \206 // both-note {{-170141183460469231731687303715884105729 is outside the range}}207}208 209namespace AddSubOffset {210 constexpr __int128 A = 1;211 constexpr int arr[] = {1,2,3};212 constexpr const int *P = arr + A;213 static_assert(*P == 2, "");214 constexpr const int *P2 = P - A;215 static_assert(*P2 == 1,"");216}217 218namespace Bitfields {219 struct S1 {220 unsigned _BitInt(128) a : 2;221 };222 constexpr S1 s1{100}; // both-warning {{changes value from 100 to 0}}223 constexpr S1 s12{3};224 static_assert(s12.a == 3, "");225 226 struct S2 {227 unsigned __int128 a : 2;228 };229 constexpr S2 s2{100}; // both-warning {{changes value from 100 to 0}}230}231 232namespace BitOps {233 constexpr unsigned __int128 UZero = 0;234 constexpr unsigned __int128 Max = ~UZero;235 static_assert(Max == ~0, "");236 static_assert((Max & 0) == 0, "");237 static_assert((UZero | 0) == 0, "");238 static_assert((Max ^ Max) == 0, "");239 static_assert((Max & 1) == 1, "");240 static_assert((UZero | 1) == 1, "");241 static_assert((Max ^ UZero) == Max, "");242}243 244namespace IncDec {245#if __cplusplus >= 201402L246 constexpr int128_t maxPlus1(bool Pre) {247 int128_t a = INT128_MAX;248 249 if (Pre)250 ++a; // both-note {{value 170141183460469231731687303715884105728 is outside the range}}251 else252 a++; // both-note {{value 170141183460469231731687303715884105728 is outside the range}}253 return a;254 }255 static_assert(maxPlus1(true) == 0, ""); // both-error {{not an integral constant expression}} \256 // both-note {{in call to}}257 static_assert(maxPlus1(false) == 0, ""); // both-error {{not an integral constant expression}} \258 // both-note {{in call to}}259 260 constexpr int128_t inc1(bool Pre) {261 int128_t A = 0;262 if (Pre)263 ++A;264 else265 A++;266 return A;267 }268 static_assert(inc1(true) == 1, "");269 static_assert(inc1(false) == 1, "");270 271 constexpr int128_t dec1(bool Pre) {272 int128_t A = 2;273 if (Pre)274 --A;275 else276 A--;277 return A;278 }279 static_assert(dec1(true) == 1, "");280 static_assert(dec1(false) == 1, "");281#endif282}283 284#if __cplusplus >= 201402L285const __int128_t a = ( (__int128_t)1 << 64 );286const _BitInt(72) b = ( 1 << 72 ); // both-warning {{shift count >= width of type}}287constexpr int shifts() { // both-error {{never produces a constant expression}}288 (void)(2 >> a); // both-warning {{shift count >= width of type}} \289 // both-note {{shift count 18446744073709551616 >= width of type 'int' (32 bits)}}290 (void)(2 >> b); // ref-warning {{shift count is negative}}291 (void)(2 << a); // both-warning {{shift count >= width of type}}292 (void)(2 << b); // ref-warning {{shift count is negative}}293 return 1;294}295 296namespace UnderlyingInt128 {297 enum F {298 a = (__int128)-1299 };300 301 constexpr int foo() { // both-error {{never produces a constant expression}}302 F f = (F)(__int128)10; // both-note 2{{integer value 10 is outside the valid range of values [-1, 0] for the enumeration type 'F'}}303 return (int)f;304 }305 static_assert(foo() == 0, ""); // both-error {{not an integral constant expression}} \306 // both-note {{in call to}}307}308 309namespace CompoundAssignOperators {310 constexpr unsigned __int128 foo() {311 long b = 10;312 313 b += (__int128)1;314 b -= (__int128)1;315 b *= (__int128)1;316 b /= (__int128)1;317 318 b += (unsigned __int128)1;319 b -= (unsigned __int128)1;320 b *= (unsigned __int128)1;321 b /= (unsigned __int128)1;322 323 __int128 i = 10;324 i += (__int128)1;325 i -= (__int128)1;326 i *= (__int128)1;327 i /= (__int128)1;328 i += (unsigned __int128)1;329 i -= (unsigned __int128)1;330 i *= (unsigned __int128)1;331 i /= (unsigned __int128)1;332 333 unsigned __int128 i2 = 10;334 i2 += (__int128)1;335 i2 -= (__int128)1;336 i2 *= (__int128)1;337 i2 /= (__int128)1;338 i2 += (unsigned __int128)1;339 i2 -= (unsigned __int128)1;340 i2 *= (unsigned __int128)1;341 i2 /= (unsigned __int128)1;342 343 return (int)b;344 }345 static_assert(foo() == 10);346}347 348#endif349 350#endif351