From b2511fb3ae9a9a3be9ef2eb587d710016e6a7e8b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Samuel=20Pol=C3=A1=C4=8Dek?= Date: Fri, 4 Aug 2023 17:38:43 +0200 Subject: [PATCH] Check if --cppcheck-build-dir exists (#5254) Cppcheck does not report that cppcheck build dir does not exist and also does not report any write issues to the non-existent directory. This means that cppcheck build dir is actually not used. We should either create the directory or fail. --- cli/cmdlineparser.cpp | 6 +++++- lib/path.cpp | 8 ++++++++ lib/path.h | 7 +++++++ test/testcmdlineparser.cpp | 25 +++++++++++++++++++++++++ 4 files changed, 45 insertions(+), 1 deletion(-) diff --git a/cli/cmdlineparser.cpp b/cli/cmdlineparser.cpp index 4f6b12e2e..a67abb02f 100644 --- a/cli/cmdlineparser.cpp +++ b/cli/cmdlineparser.cpp @@ -285,10 +285,14 @@ bool CmdLineParser::parseFromArgs(int argc, const char* const argv[]) } else if (std::strncmp(argv[i], "--cppcheck-build-dir=", 21) == 0) { - // TODO: bail out when the folder does not exist? will silently do nothing mSettings.buildDir = Path::fromNativeSeparators(argv[i] + 21); if (endsWith(mSettings.buildDir, '/')) mSettings.buildDir.pop_back(); + + if (!Path::directoryExists(mSettings.buildDir)) { + printError("Directory '" + mSettings.buildDir + "' specified by --cppcheck-build-dir argument has to be existent."); + return false; + } } // Show --debug output after the first simplifications diff --git a/lib/path.cpp b/lib/path.cpp index 442d88f44..2b6540b73 100644 --- a/lib/path.cpp +++ b/lib/path.cpp @@ -26,6 +26,7 @@ #include #include #include +#include #include #include @@ -266,6 +267,13 @@ bool Path::fileExists(const std::string &file) return f.is_open(); } + +bool Path::directoryExists(const std::string &path) +{ + struct stat info; + return stat(path.c_str(), &info) == 0 && (info.st_mode & S_IFDIR); +} + std::string Path::join(std::string path1, std::string path2) { if (path1.empty() || path2.empty()) return path1 + path2; diff --git a/lib/path.h b/lib/path.h index 621360efe..8ab8c7982 100644 --- a/lib/path.h +++ b/lib/path.h @@ -187,6 +187,13 @@ public: */ static bool fileExists(const std::string &file); + /** + * @brief Checks if a directory exists + * @param path Path to be checked + * @return true if given path is a directory + */ + static bool directoryExists(const std::string &path); + /** * join 2 paths with '/' separators */ diff --git a/test/testcmdlineparser.cpp b/test/testcmdlineparser.cpp index fffa19f5f..455f1e50c 100644 --- a/test/testcmdlineparser.cpp +++ b/test/testcmdlineparser.cpp @@ -237,6 +237,10 @@ private: TEST_CASE(undefs_noarg3); TEST_CASE(undefs); TEST_CASE(undefs2); + + TEST_CASE(cppcheckBuildDirExistent); + TEST_CASE(cppcheckBuildDirNonExistent); + TEST_CASE(cppcheckBuildDirEmpty); } @@ -1947,6 +1951,27 @@ private: ASSERT_EQUALS(false, defParser.parseFromArgs(4, argv)); ASSERT_EQUALS("cppcheck: error: argument to '-U' is missing.\n", GET_REDIRECT_OUTPUT); } + + void cppcheckBuildDirExistent() { + REDIRECT; + const char * const argv[] = {"cppcheck", "--cppcheck-build-dir=."}; + ASSERT_EQUALS(true, defParser.parseFromArgs(2, argv)); + ASSERT_EQUALS("", GET_REDIRECT_OUTPUT); + } + + void cppcheckBuildDirNonExistent() { + REDIRECT; + const char * const argv[] = {"cppcheck", "--cppcheck-build-dir=non-existent-path"}; + ASSERT_EQUALS(false, defParser.parseFromArgs(2, argv)); + ASSERT_EQUALS("cppcheck: error: Directory 'non-existent-path' specified by --cppcheck-build-dir argument has to be existent.\n", GET_REDIRECT_OUTPUT); + } + + void cppcheckBuildDirEmpty() { + REDIRECT; + const char * const argv[] = {"cppcheck", "--cppcheck-build-dir="}; + ASSERT_EQUALS(false, defParser.parseFromArgs(2, argv)); + ASSERT_EQUALS("cppcheck: error: Directory '' specified by --cppcheck-build-dir argument has to be existent.\n", GET_REDIRECT_OUTPUT); + } }; REGISTER_TEST(TestCmdlineParser)