Fixed #1545 (new check: usage of iterator pointing to invalid memory after reserve)
This commit is contained in:
parent
a42273da63
commit
dc12a9b3b5
|
@ -347,7 +347,7 @@ void CheckStl::pushback()
|
|||
}
|
||||
}
|
||||
|
||||
// Iterator becomes invalid after push_back or push_front..
|
||||
// Iterator becomes invalid after reserve, push_back or push_front..
|
||||
for (const Token *tok = _tokenizer->tokens(); tok; tok = tok->next())
|
||||
{
|
||||
if (!Token::simpleMatch(tok, "vector <"))
|
||||
|
@ -422,7 +422,7 @@ void CheckStl::pushback()
|
|||
pushbackTok = 0;
|
||||
break;
|
||||
}
|
||||
else if (Token::Match(tok3, "%varid% . push_front|push_back|insert (", varId))
|
||||
else if (Token::Match(tok3, "%varid% . push_front|push_back|insert|reserve (", varId))
|
||||
{
|
||||
pushbackTok = tok3->tokAt(2);
|
||||
}
|
||||
|
@ -448,7 +448,7 @@ void CheckStl::pushback()
|
|||
}
|
||||
|
||||
// push_back on vector..
|
||||
if (vectorid > 0 && Token::Match(tok2, "%varid% . push_front|push_back|insert (", vectorid))
|
||||
if (vectorid > 0 && Token::Match(tok2, "%varid% . push_front|push_back|insert|reserve (", vectorid))
|
||||
{
|
||||
if (!invalidIterator.empty() && Token::Match(tok2->tokAt(2), "insert ( %varid% ,", iteratorid))
|
||||
{
|
||||
|
|
|
@ -68,6 +68,7 @@ private:
|
|||
TEST_CASE(pushback7);
|
||||
TEST_CASE(pushback8);
|
||||
TEST_CASE(pushback9);
|
||||
TEST_CASE(pushback10);
|
||||
|
||||
TEST_CASE(insert1);
|
||||
|
||||
|
@ -661,6 +662,29 @@ private:
|
|||
ASSERT_EQUALS("", errout.str());
|
||||
}
|
||||
|
||||
void pushback10()
|
||||
{
|
||||
check("void f(std::vector<int> &foo)\n"
|
||||
"{\n"
|
||||
" std::vector<int>::const_iterator it = foo.begin();\n"
|
||||
" foo.reserve(100);\n"
|
||||
" *it = 0;\n"
|
||||
"}\n");
|
||||
ASSERT_EQUALS("[test.cpp:5]: (error) After reserve, the iterator 'it' may be invalid\n", errout.str());
|
||||
|
||||
// in loop
|
||||
check("void f()\n"
|
||||
"{\n"
|
||||
" std::vector<int> foo;\n"
|
||||
" foo.push_back(10);\n"
|
||||
" std::vector<int>::iterator it;\n"
|
||||
" for (it = foo.begin(); it != foo.end(); ++it)\n"
|
||||
" {\n"
|
||||
" foo.reserve(123);\n"
|
||||
" }\n"
|
||||
"}\n");
|
||||
ASSERT_EQUALS("[test.cpp:8]: (error) After reserve, the iterator 'it' may be invalid\n", errout.str());
|
||||
}
|
||||
|
||||
|
||||
void insert1()
|
||||
|
|
Loading…
Reference in New Issue