diff --git a/llvm/test/tools/llvm-cov/Inputs/binary-formats.canonical.json b/llvm/test/tools/llvm-cov/Inputs/binary-formats.canonical.json index ce13fc2ff6e34..04e31c205ca9b 100644 --- a/llvm/test/tools/llvm-cov/Inputs/binary-formats.canonical.json +++ b/llvm/test/tools/llvm-cov/Inputs/binary-formats.canonical.json @@ -33,4 +33,4 @@ CHECk-SAME: "mcdc":{"count":0,"covered":0,"notcovered":0,"percent":0}, CHECK-SAME: "regions":{"count":1,"covered":1,"notcovered":0,"percent":100}}} CHECK-SAME: ], CHECK-SAME: "type":"llvm.coverage.json.export" -CHECK-SAME: "version":"2.0.1" +CHECK-SAME: "version":"2.1.0" diff --git a/llvm/tools/llvm-cov/CoverageExporterJson.cpp b/llvm/tools/llvm-cov/CoverageExporterJson.cpp index 9a8c7c94f0612..51f7c326b7465 100644 --- a/llvm/tools/llvm-cov/CoverageExporterJson.cpp +++ b/llvm/tools/llvm-cov/CoverageExporterJson.cpp @@ -62,7 +62,7 @@ #include /// The semantic version combined as a string. -#define LLVM_COVERAGE_EXPORT_JSON_STR "2.0.1" +#define LLVM_COVERAGE_EXPORT_JSON_STR "2.1.0" /// Unique type identifier for JSON coverage export. #define LLVM_COVERAGE_EXPORT_JSON_TYPE_STR "llvm.coverage.json.export" @@ -108,11 +108,40 @@ json::Array gatherConditions(const coverage::MCDCRecord &Record) { return Conditions; } +json::Value renderCondState(const coverage::MCDCRecord::CondState CondState) { + switch (CondState) { + case coverage::MCDCRecord::MCDC_DontCare: + return json::Value(nullptr); + case coverage::MCDCRecord::MCDC_True: + return json::Value(true); + case coverage::MCDCRecord::MCDC_False: + return json::Value(false); + } +} + +json::Array gatherTestVectors(coverage::MCDCRecord &Record) { + json::Array TestVectors; + unsigned NumConditions = Record.getNumConditions(); + for (unsigned tv = 0; tv < Record.getNumTestVectors(); tv++) { + + json::Array TVConditions; + for (unsigned c = 0; c < NumConditions; c++) + TVConditions.push_back(renderCondState(Record.getTVCondition(tv, c))); + + TestVectors.push_back( + json::Object({{"executed", json::Value(true)}, + {"result", renderCondState(Record.getTVResult(tv))}, + {"conditions", std::move(TVConditions)}})); + } + return TestVectors; +} + json::Array renderMCDCRecord(const coverage::MCDCRecord &Record) { const llvm::coverage::CounterMappingRegion &CMR = Record.getDecisionRegion(); - return json::Array({CMR.LineStart, CMR.ColumnStart, CMR.LineEnd, - CMR.ColumnEnd, CMR.ExpandedFileID, int64_t(CMR.Kind), - gatherConditions(Record)}); + return json::Array( + {CMR.LineStart, CMR.ColumnStart, CMR.LineEnd, CMR.ColumnEnd, + CMR.ExpandedFileID, int64_t(CMR.Kind), gatherConditions(Record), + gatherTestVectors(const_cast(Record))}); } json::Array renderRegions(ArrayRef Regions) { @@ -214,32 +243,28 @@ json::Object renderSummary(const FileCoverageSummary &Summary) { } json::Array renderFileExpansions(const coverage::CoverageMapping &Coverage, - const coverage::CoverageData &FileCoverage, - const FileCoverageSummary &FileReport) { + const coverage::CoverageData &FileCoverage) { json::Array ExpansionArray; for (const auto &Expansion : FileCoverage.getExpansions()) ExpansionArray.push_back(renderExpansion(Coverage, Expansion)); return ExpansionArray; } -json::Array renderFileSegments(const coverage::CoverageData &FileCoverage, - const FileCoverageSummary &FileReport) { +json::Array renderFileSegments(const coverage::CoverageData &FileCoverage) { json::Array SegmentArray; for (const auto &Segment : FileCoverage) SegmentArray.push_back(renderSegment(Segment)); return SegmentArray; } -json::Array renderFileBranches(const coverage::CoverageData &FileCoverage, - const FileCoverageSummary &FileReport) { +json::Array renderFileBranches(const coverage::CoverageData &FileCoverage) { json::Array BranchArray; for (const auto &Branch : FileCoverage.getBranches()) BranchArray.push_back(renderBranch(Branch)); return BranchArray; } -json::Array renderFileMCDC(const coverage::CoverageData &FileCoverage, - const FileCoverageSummary &FileReport) { +json::Array renderFileMCDC(const coverage::CoverageData &FileCoverage) { json::Array MCDCRecordArray; for (const auto &Record : FileCoverage.getMCDCRecords()) MCDCRecordArray.push_back(renderMCDCRecord(Record)); @@ -254,12 +279,11 @@ json::Object renderFile(const coverage::CoverageMapping &Coverage, if (!Options.ExportSummaryOnly) { // Calculate and render detailed coverage information for given file. auto FileCoverage = Coverage.getCoverageForFile(Filename); - File["segments"] = renderFileSegments(FileCoverage, FileReport); - File["branches"] = renderFileBranches(FileCoverage, FileReport); - File["mcdc_records"] = renderFileMCDC(FileCoverage, FileReport); + File["segments"] = renderFileSegments(FileCoverage); + File["branches"] = renderFileBranches(FileCoverage); + File["mcdc_records"] = renderFileMCDC(FileCoverage); if (!Options.SkipExpansions) { - File["expansions"] = - renderFileExpansions(Coverage, FileCoverage, FileReport); + File["expansions"] = renderFileExpansions(Coverage, FileCoverage); } } File["summary"] = renderSummary(FileReport);