[llvm] [PredicateInfo] Support `PredicateInfo` by adding `PHI` nodes that pick up info from created branch predicates (PR #151132)
Yingwei Zheng via llvm-commits
llvm-commits at lists.llvm.org
Fri Dec 12 07:57:07 PST 2025
================
@@ -460,6 +471,114 @@ void PredicateInfoBuilder::processSwitch(
}
}
+void PredicateInfoBuilder::identifyPHICandidates(
+ SmallVectorImpl<Value *> &OpsToRename) {
+ for (Value *Op : OpsToRename) {
+ const auto &ValueInfo = getValueInfo(Op);
+ SmallPtrSet<BasicBlock *, 4> DefiningBlocks;
+ for (const auto *PInfo : ValueInfo.Infos) {
+ if (auto *PBranch = dyn_cast<PredicateBranch>(PInfo)) {
+ DefiningBlocks.insert(PBranch->From);
+ } else if (auto *PSwitch = dyn_cast<PredicateSwitch>(PInfo)) {
+ DefiningBlocks.insert(PSwitch->From);
+ }
+ }
+
+ if (DefiningBlocks.size() > 1) {
+ SmallPtrSet<BasicBlock *, 8> PHIBlocks;
+ needsPHIInsertion(Op, DefiningBlocks, PHIBlocks);
+ for (BasicBlock *PHIBlock : PHIBlocks) {
+ PHICandidates[PHIBlock].push_back(Op);
+ }
+ }
+ }
+}
+
+void PredicateInfoBuilder::needsPHIInsertion(
+ Value *Op, const SmallPtrSetImpl<BasicBlock *> &DefiningBlocks,
+ SmallPtrSetImpl<BasicBlock *> &PHIBlocks) {
+ IDFCalculator<false> IDF(DT);
+ IDF.setDefiningBlocks(DefiningBlocks);
+
+ SmallPtrSet<BasicBlock *, 8> LiveInBlocks;
+ for (auto CurUser = Op->users().begin(); CurUser != Op->users().end();
+ ++CurUser) {
+ if (auto *I = dyn_cast<Instruction>(*CurUser)) {
+ LiveInBlocks.insert(I->getParent());
+ }
+ }
+ IDF.setLiveInBlocks(LiveInBlocks);
+
+ SmallVector<BasicBlock *, 4> IDFBlocks;
+ IDF.calculate(IDFBlocks);
+
+ for (const auto &IDFBlock : IDFBlocks) {
+ PHIBlocks.insert(std::move(IDFBlock));
+ }
+}
+
+PHINode *PredicateInfoBuilder::insertPredicatePHIs(
+ Value *Op, BasicBlock *PHIBlock, SmallVectorImpl<Value *> &OpsToRename) {
+ IRBuilder<> Builder(&PHIBlock->front());
+
+ PHINode *PHI = Builder.CreatePHI(Op->getType(), pred_size(PHIBlock),
+ Op->getName() + ".predicate.phi");
+ const auto &ValueInfo = getValueInfo(Op);
+
+ for (BasicBlock *Pred : predecessors(PHIBlock)) {
+ Value *IncomingValue = nullptr;
+ for (const auto *PInfo : ValueInfo.Infos) {
+ if (auto *PBranch = dyn_cast<PredicateBranch>(PInfo)) {
+ if (PBranch->From == Pred && PBranch->To == PHIBlock) {
+ IncomingValue = PBranch->OriginalOp;
+ }
+ } else if (auto *PSwitch = dyn_cast<PredicateSwitch>(PInfo)) {
+ if (PSwitch->From == Pred && PSwitch->To == PHIBlock) {
+ IncomingValue = PSwitch->OriginalOp;
+ }
+ }
+ }
+ if (IncomingValue) {
+ PHI->addIncoming(IncomingValue, Pred);
+ } else {
+ PHI->eraseFromParent();
+ return nullptr;
+ }
+ }
+
+ return PHI;
+}
+
+void PredicateInfoBuilder::processPredicatePHIs(
+ SmallVectorImpl<Value *> &OpsToRename) {
+ SmallVector<PHINode *, 4> InsertedPHINodes;
+
+ for (const auto &PHICandidate : PHICandidates) {
+ BasicBlock *PHIBlock = PHICandidate.first;
+ for (Value *Op : PHICandidate.second) {
+ auto *PHI = insertPredicatePHIs(Op, PHIBlock, OpsToRename);
+ InsertedPHINodes.push_back(PHI);
+ }
+ }
+
+ size_t Idx = 0, NumNodes = InsertedPHINodes.size();
+ for (const auto &PHICandidate : PHICandidates) {
+ BasicBlock *PHIBlock = PHICandidate.first;
+ for (Value *Op : PHICandidate.second) {
+ while (Idx < NumNodes && InsertedPHINodes[Idx] == nullptr) {
----------------
dtcxzyw wrote:
I don't understand this part. Can you add some comments?
https://github.com/llvm/llvm-project/pull/151132
More information about the llvm-commits
mailing list