Skip to content

Commit 9dc6fc9

Browse files
committed
analyzerinfo [skip ci]
1 parent b07f0f2 commit 9dc6fc9

File tree

6 files changed

+32
-17
lines changed

6 files changed

+32
-17
lines changed

cli/cppcheckexecutor.cpp

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -299,7 +299,7 @@ int CppCheckExecutor::check_wrapper(const Settings& settings, Suppressions& supp
299299
* @param unmatched list of unmatched suppressions (from Settings::Suppressions::getUnmatched(Local|Global)Suppressions)
300300
* @return true is returned if errors are reported
301301
*/
302-
static bool reportUnmatchedSuppressions(const std::list<SuppressionList::Suppression> &unmatched, ErrorLogger &errorLogger, const std::vector<std::string>& filters)
302+
static bool reportUnmatchedSuppressions(const std::list<SuppressionList::Suppression> &unmatched, ErrorLogger &errorLogger, AnalyzerInformation* analyzerInfo, const std::vector<std::string>& filters)
303303
{
304304
bool err = false;
305305
// Report unmatched suppressions
@@ -329,13 +329,16 @@ static bool reportUnmatchedSuppressions(const std::list<SuppressionList::Suppres
329329
if (!s.fileName.empty()) {
330330
callStack.emplace_back(s.fileName, s.lineNumber, 0);
331331
}
332-
errorLogger.reportErr(::ErrorMessage(std::move(callStack), "", Severity::information, "Unmatched suppression: " + s.errorId, "unmatchedSuppression", Certainty::normal));
332+
const auto errmsg = ::ErrorMessage(std::move(callStack), "", Severity::information, "Unmatched suppression: " + s.errorId, "unmatchedSuppression", Certainty::normal);
333+
if (analyzerInfo)
334+
analyzerInfo->reportErr(errmsg);
335+
errorLogger.reportErr(errmsg);
333336
err = true;
334337
}
335338
return err;
336339
}
337340

338-
bool CppCheckExecutor::reportUnmatchedSuppressions(const Settings &settings, const SuppressionList& suppressions, const std::list<FileWithDetails> &files, const std::list<FileSettings>& fileSettings, ErrorLogger& errorLogger) {
341+
bool CppCheckExecutor::reportUnmatchedSuppressions(const Settings &settings, const SuppressionList& suppressions, const std::list<FileWithDetails> &files, const std::list<FileSettings>& fileSettings, ErrorLogger& errorLogger, AnalyzerInformation* analyzerInfo) {
339342
// the two inputs may only be used exclusively
340343
assert(!(!files.empty() && !fileSettings.empty()));
341344

@@ -361,18 +364,18 @@ bool CppCheckExecutor::reportUnmatchedSuppressions(const Settings &settings, con
361364
bool err = false;
362365

363366
for (auto i = files.cbegin(); i != files.cend(); ++i) {
364-
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedLocalSuppressions(*i), errorLogger, settings.unmatchedSuppressionFilters);
367+
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedLocalSuppressions(*i), errorLogger, analyzerInfo, settings.unmatchedSuppressionFilters);
365368
}
366369

367370
for (auto i = fileSettings.cbegin(); i != fileSettings.cend(); ++i) {
368-
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedLocalSuppressions(i->file), errorLogger, settings.unmatchedSuppressionFilters);
371+
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedLocalSuppressions(i->file), errorLogger, analyzerInfo, settings.unmatchedSuppressionFilters);
369372
}
370373

371374
if (settings.inlineSuppressions) {
372-
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedInlineSuppressions(), errorLogger, settings.unmatchedSuppressionFilters);
375+
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedInlineSuppressions(), errorLogger, analyzerInfo, settings.unmatchedSuppressionFilters);
373376
}
374377

375-
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedGlobalSuppressions(), errorLogger, settings.unmatchedSuppressionFilters);
378+
err |= ::reportUnmatchedSuppressions(supprlist.getUnmatchedGlobalSuppressions(), errorLogger, analyzerInfo, settings.unmatchedSuppressionFilters);
376379
return err;
377380
}
378381

@@ -424,10 +427,13 @@ int CppCheckExecutor::check_internal(const Settings& settings, Suppressions& sup
424427
#endif
425428
}
426429

430+
// TODO: is this run again instead of using previously cached results?
427431
returnValue |= cppcheck.analyseWholeProgram(settings.buildDir, mFiles, mFileSettings, stdLogger.getCtuInfo());
428432

429433
if (settings.severity.isEnabled(Severity::information) || settings.checkConfiguration) {
430-
const bool err = reportUnmatchedSuppressions(settings, supprs.nomsg, mFiles, mFileSettings, stdLogger);
434+
AnalyzerInformation analyzerInfo(true);
435+
const bool err = reportUnmatchedSuppressions(settings, supprs.nomsg, mFiles, mFileSettings, stdLogger, &analyzerInfo);
436+
analyzerInfo.close();
431437
if (err && returnValue == 0)
432438
returnValue = settings.exitCode;
433439
}

cli/cppcheckexecutor.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ class Settings;
2929
class ErrorLogger;
3030
class SuppressionList;
3131
struct Suppressions;
32+
class AnalyzerInformation;
3233

