Refactoring CheckUnusedFunctions so it uses new infrastructure for multifile analysis

This commit is contained in:
Daniel Marjamäki 2014-12-02 06:41:18 +01:00
parent cf3f8c2f38
commit 0b9d80c95d
10 changed files with 37 additions and 42 deletions

View File

@ -790,8 +790,6 @@ int CppCheckExecutor::check_internal(CppCheck& cppcheck, int /*argc*/, const cha
c++; c++;
} }
} }
cppcheck.checkFunctionUsage();
cppcheck.analyseWholeProgram(); cppcheck.analyseWholeProgram();
} else if (!ThreadExecutor::isEnabled()) { } else if (!ThreadExecutor::isEnabled()) {
std::cout << "No thread support yet implemented for this platform." << std::endl; std::cout << "No thread support yet implemented for this platform." << std::endl;

View File

@ -91,8 +91,9 @@ public:
virtual ~FileInfo() {} virtual ~FileInfo() {}
}; };
virtual FileInfo * getFileInfo(const Tokenizer *tokenizer) const { virtual FileInfo * getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const {
(void)tokenizer; (void)tokenizer;
(void)settings;
return nullptr; return nullptr;
} }

View File

@ -1805,8 +1805,10 @@ void CheckBufferOverrun::writeOutsideBufferSizeError(const Token *tok, const std
" Please check the second and the third parameter of the function '"+strFunctionName+"'."); " Please check the second and the third parameter of the function '"+strFunctionName+"'.");
} }
Check::FileInfo* CheckBufferOverrun::getFileInfo(const Tokenizer *tokenizer) const Check::FileInfo* CheckBufferOverrun::getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const
{ {
(void)settings;
MyFileInfo *fileInfo = new MyFileInfo; MyFileInfo *fileInfo = new MyFileInfo;
// Array usage.. // Array usage..

View File

@ -220,10 +220,10 @@ public:
}; };
/** @brief Parse current TU and extract file info */ /** @brief Parse current TU and extract file info */
Check::FileInfo *getFileInfo(const Tokenizer *tokenizer) const; Check::FileInfo *getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const;
/** @brief Analyse all file infos for all TU */ /** @brief Analyse all file infos for all TU */
virtual void analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger); void analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger);
private: private:

View File

@ -1013,8 +1013,9 @@ public:
/// @} /// @}
Check::FileInfo *CheckUninitVar::getFileInfo(const Tokenizer *tokenizer) const Check::FileInfo *CheckUninitVar::getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const
{ {
(void)settings;
MyFileInfo * mfi = new MyFileInfo; MyFileInfo * mfi = new MyFileInfo;
analyseFunctions(tokenizer, mfi->uvarFunctions); analyseFunctions(tokenizer, mfi->uvarFunctions);
// TODO: add suspicious function calls // TODO: add suspicious function calls

View File

@ -80,10 +80,10 @@ public:
}; };
/** @brief Parse current TU and extract file info */ /** @brief Parse current TU and extract file info */
Check::FileInfo *getFileInfo(const Tokenizer *tokenizer) const; Check::FileInfo *getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const;
/** @brief Analyse all file infos for all TU */ /** @brief Analyse all file infos for all TU */
virtual void analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger); void analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger);
void analyseFunctions(const Tokenizer *tokenizer, std::set<std::string> &f) const; void analyseFunctions(const Tokenizer *tokenizer, std::set<std::string> &f) const;

View File

@ -263,3 +263,17 @@ void CheckUnusedFunctions::unusedFunctionError(ErrorLogger * const errorLogger,
else else
reportError(errmsg); reportError(errmsg);
} }
Check::FileInfo *CheckUnusedFunctions::getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const
{
if (settings->isEnabled("unusedFunction") && settings->_jobs == 1)
instance.parseTokens(*tokenizer, tokenizer->list.getFiles().front().c_str(), settings);
return nullptr;
}
void CheckUnusedFunctions::analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger)
{
(void)fileInfo;
instance.check(&errorLogger);
}

View File

@ -47,6 +47,12 @@ public:
void check(ErrorLogger * const errorLogger); void check(ErrorLogger * const errorLogger);
/** @brief Parse current TU and extract file info */
Check::FileInfo *getFileInfo(const Tokenizer *tokenizer, const Settings *settings) const;
/** @brief Analyse all file infos for all TU */
void analyseWholeProgram(const std::list<Check::FileInfo*> &fileInfo, ErrorLogger &errorLogger);
static CheckUnusedFunctions instance; static CheckUnusedFunctions instance;
private: private:

View File

@ -19,7 +19,6 @@
#include "preprocessor.h" // Preprocessor #include "preprocessor.h" // Preprocessor
#include "tokenize.h" // Tokenizer #include "tokenize.h" // Tokenizer
#include "checkunusedfunctions.h"
#include "check.h" #include "check.h"
#include "path.h" #include "path.h"
@ -278,23 +277,6 @@ void CppCheck::internalError(const std::string &filename, const std::string &msg
} }
} }
void CppCheck::checkFunctionUsage()
{
// This generates false positives - especially for libraries
if (_settings.isEnabled("unusedFunction") && _settings._jobs == 1) {
const bool verbose_orig = _settings._verbose;
_settings._verbose = false;
if (_settings._errorsOnly == false)
_errorLogger.reportOut("Checking usage of global functions..");
CheckUnusedFunctions::instance.check(this);
_settings._verbose = verbose_orig;
}
}
void CppCheck::analyseFile(std::istream &fin, const std::string &filename) void CppCheck::analyseFile(std::istream &fin, const std::string &filename)
{ {
// Preprocess file.. // Preprocess file..
@ -379,8 +361,12 @@ bool CppCheck::checkFile(const std::string &code, const char FileName[], std::se
(*it)->runChecks(&_tokenizer, &_settings, this); (*it)->runChecks(&_tokenizer, &_settings, this);
} }
if (_settings.isEnabled("unusedFunction") && _settings._jobs == 1) // Analyse the tokens..
CheckUnusedFunctions::instance.parseTokens(_tokenizer, FileName, &_settings); for (std::list<Check *>::const_iterator it = Check::instances().begin(); it != Check::instances().end(); ++it) {
Check::FileInfo *fi = (*it)->getFileInfo(&_tokenizer, &_settings);
if (fi != nullptr)
fileInfo.push_back(fi);
}
executeRules("normal", _tokenizer); executeRules("normal", _tokenizer);
@ -402,13 +388,6 @@ bool CppCheck::checkFile(const std::string &code, const char FileName[], std::se
(*it)->runSimplifiedChecks(&_tokenizer, &_settings, this); (*it)->runSimplifiedChecks(&_tokenizer, &_settings, this);
} }
// Analyse the tokens..
for (std::list<Check *>::const_iterator it = Check::instances().begin(); it != Check::instances().end(); ++it) {
Check::FileInfo *fi = (*it)->getFileInfo(&_tokenizer);
if (fi != nullptr)
fileInfo.push_back(fi);
}
if (_settings.terminated()) if (_settings.terminated())
return true; return true;

View File

@ -82,12 +82,6 @@ public:
*/ */
unsigned int check(const std::string &path, const std::string &content); unsigned int check(const std::string &path, const std::string &content);
/**
* @brief Check function usage.
* @note Call this after all files has been checked
*/
void checkFunctionUsage();
/** /**
* @brief Get reference to current settings. * @brief Get reference to current settings.
* @return a reference to current settings * @return a reference to current settings