ASSERT_EQUALS("[test.cpp:1:19]: (error) Signed integer overflow for expression '(long)0x10000*(long)0x10000'. [integerOverflow]\n", errout_str());
check("void foo() {\n"
" int intmax = 0x7fffffff;\n"
" return intmax + 1;\n"
"}",dinit(CheckOptions, $.settings = &settings));
ASSERT_EQUALS("[test.cpp:3:19]: (error) Signed integer overflow for expression 'intmax+1'. [integerOverflow]\n", errout_str());
check("void foo() {\n"
" int intmax = 0x7fffffff;\n"
" return intmax - 1;\n"
"}",dinit(CheckOptions, $.settings = &settings));
ASSERT_EQUALS("", errout_str());
check("int foo(signed int x) {\n"
" if (x==123456) {}\n"
" return x * x;\n"
"}",dinit(CheckOptions, $.settings = &settings));
ASSERT_EQUALS("[test.cpp:2:9] -> [test.cpp:3:13]: (warning) Either the condition 'x==123456' is redundant or there is signed integer overflow for expression 'x*x'. [integerOverflowCond]\n", errout_str());
check("int foo(signed int x) {\n"
" if (x==123456) {}\n"
" return -123456 * x;\n"
"}",dinit(CheckOptions, $.settings = &settings));
ASSERT_EQUALS("[test.cpp:2:9] -> [test.cpp:3:19]: (warning) Either the condition 'x==123456' is redundant or there is signed integer underflow for expression '-123456*x'. [integerOverflowCond]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:15] -> [test.cpp:2:26]: (warning) Shifting signed 32-bit value by 31 bits is undefined behaviour. See condition at line 2. [shiftTooManyBitsSigned]\n", errout_str());
ASSERT_EQUALS("[test.cpp:1:6]: (warning) Expression '-4' has a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversion]\n", errout_str());
check("x = (unsigned)y * -4;");
ASSERT_EQUALS("[test.cpp:1:20]: (warning) Expression '-4' has a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversion]\n", errout_str());
check("unsigned int dostuff(int x) {\n"// x is signed
ASSERT_EQUALS("[test.cpp:2:8] -> [test.cpp:3:12]: (warning) Expression 'x-1' can have a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversionCond]\n", errout_str());
check("unsigned int f1(signed int x, unsigned int y) {"// x is signed
" return x * y;\n"
"}\n"
"void f2() { f1(-4,4); }");
ASSERT_EQUALS(
"[test.cpp:1:57]: (warning) Expression 'x' can have a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversion]\n",
errout_str());
check("unsigned int f1(int x) {"
" return x * 5U;\n"
"}\n"
"void f2() { f1(-4); }");
ASSERT_EQUALS(
"[test.cpp:1:34]: (warning) Expression 'x' can have a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversion]\n",
errout_str());
check("unsigned int f1(int x) {"// #6168: FP for inner calculation
" return 5U * (1234 - x);\n"// <- signed subtraction, x is not sign converted
"}\n"
"void f2() { f1(-4); }");
ASSERT_EQUALS("", errout_str());
// Don't warn for + and -
check("void f1(int x) {"
" a = x + 5U;\n"
"}\n"
"void f2() { f1(-4); }");
ASSERT_EQUALS("", errout_str());
check("size_t foo(size_t x) {\n"
" return -2 * x;\n"
"}");
ASSERT_EQUALS("[test.cpp:2:10]: (warning) Expression '-2' has a negative value. That is converted to an unsigned value and used in an unsigned calculation. [signConversion]\n", errout_str());
checkP("void f() {\n"// #12110 FP signConversion with integer overflow
ASSERT_EQUALS("[test.cpp:2:18]: (style) int result is assigned to long variable. If the variable is long to avoid loss of information, then you have loss of information. [truncLongCastAssignment]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:12]: (style) int result is assigned to long variable. If the variable is long to avoid loss of information, then you have loss of information. [truncLongCastAssignment]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:5]: (style) float result is returned as double value. If the return value is double to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n",
ASSERT_EQUALS("[test.cpp:2:3]: (style) int result is returned as long value. If the return value is long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:3]: (style) int result is returned as long long value. If the return value is long long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:3]: (style) int result is returned as long long value. If the return value is long long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:5]: (style) int result is returned as long value. If the return value is long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
ASSERT_EQUALS("[test.cpp:3:5]: (style) int result is returned as long value. If the return value is long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
ASSERT_EQUALS("[test.cpp:2:3]: (style) int result is returned as long value. If the return value is long to avoid loss of information, then you have loss of information. [truncLongCastReturn]\n", errout_str());
}
// This function ensure that test works with different compilers. Floats can