LCOV - code coverage report
Current view: top level - test - testcmdlineparser.cpp (source / functions) Hit Total Coverage
Test: lcov.info Lines: 1763 1764 99.9 %
Date: 2024-04-28 12:00:40 Functions: 263 263 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :  * Cppcheck - A tool for static C/C++ code analysis
       3             :  * Copyright (C) 2007-2024 Cppcheck team.
       4             :  *
       5             :  * This program is free software: you can redistribute it and/or modify
       6             :  * it under the terms of the GNU General Public License as published by
       7             :  * the Free Software Foundation, either version 3 of the License, or
       8             :  * (at your option) any later version.
       9             :  *
      10             :  * This program is distributed in the hope that it will be useful,
      11             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      12             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      13             :  * GNU General Public License for more details.
      14             :  *
      15             :  * You should have received a copy of the GNU General Public License
      16             :  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
      17             :  */
      18             : 
      19             : #include "cmdlinelogger.h"
      20             : #include "cmdlineparser.h"
      21             : #include "config.h"
      22             : #include "cppcheckexecutor.h"
      23             : #include "errorlogger.h"
      24             : #include "errortypes.h"
      25             : #include "helpers.h"
      26             : #include "path.h"
      27             : #include "platform.h"
      28             : #include "redirect.h"
      29             : #include "settings.h"
      30             : #include "standards.h"
      31             : #include "suppressions.h"
      32             : #include "fixture.h"
      33             : #include "timer.h"
      34             : #include "utils.h"
      35             : 
      36             : #include <cstdio>
      37             : #include <list>
      38             : #include <memory>
      39             : #include <set>
      40             : #include <stdexcept>
      41             : #include <string>
      42             : #include <unordered_set>
      43             : #include <vector>
      44             : 
      45             : class TestCmdlineParser : public TestFixture {
      46             : public:
      47           1 :     TestCmdlineParser() : TestFixture("TestCmdlineParser")
      48           1 :     {}
      49             : 
      50             : private:
      51             :     class CmdLineLoggerTest : public CmdLineLogger
      52             :     {
      53             :     public:
      54         252 :         CmdLineLoggerTest() = default;
      55             : 
      56          92 :         void printMessage(const std::string &message) override
      57             :         {
      58          92 :             printInternal("cppcheck: " + message + '\n');
      59          92 :         }
      60             : 
      61          87 :         void printError(const std::string &message) override
      62             :         {
      63          87 :             printMessage("error: " + message);
      64          87 :         }
      65             : 
      66          11 :         void printRaw(const std::string &message) override
      67             :         {
      68          11 :             printInternal(message + '\n');
      69          11 :         }
      70             : 
      71         111 :         std::string str()
      72             :         {
      73         111 :             std::string s;
      74         111 :             std::swap(buf, s);
      75         111 :             return s;
      76             :         }
      77             : 
      78         252 :         void destroy()
      79             :         {
      80         252 :             if (!buf.empty())
      81           0 :                 throw std::runtime_error("unconsumed messages: " + buf);
      82         252 :         }
      83             : 
      84             :     private:
      85         103 :         void printInternal(const std::string &message)
      86             :         {
      87         103 :             buf += message;
      88         103 :         }
      89             : 
      90             :         std::string buf;
      91             :     };
      92             : 
      93             :     std::unique_ptr<CmdLineLoggerTest> logger;
      94             :     std::unique_ptr<Settings> settings;
      95             :     std::unique_ptr<CmdLineParser> parser;
      96             : 
      97         252 :     void prepareTestInternal() override {
      98         252 :         logger.reset(new CmdLineLoggerTest());
      99         252 :         settings.reset(new Settings());
     100         252 :         parser.reset(new CmdLineParser(*logger, *settings, settings->supprs));
     101         252 :     }
     102             : 
     103         252 :     void teardownTestInternal() override {
     104         252 :         logger->destroy();
     105         252 :     }
     106             : 
     107           8 :     void asPremium() {
     108             :         // set this so we think it is the premium
     109           8 :         settings->cppcheckCfgProductName = "Cppcheck Premium 0.0.0";
     110           8 :     }
     111             : 
     112           1 :     void run() override {
     113           1 :         TEST_CASE(nooptions);
     114           1 :         TEST_CASE(helpshort);
     115           1 :         TEST_CASE(helpshortExclusive);
     116           1 :         TEST_CASE(helplong);
     117           1 :         TEST_CASE(helplongExclusive);
     118           1 :         TEST_CASE(version);
     119           1 :         TEST_CASE(versionWithCfg);
     120           1 :         TEST_CASE(versionExclusive);
     121           1 :         TEST_CASE(versionWithInvalidCfg);
     122           1 :         TEST_CASE(checkVersionCorrect);
     123           1 :         TEST_CASE(checkVersionIncorrect);
     124           1 :         TEST_CASE(onefile);
     125           1 :         TEST_CASE(onepath);
     126           1 :         TEST_CASE(optionwithoutfile);
     127           1 :         TEST_CASE(verboseshort);
     128           1 :         TEST_CASE(verboselong);
     129           1 :         TEST_CASE(debugSimplified);
     130           1 :         TEST_CASE(debugwarnings);
     131           1 :         TEST_CASE(forceshort);
     132           1 :         TEST_CASE(forcelong);
     133           1 :         TEST_CASE(relativePaths1);
     134           1 :         TEST_CASE(relativePaths2);
     135           1 :         TEST_CASE(relativePaths3);
     136           1 :         TEST_CASE(relativePaths4);
     137           1 :         TEST_CASE(quietshort);
     138           1 :         TEST_CASE(quietlong);
     139           1 :         TEST_CASE(defines_noarg);
     140           1 :         TEST_CASE(defines_noarg2);
     141           1 :         TEST_CASE(defines_noarg3);
     142           1 :         TEST_CASE(defines);
     143           1 :         TEST_CASE(defines2);
     144           1 :         TEST_CASE(defines3);
     145           1 :         TEST_CASE(defines4);
     146           1 :         TEST_CASE(enforceLanguage1);
     147           1 :         TEST_CASE(enforceLanguage2);
     148           1 :         TEST_CASE(enforceLanguage3);
     149           1 :         TEST_CASE(enforceLanguage4);
     150           1 :         TEST_CASE(enforceLanguage5);
     151           1 :         TEST_CASE(enforceLanguage6);
     152           1 :         TEST_CASE(enforceLanguage7);
     153           1 :         TEST_CASE(includesnopath);
     154           1 :         TEST_CASE(includes);
     155           1 :         TEST_CASE(includesslash);
     156           1 :         TEST_CASE(includesbackslash);
     157           1 :         TEST_CASE(includesnospace);
     158           1 :         TEST_CASE(includes2);
     159           1 :         TEST_CASE(includesFile);
     160           1 :         TEST_CASE(includesFileNoFile);
     161           1 :         TEST_CASE(configExcludesFile);
     162           1 :         TEST_CASE(configExcludesFileNoFile);
     163           1 :         TEST_CASE(enabledAll);
     164           1 :         TEST_CASE(enabledStyle);
     165           1 :         TEST_CASE(enabledPerformance);
     166           1 :         TEST_CASE(enabledPortability);
     167           1 :         TEST_CASE(enabledInformation);
     168           1 :         TEST_CASE(enabledUnusedFunction);
     169           1 :         TEST_CASE(enabledMissingInclude);
     170           1 :         TEST_CASE(disabledMissingIncludeWithInformation);
     171           1 :         TEST_CASE(enabledMissingIncludeWithInformation);
     172           1 :         TEST_CASE(enabledMissingIncludeWithInformationReverseOrder);
     173             : #ifdef CHECK_INTERNAL
     174             :         TEST_CASE(enabledInternal);
     175             : #endif
     176           1 :         TEST_CASE(enabledMultiple);
     177           1 :         TEST_CASE(enabledInvalid);
     178           1 :         TEST_CASE(enabledError);
     179           1 :         TEST_CASE(enabledEmpty);
     180           1 :         TEST_CASE(disableAll);
     181           1 :         TEST_CASE(disableMultiple);
     182           1 :         TEST_CASE(disableStylePartial);
     183           1 :         TEST_CASE(disableInformationPartial);
     184           1 :         TEST_CASE(disableInformationPartial2);
     185           1 :         TEST_CASE(disableInvalid);
     186           1 :         TEST_CASE(disableError);
     187           1 :         TEST_CASE(disableEmpty);
     188           1 :         TEST_CASE(inconclusive);
     189           1 :         TEST_CASE(errorExitcode);
     190           1 :         TEST_CASE(errorExitcodeMissing);
     191           1 :         TEST_CASE(errorExitcodeStr);
     192           1 :         TEST_CASE(exitcodeSuppressionsOld);
     193           1 :         TEST_CASE(exitcodeSuppressions);
     194           1 :         TEST_CASE(exitcodeSuppressionsNoFile);
     195           1 :         TEST_CASE(fileFilterStdin);
     196           1 :         TEST_CASE(fileList);
     197           1 :         TEST_CASE(fileListNoFile);
     198           1 :         TEST_CASE(fileListStdin);
     199           1 :         TEST_CASE(fileListInvalid);
     200           1 :         TEST_CASE(inlineSuppr);
     201           1 :         TEST_CASE(jobs);
     202           1 :         TEST_CASE(jobs2);
     203           1 :         TEST_CASE(jobsMissingCount);
     204           1 :         TEST_CASE(jobsInvalid);
     205           1 :         TEST_CASE(jobsNoJobs);
     206           1 :         TEST_CASE(jobsTooBig);
     207           1 :         TEST_CASE(maxConfigs);
     208           1 :         TEST_CASE(maxConfigsMissingCount);
     209           1 :         TEST_CASE(maxConfigsInvalid);
     210           1 :         TEST_CASE(maxConfigsTooSmall);
     211           1 :         TEST_CASE(premiumOptions1);
     212           1 :         TEST_CASE(premiumOptions2);
     213           1 :         TEST_CASE(premiumOptions3);
     214           1 :         TEST_CASE(premiumOptions4);
     215           1 :         TEST_CASE(premiumOptions5);
     216           1 :         TEST_CASE(premiumOptionsInvalid1);
     217           1 :         TEST_CASE(premiumOptionsInvalid2);
     218           1 :         TEST_CASE(premiumSafety);
     219           1 :         TEST_CASE(reportProgress1);
     220           1 :         TEST_CASE(reportProgress2);
     221           1 :         TEST_CASE(reportProgress3);
     222           1 :         TEST_CASE(reportProgress4);
     223           1 :         TEST_CASE(reportProgress5);
     224           1 :         TEST_CASE(stdc99);
     225           1 :         TEST_CASE(stdcpp11);
     226           1 :         TEST_CASE(stdunknown1);
     227           1 :         TEST_CASE(stdunknown2);
     228           1 :         TEST_CASE(platformWin64);
     229           1 :         TEST_CASE(platformWin32A);
     230           1 :         TEST_CASE(platformWin32W);
     231           1 :         TEST_CASE(platformUnix32);
     232           1 :         TEST_CASE(platformUnix32Unsigned);
     233           1 :         TEST_CASE(platformUnix64);
     234           1 :         TEST_CASE(platformUnix64Unsigned);
     235           1 :         TEST_CASE(platformNative);
     236           1 :         TEST_CASE(platformUnspecified);
     237           1 :         TEST_CASE(platformPlatformFile);
     238           1 :         TEST_CASE(platformUnknown);
     239           1 :         TEST_CASE(plistEmpty);
     240           1 :         TEST_CASE(plistDoesNotExist);
     241           1 :         TEST_CASE(suppressionsOld);
     242           1 :         TEST_CASE(suppressions);
     243           1 :         TEST_CASE(suppressionsNoFile1);
     244           1 :         TEST_CASE(suppressionsNoFile2);
     245           1 :         TEST_CASE(suppressionsNoFile3);
     246           1 :         TEST_CASE(suppressionSingle);
     247           1 :         TEST_CASE(suppressionSingleFile);
     248           1 :         TEST_CASE(suppressionTwo);
     249           1 :         TEST_CASE(suppressionTwoSeparate);
     250           1 :         TEST_CASE(templates);
     251           1 :         TEST_CASE(templatesGcc);
     252           1 :         TEST_CASE(templatesVs);
     253           1 :         TEST_CASE(templatesEdit);
     254           1 :         TEST_CASE(templatesCppcheck1);
     255           1 :         TEST_CASE(templatesDaca2);
     256           1 :         TEST_CASE(templatesSelfcheck);
     257           1 :         TEST_CASE(templatesSimple);
     258           1 :         TEST_CASE(templatesNoPlaceholder);
     259           1 :         TEST_CASE(templateFormatInvalid);
     260           1 :         TEST_CASE(templateFormatEmpty);
     261           1 :         TEST_CASE(templateLocationInvalid);
     262           1 :         TEST_CASE(templateLocationEmpty);
     263           1 :         TEST_CASE(xml);
     264           1 :         TEST_CASE(xmlver2);
     265           1 :         TEST_CASE(xmlver2both);
     266           1 :         TEST_CASE(xmlver2both2);
     267           1 :         TEST_CASE(xmlverunknown);
     268           1 :         TEST_CASE(xmlverinvalid);
     269           1 :         TEST_CASE(doc);
     270           1 :         TEST_CASE(docExclusive);
     271           1 :         TEST_CASE(showtimeFile);
     272           1 :         TEST_CASE(showtimeFileTotal);
     273           1 :         TEST_CASE(showtimeTop5);
     274           1 :         TEST_CASE(showtimeTop5File);
     275           1 :         TEST_CASE(showtimeTop5Summary);
     276           1 :         TEST_CASE(showtimeNone);
     277           1 :         TEST_CASE(showtimeEmpty);
     278           1 :         TEST_CASE(showtimeInvalid);
     279           1 :         TEST_CASE(errorlist);
     280           1 :         TEST_CASE(errorlistWithCfg);
     281           1 :         TEST_CASE(errorlistExclusive);
     282           1 :         TEST_CASE(errorlistWithInvalidCfg);
     283           1 :         TEST_CASE(ignorepathsnopath);
     284             : #if defined(USE_WINDOWS_SEH) || defined(USE_UNIX_SIGNAL_HANDLING)
     285           1 :         TEST_CASE(exceptionhandling);
     286           1 :         TEST_CASE(exceptionhandling2);
     287           1 :         TEST_CASE(exceptionhandling3);
     288           1 :         TEST_CASE(exceptionhandlingInvalid);
     289           1 :         TEST_CASE(exceptionhandlingInvalid2);
     290             : #else
     291             :         TEST_CASE(exceptionhandlingNotSupported);
     292             :         TEST_CASE(exceptionhandlingNotSupported2);
     293             : #endif
     294           1 :         TEST_CASE(clang);
     295           1 :         TEST_CASE(clang2);
     296           1 :         TEST_CASE(clangInvalid);
     297           1 :         TEST_CASE(valueFlowMaxIterations);
     298           1 :         TEST_CASE(valueFlowMaxIterations2);
     299           1 :         TEST_CASE(valueFlowMaxIterationsInvalid);
     300           1 :         TEST_CASE(valueFlowMaxIterationsInvalid2);
     301           1 :         TEST_CASE(valueFlowMaxIterationsInvalid3);
     302           1 :         TEST_CASE(checksMaxTime);
     303           1 :         TEST_CASE(checksMaxTime2);
     304           1 :         TEST_CASE(checksMaxTimeInvalid);
     305             : #ifdef HAS_THREADING_MODEL_FORK
     306           1 :         TEST_CASE(loadAverage);
     307           1 :         TEST_CASE(loadAverage2);
     308           1 :         TEST_CASE(loadAverageInvalid);
     309             : #else
     310             :         TEST_CASE(loadAverageNotSupported);
     311             : #endif
     312           1 :         TEST_CASE(maxCtuDepth);
     313           1 :         TEST_CASE(maxCtuDepthInvalid);
     314           1 :         TEST_CASE(performanceValueflowMaxTime);
     315           1 :         TEST_CASE(performanceValueflowMaxTimeInvalid);
     316           1 :         TEST_CASE(performanceValueFlowMaxIfCount);
     317           1 :         TEST_CASE(performanceValueFlowMaxIfCountInvalid);
     318           1 :         TEST_CASE(templateMaxTime);
     319           1 :         TEST_CASE(templateMaxTimeInvalid);
     320           1 :         TEST_CASE(templateMaxTimeInvalid2);
     321           1 :         TEST_CASE(typedefMaxTime);
     322           1 :         TEST_CASE(typedefMaxTimeInvalid);
     323           1 :         TEST_CASE(typedefMaxTimeInvalid2);
     324           1 :         TEST_CASE(templateMaxTime);
     325           1 :         TEST_CASE(templateMaxTime);
     326           1 :         TEST_CASE(project);
     327           1 :         TEST_CASE(projectMultiple);
     328           1 :         TEST_CASE(projectAndSource);
     329           1 :         TEST_CASE(projectEmpty);
     330           1 :         TEST_CASE(projectMissing);
     331           1 :         TEST_CASE(projectNoPaths);
     332           1 :         TEST_CASE(addon);
     333           1 :         TEST_CASE(addonMissing);
     334             : #ifdef HAVE_RULES
     335             :         TEST_CASE(rule);
     336             :         TEST_CASE(ruleMissingPattern);
     337             : #else
     338           1 :         TEST_CASE(ruleNotSupported);
     339             : #endif
     340             : #ifdef HAVE_RULES
     341             :         TEST_CASE(ruleFileMulti);
     342             :         TEST_CASE(ruleFileSingle);
     343             :         TEST_CASE(ruleFileEmpty);
     344             :         TEST_CASE(ruleFileMissing);
     345             :         TEST_CASE(ruleFileInvalid);
     346             :         TEST_CASE(ruleFileNoRoot);
     347             :         TEST_CASE(ruleFileEmptyElements1);
     348             :         TEST_CASE(ruleFileEmptyElements2);
     349             :         TEST_CASE(ruleFileUnknownElement1);
     350             :         TEST_CASE(ruleFileUnknownElement2);
     351             :         TEST_CASE(ruleFileMissingTokenList);
     352             :         TEST_CASE(ruleFileUnknownTokenList);
     353             :         TEST_CASE(ruleFileMissingId);
     354             :         TEST_CASE(ruleFileInvalidSeverity1);
     355             :         TEST_CASE(ruleFileInvalidSeverity2);
     356             : #else
     357           1 :         TEST_CASE(ruleFileNotSupported);
     358             : #endif
     359           1 :         TEST_CASE(signedChar);
     360           1 :         TEST_CASE(signedChar2);
     361           1 :         TEST_CASE(unsignedChar);
     362           1 :         TEST_CASE(unsignedChar2);
     363           1 :         TEST_CASE(signedCharUnsignedChar);
     364           1 :         TEST_CASE(library);
     365           1 :         TEST_CASE(libraryMissing);
     366           1 :         TEST_CASE(suppressXml);
     367           1 :         TEST_CASE(suppressXmlEmpty);
     368           1 :         TEST_CASE(suppressXmlMissing);
     369           1 :         TEST_CASE(suppressXmlInvalid);
     370           1 :         TEST_CASE(suppressXmlNoRoot);
     371           1 :         TEST_CASE(executorDefault);
     372           1 :         TEST_CASE(executorAuto);
     373           1 :         TEST_CASE(executorAutoNoJobs);
     374             : #if defined(HAS_THREADING_MODEL_THREAD)
     375           1 :         TEST_CASE(executorThread);
     376           1 :         TEST_CASE(executorThreadNoJobs);
     377             : #else
     378             :         TEST_CASE(executorThreadNotSupported);
     379             : #endif
     380             : #if defined(HAS_THREADING_MODEL_FORK)
     381           1 :         TEST_CASE(executorProcess);
     382           1 :         TEST_CASE(executorProcessNoJobs);
     383             : #else
     384             :         TEST_CASE(executorProcessNotSupported);
     385             : #endif
     386           1 :         TEST_CASE(checkLevelDefault);
     387           1 :         TEST_CASE(checkLevelNormal);
     388           1 :         TEST_CASE(checkLevelExhaustive);
     389           1 :         TEST_CASE(checkLevelUnknown);
     390             : 
     391           1 :         TEST_CASE(ignorepaths1);
     392           1 :         TEST_CASE(ignorepaths2);
     393           1 :         TEST_CASE(ignorepaths3);
     394           1 :         TEST_CASE(ignorepaths4);
     395           1 :         TEST_CASE(ignorefilepaths1);
     396           1 :         TEST_CASE(ignorefilepaths2);
     397           1 :         TEST_CASE(ignorefilepaths3);
     398             : 
     399           1 :         TEST_CASE(checkconfig);
     400           1 :         TEST_CASE(unknownParam);
     401             : 
     402           1 :         TEST_CASE(undefs_noarg);
     403           1 :         TEST_CASE(undefs_noarg2);
     404           1 :         TEST_CASE(undefs_noarg3);
     405           1 :         TEST_CASE(undefs);
     406           1 :         TEST_CASE(undefs2);
     407             : 
     408           1 :         TEST_CASE(cppcheckBuildDirExistent);
     409           1 :         TEST_CASE(cppcheckBuildDirNonExistent);
     410           1 :         TEST_CASE(cppcheckBuildDirEmpty);
     411             : 
     412           1 :         TEST_CASE(invalidCppcheckCfg);
     413           1 :     }
     414             : 
     415           1 :     void nooptions() {
     416           1 :         REDIRECT;
     417           1 :         const char * const argv[] = {"cppcheck"};
     418           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(1, argv));
     419           1 :         ASSERT(startsWith(logger->str(), "Cppcheck - A tool for static C/C++ code analysis"));
     420             :     }
     421             : 
     422           1 :     void helpshort() {
     423           1 :         REDIRECT;
     424           1 :         const char * const argv[] = {"cppcheck", "-h"};
     425           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
     426           1 :         ASSERT(startsWith(logger->str(), "Cppcheck - A tool for static C/C++ code analysis"));
     427             :     }
     428             : 
     429           1 :     void helpshortExclusive() {
     430           1 :         REDIRECT;
     431           1 :         const char * const argv[] = {"cppcheck", "--library=missing", "-h"};
     432           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(3, argv));
     433           1 :         ASSERT(startsWith(logger->str(), "Cppcheck - A tool for static C/C++ code analysis"));
     434             :     }
     435             : 
     436           1 :     void helplong() {
     437           1 :         REDIRECT;
     438           1 :         const char * const argv[] = {"cppcheck", "--help"};
     439           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
     440           1 :         ASSERT(startsWith(logger->str(), "Cppcheck - A tool for static C/C++ code analysis"));
     441             :     }
     442             : 
     443           1 :     void helplongExclusive() {
     444           1 :         REDIRECT;
     445           1 :         const char * const argv[] = {"cppcheck", "--library=missing", "--help"};
     446           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(3, argv));
     447           1 :         ASSERT(startsWith(logger->str(), "Cppcheck - A tool for static C/C++ code analysis"));
     448             :     }
     449             : 
     450           1 :     void version() {
     451           1 :         REDIRECT;
     452           1 :         const char * const argv[] = {"cppcheck", "--version"};
     453           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
     454           1 :         ASSERT(logger->str().compare(0, 11, "Cppcheck 2.") == 0);
     455             :     }
     456             : 
     457           1 :     void versionWithCfg() {
     458           1 :         REDIRECT;
     459           2 :         ScopedFile file(Path::join(Path::getPathFromFilename(Path::getCurrentExecutablePath("")), "cppcheck.cfg"),
     460             :                         "{\n"
     461             :                         "\"productName\": \"The Product\""
     462           4 :                         "}\n");
     463           1 :         const char * const argv[] = {"cppcheck", "--version"};
     464           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
     465             :         // TODO: somehow the config is not loaded on some systems
     466           1 :         (void)logger->str(); //ASSERT_EQUALS("The Product\n", logger->str()); // TODO: include version?
     467             :     }
     468             : 
     469             :     // TODO: test --version with extraVersion
     470             : 
     471           1 :     void versionExclusive() {
     472           1 :         REDIRECT;
     473           1 :         const char * const argv[] = {"cppcheck", "--library=missing", "--version"};
     474           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(3, argv));
     475           1 :         ASSERT(logger->str().compare(0, 11, "Cppcheck 2.") == 0);
     476             :     }
     477             : 
     478           1 :     void versionWithInvalidCfg() {
     479           1 :         REDIRECT;
     480           2 :         ScopedFile file(Path::join(Path::getPathFromFilename(Path::getCurrentExecutablePath("")), "cppcheck.cfg"),
     481           4 :                         "{\n");
     482           1 :         const char * const argv[] = {"cppcheck", "--version"};
     483           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
     484           1 :         ASSERT_EQUALS("cppcheck: error: could not load cppcheck.cfg - not a valid JSON - syntax error at line 2 near: \n", logger->str());
     485             :     }
     486             : 
     487           1 :     void checkVersionCorrect() {
     488           1 :         REDIRECT;
     489           1 :         const std::string currentVersion = parser->getVersion();
     490           1 :         const std::string checkVersion = "--check-version=" + currentVersion;
     491           1 :         const char * const argv[] = {"cppcheck", checkVersion.c_str(), "file.cpp"};
     492           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     493             :     }
     494             : 
     495           1 :     void checkVersionIncorrect() {
     496           1 :         REDIRECT;
     497           1 :         const char * const argv[] = {"cppcheck", "--check-version=Cppcheck 2.0", "file.cpp"};
     498           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     499           1 :         ASSERT_EQUALS("cppcheck: error: --check-version check failed. Aborting.\n", logger->str());
     500             :     }
     501             : 
     502           1 :     void onefile() {
     503           1 :         REDIRECT;
     504           1 :         const char * const argv[] = {"cppcheck", "file.cpp"};
     505           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
     506           1 :         ASSERT_EQUALS(1, (int)parser->getPathNames().size());
     507           1 :         ASSERT_EQUALS("file.cpp", parser->getPathNames().at(0));
     508             :     }
     509             : 
     510           1 :     void onepath() {
     511           1 :         REDIRECT;
     512           1 :         const char * const argv[] = {"cppcheck", "src"};
     513           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
     514           1 :         ASSERT_EQUALS(1, (int)parser->getPathNames().size());
     515           1 :         ASSERT_EQUALS("src", parser->getPathNames().at(0));
     516             :     }
     517             : 
     518           1 :     void optionwithoutfile() {
     519           1 :         REDIRECT;
     520           1 :         const char * const argv[] = {"cppcheck", "-v"};
     521           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
     522           1 :         ASSERT_EQUALS(0, (int)parser->getPathNames().size());
     523           1 :         ASSERT_EQUALS("cppcheck: error: no C or C++ source files found.\n", logger->str());
     524             :     }
     525             : 
     526           1 :     void verboseshort() {
     527           1 :         REDIRECT;
     528           1 :         const char * const argv[] = {"cppcheck", "-v", "file.cpp"};
     529           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     530           1 :         ASSERT_EQUALS(true, settings->verbose);
     531             :     }
     532             : 
     533           1 :     void verboselong() {
     534           1 :         REDIRECT;
     535           1 :         const char * const argv[] = {"cppcheck", "--verbose", "file.cpp"};
     536           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     537           1 :         ASSERT_EQUALS(true, settings->verbose);
     538             :     }
     539             : 
     540           1 :     void debugSimplified() {
     541           1 :         REDIRECT;
     542           1 :         const char * const argv[] = {"cppcheck", "--debug-simplified", "file.cpp"};
     543           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     544           1 :         ASSERT_EQUALS(true, settings->debugSimplified);
     545             :     }
     546             : 
     547           1 :     void debugwarnings() {
     548           1 :         REDIRECT;
     549           1 :         const char * const argv[] = {"cppcheck", "--debug-warnings", "file.cpp"};
     550           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     551           1 :         ASSERT_EQUALS(true, settings->debugwarnings);
     552             :     }
     553             : 
     554           1 :     void forceshort() {
     555           1 :         REDIRECT;
     556           1 :         const char * const argv[] = {"cppcheck", "-f", "file.cpp"};
     557           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     558           1 :         ASSERT_EQUALS(true, settings->force);
     559             :     }
     560             : 
     561           1 :     void forcelong() {
     562           1 :         REDIRECT;
     563           1 :         const char * const argv[] = {"cppcheck", "--force", "file.cpp"};
     564           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     565           1 :         ASSERT_EQUALS(true, settings->force);
     566             :     }
     567             : 
     568           1 :     void relativePaths1() {
     569           1 :         REDIRECT;
     570           1 :         const char * const argv[] = {"cppcheck", "-rp", "file.cpp"};
     571           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     572           1 :         ASSERT_EQUALS(true, settings->relativePaths);
     573             :     }
     574             : 
     575           1 :     void relativePaths2() {
     576           1 :         REDIRECT;
     577           1 :         const char * const argv[] = {"cppcheck", "--relative-paths", "file.cpp"};
     578           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     579           1 :         ASSERT_EQUALS(true, settings->relativePaths);
     580             :     }
     581             : 
     582           1 :     void relativePaths3() {
     583           1 :         REDIRECT;
     584           1 :         const char * const argv[] = {"cppcheck", "-rp=C:/foo;C:\\bar", "file.cpp"};
     585           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     586           1 :         ASSERT_EQUALS(true, settings->relativePaths);
     587           1 :         ASSERT_EQUALS(2, settings->basePaths.size());
     588           1 :         ASSERT_EQUALS("C:/foo", settings->basePaths[0]);
     589           1 :         ASSERT_EQUALS("C:/bar", settings->basePaths[1]);
     590             :     }
     591             : 
     592           1 :     void relativePaths4() {
     593           1 :         REDIRECT;
     594           1 :         const char * const argv[] = {"cppcheck", "--relative-paths=C:/foo;C:\\bar", "file.cpp"};
     595           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     596           1 :         ASSERT_EQUALS(true, settings->relativePaths);
     597           1 :         ASSERT_EQUALS(2, settings->basePaths.size());
     598           1 :         ASSERT_EQUALS("C:/foo", settings->basePaths[0]);
     599           1 :         ASSERT_EQUALS("C:/bar", settings->basePaths[1]);
     600             :     }
     601             : 
     602           1 :     void quietshort() {
     603           1 :         REDIRECT;
     604           1 :         const char * const argv[] = {"cppcheck", "-q", "file.cpp"};
     605           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     606           1 :         ASSERT_EQUALS(true, settings->quiet);
     607             :     }
     608             : 
     609           1 :     void quietlong() {
     610           1 :         REDIRECT;
     611           1 :         const char * const argv[] = {"cppcheck", "--quiet", "file.cpp"};
     612           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     613           1 :         ASSERT_EQUALS(true, settings->quiet);
     614             :     }
     615             : 
     616           1 :     void defines_noarg() {
     617           1 :         REDIRECT;
     618           1 :         const char * const argv[] = {"cppcheck", "-D"};
     619             :         // Fails since -D has no param
     620           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
     621           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-D' is missing.\n", logger->str());
     622             :     }
     623             : 
     624           1 :     void defines_noarg2() {
     625           1 :         REDIRECT;
     626           1 :         const char * const argv[] = {"cppcheck", "-D", "-v", "file.cpp"};
     627             :         // Fails since -D has no param
     628           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
     629           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-D' is missing.\n", logger->str());
     630             :     }
     631             : 
     632           1 :     void defines_noarg3() {
     633           1 :         REDIRECT;
     634           1 :         const char * const argv[] = {"cppcheck", "-D", "--quiet", "file.cpp"};
     635             :         // Fails since -D has no param
     636           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
     637           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-D' is missing.\n", logger->str());
     638             :     }
     639             : 
     640           1 :     void defines() {
     641           1 :         REDIRECT;
     642           1 :         const char * const argv[] = {"cppcheck", "-D_WIN32", "file.cpp"};
     643           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     644           1 :         ASSERT_EQUALS("_WIN32=1", settings->userDefines);
     645             :     }
     646             : 
     647           1 :     void defines2() {
     648           1 :         REDIRECT;
     649           1 :         const char * const argv[] = {"cppcheck", "-D_WIN32", "-DNODEBUG", "file.cpp"};
     650           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     651           1 :         ASSERT_EQUALS("_WIN32=1;NODEBUG=1", settings->userDefines);
     652             :     }
     653             : 
     654           1 :     void defines3() {
     655           1 :         REDIRECT;
     656           1 :         const char * const argv[] = {"cppcheck", "-D", "DEBUG", "file.cpp"};
     657           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     658           1 :         ASSERT_EQUALS("DEBUG=1", settings->userDefines);
     659             :     }
     660             : 
     661           1 :     void defines4() {
     662           1 :         REDIRECT;
     663           1 :         const char * const argv[] = {"cppcheck", "-DDEBUG=", "file.cpp"}; // #5137 - defining empty macro
     664           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     665           1 :         ASSERT_EQUALS("DEBUG=", settings->userDefines);
     666             :     }
     667             : 
     668           1 :     void enforceLanguage1() {
     669           1 :         REDIRECT;
     670           1 :         const char * const argv[] = {"cppcheck", "file.cpp"};
     671           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
     672           1 :         ASSERT_EQUALS(Standards::Language::None, settings->enforcedLang);
     673             :     }
     674             : 
     675           1 :     void enforceLanguage2() {
     676           1 :         REDIRECT;
     677           1 :         const char * const argv[] = {"cppcheck", "-x", "c++", "file.cpp"};
     678           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     679           1 :         ASSERT_EQUALS(Standards::Language::CPP, settings->enforcedLang);
     680             :     }
     681             : 
     682           1 :     void enforceLanguage3() {
     683           1 :         REDIRECT;
     684           1 :         const char * const argv[] = {"cppcheck", "-x"};
     685           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
     686           1 :         ASSERT_EQUALS("cppcheck: error: no language given to '-x' option.\n", logger->str());
     687             :     }
     688             : 
     689           1 :     void enforceLanguage4() {
     690           1 :         REDIRECT;
     691           1 :         const char * const argv[] = {"cppcheck", "-x", "--inconclusive", "file.cpp"};
     692           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
     693           1 :         ASSERT_EQUALS("cppcheck: error: no language given to '-x' option.\n", logger->str());
     694             :     }
     695             : 
     696           1 :     void enforceLanguage5() {
     697           1 :         REDIRECT;
     698           1 :         const char * const argv[] = {"cppcheck", "--language=c++", "file.cpp"};
     699           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     700           1 :         ASSERT_EQUALS(Standards::Language::CPP, settings->enforcedLang);
     701             :     }
     702             : 
     703           1 :     void enforceLanguage6() {
     704           1 :         REDIRECT;
     705           1 :         const char * const argv[] = {"cppcheck", "--language=c", "file.cpp"};
     706           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     707           1 :         ASSERT_EQUALS(Standards::Language::C, settings->enforcedLang);
     708             :     }
     709             : 
     710           1 :     void enforceLanguage7() {
     711           1 :         REDIRECT;
     712           1 :         const char * const argv[] = {"cppcheck", "--language=unknownLanguage", "file.cpp"};
     713           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     714           1 :         ASSERT_EQUALS("cppcheck: error: unknown language 'unknownLanguage' enforced.\n", logger->str());
     715             :     }
     716             : 
     717           1 :     void includesnopath() {
     718           1 :         REDIRECT;
     719           1 :         const char * const argv[] = {"cppcheck", "-I"};
     720             :         // Fails since -I has no param
     721           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
     722           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-I' is missing.\n", logger->str());
     723             :     }
     724             : 
     725           1 :     void includes() {
     726           1 :         REDIRECT;
     727           1 :         const char * const argv[] = {"cppcheck", "-I", "include", "file.cpp"};
     728           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     729           1 :         ASSERT_EQUALS("include/", settings->includePaths.front());
     730             :     }
     731             : 
     732           1 :     void includesslash() {
     733           1 :         REDIRECT;
     734           1 :         const char * const argv[] = {"cppcheck", "-I", "include/", "file.cpp"};
     735           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     736           1 :         ASSERT_EQUALS("include/", settings->includePaths.front());
     737             :     }
     738             : 
     739           1 :     void includesbackslash() {
     740           1 :         REDIRECT;
     741           1 :         const char * const argv[] = {"cppcheck", "-I", "include\\", "file.cpp"};
     742           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     743           1 :         ASSERT_EQUALS("include/", settings->includePaths.front());
     744             :     }
     745             : 
     746           1 :     void includesnospace() {
     747           1 :         REDIRECT;
     748           1 :         const char * const argv[] = {"cppcheck", "-Iinclude", "file.cpp"};
     749           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     750           1 :         ASSERT_EQUALS("include/", settings->includePaths.front());
     751             :     }
     752             : 
     753           1 :     void includes2() {
     754           1 :         REDIRECT;
     755           1 :         const char * const argv[] = {"cppcheck", "-I", "include/", "-I", "framework/", "file.cpp"};
     756           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(6, argv));
     757           1 :         ASSERT_EQUALS("include/", settings->includePaths.front());
     758           1 :         settings->includePaths.pop_front();
     759           1 :         ASSERT_EQUALS("framework/", settings->includePaths.front());
     760             :     }
     761             : 
     762           1 :     void includesFile() {
     763           1 :         REDIRECT;
     764             :         ScopedFile file("includes.txt",
     765             :                         "path/sub\n"
     766           4 :                         "path2/sub1\n");
     767           1 :         const char * const argv[] = {"cppcheck", "--includes-file=includes.txt", "file.cpp"};
     768           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     769           1 :         ASSERT_EQUALS(2, settings->includePaths.size());
     770           1 :         auto it = settings->includePaths.cbegin();
     771           1 :         ASSERT_EQUALS("path/sub/", *it++);
     772           1 :         ASSERT_EQUALS("path2/sub1/", *it);
     773             :     }
     774             : 
     775           1 :     void includesFileNoFile() {
     776           1 :         REDIRECT;
     777           1 :         const char * const argv[] = {"cppcheck", "--includes-file=fileThatDoesNotExist.txt", "file.cpp"};
     778           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     779           1 :         ASSERT_EQUALS("cppcheck: error: unable to open includes file at 'fileThatDoesNotExist.txt'\n", logger->str());
     780             :     }
     781             : 
     782           1 :     void configExcludesFile() {
     783           1 :         REDIRECT;
     784             :         ScopedFile file("excludes.txt",
     785             :                         "path/sub\n"
     786           4 :                         "path2/sub1\n");
     787           1 :         const char * const argv[] = {"cppcheck", "--config-excludes-file=excludes.txt", "file.cpp"};
     788           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     789           1 :         ASSERT_EQUALS(2, settings->configExcludePaths.size());
     790           1 :         auto it = settings->configExcludePaths.cbegin();
     791           1 :         ASSERT_EQUALS("path/sub/", *it++);
     792           1 :         ASSERT_EQUALS("path2/sub1/", *it);
     793             :     }
     794             : 
     795           1 :     void configExcludesFileNoFile() {
     796           1 :         REDIRECT;
     797           1 :         const char * const argv[] = {"cppcheck", "--config-excludes-file=fileThatDoesNotExist.txt", "file.cpp"};
     798           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     799           1 :         ASSERT_EQUALS("cppcheck: error: unable to open config excludes file at 'fileThatDoesNotExist.txt'\n", logger->str());
     800             :     }
     801             : 
     802           1 :     void enabledAll() {
     803           1 :         REDIRECT;
     804           1 :         const char * const argv[] = {"cppcheck", "--enable=all", "file.cpp"};
     805           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     806           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     807           1 :         ASSERT(settings->severity.isEnabled(Severity::style));
     808           1 :         ASSERT(settings->severity.isEnabled(Severity::warning));
     809           1 :         ASSERT(settings->checks.isEnabled(Checks::unusedFunction));
     810           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     811           1 :         ASSERT(!settings->checks.isEnabled(Checks::internalCheck));
     812             :     }
     813             : 
     814           1 :     void enabledStyle() {
     815           1 :         REDIRECT;
     816           1 :         const char * const argv[] = {"cppcheck", "--enable=style", "file.cpp"};
     817           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     818           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     819           1 :         ASSERT(settings->severity.isEnabled(Severity::style));
     820           1 :         ASSERT(settings->severity.isEnabled(Severity::warning));
     821           1 :         ASSERT(settings->severity.isEnabled(Severity::performance));
     822           1 :         ASSERT(settings->severity.isEnabled(Severity::portability));
     823           1 :         ASSERT(!settings->checks.isEnabled(Checks::unusedFunction));
     824           1 :         ASSERT(!settings->checks.isEnabled(Checks::internalCheck));
     825             :     }
     826             : 
     827           1 :     void enabledPerformance() {
     828           1 :         REDIRECT;
     829           1 :         const char * const argv[] = {"cppcheck", "--enable=performance", "file.cpp"};
     830           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     831           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     832           1 :         ASSERT(!settings->severity.isEnabled(Severity::style));
     833           1 :         ASSERT(!settings->severity.isEnabled(Severity::warning));
     834           1 :         ASSERT(settings->severity.isEnabled(Severity::performance));
     835           1 :         ASSERT(!settings->severity.isEnabled(Severity::portability));
     836           1 :         ASSERT(!settings->checks.isEnabled(Checks::unusedFunction));
     837           1 :         ASSERT(!settings->checks.isEnabled(Checks::missingInclude));
     838             :     }
     839             : 
     840           1 :     void enabledPortability() {
     841           1 :         REDIRECT;
     842           1 :         const char * const argv[] = {"cppcheck", "--enable=portability", "file.cpp"};
     843           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     844           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     845           1 :         ASSERT(!settings->severity.isEnabled(Severity::style));
     846           1 :         ASSERT(!settings->severity.isEnabled(Severity::warning));
     847           1 :         ASSERT(!settings->severity.isEnabled(Severity::performance));
     848           1 :         ASSERT(settings->severity.isEnabled(Severity::portability));
     849           1 :         ASSERT(!settings->checks.isEnabled(Checks::unusedFunction));
     850           1 :         ASSERT(!settings->checks.isEnabled(Checks::missingInclude));
     851             :     }
     852             : 
     853           1 :     void enabledInformation() {
     854           1 :         REDIRECT;
     855           1 :         const char * const argv[] = {"cppcheck", "--enable=information", "file.cpp"};
     856           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     857           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     858           1 :         ASSERT(settings->severity.isEnabled(Severity::information));
     859           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     860           1 :         ASSERT_EQUALS("cppcheck: '--enable=information' will no longer implicitly enable 'missingInclude' starting with 2.16. Please enable it explicitly if you require it.\n", logger->str());
     861             :     }
     862             : 
     863           1 :     void enabledUnusedFunction() {
     864           1 :         REDIRECT;
     865           1 :         const char * const argv[] = {"cppcheck", "--enable=unusedFunction", "file.cpp"};
     866           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     867           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     868           1 :         ASSERT(settings->checks.isEnabled(Checks::unusedFunction));
     869             :     }
     870             : 
     871           1 :     void enabledMissingInclude() {
     872           1 :         REDIRECT;
     873           1 :         const char * const argv[] = {"cppcheck", "--enable=missingInclude", "file.cpp"};
     874           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     875           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     876           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     877             :     }
     878             : 
     879           1 :     void disabledMissingIncludeWithInformation() {
     880           1 :         REDIRECT;
     881           1 :         const char * const argv[] = {"cppcheck", "--disable=missingInclude", "--enable=information", "file.cpp"};
     882           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     883           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     884           1 :         ASSERT(settings->severity.isEnabled(Severity::information));
     885           1 :         ASSERT(!settings->checks.isEnabled(Checks::missingInclude));
     886           1 :         ASSERT_EQUALS("", logger->str());
     887             :     }
     888             : 
     889           1 :     void enabledMissingIncludeWithInformation() {
     890           1 :         REDIRECT;
     891           1 :         const char * const argv[] = {"cppcheck", "--enable=information", "--enable=missingInclude", "file.cpp"};
     892           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     893           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     894           1 :         ASSERT(settings->severity.isEnabled(Severity::information));
     895           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     896           1 :         ASSERT_EQUALS("", logger->str());
     897             :     }
     898             : 
     899           1 :     void enabledMissingIncludeWithInformationReverseOrder() {
     900           1 :         REDIRECT;
     901           1 :         const char * const argv[] = {"cppcheck", "--enable=missingInclude", "--enable=information", "file.cpp"};
     902           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     903           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     904           1 :         ASSERT(settings->severity.isEnabled(Severity::information));
     905           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     906           1 :         ASSERT_EQUALS("", logger->str());
     907             :     }
     908             : 
     909             : #ifdef CHECK_INTERNAL
     910             :     void enabledInternal() {
     911             :         REDIRECT;
     912             :         const char * const argv[] = {"cppcheck", "--enable=internal", "file.cpp"};
     913             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     914             :         ASSERT(settings->severity.isEnabled(Severity::error));
     915             :         ASSERT(settings->checks.isEnabled(Checks::internalCheck));
     916             :     }
     917             : #endif
     918             : 
     919           1 :     void enabledMultiple() {
     920           1 :         REDIRECT;
     921           1 :         const char * const argv[] = {"cppcheck", "--enable=missingInclude,portability,warning", "file.cpp"};
     922           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
     923           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
     924           1 :         ASSERT(!settings->severity.isEnabled(Severity::style));
     925           1 :         ASSERT(settings->severity.isEnabled(Severity::warning));
     926           1 :         ASSERT(!settings->severity.isEnabled(Severity::performance));
     927           1 :         ASSERT(settings->severity.isEnabled(Severity::portability));
     928           1 :         ASSERT(!settings->checks.isEnabled(Checks::unusedFunction));
     929           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
     930             :     }
     931             : 
     932           1 :     void enabledInvalid() {
     933           1 :         REDIRECT;
     934           1 :         const char * const argv[] = {"cppcheck", "--enable=warning,missingIncludeSystem,style", "file.cpp"};
     935           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     936           1 :         ASSERT_EQUALS("cppcheck: error: --enable parameter with the unknown name 'missingIncludeSystem'\n", logger->str());
     937             :     }
     938             : 
     939           1 :     void enabledError() {
     940           1 :         REDIRECT;
     941           1 :         const char * const argv[] = {"cppcheck", "--enable=error", "file.cpp"};
     942           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     943           1 :         ASSERT_EQUALS("cppcheck: error: --enable parameter with the unknown name 'error'\n", logger->str());
     944             :     }
     945             : 
     946           1 :     void enabledEmpty() {
     947           1 :         REDIRECT;
     948           1 :         const char * const argv[] = {"cppcheck", "--enable=", "file.cpp"};
     949           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
     950           1 :         ASSERT_EQUALS("cppcheck: error: --enable parameter is empty\n", logger->str());
     951             :     }
     952             : 
     953             : 
     954           1 :     void disableAll() {
     955           1 :         REDIRECT;
     956           1 :         const char * const argv[] = {"cppcheck", "--enable=all", "--disable=all", "file.cpp"};
     957           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
     958           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::error));
     959           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::warning));
     960           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::style));
     961           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::performance));
     962           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::portability));
     963           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::debug));
     964           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::unusedFunction));
     965           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::missingInclude));
     966           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::internalCheck));
     967             :     }
     968             : 
     969           1 :     void disableMultiple() {
     970           1 :         REDIRECT;
     971           1 :         const char * const argv[] = {"cppcheck", "--enable=all", "--disable=style", "--disable=unusedFunction", "file.cpp"};
     972           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(5, argv));
     973           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::error));
     974           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
     975           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::style));
     976           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::performance));
     977           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::portability));
     978           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::debug));
     979           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::unusedFunction));
     980           1 :         ASSERT_EQUALS(true, settings->checks.isEnabled(Checks::missingInclude));
     981           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::internalCheck));
     982             :     }
     983             : 
     984             :     // make sure the implied "style" checks are not added when "--enable=style" is specified
     985           1 :     void disableStylePartial() {
     986           1 :         REDIRECT;
     987           1 :         const char * const argv[] = {"cppcheck", "--enable=style", "--disable=performance", "--enable=unusedFunction", "file.cpp"};
     988           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(5, argv));
     989           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::error));
     990           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
     991           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::style));
     992           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::performance));
     993           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::portability));
     994           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::debug));
     995           1 :         ASSERT_EQUALS(true, settings->checks.isEnabled(Checks::unusedFunction));
     996           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::missingInclude));
     997           1 :         ASSERT_EQUALS(false, settings->checks.isEnabled(Checks::internalCheck));
     998             :     }
     999             : 
    1000           1 :     void disableInformationPartial() {
    1001           1 :         REDIRECT;
    1002           1 :         const char * const argv[] = {"cppcheck", "--enable=information", "--disable=missingInclude", "file.cpp"};
    1003           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1004           1 :         ASSERT(settings->severity.isEnabled(Severity::information));
    1005           1 :         ASSERT(!settings->checks.isEnabled(Checks::missingInclude));
    1006           1 :         ASSERT_EQUALS("", logger->str());
    1007             :     }
    1008             : 
    1009           1 :     void disableInformationPartial2() {
    1010           1 :         REDIRECT;
    1011           1 :         const char * const argv[] = {"cppcheck", "--enable=missingInclude", "--disable=information", "file.cpp"};
    1012           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1013           1 :         ASSERT(!settings->severity.isEnabled(Severity::information));
    1014           1 :         ASSERT(settings->checks.isEnabled(Checks::missingInclude));
    1015             :     }
    1016             : 
    1017           1 :     void disableInvalid() {
    1018           1 :         REDIRECT;
    1019           1 :         const char * const argv[] = {"cppcheck", "--disable=leaks", "file.cpp"};
    1020           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1021           1 :         ASSERT_EQUALS("cppcheck: error: --disable parameter with the unknown name 'leaks'\n", logger->str());
    1022             :     }
    1023             : 
    1024           1 :     void disableError() {
    1025           1 :         REDIRECT;
    1026           1 :         const char * const argv[] = {"cppcheck", "--disable=error", "file.cpp"};
    1027           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1028           1 :         ASSERT_EQUALS("cppcheck: error: --disable parameter with the unknown name 'error'\n", logger->str());
    1029             :     }
    1030             : 
    1031           1 :     void disableEmpty() {
    1032           1 :         REDIRECT;
    1033           1 :         const char * const argv[] = {"cppcheck", "--disable=", "file.cpp"};
    1034           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1035           1 :         ASSERT_EQUALS("cppcheck: error: --disable parameter is empty\n", logger->str());
    1036             :     }
    1037             : 
    1038           1 :     void inconclusive() {
    1039           1 :         REDIRECT;
    1040           1 :         const char * const argv[] = {"cppcheck", "--inconclusive", "file.cpp"};
    1041           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1042           1 :         ASSERT_EQUALS(true, settings->certainty.isEnabled(Certainty::inconclusive));
    1043             :     }
    1044             : 
    1045           1 :     void errorExitcode() {
    1046           1 :         REDIRECT;
    1047           1 :         const char * const argv[] = {"cppcheck", "--error-exitcode=5", "file.cpp"};
    1048           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1049           1 :         ASSERT_EQUALS(5, settings->exitCode);
    1050             :     }
    1051             : 
    1052           1 :     void errorExitcodeMissing() {
    1053           1 :         REDIRECT;
    1054           1 :         const char * const argv[] = {"cppcheck", "--error-exitcode=", "file.cpp"};
    1055             :         // Fails since exit code not given
    1056           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1057           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--error-exitcode=' is not valid - not an integer.\n", logger->str());
    1058             :     }
    1059             : 
    1060           1 :     void errorExitcodeStr() {
    1061           1 :         REDIRECT;
    1062           1 :         const char * const argv[] = {"cppcheck", "--error-exitcode=foo", "file.cpp"};
    1063             :         // Fails since invalid exit code
    1064           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1065           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--error-exitcode=' is not valid - not an integer.\n", logger->str());
    1066             :     }
    1067             : 
    1068           1 :     void exitcodeSuppressionsOld() {
    1069           1 :         REDIRECT;
    1070           1 :         const char * const argv[] = {"cppcheck", "--exitcode-suppressions", "suppr.txt", "file.cpp"};
    1071           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1072           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--exitcode-suppressions\".\n", logger->str());
    1073             :     }
    1074             : 
    1075           1 :     void exitcodeSuppressions() {
    1076           1 :         REDIRECT;
    1077             :         ScopedFile file("suppr.txt",
    1078             :                         "uninitvar\n"
    1079           4 :                         "unusedFunction\n");
    1080           1 :         const char * const argv[] = {"cppcheck", "--exitcode-suppressions=suppr.txt", "file.cpp"};
    1081           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1082           1 :         ASSERT_EQUALS(2, settings->supprs.nofail.getSuppressions().size());
    1083           1 :         auto it = settings->supprs.nofail.getSuppressions().cbegin();
    1084           1 :         ASSERT_EQUALS("uninitvar", (it++)->errorId);
    1085           1 :         ASSERT_EQUALS("unusedFunction", it->errorId);
    1086             :     }
    1087             : 
    1088           1 :     void exitcodeSuppressionsNoFile() {
    1089           1 :         REDIRECT;
    1090           1 :         const char * const argv[] = {"cppcheck", "--exitcode-suppressions", "file.cpp"};
    1091           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1092           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--exitcode-suppressions\".\n", logger->str());
    1093             :     }
    1094             : 
    1095           1 :     void fileFilterStdin() {
    1096           1 :         REDIRECT;
    1097           2 :         RedirectInput input("file1.c\nfile2.cpp\n");
    1098           1 :         const char * const argv[] = {"cppcheck", "--file-filter=-"};
    1099           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1100           1 :         ASSERT_EQUALS("cppcheck: error: no C or C++ source files found.\n", logger->str());
    1101           1 :         ASSERT_EQUALS(2U, settings->fileFilters.size());
    1102           1 :         ASSERT_EQUALS("file1.c", settings->fileFilters[0]);
    1103           1 :         ASSERT_EQUALS("file2.cpp", settings->fileFilters[1]);
    1104             :     }
    1105             : 
    1106           1 :     void fileList() {
    1107           1 :         REDIRECT;
    1108             :         ScopedFile file("files.txt",
    1109             :                         "file1.c\n"
    1110           4 :                         "file2.cpp\n");
    1111           1 :         const char * const argv[] = {"cppcheck", "--file-list=files.txt", "file.cpp"};
    1112           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1113           1 :         ASSERT_EQUALS(3, parser->getPathNames().size());
    1114           1 :         auto it = parser->getPathNames().cbegin();
    1115           1 :         ASSERT_EQUALS("file1.c", *it++);
    1116           1 :         ASSERT_EQUALS("file2.cpp", *it++);
    1117           1 :         ASSERT_EQUALS("file.cpp", *it);
    1118             :     }
    1119             : 
    1120           1 :     void fileListNoFile() {
    1121           1 :         REDIRECT;
    1122           1 :         const char * const argv[] = {"cppcheck", "--file-list=files.txt", "file.cpp"};
    1123           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1124           1 :         ASSERT_EQUALS("cppcheck: error: couldn't open the file: \"files.txt\".\n", logger->str());
    1125             :     }
    1126             : 
    1127           1 :     void fileListStdin() {
    1128           1 :         REDIRECT;
    1129           2 :         RedirectInput input("file1.c\nfile2.cpp\n");
    1130           1 :         const char * const argv[] = {"cppcheck", "--file-list=-", "file.cpp"};
    1131           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1132           1 :         ASSERT_EQUALS(3, parser->getPathNames().size());
    1133           1 :         auto it = parser->getPathNames().cbegin();
    1134           1 :         ASSERT_EQUALS("file1.c", *it++);
    1135           1 :         ASSERT_EQUALS("file2.cpp", *it++);
    1136           1 :         ASSERT_EQUALS("file.cpp", *it);
    1137             :     }
    1138             : 
    1139           1 :     void fileListInvalid() {
    1140           1 :         REDIRECT;
    1141           1 :         const char * const argv[] = {"cppcheck", "--file-list", "files.txt", "file.cpp"};
    1142           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1143           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--file-list\".\n", logger->str());
    1144             :     }
    1145             : 
    1146           1 :     void inlineSuppr() {
    1147           1 :         REDIRECT;
    1148           1 :         const char * const argv[] = {"cppcheck", "--inline-suppr", "file.cpp"};
    1149           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1150           1 :         ASSERT(settings->inlineSuppressions);
    1151             :     }
    1152             : 
    1153           1 :     void jobs() {
    1154           1 :         REDIRECT;
    1155           1 :         const char * const argv[] = {"cppcheck", "-j", "3", "file.cpp"};
    1156           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1157           1 :         ASSERT_EQUALS(3, settings->jobs);
    1158             :     }
    1159             : 
    1160           1 :     void jobs2() {
    1161           1 :         REDIRECT;
    1162           1 :         const char * const argv[] = {"cppcheck", "-j3", "file.cpp"};
    1163           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1164           1 :         ASSERT_EQUALS(3, settings->jobs);
    1165             :     }
    1166             : 
    1167           1 :     void jobsMissingCount() {
    1168           1 :         REDIRECT;
    1169           1 :         const char * const argv[] = {"cppcheck", "-j", "file.cpp"};
    1170             :         // Fails since -j is missing thread count
    1171           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1172           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-j' is not valid - not an integer.\n", logger->str());
    1173             :     }
    1174             : 
    1175           1 :     void jobsInvalid() {
    1176           1 :         REDIRECT;
    1177           1 :         const char * const argv[] = {"cppcheck", "-j", "e", "file.cpp"};
    1178             :         // Fails since invalid count given for -j
    1179           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1180           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-j' is not valid - not an integer.\n", logger->str());
    1181             :     }
    1182             : 
    1183           1 :     void jobsNoJobs() {
    1184           1 :         REDIRECT;
    1185           1 :         const char * const argv[] = {"cppcheck", "-j0", "file.cpp"};
    1186           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1187           1 :         ASSERT_EQUALS("cppcheck: error: argument for '-j' must be greater than 0.\n", logger->str());
    1188             :     }
    1189             : 
    1190           1 :     void jobsTooBig() {
    1191           1 :         REDIRECT;
    1192           1 :         const char * const argv[] = {"cppcheck", "-j1025", "file.cpp"};
    1193           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1194           1 :         ASSERT_EQUALS("cppcheck: error: argument for '-j' is allowed to be 1024 at max.\n", logger->str());
    1195             :     }
    1196             : 
    1197           1 :     void maxConfigs() {
    1198           1 :         REDIRECT;
    1199           1 :         const char * const argv[] = {"cppcheck", "-f", "--max-configs=12", "file.cpp"};
    1200           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1201           1 :         ASSERT_EQUALS(12, settings->maxConfigs);
    1202           1 :         ASSERT_EQUALS(false, settings->force);
    1203             :     }
    1204             : 
    1205           1 :     void maxConfigsMissingCount() {
    1206           1 :         REDIRECT;
    1207           1 :         const char * const argv[] = {"cppcheck", "--max-configs=", "file.cpp"};
    1208             :         // Fails since --max-configs= is missing limit
    1209           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1210           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--max-configs=' is not valid - not an integer.\n", logger->str());
    1211             :     }
    1212             : 
    1213           1 :     void maxConfigsInvalid() {
    1214           1 :         REDIRECT;
    1215           1 :         const char * const argv[] = {"cppcheck", "--max-configs=e", "file.cpp"};
    1216             :         // Fails since invalid count given for --max-configs=
    1217           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1218           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--max-configs=' is not valid - not an integer.\n", logger->str());
    1219             :     }
    1220             : 
    1221           1 :     void maxConfigsTooSmall() {
    1222           1 :         REDIRECT;
    1223           1 :         const char * const argv[] = {"cppcheck", "--max-configs=0", "file.cpp"};
    1224             :         // Fails since limit must be greater than 0
    1225           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1226           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--max-configs=' must be greater than 0.\n", logger->str());
    1227             :     }
    1228             : 
    1229           1 :     void premiumOptions1() {
    1230           1 :         REDIRECT;
    1231           1 :         asPremium();
    1232           1 :         const char * const argv[] = {"cppcheck", "--premium=autosar", "file.c"};
    1233           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1234           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
    1235           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
    1236             :     }
    1237             : 
    1238           1 :     void premiumOptions2() {
    1239           1 :         REDIRECT;
    1240           1 :         asPremium();
    1241           1 :         const char * const argv[] = {"cppcheck", "--premium=misra-c-2012", "file.c"};
    1242           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1243           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
    1244           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
    1245             :     }
    1246             : 
    1247           1 :     void premiumOptions3() {
    1248           1 :         REDIRECT;
    1249           1 :         asPremium();
    1250           1 :         const char * const argv[] = {"cppcheck", "--premium=misra-c++-2023", "file.c"};
    1251           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1252           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
    1253           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
    1254             :     }
    1255             : 
    1256           1 :     void premiumOptions4() {
    1257           1 :         REDIRECT;
    1258           1 :         asPremium();
    1259           1 :         const char * const argv[] = {"cppcheck", "--premium=cert-c++-2016", "file.c"};
    1260           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1261           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
    1262           1 :         ASSERT_EQUALS(true, settings->severity.isEnabled(Severity::warning));
    1263             :     }
    1264             : 
    1265           1 :     void premiumOptions5() {
    1266           1 :         REDIRECT;
    1267           1 :         asPremium();
    1268           1 :         const char * const argv[] = {"cppcheck", "--premium=safety", "file.c"};
    1269           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1270           1 :         ASSERT(settings->severity.isEnabled(Severity::error));
    1271           1 :         ASSERT_EQUALS(false, settings->severity.isEnabled(Severity::warning));
    1272             :     }
    1273             : 
    1274           1 :     void premiumOptionsInvalid1() {
    1275           1 :         REDIRECT;
    1276           1 :         asPremium();
    1277           1 :         const char * const argv[] = {"cppcheck", "--premium=misra", "file.c"};
    1278           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1279           1 :         ASSERT_EQUALS("cppcheck: error: invalid --premium option 'misra'.\n", logger->str());
    1280             :     }
    1281             : 
    1282           1 :     void premiumOptionsInvalid2() {
    1283           1 :         REDIRECT;
    1284           1 :         asPremium();
    1285           1 :         const char * const argv[] = {"cppcheck", "--premium=cert", "file.c"};
    1286           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1287           1 :         ASSERT_EQUALS("cppcheck: error: invalid --premium option 'cert'.\n", logger->str());
    1288             :     }
    1289             : 
    1290           1 :     void premiumSafety() {
    1291           1 :         REDIRECT;
    1292           1 :         asPremium();
    1293           1 :         const char * const argv[] = {"cppcheck", "--premium=safety", "file.cpp"};
    1294           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1295           1 :         ASSERT_EQUALS(true, settings->safety);
    1296             :     }
    1297             : 
    1298           1 :     void reportProgress1() {
    1299           1 :         REDIRECT;
    1300           1 :         const char * const argv[] = {"cppcheck", "--report-progress", "file.cpp"};
    1301           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1302           1 :         ASSERT_EQUALS(10, settings->reportProgress);
    1303             :     }
    1304             : 
    1305           1 :     void reportProgress2() {
    1306           1 :         REDIRECT;
    1307           1 :         const char * const argv[] = {"cppcheck", "--report-progress=", "file.cpp"};
    1308           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1309           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--report-progress=' is not valid - not an integer.\n", logger->str());
    1310             :     }
    1311             : 
    1312           1 :     void reportProgress3() {
    1313           1 :         REDIRECT;
    1314           1 :         const char * const argv[] = {"cppcheck", "--report-progress=-1", "file.cpp"};
    1315           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1316           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--report-progress=' needs to be a positive integer.\n", logger->str());
    1317             :     }
    1318             : 
    1319           1 :     void reportProgress4() {
    1320           1 :         REDIRECT;
    1321           1 :         const char * const argv[] = {"cppcheck", "--report-progress=0", "file.cpp"};
    1322           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1323           1 :         ASSERT_EQUALS(0, settings->reportProgress);
    1324             :     }
    1325             : 
    1326           1 :     void reportProgress5() {
    1327           1 :         REDIRECT;
    1328           1 :         const char * const argv[] = {"cppcheck", "--report-progress=1", "file.cpp"};
    1329           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1330           1 :         ASSERT_EQUALS(1, settings->reportProgress);
    1331             :     }
    1332             : 
    1333           1 :     void stdc99() {
    1334           1 :         REDIRECT;
    1335           1 :         const char * const argv[] = {"cppcheck", "--std=c99", "file.cpp"};
    1336           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1337           1 :         ASSERT(settings->standards.c == Standards::C99);
    1338             :     }
    1339             : 
    1340           1 :     void stdcpp11() {
    1341           1 :         REDIRECT;
    1342           1 :         const char * const argv[] = {"cppcheck", "--std=c++11", "file.cpp"};
    1343           1 :         settings->standards.cpp = Standards::CPP03;
    1344           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1345           1 :         ASSERT(settings->standards.cpp == Standards::CPP11);
    1346             :     }
    1347             : 
    1348           1 :     void stdunknown1() {
    1349           1 :         REDIRECT;
    1350           1 :         const char *const argv[] = {"cppcheck", "--std=d++11", "file.cpp"};
    1351           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1352           1 :         ASSERT_EQUALS("cppcheck: error: unknown --std value 'd++11'\n", logger->str());
    1353             :     }
    1354             : 
    1355           1 :     void stdunknown2() {
    1356           1 :         REDIRECT;
    1357           1 :         const char *const argv[] = {"cppcheck", "--std=cplusplus11", "file.cpp"};
    1358           1 :         TODO_ASSERT_EQUALS(static_cast<int>(CmdLineParser::Result::Fail), static_cast<int>(CmdLineParser::Result::Success), static_cast<int>(parser->parseFromArgs(3, argv)));
    1359           1 :         TODO_ASSERT_EQUALS("cppcheck: error: unknown --std value 'cplusplus11'\n", "", logger->str());
    1360           1 :     }
    1361             : 
    1362           1 :     void platformWin64() {
    1363           1 :         REDIRECT;
    1364           1 :         const char * const argv[] = {"cppcheck", "--platform=win64", "file.cpp"};
    1365           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1366           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1367           1 :         ASSERT_EQUALS(Platform::Type::Win64, settings->platform.type);
    1368             :     }
    1369             : 
    1370           1 :     void platformWin32A() {
    1371           1 :         REDIRECT;
    1372           1 :         const char * const argv[] = {"cppcheck", "--platform=win32A", "file.cpp"};
    1373           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1374           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1375           1 :         ASSERT_EQUALS(Platform::Type::Win32A, settings->platform.type);
    1376             :     }
    1377             : 
    1378           1 :     void platformWin32W() {
    1379           1 :         REDIRECT;
    1380           1 :         const char * const argv[] = {"cppcheck", "--platform=win32W", "file.cpp"};
    1381           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1382           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1383           1 :         ASSERT_EQUALS(Platform::Type::Win32W, settings->platform.type);
    1384             :     }
    1385             : 
    1386           1 :     void platformUnix32() {
    1387           1 :         REDIRECT;
    1388           1 :         const char * const argv[] = {"cppcheck", "--platform=unix32", "file.cpp"};
    1389           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1390           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1391           1 :         ASSERT_EQUALS(Platform::Type::Unix32, settings->platform.type);
    1392             :     }
    1393             : 
    1394           1 :     void platformUnix32Unsigned() {
    1395           1 :         REDIRECT;
    1396           1 :         const char * const argv[] = {"cppcheck", "--platform=unix32-unsigned", "file.cpp"};
    1397           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1398           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1399           1 :         ASSERT_EQUALS(Platform::Type::Unix32, settings->platform.type);
    1400             :     }
    1401             : 
    1402           1 :     void platformUnix64() {
    1403           1 :         REDIRECT;
    1404           1 :         const char * const argv[] = {"cppcheck", "--platform=unix64", "file.cpp"};
    1405           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1406           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1407           1 :         ASSERT_EQUALS(Platform::Type::Unix64, settings->platform.type);
    1408             :     }
    1409             : 
    1410           1 :     void platformUnix64Unsigned() {
    1411           1 :         REDIRECT;
    1412           1 :         const char * const argv[] = {"cppcheck", "--platform=unix64-unsigned", "file.cpp"};
    1413           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1414           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1415           1 :         ASSERT_EQUALS(Platform::Type::Unix64, settings->platform.type);
    1416             :     }
    1417             : 
    1418           1 :     void platformNative() {
    1419           1 :         REDIRECT;
    1420           1 :         const char * const argv[] = {"cppcheck", "--platform=native", "file.cpp"};
    1421           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1422           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1423           1 :         ASSERT_EQUALS(Platform::Type::Native, settings->platform.type);
    1424             :     }
    1425             : 
    1426           1 :     void platformUnspecified() {
    1427           1 :         REDIRECT;
    1428           1 :         const char * const argv[] = {"cppcheck", "--platform=unspecified", "file.cpp"};
    1429           1 :         ASSERT(settings->platform.set(Platform::Type::Native));
    1430           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1431           1 :         ASSERT_EQUALS(Platform::Type::Unspecified, settings->platform.type);
    1432             :     }
    1433             : 
    1434           1 :     void platformPlatformFile() {
    1435           1 :         REDIRECT;
    1436           1 :         const char * const argv[] = {"cppcheck", "--platform=avr8", "file.cpp"};
    1437           1 :         ASSERT(settings->platform.set(Platform::Type::Unspecified));
    1438           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1439           1 :         ASSERT_EQUALS(Platform::Type::File, settings->platform.type);
    1440             :     }
    1441             : 
    1442           1 :     void platformUnknown() {
    1443           1 :         REDIRECT;
    1444           1 :         const char * const argv[] = {"cppcheck", "--platform=win128", "file.cpp"};
    1445           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1446           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized platform: 'win128'.\n", logger->str());
    1447             :     }
    1448             : 
    1449           1 :     void plistEmpty() {
    1450           1 :         REDIRECT;
    1451           1 :         const char * const argv[] = {"cppcheck", "--plist-output=", "file.cpp"};
    1452           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1453           1 :         ASSERT(settings->plistOutput == "./");
    1454             :     }
    1455             : 
    1456           1 :     void plistDoesNotExist() {
    1457           1 :         REDIRECT;
    1458           1 :         const char * const argv[] = {"cppcheck", "--plist-output=./cppcheck_reports", "file.cpp"};
    1459             :         // Fails since folder pointed by --plist-output= does not exist
    1460           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1461           1 :         ASSERT_EQUALS("cppcheck: error: plist folder does not exist: 'cppcheck_reports'.\n", logger->str());
    1462             :     }
    1463             : 
    1464           1 :     void suppressionsOld() {
    1465           1 :         REDIRECT;
    1466           1 :         const char * const argv[] = {"cppcheck", "--suppressions", "suppr.txt", "file.cpp"};
    1467           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1468           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--suppressions\".\n", logger->str());
    1469             :     }
    1470             : 
    1471           1 :     void suppressions() {
    1472           1 :         REDIRECT;
    1473             :         ScopedFile file("suppr.txt",
    1474             :                         "uninitvar\n"
    1475           4 :                         "unusedFunction\n");
    1476           1 :         const char * const argv[] = {"cppcheck", "--suppressions-list=suppr.txt", "file.cpp"};
    1477           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1478           1 :         ASSERT_EQUALS(2, settings->supprs.nomsg.getSuppressions().size());
    1479           1 :         auto it = settings->supprs.nomsg.getSuppressions().cbegin();
    1480           1 :         ASSERT_EQUALS("uninitvar", (it++)->errorId);
    1481           1 :         ASSERT_EQUALS("unusedFunction", it->errorId);
    1482             :     }
    1483             : 
    1484           1 :     void suppressionsNoFile1() {
    1485           1 :         REDIRECT;
    1486           1 :         const char * const argv[] = {"cppcheck", "--suppressions-list=", "file.cpp"};
    1487           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1488           1 :         ASSERT_EQUALS(false, logger->str().find("If you want to pass two files") != std::string::npos);
    1489             :     }
    1490             : 
    1491           1 :     void suppressionsNoFile2() {
    1492           1 :         REDIRECT;
    1493           1 :         const char * const argv[] = {"cppcheck", "--suppressions-list=a.suppr,b.suppr", "file.cpp"};
    1494           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1495           1 :         ASSERT_EQUALS(true, logger->str().find("If you want to pass two files") != std::string::npos);
    1496             :     }
    1497             : 
    1498           1 :     void suppressionsNoFile3() {
    1499           1 :         REDIRECT;
    1500           1 :         const char * const argv[] = {"cppcheck", "--suppressions-list=a.suppr b.suppr", "file.cpp"};
    1501           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1502           1 :         ASSERT_EQUALS(true, logger->str().find("If you want to pass two files") != std::string::npos);
    1503             :     }
    1504             : 
    1505           6 :     static SuppressionList::ErrorMessage errorMessage(const std::string &errorId, const std::string &fileName, int lineNumber) {
    1506           6 :         SuppressionList::ErrorMessage e;
    1507           6 :         e.errorId = errorId;
    1508           6 :         e.setFileName(fileName);
    1509           6 :         e.lineNumber = lineNumber;
    1510           6 :         return e;
    1511             :     }
    1512             : 
    1513           1 :     void suppressionSingle() {
    1514           1 :         REDIRECT;
    1515           1 :         const char * const argv[] = {"cppcheck", "--suppress=uninitvar", "file.cpp"};
    1516           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1517           1 :         ASSERT_EQUALS(true, settings->supprs.nomsg.isSuppressed(errorMessage("uninitvar", "file.cpp", 1)));
    1518             :     }
    1519             : 
    1520           1 :     void suppressionSingleFile() {
    1521           1 :         REDIRECT;
    1522           1 :         const char * const argv[] = {"cppcheck", "--suppress=uninitvar:file.cpp", "file.cpp"};
    1523           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1524           1 :         ASSERT_EQUALS(true, settings->supprs.nomsg.isSuppressed(errorMessage("uninitvar", "file.cpp", 1U)));
    1525             :     }
    1526             : 
    1527           1 :     void suppressionTwo() {
    1528           1 :         REDIRECT;
    1529           1 :         const char * const argv[] = {"cppcheck", "--suppress=uninitvar,noConstructor", "file.cpp"};
    1530           1 :         TODO_ASSERT_EQUALS(static_cast<int>(CmdLineParser::Result::Success), static_cast<int>(CmdLineParser::Result::Fail), static_cast<int>(parser->parseFromArgs(3, argv)));
    1531           1 :         TODO_ASSERT_EQUALS(true, false, settings->supprs.nomsg.isSuppressed(errorMessage("uninitvar", "file.cpp", 1U)));
    1532           1 :         TODO_ASSERT_EQUALS(true, false, settings->supprs.nomsg.isSuppressed(errorMessage("noConstructor", "file.cpp", 1U)));
    1533           1 :         TODO_ASSERT_EQUALS("", "cppcheck: error: Failed to add suppression. Invalid id \"uninitvar,noConstructor\"\n", logger->str());
    1534           1 :     }
    1535             : 
    1536           1 :     void suppressionTwoSeparate() {
    1537           1 :         REDIRECT;
    1538           1 :         const char * const argv[] = {"cppcheck", "--suppress=uninitvar", "--suppress=noConstructor", "file.cpp"};
    1539           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1540           1 :         ASSERT_EQUALS(true, settings->supprs.nomsg.isSuppressed(errorMessage("uninitvar", "file.cpp", 1U)));
    1541           1 :         ASSERT_EQUALS(true, settings->supprs.nomsg.isSuppressed(errorMessage("noConstructor", "file.cpp", 1U)));
    1542             :     }
    1543             : 
    1544           1 :     void templates() {
    1545           1 :         REDIRECT;
    1546           1 :         const char * const argv[] = {"cppcheck", "--template={file}:{line},{severity},{id},{message}", "--template-location={file}:{line}:{column} {info}", "file.cpp"};
    1547           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1548           1 :         ASSERT_EQUALS("{file}:{line},{severity},{id},{message}", settings->templateFormat);
    1549           1 :         ASSERT_EQUALS("{file}:{line}:{column} {info}", settings->templateLocation);
    1550             :     }
    1551             : 
    1552           1 :     void templatesGcc() {
    1553           1 :         REDIRECT;
    1554           1 :         const char * const argv[] = {"cppcheck", "--template=gcc", "file.cpp"};
    1555           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1556           1 :         ASSERT_EQUALS("{file}:{line}:{column}: warning: {message} [{id}]\n{code}", settings->templateFormat);
    1557           1 :         ASSERT_EQUALS("{file}:{line}:{column}: note: {info}\n{code}", settings->templateLocation);
    1558             :     }
    1559             : 
    1560           1 :     void templatesVs() {
    1561           1 :         REDIRECT;
    1562           1 :         const char * const argv[] = {"cppcheck", "--template=vs", "file.cpp"};
    1563           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1564           1 :         ASSERT_EQUALS("{file}({line}): {severity}: {message}", settings->templateFormat);
    1565           1 :         ASSERT_EQUALS("", settings->templateLocation);
    1566             :     }
    1567             : 
    1568           1 :     void templatesEdit() {
    1569           1 :         REDIRECT;
    1570           1 :         const char * const argv[] = {"cppcheck", "--template=edit", "file.cpp"};
    1571           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1572           1 :         ASSERT_EQUALS("{file} +{line}: {severity}: {message}", settings->templateFormat);
    1573           1 :         ASSERT_EQUALS("", settings->templateLocation);
    1574             :     }
    1575             : 
    1576           1 :     void templatesCppcheck1() {
    1577           1 :         REDIRECT;
    1578           1 :         const char * const argv[] = {"cppcheck", "--template=cppcheck1", "file.cpp"};
    1579           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1580           1 :         ASSERT_EQUALS("{callstack}: ({severity}{inconclusive:, inconclusive}) {message}", settings->templateFormat);
    1581           1 :         ASSERT_EQUALS("", settings->templateLocation);
    1582             :     }
    1583             : 
    1584           1 :     void templatesDaca2() {
    1585           1 :         REDIRECT;
    1586           1 :         const char * const argv[] = {"cppcheck", "--template=daca2", "file.cpp"};
    1587           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1588           1 :         ASSERT_EQUALS("{file}:{line}:{column}: {severity}:{inconclusive:inconclusive:} {message} [{id}]", settings->templateFormat);
    1589           1 :         ASSERT_EQUALS("{file}:{line}:{column}: note: {info}", settings->templateLocation);
    1590           1 :         ASSERT_EQUALS(true, settings->daca);
    1591             :     }
    1592             : 
    1593           1 :     void templatesSelfcheck() {
    1594           1 :         REDIRECT;
    1595           1 :         const char * const argv[] = {"cppcheck", "--template=selfcheck", "file.cpp"};
    1596           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1597           1 :         ASSERT_EQUALS("{file}:{line}:{column}: {severity}:{inconclusive:inconclusive:} {message} [{id}]\n{code}", settings->templateFormat);
    1598           1 :         ASSERT_EQUALS("{file}:{line}:{column}: note: {info}\n{code}", settings->templateLocation);
    1599             :     }
    1600             : 
    1601           1 :     void templatesSimple() {
    1602           1 :         REDIRECT;
    1603           1 :         const char * const argv[] = {"cppcheck", "--template=simple", "file.cpp"};
    1604           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1605           1 :         ASSERT_EQUALS("{file}:{line}:{column}: {severity}:{inconclusive:inconclusive:} {message} [{id}]", settings->templateFormat);
    1606           1 :         ASSERT_EQUALS("", settings->templateLocation);
    1607             :     }
    1608             : 
    1609             :     // TODO: we should bail out on this
    1610           1 :     void templatesNoPlaceholder() {
    1611           1 :         REDIRECT;
    1612           1 :         const char * const argv[] = {"cppcheck", "--template=selfchek", "file.cpp"};
    1613           1 :         TODO_ASSERT_EQUALS(static_cast<int>(CmdLineParser::Result::Fail), static_cast<int>(CmdLineParser::Result::Success), static_cast<int>(parser->parseFromArgs(3, argv)));
    1614           1 :         ASSERT_EQUALS("selfchek", settings->templateFormat);
    1615           1 :         ASSERT_EQUALS("", settings->templateLocation);
    1616             :     }
    1617             : 
    1618           1 :     void templateFormatInvalid() {
    1619           1 :         REDIRECT;
    1620           1 :         const char* const argv[] = { "cppcheck", "--template", "file.cpp" };
    1621           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1622           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--template\".\n", logger->str());
    1623             :     }
    1624             : 
    1625             :     // will use the default
    1626             :     // TODO: bail out on empty?
    1627           1 :     void templateFormatEmpty() {
    1628           1 :         REDIRECT;
    1629           1 :         const char* const argv[] = { "cppcheck", "--template=", "file.cpp" };
    1630           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1631           1 :         ASSERT_EQUALS("{file}:{line}:{column}: {inconclusive:}{severity}:{inconclusive: inconclusive:} {message} [{id}]\n{code}", settings->templateFormat);
    1632           1 :         ASSERT_EQUALS("{file}:{line}:{column}: note: {info}\n{code}", settings->templateLocation);
    1633             :     }
    1634             : 
    1635           1 :     void templateLocationInvalid() {
    1636           1 :         REDIRECT;
    1637           1 :         const char* const argv[] = { "cppcheck", "--template-location", "--template={file}", "file.cpp" };
    1638           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1639           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--template-location\".\n", logger->str());
    1640             :     }
    1641             : 
    1642             :     // will use the default
    1643             :     // TODO: bail out on empty?
    1644           1 :     void templateLocationEmpty() {
    1645           1 :         REDIRECT;
    1646           1 :         const char* const argv[] = { "cppcheck", "--template-location=", "file.cpp" };
    1647           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1648           1 :         ASSERT_EQUALS("{file}:{line}:{column}: {inconclusive:}{severity}:{inconclusive: inconclusive:} {message} [{id}]\n{code}", settings->templateFormat);
    1649           1 :         ASSERT_EQUALS("{file}:{line}:{column}: note: {info}\n{code}", settings->templateLocation);
    1650             :     }
    1651             : 
    1652           1 :     void xml() {
    1653           1 :         REDIRECT;
    1654           1 :         const char * const argv[] = {"cppcheck", "--xml", "file.cpp"};
    1655           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1656           1 :         ASSERT(settings->xml);
    1657           1 :         ASSERT_EQUALS(2, settings->xml_version);
    1658             :     }
    1659             : 
    1660           1 :     void xmlver2() {
    1661           1 :         REDIRECT;
    1662           1 :         const char * const argv[] = {"cppcheck", "--xml-version=2", "file.cpp"};
    1663           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1664           1 :         ASSERT(settings->xml);
    1665           1 :         ASSERT_EQUALS(2, settings->xml_version);
    1666             :     }
    1667             : 
    1668           1 :     void xmlver2both() {
    1669           1 :         REDIRECT;
    1670           1 :         const char * const argv[] = {"cppcheck", "--xml", "--xml-version=2", "file.cpp"};
    1671           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1672           1 :         ASSERT(settings->xml);
    1673           1 :         ASSERT_EQUALS(2, settings->xml_version);
    1674             :     }
    1675             : 
    1676           1 :     void xmlver2both2() {
    1677           1 :         REDIRECT;
    1678           1 :         const char * const argv[] = {"cppcheck", "--xml-version=2", "--xml", "file.cpp"};
    1679           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1680           1 :         ASSERT(settings->xml);
    1681           1 :         ASSERT_EQUALS(2, settings->xml_version);
    1682             :     }
    1683             : 
    1684           1 :     void xmlverunknown() {
    1685           1 :         REDIRECT;
    1686           1 :         const char * const argv[] = {"cppcheck", "--xml", "--xml-version=3", "file.cpp"};
    1687             :         // FAils since unknown XML format version
    1688           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1689           1 :         ASSERT_EQUALS("cppcheck: error: '--xml-version' can only be 2.\n", logger->str());
    1690             :     }
    1691             : 
    1692           1 :     void xmlverinvalid() {
    1693           1 :         REDIRECT;
    1694           1 :         const char * const argv[] = {"cppcheck", "--xml", "--xml-version=a", "file.cpp"};
    1695             :         // FAils since unknown XML format version
    1696           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1697           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--xml-version=' is not valid - not an integer.\n", logger->str());
    1698             :     }
    1699             : 
    1700           1 :     void doc() {
    1701           1 :         REDIRECT;
    1702           1 :         const char * const argv[] = {"cppcheck", "--doc"};
    1703           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
    1704           1 :         ASSERT(startsWith(logger->str(), "## "));
    1705             :     }
    1706             : 
    1707           1 :     void docExclusive() {
    1708           1 :         REDIRECT;
    1709           1 :         const char * const argv[] = {"cppcheck", "--library=missing", "--doc"};
    1710           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(3, argv));
    1711           1 :         ASSERT(startsWith(logger->str(), "## "));
    1712             :     }
    1713             : 
    1714             :     void showtimeSummary() {
    1715             :         REDIRECT;
    1716             :         const char * const argv[] = {"cppcheck", "--showtime=summary", "file.cpp"};
    1717             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1718             :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_SUMMARY);
    1719             :     }
    1720             : 
    1721           1 :     void showtimeFile() {
    1722           1 :         REDIRECT;
    1723           1 :         const char * const argv[] = {"cppcheck", "--showtime=file", "file.cpp"};
    1724           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1725           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_FILE);
    1726             :     }
    1727             : 
    1728           1 :     void showtimeFileTotal() {
    1729           1 :         REDIRECT;
    1730           1 :         const char * const argv[] = {"cppcheck", "--showtime=file-total", "file.cpp"};
    1731           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1732           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_FILE_TOTAL);
    1733             :     }
    1734             : 
    1735           1 :     void showtimeTop5() {
    1736           1 :         REDIRECT;
    1737           1 :         const char * const argv[] = {"cppcheck", "--showtime=top5", "file.cpp"};
    1738           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1739           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_TOP5_FILE);
    1740           1 :         ASSERT_EQUALS("cppcheck: --showtime=top5 is deprecated and will be removed in Cppcheck 2.14. Please use --showtime=top5_file or --showtime=top5_summary instead.\n", logger->str());
    1741             :     }
    1742             : 
    1743           1 :     void showtimeTop5File() {
    1744           1 :         REDIRECT;
    1745           1 :         const char * const argv[] = {"cppcheck", "--showtime=top5_file", "file.cpp"};
    1746           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1747           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_TOP5_FILE);
    1748             :     }
    1749             : 
    1750           1 :     void showtimeTop5Summary() {
    1751           1 :         REDIRECT;
    1752           1 :         const char * const argv[] = {"cppcheck", "--showtime=top5_summary", "file.cpp"};
    1753           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1754           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_TOP5_SUMMARY);
    1755             :     }
    1756             : 
    1757           1 :     void showtimeNone() {
    1758           1 :         REDIRECT;
    1759           1 :         const char * const argv[] = {"cppcheck", "--showtime=none", "file.cpp"};
    1760           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1761           1 :         ASSERT(settings->showtime == SHOWTIME_MODES::SHOWTIME_NONE);
    1762             :     }
    1763             : 
    1764           1 :     void showtimeEmpty() {
    1765           1 :         REDIRECT;
    1766           1 :         const char * const argv[] = {"cppcheck", "--showtime=", "file.cpp"};
    1767           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1768           1 :         ASSERT_EQUALS("cppcheck: error: no mode provided for --showtime\n", logger->str());
    1769             :     }
    1770             : 
    1771           1 :     void showtimeInvalid() {
    1772           1 :         REDIRECT;
    1773           1 :         const char * const argv[] = {"cppcheck", "--showtime=top10", "file.cpp"};
    1774           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1775           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized --showtime mode: 'top10'. Supported modes: file, file-total, summary, top5, top5_file, top5_summary.\n", logger->str());
    1776             :     }
    1777             : 
    1778           1 :     void errorlist() {
    1779           1 :         REDIRECT;
    1780           1 :         const char * const argv[] = {"cppcheck", "--errorlist"};
    1781           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
    1782           1 :         ASSERT_EQUALS("", logger->str()); // empty since it is logged via ErrorLogger
    1783           1 :         const std::string errout_s = GET_REDIRECT_OUTPUT;
    1784           1 :         ASSERT(startsWith(errout_s, ErrorMessage::getXMLHeader("")));
    1785           1 :         ASSERT(endsWith(errout_s, "</results>\n"));
    1786             :     }
    1787             : 
    1788           1 :     void errorlistWithCfg() {
    1789           1 :         REDIRECT;
    1790           2 :         ScopedFile file(Path::join(Path::getPathFromFilename(Path::getCurrentExecutablePath("")), "cppcheck.cfg"),
    1791           4 :                         R"({"productName": "The Product"}\n)");
    1792           1 :         const char * const argv[] = {"cppcheck", "--errorlist"};
    1793           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(2, argv));
    1794           1 :         ASSERT_EQUALS("", logger->str()); // empty since it is logged via ErrorLogger
    1795           1 :         ASSERT(startsWith(GET_REDIRECT_OUTPUT, ErrorMessage::getXMLHeader("The Product")));
    1796             :     }
    1797             : 
    1798           1 :     void errorlistExclusive() {
    1799           1 :         REDIRECT;
    1800           1 :         const char * const argv[] = {"cppcheck", "--library=missing", "--errorlist"};
    1801           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Exit, parser->parseFromArgs(3, argv));
    1802           1 :         ASSERT_EQUALS("", logger->str()); // empty since it is logged via ErrorLogger
    1803           1 :         const std::string errout_s = GET_REDIRECT_OUTPUT;
    1804           1 :         ASSERT(startsWith(errout_s, ErrorMessage::getXMLHeader("")));
    1805           1 :         ASSERT(endsWith(errout_s, "</results>\n"));
    1806             :     }
    1807             : 
    1808           1 :     void errorlistWithInvalidCfg() {
    1809           1 :         REDIRECT;
    1810           2 :         ScopedFile file(Path::join(Path::getPathFromFilename(Path::getCurrentExecutablePath("")), "cppcheck.cfg"),
    1811           4 :                         "{\n");
    1812           1 :         const char * const argv[] = {"cppcheck", "--errorlist"};
    1813           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1814           1 :         ASSERT_EQUALS("cppcheck: error: could not load cppcheck.cfg - not a valid JSON - syntax error at line 2 near: \n", logger->str());
    1815             :     }
    1816             : 
    1817           1 :     void ignorepathsnopath() {
    1818           1 :         REDIRECT;
    1819           1 :         const char * const argv[] = {"cppcheck", "-i"};
    1820             :         // Fails since no ignored path given
    1821           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1822           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-i' is missing.\n", logger->str());
    1823             :     }
    1824             : 
    1825             : #if defined(USE_WINDOWS_SEH) || defined(USE_UNIX_SIGNAL_HANDLING)
    1826           1 :     void exceptionhandling() {
    1827           1 :         REDIRECT;
    1828           1 :         const char * const argv[] = {"cppcheck", "--exception-handling", "file.cpp"};
    1829           1 :         CppCheckExecutor::setExceptionOutput(stderr);
    1830           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1831           1 :         ASSERT(settings->exceptionHandling);
    1832           1 :         ASSERT_EQUALS(stderr, CppCheckExecutor::getExceptionOutput());
    1833             :     }
    1834             : 
    1835           1 :     void exceptionhandling2() {
    1836           1 :         REDIRECT;
    1837           1 :         const char * const argv[] = {"cppcheck", "--exception-handling=stderr", "file.cpp"};
    1838           1 :         CppCheckExecutor::setExceptionOutput(stdout);
    1839           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1840           1 :         ASSERT(settings->exceptionHandling);
    1841           1 :         ASSERT_EQUALS(stderr, CppCheckExecutor::getExceptionOutput());
    1842             :     }
    1843             : 
    1844           1 :     void exceptionhandling3() {
    1845           1 :         REDIRECT;
    1846           1 :         const char * const argv[] = {"cppcheck", "--exception-handling=stdout", "file.cpp"};
    1847           1 :         CppCheckExecutor::setExceptionOutput(stderr);
    1848           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1849           1 :         ASSERT(settings->exceptionHandling);
    1850           1 :         ASSERT_EQUALS(stdout, CppCheckExecutor::getExceptionOutput());
    1851             :     }
    1852             : 
    1853           1 :     void exceptionhandlingInvalid() {
    1854           1 :         REDIRECT;
    1855           1 :         const char * const argv[] = {"cppcheck", "--exception-handling=exfile"};
    1856           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1857           1 :         ASSERT_EQUALS("cppcheck: error: invalid '--exception-handling' argument\n", logger->str());
    1858             :     }
    1859             : 
    1860           1 :     void exceptionhandlingInvalid2() {
    1861           1 :         REDIRECT;
    1862           1 :         const char * const argv[] = {"cppcheck", "--exception-handling-foo"};
    1863           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1864           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--exception-handling-foo\".\n", logger->str());
    1865             :     }
    1866             : #else
    1867             :     void exceptionhandlingNotSupported() {
    1868             :         REDIRECT;
    1869             :         const char * const argv[] = {"cppcheck", "--exception-handling", "file.cpp"};
    1870             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1871             :         ASSERT_EQUALS("cppcheck: error: Option --exception-handling is not supported since Cppcheck has not been built with any exception handling enabled.\n", logger->str());
    1872             :     }
    1873             : 
    1874             :     void exceptionhandlingNotSupported2() {
    1875             :         REDIRECT;
    1876             :         const char * const argv[] = {"cppcheck", "--exception-handling=stderr", "file.cpp"};
    1877             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1878             :         ASSERT_EQUALS("cppcheck: error: Option --exception-handling is not supported since Cppcheck has not been built with any exception handling enabled.\n", logger->str());
    1879             :     }
    1880             : #endif
    1881             : 
    1882           1 :     void clang() {
    1883           1 :         REDIRECT;
    1884           1 :         const char * const argv[] = {"cppcheck", "--clang", "file.cpp"};
    1885           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1886           1 :         ASSERT(settings->clang);
    1887           1 :         ASSERT_EQUALS("clang", settings->clangExecutable);
    1888             :     }
    1889             : 
    1890           1 :     void clang2() {
    1891           1 :         REDIRECT;
    1892           1 :         const char * const argv[] = {"cppcheck", "--clang=clang-14", "file.cpp"};
    1893           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1894           1 :         ASSERT(settings->clang);
    1895           1 :         ASSERT_EQUALS("clang-14", settings->clangExecutable);
    1896             :     }
    1897             : 
    1898           1 :     void clangInvalid() {
    1899           1 :         REDIRECT;
    1900           1 :         const char * const argv[] = {"cppcheck", "--clang-foo"};
    1901           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1902           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--clang-foo\".\n", logger->str());
    1903             :     }
    1904             : 
    1905           1 :     void valueFlowMaxIterations() {
    1906           1 :         REDIRECT;
    1907           1 :         const char * const argv[] = {"cppcheck", "--valueflow-max-iterations=0", "file.cpp"};
    1908           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1909           1 :         ASSERT_EQUALS(0, settings->valueFlowMaxIterations);
    1910             :     }
    1911             : 
    1912           1 :     void valueFlowMaxIterations2() {
    1913           1 :         REDIRECT;
    1914           1 :         const char * const argv[] = {"cppcheck", "--valueflow-max-iterations=11", "file.cpp"};
    1915           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1916           1 :         ASSERT_EQUALS(11, settings->valueFlowMaxIterations);
    1917             :     }
    1918             : 
    1919           1 :     void valueFlowMaxIterationsInvalid() {
    1920           1 :         REDIRECT;
    1921           1 :         const char * const argv[] = {"cppcheck", "--valueflow-max-iterations"};
    1922           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1923           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--valueflow-max-iterations\".\n", logger->str());
    1924             :     }
    1925             : 
    1926           1 :     void valueFlowMaxIterationsInvalid2() {
    1927           1 :         REDIRECT;
    1928           1 :         const char * const argv[] = {"cppcheck", "--valueflow-max-iterations=seven"};
    1929           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1930           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--valueflow-max-iterations=' is not valid - not an integer.\n", logger->str());
    1931             :     }
    1932             : 
    1933           1 :     void valueFlowMaxIterationsInvalid3() {
    1934           1 :         REDIRECT;
    1935           1 :         const char * const argv[] = {"cppcheck", "--valueflow-max-iterations=-1"};
    1936           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    1937           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--valueflow-max-iterations=' is not valid - needs to be positive.\n", logger->str());
    1938             :     }
    1939             : 
    1940           1 :     void checksMaxTime() {
    1941           1 :         REDIRECT;
    1942           1 :         const char * const argv[] = {"cppcheck", "--checks-max-time=12", "file.cpp"};
    1943           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1944           1 :         ASSERT_EQUALS(12, settings->checksMaxTime);
    1945             :     }
    1946             : 
    1947           1 :     void checksMaxTime2() {
    1948           1 :         REDIRECT;
    1949           1 :         const char * const argv[] = {"cppcheck", "--checks-max-time=-1", "file.cpp"};
    1950           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1951           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--checks-max-time=' needs to be a positive integer.\n", logger->str());
    1952             :     }
    1953             : 
    1954           1 :     void checksMaxTimeInvalid() {
    1955           1 :         REDIRECT;
    1956           1 :         const char * const argv[] = {"cppcheck", "--checks-max-time=one", "file.cpp"};
    1957           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    1958           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--checks-max-time=' is not valid - not an integer.\n", logger->str());
    1959             :     }
    1960             : 
    1961             : #ifdef HAS_THREADING_MODEL_FORK
    1962           1 :     void loadAverage() {
    1963           1 :         REDIRECT;
    1964           1 :         const char * const argv[] = {"cppcheck", "-l", "12", "file.cpp"};
    1965           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    1966           1 :         ASSERT_EQUALS(12, settings->loadAverage);
    1967             :     }
    1968             : 
    1969           1 :     void loadAverage2() {
    1970           1 :         REDIRECT;
    1971           1 :         const char * const argv[] = {"cppcheck", "-l12", "file.cpp"};
    1972           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1973           1 :         ASSERT_EQUALS(12, settings->loadAverage);
    1974             :     }
    1975             : 
    1976           1 :     void loadAverageInvalid() {
    1977           1 :         REDIRECT;
    1978           1 :         const char * const argv[] = {"cppcheck", "-l", "one", "file.cpp"};
    1979           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1980           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-l' is not valid - not an integer.\n", logger->str());
    1981             :     }
    1982             : #else
    1983             :     void loadAverageNotSupported() {
    1984             :         REDIRECT;
    1985             :         const char * const argv[] = {"cppcheck", "-l", "12", "file.cpp"};
    1986             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    1987             :         ASSERT_EQUALS("cppcheck: error: Option -l cannot be used as Cppcheck has not been built with fork threading model.\n", logger->str());
    1988             :     }
    1989             : #endif
    1990             : 
    1991           1 :     void maxCtuDepth() {
    1992           1 :         REDIRECT;
    1993           1 :         const char * const argv[] = {"cppcheck", "--max-ctu-depth=12", "file.cpp"};
    1994           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    1995           1 :         ASSERT_EQUALS(12, settings->maxCtuDepth);
    1996             :     }
    1997             : 
    1998           1 :     void maxCtuDepthInvalid() {
    1999           1 :         REDIRECT;
    2000           1 :         const char * const argv[] = {"cppcheck", "--max-ctu-depth=one", "file.cpp"};
    2001           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2002           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--max-ctu-depth=' is not valid - not an integer.\n", logger->str());
    2003             :     }
    2004             : 
    2005           1 :     void performanceValueflowMaxTime() {
    2006           1 :         REDIRECT;
    2007           1 :         const char * const argv[] = {"cppcheck", "--performance-valueflow-max-time=12", "file.cpp"};
    2008           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2009           1 :         ASSERT_EQUALS(12, settings->performanceValueFlowMaxTime);
    2010             :     }
    2011             : 
    2012           1 :     void performanceValueflowMaxTimeInvalid() {
    2013           1 :         REDIRECT;
    2014           1 :         const char * const argv[] = {"cppcheck", "--performance-valueflow-max-time=one", "file.cpp"};
    2015           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2016           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--performance-valueflow-max-time=' is not valid - not an integer.\n", logger->str());
    2017             :     }
    2018             : 
    2019           1 :     void performanceValueFlowMaxIfCount() {
    2020           1 :         REDIRECT;
    2021           1 :         const char * const argv[] = {"cppcheck", "--performance-valueflow-max-if-count=12", "file.cpp"};
    2022           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2023           1 :         ASSERT_EQUALS(12, settings->performanceValueFlowMaxIfCount);
    2024             :     }
    2025             : 
    2026           1 :     void performanceValueFlowMaxIfCountInvalid() {
    2027           1 :         REDIRECT;
    2028           1 :         const char * const argv[] = {"cppcheck", "--performance-valueflow-max-if-count=one", "file.cpp"};
    2029           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2030           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--performance-valueflow-max-if-count=' is not valid - not an integer.\n", logger->str());
    2031             :     }
    2032             : 
    2033           3 :     void templateMaxTime() {
    2034           3 :         REDIRECT;
    2035           3 :         const char * const argv[] = {"cppcheck", "--template-max-time=12", "file.cpp"};
    2036           3 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2037           3 :         ASSERT_EQUALS(12, settings->templateMaxTime);
    2038             :     }
    2039             : 
    2040           1 :     void templateMaxTimeInvalid() {
    2041           1 :         REDIRECT;
    2042           1 :         const char * const argv[] = {"cppcheck", "--template-max-time=one", "file.cpp"};
    2043           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2044           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--template-max-time=' is not valid - not an integer.\n", logger->str());
    2045             :     }
    2046             : 
    2047           1 :     void templateMaxTimeInvalid2() {
    2048           1 :         REDIRECT;
    2049           1 :         const char * const argv[] = {"cppcheck", "--template-max-time=-1", "file.cpp"};
    2050           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2051           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--template-max-time=' is not valid - needs to be positive.\n", logger->str());
    2052             :     }
    2053             : 
    2054           1 :     void typedefMaxTime() {
    2055           1 :         REDIRECT;
    2056           1 :         const char * const argv[] = {"cppcheck", "--typedef-max-time=12", "file.cpp"};
    2057           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2058           1 :         ASSERT_EQUALS(12, settings->typedefMaxTime);
    2059             :     }
    2060             : 
    2061           1 :     void typedefMaxTimeInvalid() {
    2062           1 :         REDIRECT;
    2063           1 :         const char * const argv[] = {"cppcheck", "--typedef-max-time=one", "file.cpp"};
    2064           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2065           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--typedef-max-time=' is not valid - not an integer.\n", logger->str());
    2066             :     }
    2067             : 
    2068           1 :     void typedefMaxTimeInvalid2() {
    2069           1 :         REDIRECT;
    2070           1 :         const char * const argv[] = {"cppcheck", "--typedef-max-time=-1", "file.cpp"};
    2071           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2072           1 :         ASSERT_EQUALS("cppcheck: error: argument to '--typedef-max-time=' is not valid - needs to be positive.\n", logger->str());
    2073             :     }
    2074             : 
    2075           1 :     void project() {
    2076           1 :         REDIRECT;
    2077             :         ScopedFile file("project.cppcheck",
    2078             :                         "<project>\n"
    2079             :                         "<paths>\n"
    2080             :                         "<dir name=\"dir\"/>\n"
    2081             :                         "</paths>\n"
    2082           4 :                         "</project>");
    2083           1 :         const char * const argv[] = {"cppcheck", "--project=project.cppcheck"};
    2084           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
    2085           1 :         ASSERT_EQUALS(1, parser->getPathNames().size());
    2086           1 :         auto it = parser->getPathNames().cbegin();
    2087           1 :         ASSERT_EQUALS("dir", *it);
    2088             :     }
    2089             : 
    2090           1 :     void projectMultiple() {
    2091           1 :         REDIRECT;
    2092           4 :         ScopedFile file("project.cppcheck", "<project></project>");
    2093           1 :         const char * const argv[] = {"cppcheck", "--project=project.cppcheck", "--project=project.cppcheck", "file.cpp"};
    2094           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    2095           1 :         ASSERT_EQUALS("cppcheck: error: multiple --project options are not supported.\n", logger->str());
    2096             :     }
    2097             : 
    2098           1 :     void projectAndSource() {
    2099           1 :         REDIRECT;
    2100           4 :         ScopedFile file("project.cppcheck", "<project></project>");
    2101           1 :         const char * const argv[] = {"cppcheck", "--project=project.cppcheck", "file.cpp"};
    2102           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2103           1 :         ASSERT_EQUALS("cppcheck: error: --project cannot be used in conjunction with source files.\n", logger->str());
    2104             :     }
    2105             : 
    2106           1 :     void projectEmpty() {
    2107           1 :         REDIRECT;
    2108           1 :         const char * const argv[] = {"cppcheck", "--project=", "file.cpp"};
    2109           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2110           1 :         ASSERT_EQUALS("cppcheck: error: failed to open project ''. The file does not exist.\n", logger->str());
    2111             :     }
    2112             : 
    2113           1 :     void projectMissing() {
    2114           1 :         REDIRECT;
    2115           1 :         const char * const argv[] = {"cppcheck", "--project=project.cppcheck", "file.cpp"};
    2116           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2117           1 :         ASSERT_EQUALS("cppcheck: error: failed to open project 'project.cppcheck'. The file does not exist.\n", logger->str());
    2118             :     }
    2119             : 
    2120           1 :     void projectNoPaths() {
    2121           4 :         ScopedFile file("project.cppcheck", "<project></project>");
    2122           1 :         const char * const argv[] = {"cppcheck", "--project=project.cppcheck"};
    2123           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    2124           1 :         ASSERT_EQUALS("cppcheck: error: no C or C++ source files found.\n", logger->str());
    2125             :     }
    2126             : 
    2127           1 :     void addon() {
    2128           1 :         REDIRECT;
    2129           1 :         const char * const argv[] = {"cppcheck", "--addon=misra", "file.cpp"};
    2130           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2131           1 :         ASSERT_EQUALS(1, settings->addons.size());
    2132           1 :         ASSERT_EQUALS("misra", *settings->addons.cbegin());
    2133             :     }
    2134             : 
    2135           1 :     void addonMissing() {
    2136           1 :         REDIRECT;
    2137           1 :         const char * const argv[] = {"cppcheck", "--addon=misra2", "file.cpp"};
    2138           1 :         ASSERT(!parser->fillSettingsFromArgs(3, argv));
    2139           1 :         ASSERT_EQUALS(1, settings->addons.size());
    2140           1 :         ASSERT_EQUALS("misra2", *settings->addons.cbegin());
    2141           1 :         ASSERT_EQUALS("Did not find addon misra2.py\n", logger->str());
    2142             :     }
    2143             : 
    2144           1 :     void signedChar() {
    2145           1 :         REDIRECT;
    2146           1 :         const char * const argv[] = {"cppcheck", "--fsigned-char", "file.cpp"};
    2147           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2148           1 :         ASSERT_EQUALS('s', settings->platform.defaultSign);
    2149             :     }
    2150             : 
    2151           1 :     void signedChar2() {
    2152           1 :         REDIRECT;
    2153           1 :         const char * const argv[] = {"cppcheck", "--platform=avr8", "--fsigned-char", "file.cpp"};
    2154           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2155           1 :         ASSERT_EQUALS('s', settings->platform.defaultSign);
    2156             :     }
    2157             : 
    2158           1 :     void unsignedChar() {
    2159           1 :         REDIRECT;
    2160           1 :         const char * const argv[] = {"cppcheck", "--funsigned-char", "file.cpp"};
    2161           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2162           1 :         ASSERT_EQUALS('u', settings->platform.defaultSign);
    2163             :     }
    2164             : 
    2165           1 :     void unsignedChar2() {
    2166           1 :         REDIRECT;
    2167           1 :         const char * const argv[] = {"cppcheck", "--platform=mips32", "--funsigned-char", "file.cpp"};
    2168           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2169           1 :         ASSERT_EQUALS('u', settings->platform.defaultSign);
    2170             :     }
    2171             : 
    2172           1 :     void signedCharUnsignedChar() {
    2173           1 :         REDIRECT;
    2174           1 :         const char * const argv[] = {"cppcheck", "--fsigned-char", "--funsigned-char", "file.cpp"};
    2175           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2176           1 :         ASSERT_EQUALS('u', settings->platform.defaultSign);
    2177             :     }
    2178             : 
    2179             : #ifdef HAVE_RULES
    2180             :     void rule() {
    2181             :         REDIRECT;
    2182             :         const char * const argv[] = {"cppcheck", "--rule=.+", "file.cpp"};
    2183             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2184             :         ASSERT_EQUALS(1, settings->rules.size());
    2185             :         auto it = settings->rules.cbegin();
    2186             :         ASSERT_EQUALS(".+", it->pattern);
    2187             :     }
    2188             : 
    2189             :     void ruleMissingPattern() {
    2190             :         REDIRECT;
    2191             :         const char * const argv[] = {"cppcheck", "--rule=", "file.cpp"};
    2192             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2193             :         ASSERT_EQUALS("cppcheck: error: no rule pattern provided.\n", logger->str());
    2194             :     }
    2195             : #else
    2196           1 :     void ruleNotSupported() {
    2197           1 :         REDIRECT;
    2198           1 :         const char * const argv[] = {"cppcheck", "--rule=.+", "file.cpp"};
    2199           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2200           1 :         ASSERT_EQUALS("cppcheck: error: Option --rule cannot be used as Cppcheck has not been built with rules support.\n", logger->str());
    2201             :     }
    2202             : #endif
    2203             : 
    2204             : #ifdef HAVE_RULES
    2205             :     void ruleFileMulti() {
    2206             :         REDIRECT;
    2207             :         ScopedFile file("rule.xml",
    2208             :                         "<rules>\n"
    2209             :                         "<rule>\n"
    2210             :                         "<tokenlist>raw</tokenlist>\n"
    2211             :                         "<pattern>.+</pattern>\n"
    2212             :                         "<message>\n"
    2213             :                         "<severity>error</severity>\n"
    2214             :                         "<id>ruleId1</id>\n"
    2215             :                         "<summary>ruleSummary1</summary>\n"
    2216             :                         "</message>\n"
    2217             :                         "</rule>\n"
    2218             :                         "<rule>\n"
    2219             :                         "<tokenlist>define</tokenlist>\n"
    2220             :                         "<pattern>.*</pattern>\n"
    2221             :                         "<message>\n"
    2222             :                         "<severity>warning</severity>\n"
    2223             :                         "<id>ruleId2</id>\n"
    2224             :                         "<summary>ruleSummary2</summary>\n"
    2225             :                         "</message>\n"
    2226             :                         "</rule>\n"
    2227             :                         "</rules>");
    2228             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2229             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2230             :         ASSERT_EQUALS(2, settings->rules.size());
    2231             :         auto it = settings->rules.cbegin();
    2232             :         ASSERT_EQUALS("raw", it->tokenlist);
    2233             :         ASSERT_EQUALS(".+", it->pattern);
    2234             :         ASSERT_EQUALS_ENUM(Severity::error, it->severity);
    2235             :         ASSERT_EQUALS("ruleId1", it->id);
    2236             :         ASSERT_EQUALS("ruleSummary1", it->summary);
    2237             :         ++it;
    2238             :         ASSERT_EQUALS("define", it->tokenlist);
    2239             :         ASSERT_EQUALS(".*", it->pattern);
    2240             :         ASSERT_EQUALS_ENUM(Severity::warning, it->severity);
    2241             :         ASSERT_EQUALS("ruleId2", it->id);
    2242             :         ASSERT_EQUALS("ruleSummary2", it->summary);
    2243             :     }
    2244             : 
    2245             :     void ruleFileSingle() {
    2246             :         REDIRECT;
    2247             :         ScopedFile file("rule.xml",
    2248             :                         "<rule>\n"
    2249             :                         "<tokenlist>define</tokenlist>\n"
    2250             :                         "<pattern>.+</pattern>\n"
    2251             :                         "<message>\n"
    2252             :                         "<severity>error</severity>\n"
    2253             :                         "<id>ruleId</id>\n"
    2254             :                         "<summary>ruleSummary</summary>\n"
    2255             :                         "</message>\n"
    2256             :                         "</rule>\n");
    2257             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2258             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2259             :         ASSERT_EQUALS(1, settings->rules.size());
    2260             :         auto it = settings->rules.cbegin();
    2261             :         ASSERT_EQUALS("define", it->tokenlist);
    2262             :         ASSERT_EQUALS(".+", it->pattern);
    2263             :         ASSERT_EQUALS_ENUM(Severity::error, it->severity);
    2264             :         ASSERT_EQUALS("ruleId", it->id);
    2265             :         ASSERT_EQUALS("ruleSummary", it->summary);
    2266             :     }
    2267             : 
    2268             :     void ruleFileEmpty() {
    2269             :         REDIRECT;
    2270             :         const char * const argv[] = {"cppcheck", "--rule-file=", "file.cpp"};
    2271             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2272             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file '' (XML_ERROR_FILE_NOT_FOUND).\n", logger->str());
    2273             :     }
    2274             : 
    2275             :     void ruleFileMissing() {
    2276             :         REDIRECT;
    2277             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2278             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2279             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' (XML_ERROR_FILE_NOT_FOUND).\n", logger->str());
    2280             :     }
    2281             : 
    2282             :     void ruleFileInvalid() {
    2283             :         REDIRECT;
    2284             :         ScopedFile file("rule.xml", "");
    2285             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2286             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2287             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' (XML_ERROR_EMPTY_DOCUMENT).\n", logger->str());
    2288             :     }
    2289             : 
    2290             :     void ruleFileNoRoot() {
    2291             :         REDIRECT;
    2292             :         ScopedFile file("rule.xml", "<?xml version=\"1.0\"?>");
    2293             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2294             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2295             :         ASSERT_EQUALS(0, settings->rules.size());
    2296             :     }
    2297             : 
    2298             :     void ruleFileEmptyElements1() {
    2299             :         REDIRECT;
    2300             :         ScopedFile file("rule.xml",
    2301             :                         "<rule>"
    2302             :                         "<tokenlist/>"
    2303             :                         "<pattern/>"
    2304             :                         "<message/>"
    2305             :                         "</rule>"
    2306             :                         );
    2307             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2308             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv)); // do not crash
    2309             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule is lacking a pattern.\n", logger->str());
    2310             :     }
    2311             : 
    2312             :     void ruleFileEmptyElements2() {
    2313             :         REDIRECT;
    2314             :         ScopedFile file("rule.xml",
    2315             :                         "<rule>"
    2316             :                         "<message>"
    2317             :                         "<severity/>"
    2318             :                         "<id/>"
    2319             :                         "<summary/>"
    2320             :                         "</message>"
    2321             :                         "</rule>"
    2322             :                         );
    2323             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2324             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv)); // do not crash
    2325             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule is lacking a pattern.\n", logger->str());
    2326             :     }
    2327             : 
    2328             :     void ruleFileUnknownElement1() {
    2329             :         REDIRECT;
    2330             :         ScopedFile file("rule.xml",
    2331             :                         "<rule>"
    2332             :                         "<messages/>"
    2333             :                         "</rule>"
    2334             :                         );
    2335             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2336             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2337             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - unknown element 'messages' encountered in 'rule'.\n", logger->str());
    2338             :     }
    2339             : 
    2340             :     void ruleFileUnknownElement2() {
    2341             :         REDIRECT;
    2342             :         ScopedFile file("rule.xml",
    2343             :                         "<rule>"
    2344             :                         "<message>"
    2345             :                         "<pattern/>"
    2346             :                         "</message>"
    2347             :                         "</rule>"
    2348             :                         );
    2349             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2350             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2351             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - unknown element 'pattern' encountered in 'message'.\n", logger->str());
    2352             :     }
    2353             : 
    2354             :     void ruleFileMissingTokenList() {
    2355             :         REDIRECT;
    2356             :         ScopedFile file("rule.xml",
    2357             :                         "<rule>\n"
    2358             :                         "<tokenlist/>\n"
    2359             :                         "<pattern>.+</pattern>\n"
    2360             :                         "</rule>\n");
    2361             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2362             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2363             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule is lacking a tokenlist.\n", logger->str());
    2364             :     }
    2365             : 
    2366             :     void ruleFileUnknownTokenList() {
    2367             :         REDIRECT;
    2368             :         ScopedFile file("rule.xml",
    2369             :                         "<rule>\n"
    2370             :                         "<tokenlist>simple</tokenlist>\n"
    2371             :                         "<pattern>.+</pattern>\n"
    2372             :                         "</rule>\n");
    2373             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2374             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2375             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule is using the unsupported tokenlist 'simple'.\n", logger->str());
    2376             :     }
    2377             : 
    2378             :     void ruleFileMissingId() {
    2379             :         REDIRECT;
    2380             :         ScopedFile file("rule.xml",
    2381             :                         "<rule>\n"
    2382             :                         "<pattern>.+</pattern>\n"
    2383             :                         "<message>\n"
    2384             :                         "<id/>"
    2385             :                         "</message>\n"
    2386             :                         "</rule>\n");
    2387             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2388             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2389             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule is lacking an id.\n", logger->str());
    2390             :     }
    2391             : 
    2392             :     void ruleFileInvalidSeverity1() {
    2393             :         REDIRECT;
    2394             :         ScopedFile file("rule.xml",
    2395             :                         "<rule>\n"
    2396             :                         "<pattern>.+</pattern>\n"
    2397             :                         "<message>\n"
    2398             :                         "<severity/>"
    2399             :                         "</message>\n"
    2400             :                         "</rule>\n");
    2401             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2402             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2403             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule has an invalid severity.\n", logger->str());
    2404             :     }
    2405             : 
    2406             :     void ruleFileInvalidSeverity2() {
    2407             :         REDIRECT;
    2408             :         ScopedFile file("rule.xml",
    2409             :                         "<rule>\n"
    2410             :                         "<pattern>.+</pattern>\n"
    2411             :                         "<message>\n"
    2412             :                         "<severity>none</severity>"
    2413             :                         "</message>\n"
    2414             :                         "</rule>\n");
    2415             :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2416             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2417             :         ASSERT_EQUALS("cppcheck: error: unable to load rule-file 'rule.xml' - a rule has an invalid severity.\n", logger->str());
    2418             :     }
    2419             : #else
    2420           1 :     void ruleFileNotSupported() {
    2421           1 :         REDIRECT;
    2422           1 :         const char * const argv[] = {"cppcheck", "--rule-file=rule.xml", "file.cpp"};
    2423           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2424           1 :         ASSERT_EQUALS("cppcheck: error: Option --rule-file cannot be used as Cppcheck has not been built with rules support.\n", logger->str());
    2425             :     }
    2426             : #endif
    2427             : 
    2428           1 :     void library() {
    2429           1 :         REDIRECT;
    2430           1 :         const char * const argv[] = {"cppcheck", "--library=posix", "file.cpp"};
    2431           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2432           1 :         ASSERT_EQUALS(1, settings->libraries.size());
    2433           1 :         ASSERT_EQUALS("posix", *settings->libraries.cbegin());
    2434             :     }
    2435             : 
    2436           1 :     void libraryMissing() {
    2437           1 :         REDIRECT;
    2438           1 :         const char * const argv[] = {"cppcheck", "--library=posix2", "file.cpp"};
    2439           1 :         ASSERT_EQUALS(false, parser->fillSettingsFromArgs(3, argv));
    2440           1 :         ASSERT_EQUALS(1, settings->libraries.size());
    2441           1 :         ASSERT_EQUALS("posix2", *settings->libraries.cbegin());
    2442           1 :         ASSERT_EQUALS("cppcheck: Failed to load library configuration file 'posix2'. File not found\n", logger->str());
    2443             :     }
    2444             : 
    2445           1 :     void suppressXml() {
    2446           1 :         REDIRECT;
    2447             :         ScopedFile file("suppress.xml",
    2448             :                         "<suppressions>\n"
    2449             :                         "<suppress>\n"
    2450             :                         "<id>uninitvar</id>\n"
    2451             :                         "</suppress>\n"
    2452           4 :                         "</suppressions>");
    2453           1 :         const char * const argv[] = {"cppcheck", "--suppress-xml=suppress.xml", "file.cpp"};
    2454           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2455           1 :         const auto& supprs = settings->supprs.nomsg.getSuppressions();
    2456           1 :         ASSERT_EQUALS(1, supprs.size());
    2457           1 :         const auto it = supprs.cbegin();
    2458           1 :         ASSERT_EQUALS("uninitvar", it->errorId);
    2459             :     }
    2460             : 
    2461           1 :     void suppressXmlEmpty() {
    2462           1 :         REDIRECT;
    2463           1 :         const char * const argv[] = {"cppcheck", "--suppress-xml=", "file.cpp"};
    2464           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2465           1 :         ASSERT_EQUALS("cppcheck: error: failed to load suppressions XML '' (XML_ERROR_FILE_NOT_FOUND).\n", logger->str());
    2466             :     }
    2467             : 
    2468           1 :     void suppressXmlMissing() {
    2469           1 :         REDIRECT;
    2470           1 :         const char * const argv[] = {"cppcheck", "--suppress-xml=suppress.xml", "file.cpp"};
    2471           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2472           1 :         ASSERT_EQUALS("cppcheck: error: failed to load suppressions XML 'suppress.xml' (XML_ERROR_FILE_NOT_FOUND).\n", logger->str());
    2473             :     }
    2474             : 
    2475           1 :     void suppressXmlInvalid() {
    2476           1 :         REDIRECT;
    2477           4 :         ScopedFile file("suppress.xml", "");
    2478           1 :         const char * const argv[] = {"cppcheck", "--suppress-xml=suppress.xml", "file.cpp"};
    2479           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2480           1 :         ASSERT_EQUALS("cppcheck: error: failed to load suppressions XML 'suppress.xml' (XML_ERROR_EMPTY_DOCUMENT).\n", logger->str());
    2481             :     }
    2482             : 
    2483           1 :     void suppressXmlNoRoot() {
    2484           1 :         REDIRECT;
    2485           4 :         ScopedFile file("suppress.xml", "<?xml version=\"1.0\"?>");
    2486           1 :         const char * const argv[] = {"cppcheck", "--suppress-xml=suppress.xml", "file.cpp"};
    2487           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2488           1 :         ASSERT_EQUALS("cppcheck: error: failed to load suppressions XML 'suppress.xml' (no root node found).\n", logger->str());
    2489             :     }
    2490             : 
    2491           1 :     void executorDefault() {
    2492           1 :         REDIRECT;
    2493           1 :         const char * const argv[] = {"cppcheck", "file.cpp"};
    2494           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
    2495             : #if defined(HAS_THREADING_MODEL_FORK)
    2496           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Process, settings->executor);
    2497             : #elif defined(HAS_THREADING_MODEL_THREAD)
    2498             :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Thread, settings->executor);
    2499             : #endif
    2500             :     }
    2501             : 
    2502           1 :     void executorAuto() {
    2503           1 :         REDIRECT;
    2504           1 :         const char * const argv[] = {"cppcheck", "-j2", "--executor=auto", "file.cpp"};
    2505           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2506             : #if defined(HAS_THREADING_MODEL_FORK)
    2507           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Process, settings->executor);
    2508             : #elif defined(HAS_THREADING_MODEL_THREAD)
    2509             :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Thread, settings->executor);
    2510             : #endif
    2511             :     }
    2512             : 
    2513           1 :     void executorAutoNoJobs() {
    2514           1 :         REDIRECT;
    2515           1 :         const char * const argv[] = {"cppcheck", "--executor=auto", "file.cpp"};
    2516           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2517             : #if defined(HAS_THREADING_MODEL_FORK)
    2518           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Process, settings->executor);
    2519             : #elif defined(HAS_THREADING_MODEL_THREAD)
    2520             :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Thread, settings->executor);
    2521             : #endif
    2522             :     }
    2523             : 
    2524             : #if defined(HAS_THREADING_MODEL_THREAD)
    2525           1 :     void executorThread() {
    2526           1 :         REDIRECT;
    2527           1 :         const char * const argv[] = {"cppcheck", "-j2", "--executor=thread", "file.cpp"};
    2528           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2529           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Thread, settings->executor);
    2530             :     }
    2531             : 
    2532           1 :     void executorThreadNoJobs() {
    2533           1 :         REDIRECT;
    2534           1 :         const char * const argv[] = {"cppcheck", "--executor=thread", "file.cpp"};
    2535           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2536           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Thread, settings->executor);
    2537           1 :         ASSERT_EQUALS("cppcheck: '--executor' has no effect as only a single job will be used.\n", logger->str());
    2538             :     }
    2539             : #else
    2540             :     void executorThreadNotSupported() {
    2541             :         REDIRECT;
    2542             :         const char * const argv[] = {"cppcheck", "-j2", "--executor=thread", "file.cpp"};
    2543             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    2544             :         ASSERT_EQUALS("cppcheck: error: executor type 'thread' cannot be used as Cppcheck has not been built with a respective threading model.\n", logger->str());
    2545             :     }
    2546             : #endif
    2547             : 
    2548             : #if defined(HAS_THREADING_MODEL_FORK)
    2549           1 :     void executorProcess() {
    2550           1 :         REDIRECT;
    2551           1 :         const char * const argv[] = {"cppcheck", "-j2", "--executor=process", "file.cpp"};
    2552           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2553           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Process, settings->executor);
    2554             :     }
    2555             : 
    2556           1 :     void executorProcessNoJobs() {
    2557           1 :         REDIRECT;
    2558           1 :         const char * const argv[] = {"cppcheck", "--executor=process", "file.cpp"};
    2559           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2560           1 :         ASSERT_EQUALS_ENUM(Settings::ExecutorType::Process, settings->executor);
    2561           1 :         ASSERT_EQUALS("cppcheck: '--executor' has no effect as only a single job will be used.\n", logger->str());
    2562             :     }
    2563             : #else
    2564             :     void executorProcessNotSupported() {
    2565             :         REDIRECT;
    2566             :         const char * const argv[] = {"cppcheck", "-j2", "--executor=process", "file.cpp"};
    2567             :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    2568             :         ASSERT_EQUALS("cppcheck: error: executor type 'process' cannot be used as Cppcheck has not been built with a respective threading model.\n", logger->str());
    2569             :     }
    2570             : #endif
    2571             : 
    2572           1 :     void checkLevelDefault() {
    2573           1 :         REDIRECT;
    2574           1 :         const char * const argv[] = {"cppcheck", "file.cpp"};
    2575           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(2, argv));
    2576           1 :         ASSERT_EQUALS_ENUM(Settings::CheckLevel::normal, settings->checkLevel);
    2577           1 :         ASSERT_EQUALS(100, settings->performanceValueFlowMaxIfCount);
    2578           1 :         ASSERT_EQUALS(8, settings->performanceValueFlowMaxSubFunctionArgs);
    2579             :     }
    2580             : 
    2581           1 :     void checkLevelNormal() {
    2582           1 :         REDIRECT;
    2583           1 :         const char * const argv[] = {"cppcheck", "--check-level=normal", "file.cpp"};
    2584           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2585           1 :         ASSERT_EQUALS_ENUM(Settings::CheckLevel::normal, settings->checkLevel);
    2586           1 :         ASSERT_EQUALS(100, settings->performanceValueFlowMaxIfCount);
    2587           1 :         ASSERT_EQUALS(8, settings->performanceValueFlowMaxSubFunctionArgs);
    2588             :     }
    2589             : 
    2590           1 :     void checkLevelExhaustive() {
    2591           1 :         REDIRECT;
    2592           1 :         const char * const argv[] = {"cppcheck", "--check-level=exhaustive", "file.cpp"};
    2593           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2594           1 :         ASSERT_EQUALS_ENUM(Settings::CheckLevel::exhaustive, settings->checkLevel);
    2595           1 :         ASSERT_EQUALS(-1, settings->performanceValueFlowMaxIfCount);
    2596           1 :         ASSERT_EQUALS(256, settings->performanceValueFlowMaxSubFunctionArgs);
    2597             :     }
    2598             : 
    2599           1 :     void checkLevelUnknown() {
    2600           1 :         REDIRECT;
    2601           1 :         const char * const argv[] = {"cppcheck", "--check-level=default", "file.cpp"};
    2602           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2603           1 :         ASSERT_EQUALS("cppcheck: error: unknown '--check-level' value 'default'.\n", logger->str());
    2604             :     }
    2605             : 
    2606           1 :     void ignorepaths1() {
    2607           1 :         REDIRECT;
    2608           1 :         const char * const argv[] = {"cppcheck", "-isrc", "file.cpp"};
    2609           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2610           1 :         ASSERT_EQUALS(1, parser->getIgnoredPaths().size());
    2611           1 :         ASSERT_EQUALS("src", parser->getIgnoredPaths()[0]);
    2612             :     }
    2613             : 
    2614           1 :     void ignorepaths2() {
    2615           1 :         REDIRECT;
    2616           1 :         const char * const argv[] = {"cppcheck", "-i", "src", "file.cpp"};
    2617           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2618           1 :         ASSERT_EQUALS(1, parser->getIgnoredPaths().size());
    2619           1 :         ASSERT_EQUALS("src", parser->getIgnoredPaths()[0]);
    2620             :     }
    2621             : 
    2622           1 :     void ignorepaths3() {
    2623           1 :         REDIRECT;
    2624           1 :         const char * const argv[] = {"cppcheck", "-isrc", "-imodule", "file.cpp"};
    2625           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2626           1 :         ASSERT_EQUALS(2, parser->getIgnoredPaths().size());
    2627           1 :         ASSERT_EQUALS("src", parser->getIgnoredPaths()[0]);
    2628           1 :         ASSERT_EQUALS("module", parser->getIgnoredPaths()[1]);
    2629             :     }
    2630             : 
    2631           1 :     void ignorepaths4() {
    2632           1 :         REDIRECT;
    2633           1 :         const char * const argv[] = {"cppcheck", "-i", "src", "-i", "module", "file.cpp"};
    2634           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(6, argv));
    2635           1 :         ASSERT_EQUALS(2, parser->getIgnoredPaths().size());
    2636           1 :         ASSERT_EQUALS("src", parser->getIgnoredPaths()[0]);
    2637           1 :         ASSERT_EQUALS("module", parser->getIgnoredPaths()[1]);
    2638             :     }
    2639             : 
    2640           1 :     void ignorefilepaths1() {
    2641           1 :         REDIRECT;
    2642           1 :         const char * const argv[] = {"cppcheck", "-ifoo.cpp", "file.cpp"};
    2643           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2644           1 :         ASSERT_EQUALS(1, parser->getIgnoredPaths().size());
    2645           1 :         ASSERT_EQUALS("foo.cpp", parser->getIgnoredPaths()[0]);
    2646             :     }
    2647             : 
    2648           1 :     void ignorefilepaths2() {
    2649           1 :         REDIRECT;
    2650           1 :         const char * const argv[] = {"cppcheck", "-isrc/foo.cpp", "file.cpp"};
    2651           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2652           1 :         ASSERT_EQUALS(1, parser->getIgnoredPaths().size());
    2653           1 :         ASSERT_EQUALS("src/foo.cpp", parser->getIgnoredPaths()[0]);
    2654             :     }
    2655             : 
    2656           1 :     void ignorefilepaths3() {
    2657           1 :         REDIRECT;
    2658           1 :         const char * const argv[] = {"cppcheck", "-i", "foo.cpp", "file.cpp"};
    2659           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2660           1 :         ASSERT_EQUALS(1, parser->getIgnoredPaths().size());
    2661           1 :         ASSERT_EQUALS("foo.cpp", parser->getIgnoredPaths()[0]);
    2662             :     }
    2663             : 
    2664           1 :     void checkconfig() {
    2665           1 :         REDIRECT;
    2666           1 :         const char * const argv[] = {"cppcheck", "--check-config", "file.cpp"};
    2667           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2668           1 :         ASSERT_EQUALS(true, settings->checkConfiguration);
    2669             :     }
    2670             : 
    2671           1 :     void unknownParam() {
    2672           1 :         REDIRECT;
    2673           1 :         const char * const argv[] = {"cppcheck", "--foo", "file.cpp"};
    2674           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(3, argv));
    2675           1 :         ASSERT_EQUALS("cppcheck: error: unrecognized command line option: \"--foo\".\n", logger->str());
    2676             :     }
    2677             : 
    2678           1 :     void undefs() {
    2679           1 :         REDIRECT;
    2680           1 :         const char * const argv[] = {"cppcheck", "-U_WIN32", "file.cpp"};
    2681           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2682           1 :         ASSERT_EQUALS(1, settings->userUndefs.size());
    2683           1 :         ASSERT(settings->userUndefs.find("_WIN32") != settings->userUndefs.end());
    2684             :     }
    2685             : 
    2686           1 :     void undefs2() {
    2687           1 :         REDIRECT;
    2688           1 :         const char * const argv[] = {"cppcheck", "-U_WIN32", "-UNODEBUG", "file.cpp"};
    2689           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(4, argv));
    2690           1 :         ASSERT_EQUALS(2, settings->userUndefs.size());
    2691           1 :         ASSERT(settings->userUndefs.find("_WIN32") != settings->userUndefs.end());
    2692           1 :         ASSERT(settings->userUndefs.find("NODEBUG") != settings->userUndefs.end());
    2693             :     }
    2694             : 
    2695           1 :     void undefs_noarg() {
    2696           1 :         REDIRECT;
    2697           1 :         const char * const argv[] = {"cppcheck", "-U"};
    2698             :         // Fails since -U has no param
    2699           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    2700           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-U' is missing.\n", logger->str());
    2701             :     }
    2702             : 
    2703           1 :     void undefs_noarg2() {
    2704           1 :         REDIRECT;
    2705           1 :         const char * const argv[] = {"cppcheck", "-U", "-v", "file.cpp"};
    2706             :         // Fails since -U has no param
    2707           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    2708           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-U' is missing.\n", logger->str());
    2709             :     }
    2710             : 
    2711           1 :     void undefs_noarg3() {
    2712           1 :         REDIRECT;
    2713           1 :         const char * const argv[] = {"cppcheck", "-U", "--quiet", "file.cpp"};
    2714             :         // Fails since -U has no param
    2715           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(4, argv));
    2716           1 :         ASSERT_EQUALS("cppcheck: error: argument to '-U' is missing.\n", logger->str());
    2717             :     }
    2718             : 
    2719           1 :     void cppcheckBuildDirExistent() {
    2720           1 :         REDIRECT;
    2721           1 :         const char * const argv[] = {"cppcheck", "--cppcheck-build-dir=.", "file.cpp"};
    2722           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Success, parser->parseFromArgs(3, argv));
    2723             :     }
    2724             : 
    2725           1 :     void cppcheckBuildDirNonExistent() {
    2726           1 :         REDIRECT;
    2727           1 :         const char * const argv[] = {"cppcheck", "--cppcheck-build-dir=non-existent-path"};
    2728           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    2729           1 :         ASSERT_EQUALS("cppcheck: error: Directory 'non-existent-path' specified by --cppcheck-build-dir argument has to be existent.\n", logger->str());
    2730             :     }
    2731             : 
    2732           1 :     void cppcheckBuildDirEmpty() {
    2733           1 :         REDIRECT;
    2734           1 :         const char * const argv[] = {"cppcheck", "--cppcheck-build-dir="};
    2735           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    2736           1 :         ASSERT_EQUALS("cppcheck: error: Directory '' specified by --cppcheck-build-dir argument has to be existent.\n", logger->str());
    2737             :     }
    2738             : 
    2739           1 :     void invalidCppcheckCfg() {
    2740           1 :         REDIRECT;
    2741           2 :         ScopedFile file(Path::join(Path::getPathFromFilename(Path::getCurrentExecutablePath("")), "cppcheck.cfg"),
    2742           4 :                         "{\n");
    2743           1 :         const char * const argv[] = {"cppcheck", "test.cpp"};
    2744           1 :         ASSERT_EQUALS_ENUM(CmdLineParser::Result::Fail, parser->parseFromArgs(2, argv));
    2745           1 :         ASSERT_EQUALS("cppcheck: error: could not load cppcheck.cfg - not a valid JSON - syntax error at line 2 near: \n", logger->str());
    2746             :     }
    2747             : };
    2748             : 
    2749             : REGISTER_TEST(TestCmdlineParser)

Generated by: LCOV version 1.14