Fixed #2474 (false positive: Member variable 'A::m_SemVar' is not initialised in the constructor.)
This commit is contained in:
parent
c994508c3e
commit
8631ee65a3
|
@ -133,6 +133,10 @@ void CheckClass::constructors()
|
|||
continue;
|
||||
}
|
||||
|
||||
// Check if type can't be copied
|
||||
if (var->type && canNotCopy(var->type))
|
||||
continue;
|
||||
|
||||
// It's non-static and it's not initialized => error
|
||||
if (func->type == Function::eOperatorEqual)
|
||||
{
|
||||
|
@ -162,6 +166,23 @@ void CheckClass::constructors()
|
|||
}
|
||||
}
|
||||
|
||||
bool CheckClass::canNotCopy(const Scope *scope) const
|
||||
{
|
||||
std::list<Function>::const_iterator func;
|
||||
bool privateAssign = false;
|
||||
bool privateCopy = false;
|
||||
|
||||
for (func = scope->functionList.begin(); func != scope->functionList.end(); ++func)
|
||||
{
|
||||
if (func->type == Function::eCopyConstructor && func->access == Private)
|
||||
privateCopy = true;
|
||||
else if (func->type == Function::eOperatorEqual && func->access == Private)
|
||||
privateAssign = true;
|
||||
}
|
||||
|
||||
return privateAssign && privateCopy;
|
||||
}
|
||||
|
||||
void CheckClass::assignVar(const std::string &varname, const Scope *scope, std::vector<Usage> &usage)
|
||||
{
|
||||
std::list<Variable>::const_iterator var;
|
||||
|
|
|
@ -227,6 +227,8 @@ private:
|
|||
* @param usage reference to usage vector
|
||||
*/
|
||||
void initializeVarList(const Function &func, std::list<std::string> &callstack, const Scope *scope, std::vector<Usage> &usage);
|
||||
|
||||
bool canNotCopy(const Scope *scope) const;
|
||||
};
|
||||
/// @}
|
||||
//---------------------------------------------------------------------------
|
||||
|
|
|
@ -76,6 +76,7 @@ private:
|
|||
TEST_CASE(initvar_private_constructor); // BUG 2354171 - private constructor
|
||||
TEST_CASE(initvar_copy_constructor); // ticket #1611
|
||||
TEST_CASE(initvar_nested_constructor); // ticket #1375
|
||||
TEST_CASE(initvar_nocopy); // ticket #2474
|
||||
|
||||
TEST_CASE(initvar_destructor); // No variables need to be initialized in a destructor
|
||||
|
||||
|
@ -905,6 +906,52 @@ private:
|
|||
"[test.cpp:24]: (warning) Member variable 'D::d' is not initialised in the constructor.\n", errout.str());
|
||||
}
|
||||
|
||||
void initvar_nocopy() // ticket #2474
|
||||
{
|
||||
check("class B\n"
|
||||
"{\n"
|
||||
" B (const B & Var);\n"
|
||||
" B & operator= (const B & Var);\n"
|
||||
"};\n"
|
||||
"class A\n"
|
||||
"{\n"
|
||||
" B m_SemVar;\n"
|
||||
"public:\n"
|
||||
" A(){}\n"
|
||||
" A(const A&){}\n"
|
||||
" const A& operator=(const A&){return *this;}\n"
|
||||
"};\n");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("class B\n"
|
||||
"{\n"
|
||||
"public:\n"
|
||||
" B (const B & Var);\n"
|
||||
" B & operator= (const B & Var);\n"
|
||||
"};\n"
|
||||
"class A\n"
|
||||
"{\n"
|
||||
" B m_SemVar;\n"
|
||||
"public:\n"
|
||||
" A(){}\n"
|
||||
" A(const A&){}\n"
|
||||
" const A& operator=(const A&){return *this;}\n"
|
||||
"};\n");
|
||||
ASSERT_EQUALS("[test.cpp:12]: (warning) Member variable 'A::m_SemVar' is not initialised in the constructor.\n"
|
||||
"[test.cpp:13]: (warning) Member variable 'A::m_SemVar' is not assigned a value in 'A::operator='\n", errout.str());
|
||||
|
||||
check("class A\n"
|
||||
"{\n"
|
||||
" B m_SemVar;\n"
|
||||
"public:\n"
|
||||
" A(){}\n"
|
||||
" A(const A&){}\n"
|
||||
" const A& operator=(const A&){return *this;}\n"
|
||||
"};\n");
|
||||
ASSERT_EQUALS("[test.cpp:6]: (warning) Member variable 'A::m_SemVar' is not initialised in the constructor.\n"
|
||||
"[test.cpp:7]: (warning) Member variable 'A::m_SemVar' is not assigned a value in 'A::operator='\n", errout.str());
|
||||
}
|
||||
|
||||
void initvar_destructor()
|
||||
{
|
||||
check("class Fred\n"
|
||||
|
|
Loading…
Reference in New Issue