438 lines · cpp
1// Force x86-64 because some of our heuristics are actually based2// on integer sizes.3 4// RUN: %clang_cc1 -triple x86_64-apple-darwin -fsyntax-only -pedantic -verify -Wsign-compare -Wtautological-constant-in-range-compare -std=c++11 %s5// RUN: %clang_cc1 -triple x86_64-apple-darwin -fsyntax-only -pedantic -verify -Wsign-compare -Wtype-limits -std=c++11 %s6 7int test0(long a, unsigned long b) {8 enum EnumA {A};9 enum EnumB {B};10 enum EnumC {C = 0x10000};11 return12 // (a,b)13 (a == (unsigned long) b) + // expected-warning {{comparison of integers of different signs}}14 (a == (unsigned int) b) +15 (a == (unsigned short) b) +16 (a == (unsigned char) b) +17 ((long) a == b) + // expected-warning {{comparison of integers of different signs}}18 ((int) a == b) + // expected-warning {{comparison of integers of different signs}}19 ((short) a == b) + // expected-warning {{comparison of integers of different signs}}20 ((signed char) a == b) + // expected-warning {{comparison of integers of different signs}}21 ((long) a == (unsigned long) b) + // expected-warning {{comparison of integers of different signs}}22 ((int) a == (unsigned int) b) + // expected-warning {{comparison of integers of different signs}}23 ((short) a == (unsigned short) b) +24 ((signed char) a == (unsigned char) b) +25 (a < (unsigned long) b) + // expected-warning {{comparison of integers of different signs}}26 (a < (unsigned int) b) +27 (a < (unsigned short) b) +28 (a < (unsigned char) b) +29 ((long) a < b) + // expected-warning {{comparison of integers of different signs}}30 ((int) a < b) + // expected-warning {{comparison of integers of different signs}}31 ((short) a < b) + // expected-warning {{comparison of integers of different signs}}32 ((signed char) a < b) + // expected-warning {{comparison of integers of different signs}}33 ((long) a < (unsigned long) b) + // expected-warning {{comparison of integers of different signs}}34 ((int) a < (unsigned int) b) + // expected-warning {{comparison of integers of different signs}}35 ((short) a < (unsigned short) b) +36 ((signed char) a < (unsigned char) b) +37 38 // (A,b)39 (A == (unsigned long) b) +40 (A == (unsigned int) b) +41 (A == (unsigned short) b) +42 (A == (unsigned char) b) +43 ((long) A == b) +44 ((int) A == b) +45 ((short) A == b) +46 ((signed char) A == b) +47 ((long) A == (unsigned long) b) +48 ((int) A == (unsigned int) b) +49 ((short) A == (unsigned short) b) +50 ((signed char) A == (unsigned char) b) +51 (A < (unsigned long) b) +52 (A < (unsigned int) b) +53 (A < (unsigned short) b) +54 (A < (unsigned char) b) +55 ((long) A < b) +56 ((int) A < b) +57 ((short) A < b) +58 ((signed char) A < b) +59 ((long) A < (unsigned long) b) +60 ((int) A < (unsigned int) b) +61 ((short) A < (unsigned short) b) +62 ((signed char) A < (unsigned char) b) +63 64 // (a,B)65 (a == (unsigned long) B) +66 (a == (unsigned int) B) +67 (a == (unsigned short) B) +68 (a == (unsigned char) B) +69 ((long) a == B) +70 ((int) a == B) +71 ((short) a == B) +72 ((signed char) a == B) +73 ((long) a == (unsigned long) B) +74 ((int) a == (unsigned int) B) +75 ((short) a == (unsigned short) B) +76 ((signed char) a == (unsigned char) B) +77 (a < (unsigned long) B) + // expected-warning {{comparison of unsigned expression < 0 is always false}}78 (a < (unsigned int) B) +79 (a < (unsigned short) B) +80 (a < (unsigned char) B) +81 ((long) a < B) +82 ((int) a < B) +83 ((short) a < B) +84 ((signed char) a < B) +85 ((long) a < (unsigned long) B) + // expected-warning {{comparison of unsigned expression < 0 is always false}}86 ((int) a < (unsigned int) B) + // expected-warning {{comparison of unsigned expression < 0 is always false}}87 ((short) a < (unsigned short) B) +88 ((signed char) a < (unsigned char) B) +89 90 // (C,b)91 (C == (unsigned long) b) +92 (C == (unsigned int) b) +93 (C == (unsigned short) b) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'unsigned short' is always false}}94 (C == (unsigned char) b) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'unsigned char' is always false}}95 ((long) C == b) +96 ((int) C == b) +97 ((short) C == b) +98 ((signed char) C == b) +99 ((long) C == (unsigned long) b) +100 ((int) C == (unsigned int) b) +101 ((short) C == (unsigned short) b) +102 ((signed char) C == (unsigned char) b) +103 (C < (unsigned long) b) +104 (C < (unsigned int) b) +105 (C < (unsigned short) b) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'unsigned short' is always false}}106 (C < (unsigned char) b) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'unsigned char' is always false}}107 ((long) C < b) +108 ((int) C < b) +109 ((short) C < b) +110 ((signed char) C < b) +111 ((long) C < (unsigned long) b) +112 ((int) C < (unsigned int) b) +113 ((short) C < (unsigned short) b) +114 ((signed char) C < (unsigned char) b) +115 116 // (a,C)117 (a == (unsigned long) C) +118 (a == (unsigned int) C) +119 (a == (unsigned short) C) +120 (a == (unsigned char) C) +121 ((long) a == C) +122 ((int) a == C) +123 ((short) a == C) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'short' is always false}}124 ((signed char) a == C) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'signed char' is always false}}125 ((long) a == (unsigned long) C) +126 ((int) a == (unsigned int) C) +127 ((short) a == (unsigned short) C) +128 ((signed char) a == (unsigned char) C) +129 (a < (unsigned long) C) + // expected-warning {{comparison of integers of different signs}}130 (a < (unsigned int) C) +131 (a < (unsigned short) C) +132 (a < (unsigned char) C) +133 ((long) a < C) +134 ((int) a < C) +135 ((short) a < C) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'short' is always true}}136 ((signed char) a < C) + // expected-warning {{comparison of constant 'C' (65536) with expression of type 'signed char' is always true}}137 ((long) a < (unsigned long) C) + // expected-warning {{comparison of integers of different signs}}138 ((int) a < (unsigned int) C) + // expected-warning {{comparison of integers of different signs}}139 ((short) a < (unsigned short) C) +140 ((signed char) a < (unsigned char) C) +141 142 // (0x80000,b)143 (0x80000 == (unsigned long) b) +144 (0x80000 == (unsigned int) b) +145 (0x80000 == (unsigned short) b) + // expected-warning {{comparison of constant 524288 with expression of type 'unsigned short' is always false}}146 (0x80000 == (unsigned char) b) + // expected-warning {{comparison of constant 524288 with expression of type 'unsigned char' is always false}}147 ((long) 0x80000 == b) +148 ((int) 0x80000 == b) +149 ((short) 0x80000 == b) +150 ((signed char) 0x80000 == b) +151 ((long) 0x80000 == (unsigned long) b) +152 ((int) 0x80000 == (unsigned int) b) +153 ((short) 0x80000 == (unsigned short) b) +154 ((signed char) 0x80000 == (unsigned char) b) +155 (0x80000 < (unsigned long) b) +156 (0x80000 < (unsigned int) b) +157 (0x80000 < (unsigned short) b) + // expected-warning {{comparison of constant 524288 with expression of type 'unsigned short' is always false}}158 (0x80000 < (unsigned char) b) + // expected-warning {{comparison of constant 524288 with expression of type 'unsigned char' is always false}}159 ((long) 0x80000 < b) +160 ((int) 0x80000 < b) +161 ((short) 0x80000 < b) +162 ((signed char) 0x80000 < b) +163 ((long) 0x80000 < (unsigned long) b) +164 ((int) 0x80000 < (unsigned int) b) +165 ((short) 0x80000 < (unsigned short) b) +166 ((signed char) 0x80000 < (unsigned char) b) +167 168 // (a,0x80000)169 (a == (unsigned long) 0x80000) +170 (a == (unsigned int) 0x80000) +171 (a == (unsigned short) 0x80000) +172 (a == (unsigned char) 0x80000) +173 ((long) a == 0x80000) +174 ((int) a == 0x80000) +175 ((short) a == 0x80000) + // expected-warning {{comparison of constant 524288 with expression of type 'short' is always false}}176 ((signed char) a == 0x80000) + // expected-warning {{comparison of constant 524288 with expression of type 'signed char' is always false}}177 ((long) a == (unsigned long) 0x80000) +178 ((int) a == (unsigned int) 0x80000) +179 ((short) a == (unsigned short) 0x80000) +180 ((signed char) a == (unsigned char) 0x80000) +181 (a < (unsigned long) 0x80000) + // expected-warning {{comparison of integers of different signs}}182 (a < (unsigned int) 0x80000) +183 (a < (unsigned short) 0x80000) +184 (a < (unsigned char) 0x80000) +185 ((long) a < 0x80000) +186 ((int) a < 0x80000) +187 ((short) a < 0x80000) + // expected-warning {{comparison of constant 524288 with expression of type 'short' is always true}}188 ((signed char) a < 0x80000) + // expected-warning {{comparison of constant 524288 with expression of type 'signed char' is always true}}189 ((long) a < (unsigned long) 0x80000) + // expected-warning {{comparison of integers of different signs}}190 ((int) a < (unsigned int) 0x80000) + // expected-warning {{comparison of integers of different signs}}191 ((short) a < (unsigned short) 0x80000) +192 ((signed char) a < (unsigned char) 0x80000) +193 194 10195 ;196}197 198int test1(int i) {199 enum en { zero };200 return i > zero;201}202 203enum E { e };204void test2(int i, void *vp) {205 if (&i == vp) { } // ok206 if (test1 == vp) { } // expected-warning{{equality comparison between function pointer and void pointer}}207 if (test1 == e) { } // expected-error{{comparison between pointer and integer}}208 if (vp < 0) { } // expected-error {{comparison between pointer and zero}}209 if (test1 < e) { } // expected-error{{comparison between pointer and integer}}210}211 212// PR7536213static const unsigned int kMax = 0;214int pr7536() {215 return (kMax > 0);216}217 218// -Wsign-compare should not warn when ?: operands have different signedness.219// This will be caught by -Wsign-conversion220void test3() {221 unsigned long a;222 signed long b;223 (void) (true ? a : b);224 (void) (true ? (unsigned int)a : (signed int)b);225 (void) (true ? b : a);226 (void) (true ? (unsigned char)b : (signed char)a);227}228 229// Test comparison of short to unsigned. If tautological compare does not230// trigger, then the signed comparison warning will.231void test4(short s) {232 // A is max short plus 1. All zero and positive shorts are smaller than it.233 // All negative shorts are cast towards the max unsigned range. Relation234 // comparisons are possible, but equality comparisons are tautological.235 const unsigned A = 32768;236 void (s < A); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}237 void (s > A); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}238 void (s <= A); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}239 void (s >= A); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}240 241 void (s == A); // expected-warning{{comparison of constant 32768 with expression of type 'short' is always false}}242 void (s != A); // expected-warning{{comparison of constant 32768 with expression of type 'short' is always true}}243 244 // When negative one is converted to an unsigned value, it becomes the max245 // unsigned. Likewise, a negative one short can also be converted to max246 // unsigned.247 const unsigned B = -1;248 void (s < B); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}249 void (s > B); // expected-warning{{comparison 'short' > 4294967295 is always false}}250 void (s <= B); // expected-warning{{comparison 'short' <= 4294967295 is always true}}251 void (s >= B); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}252 void (s == B); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}253 void (s != B); // expected-warning{{comparison of integers of different signs: 'short' and 'const unsigned int'}}254 255}256 257void test5(bool b) {258 (void) (b < -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always false}}259 (void) (b > -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always true}}260 (void) (b == -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always false}}261 (void) (b != -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always true}}262 (void) (b <= -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always false}}263 (void) (b >= -1); // expected-warning{{comparison of constant -1 with expression of type 'bool' is always true}}264 265 (void) (b < -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always false}}266 (void) (b > -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always true}}267 (void) (b == -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always false}}268 (void) (b != -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always true}}269 (void) (b <= -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always false}}270 (void) (b >= -10); // expected-warning{{comparison of constant -10 with expression of type 'bool' is always true}}271 272 (void) (b < 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always true}}273 (void) (b > 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always false}}274 (void) (b == 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always false}}275 (void) (b != 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always true}}276 (void) (b <= 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always true}}277 (void) (b >= 2); // expected-warning{{comparison of constant 2 with expression of type 'bool' is always false}}278 279 (void) (b < 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always true}}280 (void) (b > 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always false}}281 (void) (b == 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always false}}282 (void) (b != 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always true}}283 (void) (b <= 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always true}}284 (void) (b >= 10); // expected-warning{{comparison of constant 10 with expression of type 'bool' is always false}}285}286 287void test6(signed char sc) {288 (void)(sc < 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}289 (void)(sc > 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}290 (void)(sc <= 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}291 (void)(sc >= 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}292 (void)(sc == 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}293 (void)(sc != 200); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}294 295 (void)(200 < sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}296 (void)(200 > sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}297 (void)(200 <= sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}298 (void)(200 >= sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}299 (void)(200 == sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always false}}300 (void)(200 != sc); // expected-warning{{comparison of constant 200 with expression of type 'signed char' is always true}}301}302 303// Test many signedness combinations.304void test7(unsigned long other) {305 // Common unsigned, other unsigned, constant unsigned306 (void)((unsigned)other != (unsigned long)(0x1ffffffff)); // expected-warning{{true}}307 (void)((unsigned)other != (unsigned long)(0xffffffff));308 (void)((unsigned long)other != (unsigned)(0x1ffffffff));309 (void)((unsigned long)other != (unsigned)(0xffffffff));310 311 // Common unsigned, other signed, constant unsigned312 (void)((int)other != (unsigned long)(0xffffffffffffffff)); // expected-warning{{different signs}}313 (void)((int)other != (unsigned long)(0x00000000ffffffff)); // expected-warning{{true}}314 (void)((int)other != (unsigned long)(0x000000000fffffff));315 (void)((int)other < (unsigned long)(0x00000000ffffffff)); // expected-warning{{different signs}}316 (void)((int)other == (unsigned)(0x800000000));317 318 // Common unsigned, other unsigned, constant signed319 (void)((unsigned long)other != (int)(0xffffffff)); // expected-warning{{different signs}}320 321 // Common unsigned, other signed, constant signed322 // Should not be possible as the common type should also be signed.323 324 // Common signed, other signed, constant signed325 (void)((int)other != (long)(0xffffffff)); // expected-warning{{true}}326 (void)((int)other != (long)(0xffffffff00000000)); // expected-warning{{true}}327 (void)((int)other != (long)(0xfffffff));328 (void)((int)other != (long)(0xfffffffff0000000));329 330 // Common signed, other signed, constant unsigned331 (void)((int)other != (unsigned char)(0xffff));332 (void)((int)other != (unsigned char)(0xff));333 334 // Common signed, other unsigned, constant signed335 (void)((unsigned char)other != (int)(0xff));336 (void)((unsigned char)other != (int)(0xffff)); // expected-warning{{true}}337 338 // Common signed, other unsigned, constant unsigned339 (void)((unsigned char)other != (unsigned short)(0xff));340 (void)((unsigned char)other != (unsigned short)(0x100)); // expected-warning{{true}}341 (void)((unsigned short)other != (unsigned char)(0xff));342}343 344void test8(int x) {345 enum E {346 Negative = -1,347 Positive = 1348 };349 350 (void)((E)x == 1);351 (void)((E)x == -1);352}353 354void test9(int x) {355 enum E : int {356 Positive = 1357 };358 (void)((E)x == 1);359}360 361namespace templates {362 template<class T> T max();363 364 template<> constexpr int max<int>() { return 2147483647; };365 366 template<typename T>367 bool less_than_max(short num, T value) {368 const T vmax = max<T>();369 return (vmax >= num); // no warning370 }371 372 template<typename T>373 bool less_than_max(short num) {374 // This should trigger one warning on the template pattern, and not a375 // warning per specialization.376 return num < max<int>(); // expected-warning{{comparison of constant 2147483647 with expression of type 'short' is always true}}377 }378 379 void test10(short num, int x) {380 less_than_max(num, x);381 less_than_max<int>(num);382 less_than_max<long>(num);383 less_than_max<short>(num);384 }385 386 template<typename T>387 inline bool less_than_zero(T num, T value) {388 return num < 0; // no warning389 }390 391 template<typename T>392 inline bool less_than_zero(unsigned num) {393 // This should trigger one warning on the template pattern, and not a394 // warning per specialization.395 return num < 0; // expected-warning{{comparison of unsigned expression < 0 is always false}}396 }397 398 void test11(unsigned num) {399 less_than_zero(num, num);400 less_than_zero<int>(num);401 less_than_zero<long>(num);402 less_than_zero<short>(num);403 }404 405 template<unsigned n> bool compare(unsigned k) { return k >= n; }406 407 void test12() {408 compare<0>(42);409 }410 411 struct A { static int x; };412 struct B { static int x; };413 typedef A otherA;414 415 template <typename T>416 void testx() {417 if (A::x == T::x && // no warning418 A::x == otherA::x) // expected-warning{{self-comparison always evaluates to true}}419 return;420 }421 422 void test13() {423 testx<A>();424 testx<B>();425 }426}427 428namespace tautological_enum {429 enum E { a, b, c } e;430 431 // We should not warn about relational comparisons for enumerators, even if432 // they're tautological.433 bool y = e >= a && e <= b;434 const E first_in_range = a;435 const E last_in_range = b;436 bool z = e >= first_in_range && e <= last_in_range;437}438