summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Transforms
diff options
context:
space:
mode:
authorSanjay Patel <spatel@rotateright.com>2018-02-21 00:01:45 +0000
committerSanjay Patel <spatel@rotateright.com>2018-02-21 00:01:45 +0000
commit6f716a7c5e9c910bf3e098b27b10229c78412455 (patch)
tree59eeaffcd58439ff24ddadc4095472ed7525f6af /llvm/lib/Transforms
parentd8dd0151fc12fbbb3f15f71174452c81001a902c (diff)
downloadbcm5719-llvm-6f716a7c5e9c910bf3e098b27b10229c78412455.tar.gz
bcm5719-llvm-6f716a7c5e9c910bf3e098b27b10229c78412455.zip
[InstCombine] C / -X --> -C / X
We already do this in DAGCombiner, but it should also be good to eliminate the fsub use in IR. This is similar to rL325648. llvm-svn: 325649
Diffstat (limited to 'llvm/lib/Transforms')
-rw-r--r--llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp25
1 files changed, 17 insertions, 8 deletions
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp b/llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
index ec62beb4fe9..7c674bb83b2 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
@@ -1316,21 +1316,30 @@ static Instruction *foldFDivConstantDivisor(BinaryOperator &I) {
Instruction::FMul, I.getOperand(0), RecipC, &I);
}
-/// Try to reassociate C / X expressions where X includes another constant.
+/// Remove negation and try to reassociate constant math.
static Instruction *foldFDivConstantDividend(BinaryOperator &I) {
- Constant *C1;
- if (!I.hasAllowReassoc() || !I.hasAllowReciprocal() ||
- !match(I.getOperand(0), m_Constant(C1)))
+ Constant *C;
+ if (!match(I.getOperand(0), m_Constant(C)))
return nullptr;
+ // C / -X --> -C / X
Value *X;
+ if (match(I.getOperand(1), m_FNeg(m_Value(X)))) {
+ return BinaryOperator::CreateWithCopiedFlags(
+ Instruction::FDiv, ConstantExpr::getFNeg(C), X, &I);
+ }
+
+ if (!I.hasAllowReassoc() || !I.hasAllowReciprocal())
+ return nullptr;
+
+ // Try to reassociate C / X expressions where X includes another constant.
Constant *C2, *NewC = nullptr;
if (match(I.getOperand(1), m_FMul(m_Value(X), m_Constant(C2)))) {
- // C1 / (X * C2) --> (C1 / C2) / X
- NewC = ConstantExpr::getFDiv(C1, C2);
+ // C / (X * C2) --> (C / C2) / X
+ NewC = ConstantExpr::getFDiv(C, C2);
} else if (match(I.getOperand(1), m_FDiv(m_Value(X), m_Constant(C2)))) {
- // C1 / (X / C2) --> (C1 * C2) / X
- NewC = ConstantExpr::getFMul(C1, C2);
+ // C / (X / C2) --> (C * C2) / X
+ NewC = ConstantExpr::getFMul(C, C2);
}
// Disallow denormal constants because we don't know what would happen
// on all targets.
OpenPOWER on IntegriCloud