Fixed #3747 (False 'boolean result in bitwise' message with 'mask' enums)
This commit is contained in:
parent
c976325086
commit
0bb0fdedc2
|
@ -251,6 +251,15 @@ std::string MathLib::calculate(const std::string &first, const std::string &seco
|
||||||
case '%':
|
case '%':
|
||||||
return MathLib::mod(first, second);
|
return MathLib::mod(first, second);
|
||||||
|
|
||||||
|
case '&':
|
||||||
|
return MathLib::toString(MathLib::toLongNumber(first) & MathLib::toLongNumber(second));
|
||||||
|
|
||||||
|
case '|':
|
||||||
|
return MathLib::toString(MathLib::toLongNumber(first) | MathLib::toLongNumber(second));
|
||||||
|
|
||||||
|
case '^':
|
||||||
|
return MathLib::toString(MathLib::toLongNumber(first) ^ MathLib::toLongNumber(second));
|
||||||
|
|
||||||
default:
|
default:
|
||||||
throw InternalError(0, std::string("Unexpected action '") + action + "' in MathLib::calculate(). Please report this to Cppcheck developers.");
|
throw InternalError(0, std::string("Unexpected action '") + action + "' in MathLib::calculate(). Please report this to Cppcheck developers.");
|
||||||
}
|
}
|
||||||
|
|
|
@ -897,12 +897,8 @@ bool TemplateSimplifier::simplifyCalculations(Token *_tokens)
|
||||||
const MathLib::bigint rightInt(MathLib::toLongNumber(tok->strAt(2)));
|
const MathLib::bigint rightInt(MathLib::toLongNumber(tok->strAt(2)));
|
||||||
std::string result;
|
std::string result;
|
||||||
|
|
||||||
if (cop == '&')
|
if (cop == '&' || cop == '|' || cop == '^')
|
||||||
result = MathLib::toString<MathLib::bigint>(leftInt & rightInt);
|
result = MathLib::calculate(tok->str(), tok->strAt(2), cop);
|
||||||
else if (cop == '|')
|
|
||||||
result = MathLib::toString<MathLib::bigint>(leftInt | rightInt);
|
|
||||||
else if (cop == '^')
|
|
||||||
result = MathLib::toString<MathLib::bigint>(leftInt ^ rightInt);
|
|
||||||
else if (cop == '<') {
|
else if (cop == '<') {
|
||||||
if (tok->previous()->str() != "<<") // Ensure that its not a shift operator as used for streams
|
if (tok->previous()->str() != "<<") // Ensure that its not a shift operator as used for streams
|
||||||
result = MathLib::toString<MathLib::bigint>(leftInt << rightInt);
|
result = MathLib::toString<MathLib::bigint>(leftInt << rightInt);
|
||||||
|
|
|
@ -7008,6 +7008,32 @@ void Tokenizer::simplifyEnum()
|
||||||
}
|
}
|
||||||
|
|
||||||
if (simplify) {
|
if (simplify) {
|
||||||
|
// Simplify calculations..
|
||||||
|
while (Token::Match(enumValueStart, "%num% %op% %num% %op%") &&
|
||||||
|
enumValueStart->strAt(1) == enumValueStart->strAt(3)) {
|
||||||
|
const std::string &op = enumValueStart->strAt(1);
|
||||||
|
if (op.size() != 1U)
|
||||||
|
break;
|
||||||
|
const std::string &val1 = enumValueStart->str();
|
||||||
|
const std::string &val2 = enumValueStart->strAt(2);
|
||||||
|
const std::string result = MathLib::calculate(val1, val2, op[0]);
|
||||||
|
enumValueStart->str(result);
|
||||||
|
enumValueStart->deleteNext(2);
|
||||||
|
}
|
||||||
|
if (Token::Match(enumValueStart, "%num% %op% %num% [,}]")) {
|
||||||
|
const std::string &op = enumValueStart->strAt(1);
|
||||||
|
if (op.size() == 1U) {
|
||||||
|
const std::string &val1 = enumValueStart->str();
|
||||||
|
const std::string &val2 = enumValueStart->strAt(2);
|
||||||
|
const std::string result = MathLib::calculate(val1, val2, op[0]);
|
||||||
|
enumValueStart->str(result);
|
||||||
|
enumValueStart->deleteNext(2);
|
||||||
|
enumValue = enumValueStart;
|
||||||
|
enumValueStart = enumValueEnd = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
if (enumValue)
|
if (enumValue)
|
||||||
tok2->str(enumValue->str());
|
tok2->str(enumValue->str());
|
||||||
else {
|
else {
|
||||||
|
|
|
@ -344,6 +344,7 @@ private:
|
||||||
TEST_CASE(enum26); // ticket #2975 (segmentation fault)
|
TEST_CASE(enum26); // ticket #2975 (segmentation fault)
|
||||||
TEST_CASE(enum27); // ticket #3005 (segmentation fault)
|
TEST_CASE(enum27); // ticket #3005 (segmentation fault)
|
||||||
TEST_CASE(enum28);
|
TEST_CASE(enum28);
|
||||||
|
TEST_CASE(enum29); // ticket #3747 (bitwise or value)
|
||||||
|
|
||||||
// remove "std::" on some standard functions
|
// remove "std::" on some standard functions
|
||||||
TEST_CASE(removestd);
|
TEST_CASE(removestd);
|
||||||
|
@ -6985,6 +6986,11 @@ private:
|
||||||
ASSERT_EQUALS("void f ( ) { char x [ 4 ] ; memset ( x , 0 , 4 ) ; { x } } ; void g ( ) { 0 ; }", checkSimplifyEnum(code));
|
ASSERT_EQUALS("void f ( ) { char x [ 4 ] ; memset ( x , 0 , 4 ) ; { x } } ; void g ( ) { 0 ; }", checkSimplifyEnum(code));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void enum29() { // #3747 - bitwise or value
|
||||||
|
const char code[] = "enum { x=1, y=x|2 }; i = (3==y);";
|
||||||
|
ASSERT_EQUALS("i = 3 == 3 ;", checkSimplifyEnum(code));
|
||||||
|
}
|
||||||
|
|
||||||
void removestd() {
|
void removestd() {
|
||||||
ASSERT_EQUALS("; strcpy ( a , b ) ;", tok("; std::strcpy(a,b);"));
|
ASSERT_EQUALS("; strcpy ( a , b ) ;", tok("; std::strcpy(a,b);"));
|
||||||
ASSERT_EQUALS("; strcat ( a , b ) ;", tok("; std::strcat(a,b);"));
|
ASSERT_EQUALS("; strcat ( a , b ) ;", tok("; std::strcat(a,b);"));
|
||||||
|
|
Loading…
Reference in New Issue