[PATCH] D89632: [DomTree] Accept Value as Def (NFC)
Nikita Popov via Phabricator via llvm-commits
llvm-commits at lists.llvm.org
Sat Oct 17 12:01:56 PDT 2020
nikic created this revision.
nikic added reviewers: asbirlea, kuhar, dblaikie, jdoerfert.
Herald added subscribers: llvm-commits, hiraditya.
Herald added a project: LLVM.
nikic requested review of this revision.
Non-instruction defs like arguments, constants or global values always dominate all instructions/uses inside the function. This case currently needs to be treated separately by the caller, see https://reviews.llvm.org/D89623#inline-832818 for an example. This patch makes the dominator tree APIs accept a Value instead of an Instruction and always returns true for the non-Instruction case.
A complication here is that BasicBlocks are also Values. For that reason we can't support the `dominates(Value *, BasicBlock *)` variant, as it would conflict with `dominates(BasicBlock *, BasicBlock *)`, which has different semantics. For the other two APIs we assert that the passed value is not a BasicBlock.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D89632
Files:
llvm/include/llvm/IR/Dominators.h
llvm/lib/IR/Dominators.cpp
llvm/unittests/IR/DominatorTreeTest.cpp
Index: llvm/unittests/IR/DominatorTreeTest.cpp
===================================================================
--- llvm/unittests/IR/DominatorTreeTest.cpp
+++ llvm/unittests/IR/DominatorTreeTest.cpp
@@ -1071,3 +1071,32 @@
EXPECT_TRUE(DT->dominates(E23, E23));
});
}
+
+TEST(DominatorTree, ValueDomination) {
+ StringRef ModuleString = R"(
+ @foo = global i8 0
+ define i8 @f(i8 %arg) {
+ ret i8 %arg
+ }
+ )";
+
+ LLVMContext Context;
+ std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString);
+
+ runWithDomTree(*M, "f",
+ [&](Function &F, DominatorTree *DT, PostDominatorTree *PDT) {
+ Argument *A = F.getArg(0);
+ GlobalValue *G = M->getNamedValue("foo");
+ Constant *C = ConstantInt::getNullValue(Type::getInt8Ty(Context));
+
+ Instruction *I = F.getEntryBlock().getTerminator();
+ EXPECT_TRUE(DT->dominates(A, I));
+ EXPECT_TRUE(DT->dominates(G, I));
+ EXPECT_TRUE(DT->dominates(C, I));
+
+ const Use &U = I->getOperandUse(0);
+ EXPECT_TRUE(DT->dominates(A, U));
+ EXPECT_TRUE(DT->dominates(G, U));
+ EXPECT_TRUE(DT->dominates(C, U));
+ });
+}
Index: llvm/lib/IR/Dominators.cpp
===================================================================
--- llvm/lib/IR/Dominators.cpp
+++ llvm/lib/IR/Dominators.cpp
@@ -115,8 +115,14 @@
// dominates - Return true if Def dominates a use in User. This performs
// the special checks necessary if Def and User are in the same basic block.
// Note that Def doesn't dominate a use in Def itself!
-bool DominatorTree::dominates(const Instruction *Def,
+bool DominatorTree::dominates(const Value *DefV,
const Instruction *User) const {
+ const Instruction *Def = dyn_cast<Instruction>(DefV);
+ if (!Def) {
+ assert(!isa<BasicBlock>(DefV) && "Should not be called with basic blocks");
+ return true; // Arguments, constants, globals dominate everything.
+ }
+
const BasicBlock *UseBB = User->getParent();
const BasicBlock *DefBB = Def->getParent();
@@ -250,7 +256,13 @@
return dominates(BBE, UseBB);
}
-bool DominatorTree::dominates(const Instruction *Def, const Use &U) const {
+bool DominatorTree::dominates(const Value *DefV, const Use &U) const {
+ const Instruction *Def = dyn_cast<Instruction>(DefV);
+ if (!Def) {
+ assert(!isa<BasicBlock>(DefV) && "Should not be called with basic blocks");
+ return true; // Arguments, constants, globals dominate everything.
+ }
+
Instruction *UserInst = cast<Instruction>(U.getUser());
const BasicBlock *DefBB = Def->getParent();
Index: llvm/include/llvm/IR/Dominators.h
===================================================================
--- llvm/include/llvm/IR/Dominators.h
+++ llvm/include/llvm/IR/Dominators.h
@@ -169,8 +169,10 @@
///
/// This performs the special checks necessary if Def and User are in the same
/// basic block. Note that Def doesn't dominate a use in Def itself!
- bool dominates(const Instruction *Def, const Use &U) const;
- bool dominates(const Instruction *Def, const Instruction *User) const;
+ bool dominates(const Value *Def, const Use &U) const;
+ bool dominates(const Value *Def, const Instruction *User) const;
+ // Does not accept Value to avoid ambiguity with dominance checks between
+ // two basic blocks.
bool dominates(const Instruction *Def, const BasicBlock *BB) const;
/// Return true if an edge dominates a use.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D89632.298845.patch
Type: text/x-patch
Size: 3430 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20201017/dfa874b0/attachment.bin>
More information about the llvm-commits
mailing list