Fixed a couple of #6276 integer over/underflow issues

This commit is contained in:
PKEuS 2014-12-09 23:04:14 +01:00
parent 493ab541ab
commit 4d81945ac5
6 changed files with 31 additions and 18 deletions

View File

@ -288,12 +288,16 @@ bool CmdLineParser::ParseFromArgs(int argc, const char* const argv[])
_settings->_relativePaths = true;
if (argv[i][argv[i][3]=='='?4:17] != 0) {
std::string paths = argv[i]+(argv[i][3]=='='?4:17);
std::string::size_type pos;
do {
pos = paths.find(';');
_settings->_basePaths.push_back(Path::fromNativeSeparators(paths.substr(0, pos)));
paths.erase(0, pos+1);
} while (pos != std::string::npos);
for (;;) {
std::string::size_type pos = paths.find(';');
if (pos == std::string::npos) {
_settings->_basePaths.push_back(Path::fromNativeSeparators(paths));
break;
} else {
_settings->_basePaths.push_back(Path::fromNativeSeparators(paths.substr(0, pos)));
paths.erase(0, pos + 1);
}
}
} else {
PrintMessage("cppcheck: No paths specified for the '" + std::string(argv[i]) + "' option.");
return false;

View File

@ -217,9 +217,9 @@ void CheckString::checkIncorrectStringCompare()
const Scope * scope = symbolDatabase->functionScopes[i];
for (const Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) {
// skip "assert(str && ..)" and "assert(.. && str)"
if (Token::Match(tok, "%var% (") &&
(Token::Match(tok->tokAt(2), "%str% &&") || Token::Match(tok->next()->link()->tokAt(-2), "&& %str% )")) &&
(tok->str().find("assert") + 6U == tok->str().size() || tok->str().find("ASSERT") + 6U == tok->str().size()))
if (tok->str().size() >= 6U && (tok->str().find("assert") == tok->str().size() - 6U || tok->str().find("ASSERT") == tok->str().size() - 6U) &&
Token::Match(tok, "%var% (") &&
(Token::Match(tok->tokAt(2), "%str% &&") || Token::Match(tok->next()->link()->tokAt(-2), "&& %str% )")))
tok = tok->next()->link();
if (Token::simpleMatch(tok, ". substr (") && Token::Match(tok->tokAt(3)->nextArgument(), "%num% )")) {

View File

@ -283,7 +283,7 @@ void ErrorLogger::ErrorMessage::findAndReplace(std::string &source, const std::s
std::string::size_type index = 0;
while ((index = source.find(searchFor, index)) != std::string::npos) {
source.replace(index, searchFor.length(), replaceWith);
index += replaceWith.length() - searchFor.length() + 1;
index = (std::string::difference_type)index + (std::string::difference_type)replaceWith.length() - (std::string::difference_type)searchFor.length() + 1;
}
}

View File

@ -2051,7 +2051,10 @@ static bool openHeader(std::string &filename, const std::list<std::string> &incl
std::string Preprocessor::handleIncludes(const std::string &code, const std::string &filePath, const std::list<std::string> &includePaths, std::map<std::string,std::string> &defs, std::set<std::string> &pragmaOnce, std::list<std::string> includes)
{
const std::string path(filePath.substr(0, 1 + filePath.find_last_of("\\/")));
std::string path;
std::string::size_type sep_pos = filePath.find_last_of("\\/");
if (sep_pos != std::string::npos)
path = filePath.substr(0, 1 + sep_pos);
// current #if indent level.
std::stack<bool>::size_type indent = 0;
@ -2264,7 +2267,9 @@ void Preprocessor::handleIncludes(std::string &code, const std::string &filePath
std::list<std::string> paths;
std::string path;
path = filePath;
path.erase(1 + path.find_last_of("\\/"));
std::string::size_type sep_pos = path.find_last_of("\\/");
if (sep_pos != std::string::npos)
path.erase(1 + sep_pos);
paths.push_back(path);
std::string::size_type pos = 0;
std::string::size_type endfilePos = 0;

View File

@ -153,10 +153,11 @@ std::string Token::strValue() const
void Token::deleteNext(unsigned long index)
{
while (_next && index--) {
while (_next && index) {
Token *n = _next;
_next = n->next();
delete n;
--index;
}
if (_next)

View File

@ -1097,8 +1097,10 @@ void Tokenizer::simplifyTypedef()
if (good) {
// remove any extra qualification if present
while (count--)
while (count) {
tok2->tokAt(-3)->deleteNext(2);
--count;
}
// remove global namespace if present
if (tok2->strAt(-1) == "::") {
@ -1589,10 +1591,11 @@ void Tokenizer::simplifyMulAndParens()
Token::Match(tokbegin->tokAt(-2), "[;{}&(] * &") ||
Token::Match(tokbegin->tokAt(-3), "[;{}&(] * ( &")) {
//remove the excessive parentheses around the variable
while (openpars--) {
while (openpars) {
tok->deleteNext();
tokbegin->deleteNext();
--closedpars;
--openpars;
}
} else
break;
@ -4998,7 +5001,7 @@ void Tokenizer::simplifyCasts()
if (Token::Match(tok->next(), "( %type% ) %num%") && tok->next()->link()->previous()->isStandardType()) {
const MathLib::bigint value = MathLib::toLongNumber(tok->next()->link()->next()->str());
unsigned int bits = 8 * _typeSize[tok->next()->link()->previous()->str()];
if (!tok->tokAt(2)->isUnsigned())
if (!tok->tokAt(2)->isUnsigned() && bits > 0)
bits--;
if (bits < 31 && value >= 0 && value < (1LL << bits)) {
Token::eraseTokens(tok, tok->next()->link()->next());
@ -6525,8 +6528,8 @@ bool Tokenizer::simplifyKnownVariables()
const Token * const valueToken = tok2->tokAt(4);
std::string value(valueToken->str());
if (tok2->str() == "sprintf") {
std::string::size_type n = std::string::npos;
while ((n = value.find("%%",n+1)) != std::string::npos) {
std::string::difference_type n = -1;
while (static_cast<std::string::size_type>(n = value.find("%%",n+1)) != std::string::npos) {
value.replace(n,2,"%");
}
}