summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--llvm/lib/Analysis/BranchProbabilityInfo.cpp16
-rw-r--r--llvm/test/Analysis/BranchProbabilityInfo/fcmp.ll41
-rw-r--r--llvm/test/CodeGen/SystemZ/call-05.ll3
3 files changed, 57 insertions, 3 deletions
diff --git a/llvm/lib/Analysis/BranchProbabilityInfo.cpp b/llvm/lib/Analysis/BranchProbabilityInfo.cpp
index 65c9cf2f06d..a06ee096d54 100644
--- a/llvm/lib/Analysis/BranchProbabilityInfo.cpp
+++ b/llvm/lib/Analysis/BranchProbabilityInfo.cpp
@@ -118,6 +118,13 @@ static const uint32_t ZH_NONTAKEN_WEIGHT = 12;
static const uint32_t FPH_TAKEN_WEIGHT = 20;
static const uint32_t FPH_NONTAKEN_WEIGHT = 12;
+/// This is the probability for an ordered floating point comparison.
+static const uint32_t FPH_ORD_WEIGHT = 1024 * 1024 - 1;
+/// This is the probability for an unordered floating point comparison, it means
+/// one or two of the operands are NaN. Usually it is used to test for an
+/// exceptional case, so the result is unlikely.
+static const uint32_t FPH_UNO_WEIGHT = 1;
+
/// Invoke-terminating normal branch taken weight
///
/// This is the weight for branching to the normal destination of an invoke
@@ -778,6 +785,8 @@ bool BranchProbabilityInfo::calcFloatingPointHeuristics(const BasicBlock *BB) {
if (!FCmp)
return false;
+ uint32_t TakenWeight = FPH_TAKEN_WEIGHT;
+ uint32_t NontakenWeight = FPH_NONTAKEN_WEIGHT;
bool isProb;
if (FCmp->isEquality()) {
// f1 == f2 -> Unlikely
@@ -786,9 +795,13 @@ bool BranchProbabilityInfo::calcFloatingPointHeuristics(const BasicBlock *BB) {
} else if (FCmp->getPredicate() == FCmpInst::FCMP_ORD) {
// !isnan -> Likely
isProb = true;
+ TakenWeight = FPH_ORD_WEIGHT;
+ NontakenWeight = FPH_UNO_WEIGHT;
} else if (FCmp->getPredicate() == FCmpInst::FCMP_UNO) {
// isnan -> Unlikely
isProb = false;
+ TakenWeight = FPH_ORD_WEIGHT;
+ NontakenWeight = FPH_UNO_WEIGHT;
} else {
return false;
}
@@ -798,8 +811,7 @@ bool BranchProbabilityInfo::calcFloatingPointHeuristics(const BasicBlock *BB) {
if (!isProb)
std::swap(TakenIdx, NonTakenIdx);
- BranchProbability TakenProb(FPH_TAKEN_WEIGHT,
- FPH_TAKEN_WEIGHT + FPH_NONTAKEN_WEIGHT);
+ BranchProbability TakenProb(TakenWeight, TakenWeight + NontakenWeight);
setEdgeProbability(BB, TakenIdx, TakenProb);
setEdgeProbability(BB, NonTakenIdx, TakenProb.getCompl());
return true;
diff --git a/llvm/test/Analysis/BranchProbabilityInfo/fcmp.ll b/llvm/test/Analysis/BranchProbabilityInfo/fcmp.ll
new file mode 100644
index 00000000000..8089916fb76
--- /dev/null
+++ b/llvm/test/Analysis/BranchProbabilityInfo/fcmp.ll
@@ -0,0 +1,41 @@
+; RUN: opt < %s -analyze -branch-prob | FileCheck %s
+
+; This function tests the floating point unorder comparison. The probability
+; of NaN should be extremely small.
+; CHECK: Printing analysis 'Branch Probability Analysis' for function 'uno'
+; CHECK: edge -> a probability is 0x00000800 / 0x80000000 = 0.00%
+; CHECK: edge -> b probability is 0x7ffff800 / 0x80000000 = 100.00% [HOT edge]
+
+define void @uno(float %val1, float %val2) {
+ %cond = fcmp uno float %val1, %val2
+ br i1 %cond, label %a, label %b
+
+a:
+ call void @fa()
+ ret void
+
+b:
+ call void @fb()
+ ret void
+}
+
+; This function tests the floating point order comparison.
+; CHECK: Printing analysis 'Branch Probability Analysis' for function 'ord'
+; CHECK: edge -> a probability is 0x7ffff800 / 0x80000000 = 100.00% [HOT edge]
+; CHECK: edge -> b probability is 0x00000800 / 0x80000000 = 0.00%
+
+define void @ord(float %val1, float %val2) {
+ %cond = fcmp ord float %val1, %val2
+ br i1 %cond, label %a, label %b
+
+a:
+ call void @fa()
+ ret void
+
+b:
+ call void @fb()
+ ret void
+}
+
+declare void @fa()
+declare void @fb()
diff --git a/llvm/test/CodeGen/SystemZ/call-05.ll b/llvm/test/CodeGen/SystemZ/call-05.ll
index 15704531d96..b958c0b6d0d 100644
--- a/llvm/test/CodeGen/SystemZ/call-05.ll
+++ b/llvm/test/CodeGen/SystemZ/call-05.ll
@@ -451,8 +451,9 @@ b:
define void @f25(float %val1, float %val2) {
; CHECK-LABEL: f25:
; CHECK: cebr %f0, %f2
-; CHECK: bor %r1
+; CHECK: jo
; CHECK: br %r14
+; CHECK: br %r1
%fun_a = load volatile void() *, void()** @fun_a;
%cond = fcmp uno float %val1, %val2;
br i1 %cond, label %a, label %b;
OpenPOWER on IntegriCloud