[clang] e603451 - [X86] Support branch hint (#97721)
via cfe-commits
cfe-commits at lists.llvm.org
Sun Jul 7 22:12:55 PDT 2024
Author: Feng Zou
Date: 2024-07-08T13:12:50+08:00
New Revision: e603451f3cb16792fb46ab5f2fa50b05f3e5d935
URL: https://github.com/llvm/llvm-project/commit/e603451f3cb16792fb46ab5f2fa50b05f3e5d935
DIFF: https://github.com/llvm/llvm-project/commit/e603451f3cb16792fb46ab5f2fa50b05f3e5d935.diff
LOG: [X86] Support branch hint (#97721)
For more details about this feature, please refer to latest Intel 64 and
IA-32 Architectures Optimization Reference Manual Volume 1:
https://www.intel.com/content/www/us/en/content-details/821612/intel-64-and-ia-32-architectures-optimization-reference-manual-volume-1.html
Added:
llvm/test/CodeGen/X86/branch-hint.ll
Modified:
clang/lib/Basic/Targets/X86.cpp
clang/lib/Basic/Targets/X86.h
llvm/lib/Target/X86/X86.td
llvm/lib/Target/X86/X86MCInstLower.cpp
Removed:
################################################################################
diff --git a/clang/lib/Basic/Targets/X86.cpp b/clang/lib/Basic/Targets/X86.cpp
index 276d492955207..1f6fc842ddd95 100644
--- a/clang/lib/Basic/Targets/X86.cpp
+++ b/clang/lib/Basic/Targets/X86.cpp
@@ -457,6 +457,8 @@ bool X86TargetInfo::handleTargetFeatures(std::vector<std::string> &Features,
HasCF = true;
} else if (Feature == "+zu") {
HasZU = true;
+ } else if (Feature == "+branch-hint") {
+ HasBranchHint = true;
}
X86SSEEnum Level = llvm::StringSwitch<X86SSEEnum>(Feature)
@@ -1292,6 +1294,7 @@ bool X86TargetInfo::hasFeature(StringRef Feature) const {
.Case("nf", HasNF)
.Case("cf", HasCF)
.Case("zu", HasZU)
+ .Case("branch-hint", HasBranchHint)
.Default(false);
}
diff --git a/clang/lib/Basic/Targets/X86.h b/clang/lib/Basic/Targets/X86.h
index 5ce4953251bc3..a70711f4ae2bb 100644
--- a/clang/lib/Basic/Targets/X86.h
+++ b/clang/lib/Basic/Targets/X86.h
@@ -174,6 +174,7 @@ class LLVM_LIBRARY_VISIBILITY X86TargetInfo : public TargetInfo {
bool HasCF = false;
bool HasZU = false;
bool HasInlineAsmUseGPR32 = false;
+ bool HasBranchHint = false;
protected:
llvm::X86::CPUKind CPU = llvm::X86::CK_None;
diff --git a/llvm/lib/Target/X86/X86.td b/llvm/lib/Target/X86/X86.td
index 68b78c7c44771..fdd7d5f1ee0e7 100644
--- a/llvm/lib/Target/X86/X86.td
+++ b/llvm/lib/Target/X86/X86.td
@@ -749,6 +749,11 @@ def TuningUseGLMDivSqrtCosts
: SubtargetFeature<"use-glm-div-sqrt-costs", "UseGLMDivSqrtCosts", "true",
"Use Goldmont specific floating point div/sqrt costs">;
+// Starting with Redwood Cove architecture, the branch has branch taken hint
+// (i.e., instruction prefix 3EH).
+def TuningBranchHint: SubtargetFeature<"branch-hint", "HasBranchHint", "true",
+ "Target has branch hint feature">;
+
//===----------------------------------------------------------------------===//
// X86 CPU Families
// TODO: Remove these - use general tuning features to determine codegen.
@@ -1124,6 +1129,8 @@ def ProcessorFeatures {
FeaturePREFETCHI];
list<SubtargetFeature> GNRFeatures =
!listconcat(SPRFeatures, GNRAdditionalFeatures);
+ list<SubtargetFeature> GNRAdditionalTuning = [TuningBranchHint];
+ list<SubtargetFeature> GNRTuning = !listconcat(SPRTuning, GNRAdditionalTuning);
// Graniterapids D
list<SubtargetFeature> GNRDAdditionalFeatures = [FeatureAMXCOMPLEX];
@@ -1815,12 +1822,12 @@ def : ProcModel<"pantherlake", AlderlakePModel,
def : ProcModel<"clearwaterforest", AlderlakePModel,
ProcessorFeatures.CWFFeatures, ProcessorFeatures.ADLTuning>;
def : ProcModel<"graniterapids", SapphireRapidsModel,
- ProcessorFeatures.GNRFeatures, ProcessorFeatures.SPRTuning>;
+ ProcessorFeatures.GNRFeatures, ProcessorFeatures.GNRTuning>;
def : ProcModel<"emeraldrapids", SapphireRapidsModel,
- ProcessorFeatures.SPRFeatures, ProcessorFeatures.SPRTuning>;
+ ProcessorFeatures.SPRFeatures, ProcessorFeatures.GNRTuning>;
foreach P = ["graniterapids-d", "graniterapids_d"] in {
def : ProcModel<P, SapphireRapidsModel,
- ProcessorFeatures.GNRDFeatures, ProcessorFeatures.SPRTuning>;
+ ProcessorFeatures.GNRDFeatures, ProcessorFeatures.GNRTuning>;
}
// AMD CPUs.
diff --git a/llvm/lib/Target/X86/X86MCInstLower.cpp b/llvm/lib/Target/X86/X86MCInstLower.cpp
index 00f58f9432e4d..df20ecd1b9b21 100644
--- a/llvm/lib/Target/X86/X86MCInstLower.cpp
+++ b/llvm/lib/Target/X86/X86MCInstLower.cpp
@@ -25,6 +25,7 @@
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/ADT/StringExtras.h"
+#include "llvm/CodeGen/MachineBranchProbabilityInfo.h"
#include "llvm/CodeGen/MachineConstantPool.h"
#include "llvm/CodeGen/MachineFunction.h"
#include "llvm/CodeGen/MachineModuleInfoImpls.h"
@@ -54,6 +55,14 @@
using namespace llvm;
+static cl::opt<bool> EnableBranchHint("enable-branch-hint",
+ cl::desc("Enable branch hint."),
+ cl::init(false), cl::Hidden);
+static cl::opt<unsigned> BranchHintProbabilityThreshold(
+ "branch-hint-probability-threshold",
+ cl::desc("The probability threshold of enabling branch hint."),
+ cl::init(50), cl::Hidden);
+
namespace {
/// X86MCInstLower - This class is used to lower an MachineInstr into an MCInst.
@@ -2444,6 +2453,21 @@ void X86AsmPrinter::emitInstruction(const MachineInstr *MI) {
if (IndCSPrefix && MI->hasRegisterImplicitUseOperand(X86::R11))
EmitAndCountInstruction(MCInstBuilder(X86::CS_PREFIX));
break;
+ case X86::JCC_1:
+ // Two instruction prefixes (2EH for branch not-taken and 3EH for branch
+ // taken) are used as branch hints. Here we add branch taken prefix for
+ // jump instruction with higher probability than threshold.
+ if (getSubtarget().hasBranchHint() && EnableBranchHint) {
+ const MachineBranchProbabilityInfo *MBPI =
+ &getAnalysis<MachineBranchProbabilityInfoWrapperPass>().getMBPI();
+ MachineBasicBlock *DestBB = MI->getOperand(0).getMBB();
+ BranchProbability EdgeProb =
+ MBPI->getEdgeProbability(MI->getParent(), DestBB);
+ BranchProbability Threshold(BranchHintProbabilityThreshold, 100);
+ if (EdgeProb > Threshold)
+ EmitAndCountInstruction(MCInstBuilder(X86::DS_PREFIX));
+ }
+ break;
}
MCInst TmpInst;
diff --git a/llvm/test/CodeGen/X86/branch-hint.ll b/llvm/test/CodeGen/X86/branch-hint.ll
new file mode 100644
index 0000000000000..591fb324e1b7b
--- /dev/null
+++ b/llvm/test/CodeGen/X86/branch-hint.ll
@@ -0,0 +1,75 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 5
+; RUN: llc < %s -mtriple=x86_64 -mattr=+branch-hint -enable-branch-hint | FileCheck %s
+; RUN: llc < %s -mtriple=x86_64 -mattr=+branch-hint -enable-branch-hint -branch-hint-probability-threshold=50 | FileCheck %s
+; RUN: llc < %s -mtriple=x86_64 -mattr=+branch-hint -enable-branch-hint -branch-hint-probability-threshold=60 -tail-dup-placement=false | FileCheck --check-prefix=TH60 %s
+
+
+; Design: Add DS segment override prefix for condition branch who has high
+; probability to take (which is greater than the probability threshold of
+; enabling branch hint).
+
+define void @p51(i32 %x, ptr %p) {
+; CHECK-LABEL: p51:
+; CHECK: # %bb.0: # %entry
+; CHECK-NEXT: testl %edi, %edi
+; CHECK-NEXT: ds
+; CHECK-NEXT: je .LBB0_2
+; CHECK-NEXT: # %bb.1: # %if.then
+; CHECK-NEXT: movl %edi, (%rsi)
+; CHECK-NEXT: .LBB0_2: # %if.end
+; CHECK-NEXT: retq
+;
+; TH60-LABEL: p51:
+; TH60: # %bb.0: # %entry
+; TH60-NEXT: testl %edi, %edi
+; TH60-NEXT: je .LBB0_2
+; TH60-NEXT: # %bb.1: # %if.then
+; TH60-NEXT: movl %edi, (%rsi)
+; TH60-NEXT: .LBB0_2: # %if.end
+; TH60-NEXT: retq
+entry:
+ %tobool.not = icmp eq i32 %x, 0
+ br i1 %tobool.not, label %if.end, label %if.then, !prof !0
+
+if.then:
+ store i32 %x, ptr %p, align 4
+ br label %if.end
+
+if.end:
+ ret void
+}
+
+define void @p61(i32 %x, ptr %p) {
+; CHECK-LABEL: p61:
+; CHECK: # %bb.0: # %entry
+; CHECK-NEXT: testl %edi, %edi
+; CHECK-NEXT: jne .LBB1_1
+; CHECK-NEXT: # %bb.2: # %if.end
+; CHECK-NEXT: retq
+; CHECK-NEXT: .LBB1_1: # %if.then
+; CHECK-NEXT: movl %edi, (%rsi)
+; CHECK-NEXT: retq
+;
+; TH60-LABEL: p61:
+; TH60: # %bb.0: # %entry
+; TH60-NEXT: testl %edi, %edi
+; TH60-NEXT: ds
+; TH60-NEXT: je .LBB1_2
+; TH60-NEXT: # %bb.1: # %if.then
+; TH60-NEXT: movl %edi, (%rsi)
+; TH60-NEXT: .LBB1_2: # %if.end
+; TH60-NEXT: retq
+entry:
+ %tobool.not = icmp eq i32 %x, 0
+ br i1 %tobool.not, label %if.end, label %if.then, !prof !1
+
+if.then:
+ store i32 %x, ptr %p, align 4
+ br label %if.end
+
+if.end:
+ ret void
+}
+
+!0 = !{!"branch_weights", i32 51, i32 49}
+!1 = !{!"branch_weights", i32 61, i32 39}
\ No newline at end of file
More information about the cfe-commits
mailing list