3334
/**
3435
* This class works as an example of how CppCheck can be used in external
@@ -70,7 +71,7 @@ class CppCheckExecutor {
7071

7172
protected:
7273

73-
static bool reportUnmatchedSuppressions(const Settings &settings, const SuppressionList& suppressions, const std::list<FileWithDetails> &files, const std::list<FileSettings>& fileSettings, ErrorLogger& errorLogger);
74+
static bool reportUnmatchedSuppressions(const Settings &settings, const SuppressionList& suppressions, const std::list<FileWithDetails> &files, const std::list<FileSettings>& fileSettings, ErrorLogger& errorLogger, AnalyzerInformation* analyzerInfo);
7475

7576
/**
7677
* Wrapper around check_internal

lib/analyzerinfo.cpp

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,11 @@
3131

3232
#include "xml.h"
3333

34+
AnalyzerInformation::AnalyzerInformation(bool close_xml)
35+
: mCloseXml(close_xml)
36+
{
37+
}
38+
3439
AnalyzerInformation::~AnalyzerInformation()
3540
{
3641
close();
@@ -80,7 +85,8 @@ void AnalyzerInformation::close()
8085
{
8186
mAnalyzerInfoFile.clear();
8287
if (mOutputStream.is_open()) {
83-
mOutputStream << "</analyzerinfo>\n";
88+
if (mCloseXml)
89+
mOutputStream << "</analyzerinfo>\n";
8490
mOutputStream.close();
8591
}
8692
}
@@ -150,7 +156,6 @@ bool AnalyzerInformation::analyzeFile(const std::string &buildDir, const std::st
150156
{
151157
if (buildDir.empty() || sourcefile.empty())
152158
return true;
153-
close();
154159

155160
mAnalyzerInfoFile = AnalyzerInformation::getAnalyzerInfoFile(buildDir,sourcefile,cfg,fileIndex);
156161

lib/analyzerinfo.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ namespace tinyxml2 {
5353
*/
5454
class CPPCHECKLIB AnalyzerInformation {
5555
public:
56+
explicit AnalyzerInformation(bool close_xml);
5657
~AnalyzerInformation();
5758

5859
static void writeFilesTxt(const std::string &buildDir, const std::list<std::string> &sourcefiles, const std::string &userDefines, const std::list<FileSettings> &fileSettings);
@@ -85,6 +86,7 @@ class CPPCHECKLIB AnalyzerInformation {
8586
private:
8687
std::ofstream mOutputStream;
8788
std::string mAnalyzerInfoFile;
89+
bool mCloseXml;
8890
};
8991

9092
/// @}

lib/cppcheck.cpp

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -950,7 +950,8 @@ unsigned int CppCheck::checkInternal(const FileWithDetails& file, const std::str
950950
// TODO: if an exception occurs in this block it will continue in an unexpected code path
951951
if (!mSettings.buildDir.empty())
952952
{
953-
analyzerInformation.reset(new AnalyzerInformation);
953+
// XML can be closed because no further analysis is performed on markup files
954+
analyzerInformation.reset(new AnalyzerInformation(true));
954955
mLogger->setAnalyzerInfo(analyzerInformation.get());
955956
}
956957

@@ -1011,7 +1012,9 @@ unsigned int CppCheck::checkInternal(const FileWithDetails& file, const std::str
10111012
preprocessor.removeComments();
10121013

10131014
if (!mSettings.buildDir.empty()) {
1014-
analyzerInformation.reset(new AnalyzerInformation);
1015+
// FIXME: this is a horrible hack to leave the XML open so we can add unmatchedSuppression entries in CppCheckExecutor
1016+
const bool close_xml = !mSettings.severity.isEnabled(Severity::information) && !mSettings.checkConfiguration;
1017+
analyzerInformation.reset(new AnalyzerInformation(close_xml));
10151018
mLogger->setAnalyzerInfo(analyzerInformation.get());
10161019
}
10171020

@@ -1854,6 +1857,8 @@ unsigned int CppCheck::analyseWholeProgram(const std::string &buildDir, const st
18541857
std::list<Check::FileInfo*> fileInfoList;
18551858
CTU::FileInfo ctuFileInfo;
18561859

1860+
// TODO: report errors
1861+
18571862
// Load all analyzer info data..
18581863
const std::string filesTxt(buildDir + "/files.txt");
18591864
std::ifstream fin(filesTxt);

test/cli/other_test.py

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2353,8 +2353,6 @@ def test_inline_suppr_builddir(tmp_path):
23532353
__test_inline_suppr(tmp_path, ['--cppcheck-build-dir={}'.format(build_dir), '-j1'])
23542354

23552355

2356-
# TODO: the suppressions are generated outside of the scope which captures the analysis information
2357-
@pytest.mark.xfail(strict=True)
23582356
def test_inline_suppr_builddir_cached(tmp_path):
23592357
build_dir = tmp_path / 'b1'
23602358
os.mkdir(build_dir)
@@ -2368,8 +2366,6 @@ def test_inline_suppr_builddir_j(tmp_path):
23682366
__test_inline_suppr(tmp_path, ['--cppcheck-build-dir={}'.format(build_dir), '-j2'])
23692367

23702368

2371-
# TODO: the suppressions are generated outside of the scope which captures the analysis information
2372-
@pytest.mark.xfail(strict=True)
23732369
def test_inline_suppr_builddir_j_cached(tmp_path):
23742370
build_dir = tmp_path / 'b1'
23752371
os.mkdir(build_dir)

0 commit comments

Comments
 (0)