some `missingInclude`/`missingIncludeSystem` fixes and tests (#4027)
* do not emit `missingInclude` and `missingIncludeSystem` errors when not enabled / fixed and improved TestPreprocessor::inline_suppression_for_missing_include() * testpreprocessor.cpp: added missing tests for `missingInclude` and `missingIncludeSystem` * cppcheckexecutor.cpp: `missingIncludeSystem` was not emitted in normal analysis if `missingInclude` existed * dmake * added `run-dmake` as `testrunner` dependency
This commit is contained in:
parent
4587178cfa
commit
c36320747f
2
Makefile
2
Makefile
|
@ -695,7 +695,7 @@ test/testplatform.o: test/testplatform.cpp externals/tinyxml2/tinyxml2.h lib/col
|
|||
test/testpostfixoperator.o: test/testpostfixoperator.cpp lib/check.h lib/checkpostfixoperator.h lib/color.h lib/config.h lib/errorlogger.h lib/errortypes.h lib/importproject.h lib/library.h lib/mathlib.h lib/platform.h lib/settings.h lib/standards.h lib/suppressions.h lib/templatesimplifier.h lib/timer.h lib/token.h lib/tokenize.h lib/tokenlist.h lib/utils.h lib/valueflow.h test/testsuite.h
|
||||
$(CXX) ${INCLUDE_FOR_TEST} $(CPPFLAGS) $(CPPFILESDIR) $(CXXFLAGS) $(UNDEF_STRICT_ANSI) -c -o test/testpostfixoperator.o test/testpostfixoperator.cpp
|
||||
|
||||
test/testpreprocessor.o: test/testpreprocessor.cpp externals/simplecpp/simplecpp.h lib/color.h lib/config.h lib/errorlogger.h lib/errortypes.h lib/importproject.h lib/library.h lib/mathlib.h lib/platform.h lib/preprocessor.h lib/settings.h lib/standards.h lib/suppressions.h lib/timer.h lib/utils.h test/testsuite.h
|
||||
test/testpreprocessor.o: test/testpreprocessor.cpp externals/simplecpp/simplecpp.h lib/color.h lib/config.h lib/errorlogger.h lib/errortypes.h lib/importproject.h lib/library.h lib/mathlib.h lib/platform.h lib/preprocessor.h lib/settings.h lib/standards.h lib/suppressions.h lib/templatesimplifier.h lib/timer.h lib/token.h lib/tokenize.h lib/tokenlist.h lib/utils.h lib/valueflow.h test/testsuite.h test/testutils.h
|
||||
$(CXX) ${INCLUDE_FOR_TEST} $(CPPFLAGS) $(CPPFILESDIR) $(CXXFLAGS) $(UNDEF_STRICT_ANSI) -c -o test/testpreprocessor.o test/testpreprocessor.cpp
|
||||
|
||||
test/testprocessexecutor.o: test/testprocessexecutor.cpp cli/executor.h cli/processexecutor.h lib/color.h lib/config.h lib/errorlogger.h lib/errortypes.h lib/importproject.h lib/library.h lib/mathlib.h lib/platform.h lib/settings.h lib/standards.h lib/suppressions.h lib/templatesimplifier.h lib/timer.h lib/token.h lib/tokenize.h lib/tokenlist.h lib/utils.h lib/valueflow.h test/testsuite.h test/testutils.h
|
||||
|
|
|
@ -1018,10 +1018,17 @@ int CppCheckExecutor::check_internal(CppCheck& cppcheck)
|
|||
"files are found. Please check your project's include directories and add all of them "
|
||||
"as include directories for Cppcheck. To see what files Cppcheck cannot find use "
|
||||
"--check-config.",
|
||||
Preprocessor::missingIncludeFlag ? "missingInclude" : "missingIncludeSystem",
|
||||
"",
|
||||
Certainty::normal);
|
||||
if (Preprocessor::missingIncludeFlag) {
|
||||
msg.id = "missingInclude";
|
||||
reportInfo(msg);
|
||||
}
|
||||
if (Preprocessor::missingSystemIncludeFlag) {
|
||||
msg.id = "missingIncludeSystem";
|
||||
reportInfo(msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (settings.xml) {
|
||||
|
|
|
@ -840,6 +840,9 @@ void Preprocessor::error(const std::string &filename, unsigned int linenr, const
|
|||
// Report that include is missing
|
||||
void Preprocessor::missingInclude(const std::string &filename, unsigned int linenr, const std::string &header, HeaderTypes headerType)
|
||||
{
|
||||
if (!mSettings.checks.isEnabled(Checks::missingInclude) && !mSettings.checkConfiguration)
|
||||
return;
|
||||
|
||||
const std::string fname = Path::fromNativeSeparators(filename);
|
||||
Suppressions::ErrorMessage errorMessage;
|
||||
errorMessage.errorId = "missingInclude";
|
||||
|
@ -855,6 +858,7 @@ void Preprocessor::missingInclude(const std::string &filename, unsigned int line
|
|||
missingSystemIncludeFlag = true;
|
||||
else
|
||||
missingIncludeFlag = true;
|
||||
|
||||
if (mErrorLogger && mSettings.checkConfiguration) {
|
||||
|
||||
std::list<ErrorMessage::FileLocation> locationList;
|
||||
|
|
|
@ -33,6 +33,7 @@ if (BUILD_TESTS)
|
|||
|
||||
add_dependencies(testrunner copy_cfg)
|
||||
add_dependencies(testrunner copy_addons)
|
||||
add_dependencies(testrunner run-dmake)
|
||||
|
||||
if (LIBXML2_XMLLINT_EXECUTABLE)
|
||||
# TODO: run the CMake implementation of the tests
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "preprocessor.h"
|
||||
#include "settings.h"
|
||||
#include "testsuite.h"
|
||||
#include "testutils.h"
|
||||
|
||||
#include <atomic>
|
||||
#include <cstring>
|
||||
|
@ -200,8 +201,9 @@ private:
|
|||
TEST_CASE(invalid_define_1); // #2605 - hang for: '#define ='
|
||||
TEST_CASE(invalid_define_2); // #4036 - hang for: '#define () {(int f(x) }'
|
||||
|
||||
// inline suppression, missingInclude
|
||||
// inline suppression, missingInclude/missingIncludeSystem
|
||||
TEST_CASE(inline_suppression_for_missing_include);
|
||||
TEST_CASE(inline_suppression_for_missing_include_check_config);
|
||||
|
||||
// Using -D to predefine symbols
|
||||
TEST_CASE(predefine1);
|
||||
|
@ -254,6 +256,9 @@ private:
|
|||
TEST_CASE(testDirectiveIncludeTypes);
|
||||
TEST_CASE(testDirectiveIncludeLocations);
|
||||
TEST_CASE(testDirectiveIncludeComments);
|
||||
|
||||
TEST_CASE(testMissingInclude);
|
||||
TEST_CASE(testMissingIncludeCheckConfig);
|
||||
}
|
||||
|
||||
void preprocess(const char* code, std::map<std::string, std::string>& actual, const char filename[] = "file.c") {
|
||||
|
@ -1931,25 +1936,55 @@ private:
|
|||
preprocess("#define () {(int f(x) }\n", actual); // don't hang
|
||||
}
|
||||
|
||||
void inline_suppression_for_missing_include() {
|
||||
void inline_suppression_for_missing_include_internal(bool checkConfig) {
|
||||
Preprocessor::missingIncludeFlag = false;
|
||||
Preprocessor::missingSystemIncludeFlag = false;
|
||||
Settings settings;
|
||||
settings.checkConfiguration = checkConfig;
|
||||
settings.inlineSuppressions = true;
|
||||
settings.severity.fill();
|
||||
settings.severity.clear();
|
||||
// --check-config needs to report this regardless of the emanled checks
|
||||
if (!checkConfig)
|
||||
settings.checks.enable(Checks::missingInclude);
|
||||
Preprocessor preprocessor(settings, this);
|
||||
|
||||
std::istringstream src("// cppcheck-suppress missingInclude\n"
|
||||
const std::string code("// cppcheck-suppress missingInclude\n"
|
||||
"#include \"missing.h\"\n"
|
||||
"int x;");
|
||||
std::string processedFile;
|
||||
std::list<std::string> cfg;
|
||||
std::list<std::string> paths;
|
||||
|
||||
"// cppcheck-suppress missingIncludeSystem\n"
|
||||
"#include <missing2.h>\n");
|
||||
// Don't report that the include is missing
|
||||
errout.str("");
|
||||
preprocessor.preprocess(src, processedFile, cfg, "test.c", paths);
|
||||
preprocessor.getcode(code, "", "test.c");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
ASSERT_EQUALS(false, Preprocessor::missingIncludeFlag);
|
||||
ASSERT_EQUALS(false, Preprocessor::missingSystemIncludeFlag);
|
||||
|
||||
auto suppressions = settings.nomsg.getSuppressions();
|
||||
ASSERT_EQUALS(2, suppressions.size());
|
||||
|
||||
auto suppr = suppressions.front();
|
||||
suppressions.pop_front();
|
||||
ASSERT_EQUALS("missingInclude", suppr.errorId);
|
||||
ASSERT_EQUALS("test.c", suppr.fileName);
|
||||
ASSERT_EQUALS(2, suppr.lineNumber);
|
||||
ASSERT_EQUALS(true, suppr.checked);
|
||||
ASSERT_EQUALS(true, suppr.matched);
|
||||
|
||||
suppr = suppressions.front();
|
||||
suppressions.pop_front();
|
||||
ASSERT_EQUALS("missingIncludeSystem", suppr.errorId);
|
||||
ASSERT_EQUALS("test.c", suppr.fileName);
|
||||
ASSERT_EQUALS(4, suppr.lineNumber);
|
||||
ASSERT_EQUALS(true, suppr.checked);
|
||||
ASSERT_EQUALS(true, suppr.matched);
|
||||
}
|
||||
|
||||
void inline_suppression_for_missing_include() {
|
||||
inline_suppression_for_missing_include_internal(false);
|
||||
}
|
||||
|
||||
void inline_suppression_for_missing_include_check_config() {
|
||||
inline_suppression_for_missing_include_internal(true);
|
||||
}
|
||||
|
||||
void predefine1() {
|
||||
|
@ -2395,6 +2430,63 @@ private:
|
|||
preprocessor.dump(ostr);
|
||||
ASSERT_EQUALS(dumpdata, ostr.str());
|
||||
}
|
||||
|
||||
void testMissingInclude() {
|
||||
Preprocessor::missingIncludeFlag = false;
|
||||
Preprocessor::missingSystemIncludeFlag = false;
|
||||
|
||||
Settings settings;
|
||||
settings.severity.clear();
|
||||
settings.checks.enable(Checks::missingInclude);
|
||||
Preprocessor preprocessor(settings, this);
|
||||
|
||||
ScopedFile header("header.h", "");
|
||||
ScopedFile header2("header2.h", "");
|
||||
|
||||
std::string code("#include \"missing.h\"\n"
|
||||
"#include <header.h>\n"
|
||||
"#include <missing2.h>\n"
|
||||
"#include \"header2.h\"");
|
||||
errout.str("");
|
||||
preprocessor.getcode(code, "", "test.c");
|
||||
ASSERT_EQUALS(true, Preprocessor::missingIncludeFlag);
|
||||
ASSERT_EQUALS(true, Preprocessor::missingSystemIncludeFlag);
|
||||
|
||||
// the expected messages are emited outside of the Preprocessor
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
Preprocessor::missingIncludeFlag = false;
|
||||
Preprocessor::missingSystemIncludeFlag = false;
|
||||
}
|
||||
|
||||
void testMissingIncludeCheckConfig() {
|
||||
Preprocessor::missingIncludeFlag = false;
|
||||
Preprocessor::missingSystemIncludeFlag = false;
|
||||
|
||||
Settings settings;
|
||||
settings.checkConfiguration = true;
|
||||
settings.severity.clear();
|
||||
// needs to be reported regardless of enabled checks
|
||||
Preprocessor preprocessor(settings, this);
|
||||
|
||||
ScopedFile header("header.h", "");
|
||||
ScopedFile header2("header2.h", "");
|
||||
|
||||
std::string code("#include \"missing.h\"\n"
|
||||
"#include <header.h>\n"
|
||||
"#include <missing2.h>\n"
|
||||
"#include \"header2.h\"");
|
||||
errout.str("");
|
||||
preprocessor.getcode(code, "", "test.c");
|
||||
ASSERT_EQUALS(true, Preprocessor::missingIncludeFlag);
|
||||
ASSERT_EQUALS(true, Preprocessor::missingSystemIncludeFlag);
|
||||
|
||||
ASSERT_EQUALS("[test.c:1]: (information) Include file: \"missing.h\" not found.\n"
|
||||
"[test.c:3]: (information) Include file: <missing2.h> not found. Please note: Cppcheck does not need standard library headers to get proper results.\n", errout.str());
|
||||
|
||||
Preprocessor::missingIncludeFlag = false;
|
||||
Preprocessor::missingSystemIncludeFlag = false;
|
||||
}
|
||||
};
|
||||
|
||||
REGISTER_TEST(TestPreprocessor)
|
||||
|
|
Loading…
Reference in New Issue