Skip to content

Commit

Permalink
[VPlan] Use VPDominatorTree in VPlanVerifier .
Browse files Browse the repository at this point in the history
Use VPDominatorTree to generalize def-use verification.

Depends on D140513.

Reviewed By: Ayal

Differential Revision: https://reviews.llvm.org/D140514
  • Loading branch information
fhahn committed Jan 25, 2023
1 parent 93aa412 commit b6b3d20
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 41 deletions.
45 changes: 12 additions & 33 deletions llvm/lib/Transforms/Vectorize/VPlanVerifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
#include "VPlanVerifier.h"
#include "VPlan.h"
#include "VPlanCFG.h"
#include "VPlanDominatorTree.h"
#include "llvm/ADT/DepthFirstIterator.h"
#include "llvm/Support/CommandLine.h"

Expand Down Expand Up @@ -189,9 +190,8 @@ static bool verifyPhiRecipes(const VPBasicBlock *VPBB) {
return true;
}

static bool
verifyVPBasicBlock(const VPBasicBlock *VPBB,
DenseMap<const VPBlockBase *, unsigned> &BlockNumbering) {
static bool verifyVPBasicBlock(const VPBasicBlock *VPBB,
VPDominatorTree &VPDT) {
if (!verifyPhiRecipes(VPBB))
return false;

Expand All @@ -206,7 +206,8 @@ verifyVPBasicBlock(const VPBasicBlock *VPBB,
for (const VPValue *V : R.definedValues()) {
for (const VPUser *U : V->users()) {
auto *UI = dyn_cast<VPRecipeBase>(U);
if (!UI || isa<VPHeaderPHIRecipe>(UI))
// TODO: check dominance of incoming values for phis properly.
if (!UI || isa<VPHeaderPHIRecipe>(UI) || isa<VPPredInstPHIRecipe>(UI))
continue;

// If the user is in the same block, check it comes after R in the
Expand All @@ -219,27 +220,7 @@ verifyVPBasicBlock(const VPBasicBlock *VPBB,
continue;
}

// Skip blocks outside any region for now and blocks outside
// replicate-regions.
auto *ParentR = VPBB->getParent();
if (!ParentR || !ParentR->isReplicator())
continue;

// For replicators, verify that VPPRedInstPHIRecipe defs are only used
// in subsequent blocks.
if (isa<VPPredInstPHIRecipe>(&R)) {
auto I = BlockNumbering.find(UI->getParent());
unsigned BlockNumber = I == BlockNumbering.end() ? std::numeric_limits<unsigned>::max() : I->second;
if (BlockNumber < BlockNumbering[ParentR]) {
errs() << "Use before def!\n";
return false;
}
continue;
}

// All non-VPPredInstPHIRecipe recipes in the block must be used in
// the replicate region only.
if (UI->getParent()->getParent() != ParentR) {
if (!VPDT.dominates(VPBB, UI->getParent())) {
errs() << "Use before def!\n";
return false;
}
Expand All @@ -250,15 +231,13 @@ verifyVPBasicBlock(const VPBasicBlock *VPBB,
}

bool VPlanVerifier::verifyPlanIsValid(const VPlan &Plan) {
DenseMap<const VPBlockBase *, unsigned> BlockNumbering;
unsigned Cnt = 0;
VPDominatorTree VPDT;
VPDT.recalculate(const_cast<VPlan &>(Plan));

auto Iter = vp_depth_first_deep(Plan.getEntry());
for (const VPBlockBase *VPB : Iter) {
BlockNumbering[VPB] = Cnt++;
auto *VPBB = dyn_cast<VPBasicBlock>(VPB);
if (!VPBB)
continue;
if (!verifyVPBasicBlock(VPBB, BlockNumbering))
for (const VPBasicBlock *VPBB :
VPBlockUtils::blocksOnly<const VPBasicBlock>(Iter)) {
if (!verifyVPBasicBlock(VPBB, VPDT))
return false;
}

Expand Down
14 changes: 6 additions & 8 deletions llvm/unittests/Transforms/Vectorize/VPlanVerifierTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -57,14 +57,13 @@ TEST(VPVerifierTest, VPInstructionUseBeforeDefDifferentBB) {
VPlan Plan;
Plan.setEntry(VPBB1);

// TODO: UseI uses DefI but DefI does not dominate UseI. Currently missed by
// the verifier.
#if GTEST_HAS_STREAM_REDIRECTION
::testing::internal::CaptureStderr();
#endif
EXPECT_TRUE(VPlanVerifier::verifyPlanIsValid(Plan));
EXPECT_FALSE(VPlanVerifier::verifyPlanIsValid(Plan));
#if GTEST_HAS_STREAM_REDIRECTION
EXPECT_STREQ("", ::testing::internal::GetCapturedStderr().c_str());
EXPECT_STREQ("Use before def!\n",
::testing::internal::GetCapturedStderr().c_str());
#endif
}

Expand Down Expand Up @@ -99,14 +98,13 @@ TEST(VPVerifierTest, VPBlendUseBeforeDefDifferentBB) {
VPlan Plan;
Plan.setEntry(VPBB1);

// TODO: Blend uses Def but Def does not dominate Blend. Currently missed by
// the verifier.
#if GTEST_HAS_STREAM_REDIRECTION
::testing::internal::CaptureStderr();
#endif
EXPECT_TRUE(VPlanVerifier::verifyPlanIsValid(Plan));
EXPECT_FALSE(VPlanVerifier::verifyPlanIsValid(Plan));
#if GTEST_HAS_STREAM_REDIRECTION
EXPECT_STREQ("", ::testing::internal::GetCapturedStderr().c_str());
EXPECT_STREQ("Use before def!\n",
::testing::internal::GetCapturedStderr().c_str());
#endif

delete Phi;
Expand Down

0 comments on commit b6b3d20

Please sign in to comment.