diff --git a/llvm/include/llvm/SandboxIR/Instruction.h b/llvm/include/llvm/SandboxIR/Instruction.h index fb3bcbdc99dbf3..c17188ce90c7d0 100644 --- a/llvm/include/llvm/SandboxIR/Instruction.h +++ b/llvm/include/llvm/SandboxIR/Instruction.h @@ -335,26 +335,6 @@ class Instruction : public User { // TODO: Missing functions. - bool isStackSaveOrRestoreIntrinsic() const { - auto *I = cast(Val); - return match(I, - PatternMatch::m_Intrinsic()) || - match(I, PatternMatch::m_Intrinsic()); - } - - /// We consider \p I as a Memory Dependency Candidate instruction if it - /// reads/write memory or if it has side-effects. This is used by the - /// dependency graph. - bool isMemDepCandidate() const { - auto *I = cast(Val); - return I->mayReadOrWriteMemory() && - (!isa(I) || - (cast(I)->getIntrinsicID() != - Intrinsic::sideeffect && - cast(I)->getIntrinsicID() != - Intrinsic::pseudoprobe)); - } - #ifndef NDEBUG void dumpOS(raw_ostream &OS) const override; #endif diff --git a/llvm/include/llvm/SandboxIR/Utils.h b/llvm/include/llvm/SandboxIR/Utils.h index c25edd7dc74e0f..510ae8c10e62f3 100644 --- a/llvm/include/llvm/SandboxIR/Utils.h +++ b/llvm/include/llvm/SandboxIR/Utils.h @@ -99,6 +99,27 @@ class Utils { return false; return *Diff > 0; } + + static bool isStackSaveOrRestoreIntrinsic(Instruction *I) { + auto *LLVMI = cast(I->Val); + return match(LLVMI, + PatternMatch::m_Intrinsic()) || + match(LLVMI, + PatternMatch::m_Intrinsic()); + } + + /// We consider \p I as a Memory Dependency Candidate instruction if it + /// reads/write memory or if it has side-effects. This is used by the + /// dependency graph. + static bool isMemDepCandidate(Instruction *I) { + auto *LLVMI = cast(I->Val); + return LLVMI->mayReadOrWriteMemory() && + (!isa(LLVMI) || + (cast(LLVMI)->getIntrinsicID() != + Intrinsic::sideeffect && + cast(LLVMI)->getIntrinsicID() != + Intrinsic::pseudoprobe)); + } }; } // namespace llvm::sandboxir diff --git a/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/DependencyGraph.h b/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/DependencyGraph.h index 0ddc227e3a02b4..5b2089791decb0 100644 --- a/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/DependencyGraph.h +++ b/llvm/include/llvm/Transforms/Vectorize/SandboxVectorizer/DependencyGraph.h @@ -25,6 +25,7 @@ #include "llvm/ADT/DenseMap.h" #include "llvm/ADT/iterator_range.h" #include "llvm/SandboxIR/Instruction.h" +#include "llvm/SandboxIR/Utils.h" #include "llvm/Transforms/Vectorize/SandboxVectorizer/Interval.h" namespace llvm::sandboxir { @@ -63,10 +64,10 @@ class DGNode { /// \Returns true if \p I is a memory dependency candidate instruction. static bool isMemDepCandidate(Instruction *I) { AllocaInst *Alloca; - return I->isMemDepCandidate() || + return Utils::isMemDepCandidate(I) || ((Alloca = dyn_cast(I)) && Alloca->isUsedWithInAlloca()) || - I->isStackSaveOrRestoreIntrinsic(); + Utils::isStackSaveOrRestoreIntrinsic(I); } Instruction *getInstruction() const { return I; } diff --git a/llvm/unittests/SandboxIR/SandboxIRTest.cpp b/llvm/unittests/SandboxIR/SandboxIRTest.cpp index 01940e7dccbf87..0ab0eb6a434d8f 100644 --- a/llvm/unittests/SandboxIR/SandboxIRTest.cpp +++ b/llvm/unittests/SandboxIR/SandboxIRTest.cpp @@ -1977,76 +1977,6 @@ define void @foo(i8 %v1, ptr %ptr) { } } -TEST_F(SandboxIRTest, Instruction_isStackSaveOrRestoreIntrinsic) { - parseIR(C, R"IR( -declare void @llvm.sideeffect() -define void @foo(i8 %v1, ptr %ptr) { - %add = add i8 %v1, %v1 - %stacksave = call ptr @llvm.stacksave() - call void @llvm.stackrestore(ptr %stacksave) - call void @llvm.sideeffect() - ret void -} -)IR"); - llvm::Function *LLVMF = &*M->getFunction("foo"); - sandboxir::Context Ctx(C); - sandboxir::Function *F = Ctx.createFunction(LLVMF); - auto *BB = &*F->begin(); - auto It = BB->begin(); - auto *Add = cast(&*It++); - auto *StackSave = cast(&*It++); - auto *StackRestore = cast(&*It++); - auto *Other = cast(&*It++); - auto *Ret = cast(&*It++); - - EXPECT_FALSE(Add->isStackSaveOrRestoreIntrinsic()); - EXPECT_TRUE(StackSave->isStackSaveOrRestoreIntrinsic()); - EXPECT_TRUE(StackRestore->isStackSaveOrRestoreIntrinsic()); - EXPECT_FALSE(Other->isStackSaveOrRestoreIntrinsic()); - EXPECT_FALSE(Ret->isStackSaveOrRestoreIntrinsic()); -} - -TEST_F(SandboxIRTest, Instruction_isMemDepCandidate) { - parseIR(C, R"IR( -declare void @llvm.fake.use(...) -declare void @llvm.sideeffect() -declare void @llvm.pseudoprobe(i64, i64, i32, i64) -declare void @bar() -define void @foo(i8 %v1, ptr %ptr) { - %add0 = add i8 %v1, %v1 - %ld0 = load i8, ptr %ptr - store i8 %v1, ptr %ptr - call void @llvm.sideeffect() - call void @llvm.pseudoprobe(i64 42, i64 1, i32 0, i64 -1) - call void @llvm.fake.use(ptr %ptr) - call void @bar() - ret void -} -)IR"); - llvm::Function *LLVMF = &*M->getFunction("foo"); - sandboxir::Context Ctx(C); - sandboxir::Function *F = Ctx.createFunction(LLVMF); - auto *BB = &*F->begin(); - auto It = BB->begin(); - auto *Add0 = cast(&*It++); - auto *Ld0 = cast(&*It++); - auto *St0 = cast(&*It++); - auto *SideEffect0 = cast(&*It++); - auto *PseudoProbe0 = cast(&*It++); - auto *OtherIntrinsic0 = cast(&*It++); - auto *CallBar = cast(&*It++); - auto *Ret = cast(&*It++); - - EXPECT_FALSE(Add0->isMemDepCandidate()); - EXPECT_TRUE(Ld0->isMemDepCandidate()); - EXPECT_TRUE(St0->isMemDepCandidate()); - EXPECT_FALSE(SideEffect0->isMemDepCandidate()); - EXPECT_FALSE(PseudoProbe0->isMemDepCandidate()); - EXPECT_TRUE(OtherIntrinsic0->isMemDepCandidate()); - EXPECT_TRUE(CallBar->isMemDepCandidate()); - EXPECT_FALSE(Ret->isMemDepCandidate()); -} - TEST_F(SandboxIRTest, VAArgInst) { parseIR(C, R"IR( define void @foo(ptr %va) { diff --git a/llvm/unittests/SandboxIR/UtilsTest.cpp b/llvm/unittests/SandboxIR/UtilsTest.cpp index 2d76a20071d2ed..16eb1aead34668 100644 --- a/llvm/unittests/SandboxIR/UtilsTest.cpp +++ b/llvm/unittests/SandboxIR/UtilsTest.cpp @@ -173,3 +173,75 @@ define void @foo(float %arg0, double %arg1, i8 %arg2, i64 %arg3, ptr %arg4) { EXPECT_EQ(sandboxir::Utils::getNumBits(L2), 8u); EXPECT_EQ(sandboxir::Utils::getNumBits(L3), 64u); } + +TEST_F(UtilsTest, Instruction_isStackSaveOrRestoreIntrinsic) { + parseIR(C, R"IR( +declare void @llvm.sideeffect() +define void @foo(i8 %v1, ptr %ptr) { + %add = add i8 %v1, %v1 + %stacksave = call ptr @llvm.stacksave() + call void @llvm.stackrestore(ptr %stacksave) + call void @llvm.sideeffect() + ret void +} +)IR"); + llvm::Function *LLVMF = &*M->getFunction("foo"); + sandboxir::Context Ctx(C); + sandboxir::Function *F = Ctx.createFunction(LLVMF); + auto *BB = &*F->begin(); + auto It = BB->begin(); + auto *Add = cast(&*It++); + auto *StackSave = cast(&*It++); + auto *StackRestore = cast(&*It++); + auto *Other = cast(&*It++); + auto *Ret = cast(&*It++); + + EXPECT_FALSE(sandboxir::Utils::isStackSaveOrRestoreIntrinsic(Add)); + EXPECT_TRUE(sandboxir::Utils::isStackSaveOrRestoreIntrinsic(StackSave)); + EXPECT_TRUE(sandboxir::Utils::isStackSaveOrRestoreIntrinsic(StackRestore)); + EXPECT_FALSE(sandboxir::Utils::isStackSaveOrRestoreIntrinsic(Other)); + EXPECT_FALSE(sandboxir::Utils::isStackSaveOrRestoreIntrinsic(Ret)); +} + +TEST_F(UtilsTest, Instruction_isMemDepCandidate) { + parseIR(C, R"IR( +declare void @llvm.fake.use(...) +declare void @llvm.sideeffect() +declare void @llvm.pseudoprobe(i64, i64, i32, i64) +declare void @bar() +define void @foo(i8 %v1, ptr %ptr) { + %add0 = add i8 %v1, %v1 + %ld0 = load i8, ptr %ptr + store i8 %v1, ptr %ptr + call void @llvm.sideeffect() + call void @llvm.pseudoprobe(i64 42, i64 1, i32 0, i64 -1) + call void @llvm.fake.use(ptr %ptr) + call void @bar() + ret void +} +)IR"); + llvm::Function *LLVMF = &*M->getFunction("foo"); + sandboxir::Context Ctx(C); + sandboxir::Function *F = Ctx.createFunction(LLVMF); + auto *BB = &*F->begin(); + auto It = BB->begin(); + auto *Add0 = cast(&*It++); + auto *Ld0 = cast(&*It++); + auto *St0 = cast(&*It++); + auto *SideEffect0 = cast(&*It++); + auto *PseudoProbe0 = cast(&*It++); + auto *OtherIntrinsic0 = cast(&*It++); + auto *CallBar = cast(&*It++); + auto *Ret = cast(&*It++); + + using Utils = sandboxir::Utils; + + EXPECT_FALSE(Utils::isMemDepCandidate(Add0)); + EXPECT_TRUE(Utils::isMemDepCandidate(Ld0)); + EXPECT_TRUE(Utils::isMemDepCandidate(St0)); + EXPECT_FALSE(Utils::isMemDepCandidate(SideEffect0)); + EXPECT_FALSE(Utils::isMemDepCandidate(PseudoProbe0)); + EXPECT_TRUE(Utils::isMemDepCandidate(OtherIntrinsic0)); + EXPECT_TRUE(Utils::isMemDepCandidate(CallBar)); + EXPECT_FALSE(Utils::isMemDepCandidate(Ret)); +}