diff options
author | Nick Desaulniers <ndesaulniers@google.com> | 2023-02-16 17:44:02 -0800 |
---|---|---|
committer | Nick Desaulniers <ndesaulniers@google.com> | 2023-02-16 17:58:33 -0800 |
commit | 45a291b5f609fc7edd8c526772e491d68b210dbe (patch) | |
tree | d276062285f8832e92314eb6ceed7d8a139a7ad8 /llvm/unittests/IR/DominatorTreeTest.cpp | |
parent | df277ec67efd1bec3aa2fa8b02d84db0ea8b2f1c (diff) | |
download | llvm-45a291b5f609fc7edd8c526772e491d68b210dbe.zip llvm-45a291b5f609fc7edd8c526772e491d68b210dbe.tar.gz llvm-45a291b5f609fc7edd8c526772e491d68b210dbe.tar.bz2 |
[Dominators] check indirect branches of callbr
This will be necessary to support outputs from asm goto along indirect
edges.
Test via:
$ pushd llvm/build; ninja IRTests; popd
$ ./llvm/build/unittests/IR/IRTests \
--gtest_filter=DominatorTree.CallBrDomination
Also, return nullptr in Instruction::getInsertionPointAfterDef for
CallBrInst as was recommened in
https://reviews.llvm.org/D135997#3991427. The following phab review was
folded into this commit: https://reviews.llvm.org/D140166
Link: Link: https://discourse.llvm.org/t/rfc-syncing-asm-goto-with-outputs-with-gcc/65453/8
Reviewed By: void, efriedma, ChuanqiXu, MaskRay
Differential Revision: https://reviews.llvm.org/D135997
Diffstat (limited to 'llvm/unittests/IR/DominatorTreeTest.cpp')
-rw-r--r-- | llvm/unittests/IR/DominatorTreeTest.cpp | 43 |
1 files changed, 43 insertions, 0 deletions
diff --git a/llvm/unittests/IR/DominatorTreeTest.cpp b/llvm/unittests/IR/DominatorTreeTest.cpp index 6260ce2..44bde74 100644 --- a/llvm/unittests/IR/DominatorTreeTest.cpp +++ b/llvm/unittests/IR/DominatorTreeTest.cpp @@ -1100,3 +1100,46 @@ TEST(DominatorTree, ValueDomination) { EXPECT_TRUE(DT->dominates(C, U)); }); } +TEST(DominatorTree, CallBrDomination) { + StringRef ModuleString = R"( +define void @x() { + %y = alloca i32 + %w = callbr i32 asm "", "=r,!i"() + to label %asm.fallthrough [label %z] + +asm.fallthrough: + br label %cleanup + +z: + store i32 %w, ptr %y + br label %cleanup + +cleanup: + ret void +})"; + + LLVMContext Context; + std::unique_ptr<Module> M = makeLLVMModule(Context, ModuleString); + + runWithDomTree( + *M, "x", [&](Function &F, DominatorTree *DT, PostDominatorTree *PDT) { + Function::iterator FI = F.begin(); + + BasicBlock *Entry = &*FI++; + BasicBlock *ASMFallthrough = &*FI++; + BasicBlock *Z = &*FI++; + + EXPECT_TRUE(DT->dominates(Entry, ASMFallthrough)); + EXPECT_TRUE(DT->dominates(Entry, Z)); + + BasicBlock::iterator BBI = Entry->begin(); + ++BBI; + Instruction &I = *BBI; + EXPECT_TRUE(isa<CallBrInst>(I)); + EXPECT_TRUE(isa<Value>(I)); + for (const User *U : I.users()) { + EXPECT_TRUE(isa<Instruction>(U)); + EXPECT_TRUE(DT->dominates(cast<Value>(&I), cast<Instruction>(U))); + } + }); +} |