memory leak : fixed 2 bugs related to the testcases TestMemleak::if7 and TestMemleak::simple9

This commit is contained in:
Daniel Marjamäki 2008-12-17 19:21:39 +00:00
parent dd853f0d59
commit ee5e20ed1f
2 changed files with 78 additions and 26 deletions

View File

@ -357,7 +357,6 @@ TOKEN *CheckMemoryLeakClass::getcode(const TOKEN *tok, std::list<const TOKEN *>
// The first token should be ";" // The first token should be ";"
addtoken(";"); addtoken(";");
bool isloop = false; bool isloop = false;
int indentlevel = 0; int indentlevel = 0;
@ -440,16 +439,20 @@ TOKEN *CheckMemoryLeakClass::getcode(const TOKEN *tok, std::list<const TOKEN *>
addtoken( (rhs ? "use" : "assign") ); addtoken( (rhs ? "use" : "assign") );
} }
} }
AllocType dealloc = GetDeallocationType(tok, varnames); if ( TOKEN::Match(tok->previous(), "[;{})] %var%") )
if ( dealloc != No )
{ {
addtoken("dealloc"); AllocType dealloc = GetDeallocationType(tok, varnames);
if (alloctype!=No && alloctype!=dealloc) if ( dealloc != No )
MismatchError(tok, callstack, varname); {
if (dealloctype!=No && dealloctype!=dealloc) addtoken("dealloc");
MismatchError(tok, callstack, varname); if (alloctype!=No && alloctype!=dealloc)
dealloctype = dealloc; MismatchError(tok, callstack, varname);
if (dealloctype!=No && dealloctype!=dealloc)
MismatchError(tok, callstack, varname);
dealloctype = dealloc;
continue;
}
} }
// if else switch // if else switch
@ -665,7 +668,7 @@ void CheckMemoryLeakClass::simplifycode(TOKEN *tok)
done = false; done = false;
} }
// TODO Make this more generic. Delete "if ; else use ; use" // TODO Make this more generic. Delete "if ; else use ; use"
if ( TOKEN::Match(tok2, "; if ; else assign|use ; assign|use") || if ( TOKEN::Match(tok2, "; if ; else assign|use ; assign|use") ||
TOKEN::Match(tok2, "; if assign|use ; else ; assign|use") ) TOKEN::Match(tok2, "; if assign|use ; else ; assign|use") )
@ -675,9 +678,9 @@ void CheckMemoryLeakClass::simplifycode(TOKEN *tok)
} }
// Reduce "if dealloc ;" and "if use ;" that is not followed by an else.. // Reduce "if assign|dealloc|use ;" that is not followed by an else..
// If "--all" has been given these are deleted // If "--all" has been given these are deleted
// Otherwise, ony the "if" will be deleted // Otherwise, only the "if" will be deleted
if (TOKEN::Match(tok2, "[;{}] if assign|dealloc|use ; !!else") ) if (TOKEN::Match(tok2, "[;{}] if assign|dealloc|use ; !!else") )
{ {
if ( _settings._showAll ) if ( _settings._showAll )
@ -745,17 +748,20 @@ void CheckMemoryLeakClass::simplifycode(TOKEN *tok)
done = false; done = false;
} }
// Reducing if.. // Reducing if..
if (TOKEN::Match(tok2,"if assign|dealloc|use ; else")) if ( _settings._showAll )
{ {
erase(tok2, tok2->tokAt(2)); if (TOKEN::Match(tok2,"if assign|dealloc|use ; else"))
done = false; {
} erase(tok2, tok2->tokAt(2));
if (TOKEN::Match(tok2,"[;{}] if { assign|dealloc|use ; return ; } !!else") ) done = false;
{ }
erase(tok2,tok2->tokAt(8)); if (TOKEN::Match(tok2,"[;{}] if { assign|dealloc|use ; return ; } !!else") )
done = false; {
} erase(tok2,tok2->tokAt(8));
done = false;
}
}
// Reduce "if ; else %var% ;" => "if %var% ;" // Reduce "if ; else %var% ;" => "if %var% ;"
if ( TOKEN::Match(tok2, "if ; else %var% ;") ) if ( TOKEN::Match(tok2, "if ; else %var% ;") )
@ -1016,7 +1022,10 @@ void CheckMemoryLeakClass::CheckMemoryLeak_CheckScope( const TOKEN *Tok1, const
AllocType dealloctype = No; AllocType dealloctype = No;
TOKEN *tok = getcode( Tok1, callstack, varname, alloctype, dealloctype ); TOKEN *tok = getcode( Tok1, callstack, varname, alloctype, dealloctype );
//tok->printOut( "getcode result" );
simplifycode( tok ); simplifycode( tok );
//tok->printOut( "simplifycode result" );
// If the variable is not allocated at all => no memory leak // If the variable is not allocated at all => no memory leak
if (TOKEN::findmatch(tok, "alloc") == 0) if (TOKEN::findmatch(tok, "alloc") == 0)
@ -1040,7 +1049,6 @@ void CheckMemoryLeakClass::CheckMemoryLeak_CheckScope( const TOKEN *Tok1, const
else if ( (result = TOKEN::findmatch(tok, "alloc ; if break|continue|return ;")) != NULL ) else if ( (result = TOKEN::findmatch(tok, "alloc ; if break|continue|return ;")) != NULL )
{ {
// MemoryLeak(Tokenizer::gettok(TOKEN::findmatch(tok, "alloc ; if continue ;"), 3), varname);
MemoryLeak(result->tokAt(3), varname, alloctype); MemoryLeak(result->tokAt(3), varname, alloctype);
} }

View File

@ -66,7 +66,8 @@ private:
TEST_CASE( simple5 ); TEST_CASE( simple5 );
TEST_CASE( simple6 ); TEST_CASE( simple6 );
TEST_CASE( simple7 ); TEST_CASE( simple7 );
TEST_CASE( simple8 ); TEST_CASE( simple8 );
TEST_CASE( simple9 ); // Bug 2435468 - member function "free"
TEST_CASE( use1 ); TEST_CASE( use1 );
TEST_CASE( use2 ); TEST_CASE( use2 );
@ -86,7 +87,8 @@ private:
TEST_CASE( if3 ); TEST_CASE( if3 );
TEST_CASE( if4 ); TEST_CASE( if4 );
TEST_CASE( if5 ); TEST_CASE( if5 );
TEST_CASE( if6 ); // Bug 2432631 TEST_CASE( if6 ); // Bug 2432631
TEST_CASE( if7 ); // Bug 2401436
TEST_CASE( alwaysTrue ); TEST_CASE( alwaysTrue );
@ -236,6 +238,20 @@ private:
ASSERT_EQUALS( std::string(""), errout.str() ); ASSERT_EQUALS( std::string(""), errout.str() );
} }
void simple9()
{
check( "void foo()\n"
"{\n"
" MyClass *c = new MyClass();\n"
" c->free(c);\n"
" delete c;\n"
"}\n" );
ASSERT_EQUALS( std::string(""), errout.str() );
}
@ -312,6 +328,17 @@ private:
" return;\n" " return;\n"
" }\n" " }\n"
"}\n" ); "}\n" );
ASSERT_EQUALS( std::string(""), errout.str() );
check( "void f()\n"
"{\n"
" char *str = strdup(\"hello\");\n"
" if (a==b)\n"
" {\n"
" free(str);\n"
" return;\n"
" }\n"
"}\n", true );
ASSERT_EQUALS( std::string("[test.cpp:9]: Memory leak: str\n"), errout.str() ); ASSERT_EQUALS( std::string("[test.cpp:9]: Memory leak: str\n"), errout.str() );
} }
@ -491,6 +518,23 @@ private:
ASSERT_EQUALS( std::string(""), errout.str() ); ASSERT_EQUALS( std::string(""), errout.str() );
} }
void if7()
{
check( "void f( bool b )\n"
"{\n"
" int *a=0;\n"
" if( b )\n"
" {\n"
" a = new int[10];\n"
" }\n"
"\n"
" if( b )\n"
" delete [] a;\n"
" else {}\n"
"}\n" );
ASSERT_EQUALS( std::string(""), errout.str() );
}