[llvm] 0ed61db - [MC/DC] Refactor: Isolate the final result out of TestVector (#82282)
via llvm-commits
llvm-commits at lists.llvm.org
Mon Feb 26 22:31:07 PST 2024
Author: NAKAMURA Takumi
Date: 2024-02-27T15:31:04+09:00
New Revision: 0ed61db6fdf683f8def06e6a6d206d02b821cd81
URL: https://github.com/llvm/llvm-project/commit/0ed61db6fdf683f8def06e6a6d206d02b821cd81
DIFF: https://github.com/llvm/llvm-project/commit/0ed61db6fdf683f8def06e6a6d206d02b821cd81.diff
LOG: [MC/DC] Refactor: Isolate the final result out of TestVector (#82282)
To reduce conditional judges in the loop in `findIndependencePairs()`, I
have tried a couple of tweaks.
* Isolate the final result in `TestVectors`
`using TestVectors = llvm::SmallVector<std::pair<TestVector,
CondState>>;`
The final result was just piggybacked on `TestVector`, so it has been
isolated.
* Filter out and sort `ExecVectors` by the final result
It will cost more in constructing `ExecVectors`, but it can reduce at
least one conditional judgement in the loop.
Added:
Modified:
llvm/include/llvm/ProfileData/Coverage/CoverageMapping.h
llvm/lib/ProfileData/Coverage/CoverageMapping.cpp
Removed:
################################################################################
diff --git a/llvm/include/llvm/ProfileData/Coverage/CoverageMapping.h b/llvm/include/llvm/ProfileData/Coverage/CoverageMapping.h
index f8f549eea2e093..27b1c32b1fa547 100644
--- a/llvm/include/llvm/ProfileData/Coverage/CoverageMapping.h
+++ b/llvm/include/llvm/ProfileData/Coverage/CoverageMapping.h
@@ -385,7 +385,7 @@ struct MCDCRecord {
enum CondState { MCDC_DontCare = -1, MCDC_False = 0, MCDC_True = 1 };
using TestVector = llvm::SmallVector<CondState>;
- using TestVectors = llvm::SmallVector<TestVector>;
+ using TestVectors = llvm::SmallVector<std::pair<TestVector, CondState>>;
using BoolVector = llvm::SmallVector<bool>;
using TVRowPair = std::pair<unsigned, unsigned>;
using TVPairMap = llvm::DenseMap<unsigned, TVRowPair>;
@@ -426,13 +426,13 @@ struct MCDCRecord {
/// accessing conditions in the TestVectors requires a translation from a
/// ordinal position to actual condition ID. This is done via PosToID[].
CondState getTVCondition(unsigned TestVectorIndex, unsigned Condition) {
- return TV[TestVectorIndex][PosToID[Condition]];
+ return TV[TestVectorIndex].first[PosToID[Condition]];
}
/// Return the Result evaluation for an executed test vector.
/// See MCDCRecordProcessor::RecordTestVector().
CondState getTVResult(unsigned TestVectorIndex) {
- return TV[TestVectorIndex][getNumConditions()];
+ return TV[TestVectorIndex].second;
}
/// Determine whether a given condition (indicated by Condition) is covered
diff --git a/llvm/lib/ProfileData/Coverage/CoverageMapping.cpp b/llvm/lib/ProfileData/Coverage/CoverageMapping.cpp
index 3f892d7aff2f4a..64545164d597a7 100644
--- a/llvm/lib/ProfileData/Coverage/CoverageMapping.cpp
+++ b/llvm/lib/ProfileData/Coverage/CoverageMapping.cpp
@@ -370,9 +370,16 @@ class MCDCRecordProcessor : NextIDsBuilder, mcdc::TVIdxBuilder {
/// Mapping of calculated MC/DC Independence Pairs for each condition.
MCDCRecord::TVPairMap IndependencePairs;
+ /// Storage for ExecVectors
+ /// ExecVectors is the alias of its 0th element.
+ std::array<MCDCRecord::TestVectors, 2> ExecVectorsByCond;
+
/// Actual executed Test Vectors for the boolean expression, based on
/// ExecutedTestVectorBitmap.
- MCDCRecord::TestVectors ExecVectors;
+ MCDCRecord::TestVectors &ExecVectors;
+
+ /// Number of False items in ExecVectors
+ unsigned NumExecVectorsF;
#ifndef NDEBUG
DenseSet<unsigned> TVIdxs;
@@ -385,7 +392,8 @@ class MCDCRecordProcessor : NextIDsBuilder, mcdc::TVIdxBuilder {
: NextIDsBuilder(Branches), TVIdxBuilder(this->NextIDs), Bitmap(Bitmap),
Region(Region), DecisionParams(Region.getDecisionParams()),
Branches(Branches), NumConditions(DecisionParams.NumConditions),
- Folded(NumConditions, false), IndependencePairs(NumConditions) {}
+ Folded(NumConditions, false), IndependencePairs(NumConditions),
+ ExecVectors(ExecVectorsByCond[false]) {}
private:
// Walk the binary decision diagram and try assigning both false and true to
@@ -415,11 +423,9 @@ class MCDCRecordProcessor : NextIDsBuilder, mcdc::TVIdxBuilder {
continue;
// Copy the completed test vector to the vector of testvectors.
- ExecVectors.push_back(TV);
-
// The final value (T,F) is equal to the last non-dontcare state on the
// path (in a short-circuiting system).
- ExecVectors.back().push_back(MCDCCond);
+ ExecVectorsByCond[MCDCCond].push_back({TV, MCDCCond});
}
// Reset back to DontCare.
@@ -437,6 +443,14 @@ class MCDCRecordProcessor : NextIDsBuilder, mcdc::TVIdxBuilder {
buildTestVector(TV, 0, 0, 0);
assert(TVIdxs.size() == unsigned(NumTestVectors) &&
"TVIdxs wasn't fulfilled");
+
+ // Fill ExecVectors order by False items and True items.
+ // ExecVectors is the alias of ExecVectorsByCond[false], so
+ // Append ExecVectorsByCond[true] on it.
+ NumExecVectorsF = ExecVectors.size();
+ auto &ExecVectorsT = ExecVectorsByCond[true];
+ ExecVectors.append(std::make_move_iterator(ExecVectorsT.begin()),
+ std::make_move_iterator(ExecVectorsT.end()));
}
// Find an independence pair for each condition:
@@ -445,13 +459,12 @@ class MCDCRecordProcessor : NextIDsBuilder, mcdc::TVIdxBuilder {
// - All other conditions' values must be equal or marked as "don't care".
void findIndependencePairs() {
unsigned NumTVs = ExecVectors.size();
- for (unsigned I = 1; I < NumTVs; ++I) {
- const MCDCRecord::TestVector &A = ExecVectors[I];
- for (unsigned J = 0; J < I; ++J) {
- const MCDCRecord::TestVector &B = ExecVectors[J];
- // Enumerate two execution vectors whose outcomes are
diff erent.
- if (A[NumConditions] == B[NumConditions])
- continue;
+ for (unsigned I = NumExecVectorsF; I < NumTVs; ++I) {
+ const auto &[A, ACond] = ExecVectors[I];
+ assert(ACond == MCDCRecord::MCDC_True);
+ for (unsigned J = 0; J < NumExecVectorsF; ++J) {
+ const auto &[B, BCond] = ExecVectors[J];
+ assert(BCond == MCDCRecord::MCDC_False);
unsigned Flip = NumConditions, Idx;
for (Idx = 0; Idx < NumConditions; ++Idx) {
MCDCRecord::CondState ACond = A[Idx], BCond = B[Idx];
More information about the llvm-commits
mailing list