Skip to content
This repository was archived by the owner on Apr 23, 2020. It is now read-only.

Commit d7276a4

Browse files
committed
bpf: add variants of -mcpu=# and support for additional jmp insns
-mcpu=# will support: . generic: the default insn set . v1: insn set version 1, the same as generic . v2: insn set version 2, version 1 + additional jmp insns . probe: the compiler will probe the underlying kernel to decide proper version of insn set. We did not not use -mcpu=native since llc/llvm will interpret -mcpu=native as the underlying hardware architecture regardless of -march value. Currently, only x86_64 supports -mcpu=probe. Other architecture will silently revert to "generic". Also added -mcpu=help to print available cpu parameters. llvm will print out the information only if there are at least one cpu and at least one feature. Add an unused dummy feature to enable the printout. Examples for usage: $ llc -march=bpf -mcpu=v1 -filetype=asm t.ll $ llc -march=bpf -mcpu=v2 -filetype=asm t.ll $ llc -march=bpf -mcpu=generic -filetype=asm t.ll $ llc -march=bpf -mcpu=probe -filetype=asm t.ll $ llc -march=bpf -mcpu=v3 -filetype=asm t.ll 'v3' is not a recognized processor for this target (ignoring processor) ... $ llc -march=bpf -mcpu=help -filetype=asm t.ll Available CPUs for this target: generic - Select the generic processor. probe - Select the probe processor. v1 - Select the v1 processor. v2 - Select the v2 processor. Available features for this target: dummy - unused feature. Use +feature to enable a feature, or -feature to disable it. For example, llc -mcpu=mycpu -mattr=+feature1,-feature2 ... Signed-off-by: Daniel Borkmann <[email protected]> Signed-off-by: Yonghong Song <[email protected]> Acked-by: Alexei Starovoitov <[email protected]> git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@311522 91177308-0d34-0410-b5e6-96231b3b80d8
1 parent 212ebf2 commit d7276a4

File tree

9 files changed

+147
-17
lines changed

9 files changed

+147
-17
lines changed

include/llvm/Support/Host.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,7 @@ constexpr bool IsBigEndianHost = false;
9292
StringRef getHostCPUNameForPowerPC(const StringRef &ProcCpuinfoContent);
9393
StringRef getHostCPUNameForARM(const StringRef &ProcCpuinfoContent);
9494
StringRef getHostCPUNameForS390x(const StringRef &ProcCpuinfoContent);
95+
StringRef getHostCPUNameForBPF();
9596
}
9697
}
9798
}

lib/Support/Host.cpp

Lines changed: 38 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -267,6 +267,43 @@ StringRef sys::detail::getHostCPUNameForS390x(
267267
return "generic";
268268
}
269269

270+
StringRef sys::detail::getHostCPUNameForBPF() {
271+
#if !defined(__linux__) || !defined(__x86_64__)
272+
return "generic";
273+
#else
274+
uint8_t insns[40] __attribute__ ((aligned (8))) =
275+
/* BPF_MOV64_IMM(BPF_REG_0, 0) */
276+
{ 0xb7, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
277+
/* BPF_MOV64_IMM(BPF_REG_2, 1) */
278+
0xb7, 0x2, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0,
279+
/* BPF_JMP_REG(BPF_JLT, BPF_REG_0, BPF_REG_2, 1) */
280+
0xad, 0x20, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0,
281+
/* BPF_MOV64_IMM(BPF_REG_0, 1) */
282+
0xb7, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0,
283+
/* BPF_EXIT_INSN() */
284+
0x95, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 };
285+
286+
struct bpf_prog_load_attr {
287+
uint32_t prog_type;
288+
uint32_t insn_cnt;
289+
uint64_t insns;
290+
uint64_t license;
291+
uint32_t log_level;
292+
uint32_t log_size;
293+
uint64_t log_buf;
294+
uint32_t kern_version;
295+
uint32_t prog_flags;
296+
} attr = {};
297+
attr.prog_type = 1; /* BPF_PROG_TYPE_SOCKET_FILTER */
298+
attr.insn_cnt = 5;
299+
attr.insns = (uint64_t)insns;
300+
attr.license = (uint64_t)"DUMMY";
301+
302+
int fd = syscall(321 /* __NR_bpf */, 5 /* BPF_PROG_LOAD */, &attr, sizeof(attr));
303+
return (fd > 0) ? "v2" : "v1";
304+
#endif
305+
}
306+
270307
#if defined(__i386__) || defined(_M_IX86) || \
271308
defined(__x86_64__) || defined(_M_X64)
272309

@@ -1420,7 +1457,7 @@ bool sys::getHostCPUFeatures(StringMap<bool> &Features) {
14201457

14211458
Features["prefetchwt1"] = HasLeaf7 && (ECX & 1);
14221459
Features["avx512vbmi"] = HasLeaf7 && ((ECX >> 1) & 1) && HasAVX512Save;
1423-
Features["avx512vpopcntdq"] = HasLeaf7 && ((ECX >> 14) & 1) && HasAVX512Save;
1460+
Features["avx512vpopcntdq"] = HasLeaf7 && ((ECX >> 14) & 1) && HasAVX512Save;
14241461
// Enable protection keys
14251462
Features["pku"] = HasLeaf7 && ((ECX >> 4) & 1);
14261463

lib/Target/BPF/BPF.td

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,12 @@ class Proc<string Name, list<SubtargetFeature> Features>
1919
: Processor<Name, NoItineraries, Features>;
2020

2121
def : Proc<"generic", []>;
22+
def : Proc<"v1", []>;
23+
def : Proc<"v2", []>;
24+
def : Proc<"probe", []>;
25+
26+
def DummyFeature : SubtargetFeature<"dummy", "isDummyMode",
27+
"true", "unused feature">;
2228

2329
def BPFInstPrinter : AsmWriter {
2430
string AsmWriterClassName = "InstPrinter";

lib/Target/BPF/BPFISelLowering.cpp

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,9 @@ BPFTargetLowering::BPFTargetLowering(const TargetMachine &TM,
130130
MaxStoresPerMemset = MaxStoresPerMemsetOptSize = 128;
131131
MaxStoresPerMemcpy = MaxStoresPerMemcpyOptSize = 128;
132132
MaxStoresPerMemmove = MaxStoresPerMemmoveOptSize = 128;
133+
134+
// CPU/Feature control
135+
HasJmpExt = STI.getHasJmpExt();
133136
}
134137

135138
bool BPFTargetLowering::isOffsetFoldingLegal(const GlobalAddressSDNode *GA) const {
@@ -456,7 +459,8 @@ SDValue BPFTargetLowering::LowerBR_CC(SDValue Op, SelectionDAG &DAG) const {
456459
SDValue Dest = Op.getOperand(4);
457460
SDLoc DL(Op);
458461

459-
NegateCC(LHS, RHS, CC);
462+
if (!getHasJmpExt())
463+
NegateCC(LHS, RHS, CC);
460464

461465
return DAG.getNode(BPFISD::BR_CC, DL, Op.getValueType(), Chain, LHS, RHS,
462466
DAG.getConstant(CC, DL, MVT::i64), Dest);
@@ -470,7 +474,8 @@ SDValue BPFTargetLowering::LowerSELECT_CC(SDValue Op, SelectionDAG &DAG) const {
470474
ISD::CondCode CC = cast<CondCodeSDNode>(Op.getOperand(4))->get();
471475
SDLoc DL(Op);
472476

473-
NegateCC(LHS, RHS, CC);
477+
if (!getHasJmpExt())
478+
NegateCC(LHS, RHS, CC);
474479

475480
SDValue TargetCC = DAG.getConstant(CC, DL, MVT::i64);
476481

@@ -570,6 +575,18 @@ BPFTargetLowering::EmitInstrWithCustomInserter(MachineInstr &MI,
570575
case ISD::SETNE:
571576
NewCC = isSelectOp ? BPF::JNE_rr : BPF::JNE_ri;
572577
break;
578+
case ISD::SETLT:
579+
NewCC = isSelectOp ? BPF::JSLT_rr : BPF::JSLT_ri;
580+
break;
581+
case ISD::SETULT:
582+
NewCC = isSelectOp ? BPF::JULT_rr : BPF::JULT_ri;
583+
break;
584+
case ISD::SETLE:
585+
NewCC = isSelectOp ? BPF::JSLE_rr : BPF::JSLE_ri;
586+
break;
587+
case ISD::SETULE:
588+
NewCC = isSelectOp ? BPF::JULE_rr : BPF::JULE_ri;
589+
break;
573590
default:
574591
report_fatal_error("unimplemented select CondCode " + Twine(CC));
575592
}

lib/Target/BPF/BPFISelLowering.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,12 @@ class BPFTargetLowering : public TargetLowering {
5050
EmitInstrWithCustomInserter(MachineInstr &MI,
5151
MachineBasicBlock *BB) const override;
5252

53+
bool getHasJmpExt() const { return HasJmpExt; }
54+
5355
private:
56+
// Control Instruction Selection Features
57+
bool HasJmpExt;
58+
5459
SDValue LowerBR_CC(SDValue Op, SelectionDAG &DAG) const;
5560
SDValue LowerSELECT_CC(SDValue Op, SelectionDAG &DAG) const;
5661
SDValue LowerGlobalAddress(SDValue Op, SelectionDAG &DAG) const;

lib/Target/BPF/BPFInstrInfo.td

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,14 @@ def BPF_CC_GTU : PatLeaf<(i64 imm),
7979
[{return (N->getZExtValue() == ISD::SETUGT);}]>;
8080
def BPF_CC_GEU : PatLeaf<(i64 imm),
8181
[{return (N->getZExtValue() == ISD::SETUGE);}]>;
82+
def BPF_CC_LE : PatLeaf<(i64 imm),
83+
[{return (N->getZExtValue() == ISD::SETLE);}]>;
84+
def BPF_CC_LT : PatLeaf<(i64 imm),
85+
[{return (N->getZExtValue() == ISD::SETLT);}]>;
86+
def BPF_CC_LTU : PatLeaf<(i64 imm),
87+
[{return (N->getZExtValue() == ISD::SETULT);}]>;
88+
def BPF_CC_LEU : PatLeaf<(i64 imm),
89+
[{return (N->getZExtValue() == ISD::SETULE);}]>;
8290

8391
// jump instructions
8492
class JMP_RR<bits<4> Opc, string OpcodeStr, PatLeaf Cond>
@@ -136,6 +144,10 @@ defm JUGE : J<0x3, ">=", BPF_CC_GEU>;
136144
defm JNE : J<0x5, "!=", BPF_CC_NE>;
137145
defm JSGT : J<0x6, "s>", BPF_CC_GT>;
138146
defm JSGE : J<0x7, "s>=", BPF_CC_GE>;
147+
defm JULT : J<0xa, "<", BPF_CC_LTU>;
148+
defm JULE : J<0xb, "<=", BPF_CC_LEU>;
149+
defm JSLT : J<0xc, "s<", BPF_CC_LT>;
150+
defm JSLE : J<0xd, "s<=", BPF_CC_LE>;
139151
}
140152

141153
// ALU instructions

lib/Target/BPF/BPFSubtarget.cpp

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313

1414
#include "BPFSubtarget.h"
1515
#include "BPF.h"
16+
#include "llvm/Support/Host.h"
1617
#include "llvm/Support/TargetRegistry.h"
1718

1819
using namespace llvm;
@@ -25,7 +26,30 @@ using namespace llvm;
2526

2627
void BPFSubtarget::anchor() {}
2728

29+
BPFSubtarget &BPFSubtarget::initializeSubtargetDependencies(StringRef CPU,
30+
StringRef FS) {
31+
initializeEnvironment();
32+
initSubtargetFeatures(CPU, FS);
33+
return *this;
34+
}
35+
36+
void BPFSubtarget::initializeEnvironment() {
37+
HasJmpExt = false;
38+
}
39+
40+
void BPFSubtarget::initSubtargetFeatures(StringRef CPU, StringRef FS) {
41+
if (CPU == "probe")
42+
CPU = sys::detail::getHostCPUNameForBPF();
43+
if (CPU == "generic" || CPU == "v1")
44+
return;
45+
if (CPU == "v2") {
46+
HasJmpExt = true;
47+
return;
48+
}
49+
}
50+
2851
BPFSubtarget::BPFSubtarget(const Triple &TT, const std::string &CPU,
2952
const std::string &FS, const TargetMachine &TM)
30-
: BPFGenSubtargetInfo(TT, CPU, FS), InstrInfo(), FrameLowering(*this),
53+
: BPFGenSubtargetInfo(TT, CPU, FS), InstrInfo(),
54+
FrameLowering(initializeSubtargetDependencies(CPU, FS)),
3155
TLInfo(TM, *this) {}

lib/Target/BPF/BPFSubtarget.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,15 +35,30 @@ class BPFSubtarget : public BPFGenSubtargetInfo {
3535
BPFTargetLowering TLInfo;
3636
SelectionDAGTargetInfo TSInfo;
3737

38+
private:
39+
void initializeEnvironment();
40+
void initSubtargetFeatures(StringRef CPU, StringRef FS);
41+
bool probeJmpExt();
42+
43+
protected:
44+
// unused
45+
bool isDummyMode;
46+
47+
// whether the cpu supports jmp ext
48+
bool HasJmpExt;
49+
3850
public:
3951
// This constructor initializes the data members to match that
4052
// of the specified triple.
4153
BPFSubtarget(const Triple &TT, const std::string &CPU, const std::string &FS,
4254
const TargetMachine &TM);
4355

56+
BPFSubtarget &initializeSubtargetDependencies(StringRef CPU, StringRef FS);
57+
4458
// ParseSubtargetFeatures - Parses features string setting specified
4559
// subtarget options. Definition of function is auto generated by tblgen.
4660
void ParseSubtargetFeatures(StringRef CPU, StringRef FS);
61+
bool getHasJmpExt() const { return HasJmpExt; }
4762

4863
const BPFInstrInfo *getInstrInfo() const override { return &InstrInfo; }
4964
const BPFFrameLowering *getFrameLowering() const override {

test/CodeGen/BPF/setcc.ll

Lines changed: 26 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
; RUN: llc -march=bpfel < %s | FileCheck %s
1+
; RUN: llc -march=bpfel < %s | FileCheck --check-prefix=CHECK-V1 %s
2+
; RUN: llc -march=bpfel -mcpu=v2 < %s | FileCheck --check-prefix=CHECK-V2 %s
23

34
define i16 @sccweqand(i16 %a, i16 %b) nounwind {
45
%t1 = and i16 %a, %b
@@ -7,7 +8,8 @@ define i16 @sccweqand(i16 %a, i16 %b) nounwind {
78
ret i16 %t3
89
}
910
; CHECK-LABEL: sccweqand:
10-
; CHECK: if r1 == 0
11+
; CHECK-V1: if r1 == 0
12+
; CHECK-V2: if r1 == 0
1113

1214
define i16 @sccwneand(i16 %a, i16 %b) nounwind {
1315
%t1 = and i16 %a, %b
@@ -16,84 +18,95 @@ define i16 @sccwneand(i16 %a, i16 %b) nounwind {
1618
ret i16 %t3
1719
}
1820
; CHECK-LABEL: sccwneand:
19-
; CHECK: if r1 != 0
21+
; CHECK-V1: if r1 != 0
22+
; CHECK-V2: if r1 != 0
2023

2124
define i16 @sccwne(i16 %a, i16 %b) nounwind {
2225
%t1 = icmp ne i16 %a, %b
2326
%t2 = zext i1 %t1 to i16
2427
ret i16 %t2
2528
}
2629
; CHECK-LABEL:sccwne:
27-
; CHECK: if r1 != r2
30+
; CHECK-V1: if r1 != r2
31+
; CHECK-V2: if r1 != r2
2832

2933
define i16 @sccweq(i16 %a, i16 %b) nounwind {
3034
%t1 = icmp eq i16 %a, %b
3135
%t2 = zext i1 %t1 to i16
3236
ret i16 %t2
3337
}
3438
; CHECK-LABEL:sccweq:
35-
; CHECK: if r1 == r2
39+
; CHECK-V1: if r1 == r2
40+
; CHECK-V2: if r1 == r2
3641

3742
define i16 @sccwugt(i16 %a, i16 %b) nounwind {
3843
%t1 = icmp ugt i16 %a, %b
3944
%t2 = zext i1 %t1 to i16
4045
ret i16 %t2
4146
}
4247
; CHECK-LABEL:sccwugt:
43-
; CHECK: if r1 > r2
48+
; CHECK-V1: if r1 > r2
49+
; CHECK-V2: if r1 > r2
4450

4551
define i16 @sccwuge(i16 %a, i16 %b) nounwind {
4652
%t1 = icmp uge i16 %a, %b
4753
%t2 = zext i1 %t1 to i16
4854
ret i16 %t2
4955
}
5056
; CHECK-LABEL:sccwuge:
51-
; CHECK: if r1 >= r2
57+
; CHECK-V1: if r1 >= r2
58+
; CHECK-V2: if r1 >= r2
5259

5360
define i16 @sccwult(i16 %a, i16 %b) nounwind {
5461
%t1 = icmp ult i16 %a, %b
5562
%t2 = zext i1 %t1 to i16
5663
ret i16 %t2
5764
}
5865
; CHECK-LABEL:sccwult:
59-
; CHECK: if r2 > r1
66+
; CHECK-V1: if r2 > r1
67+
; CHECK-V2: if r1 < r2
6068

6169
define i16 @sccwule(i16 %a, i16 %b) nounwind {
6270
%t1 = icmp ule i16 %a, %b
6371
%t2 = zext i1 %t1 to i16
6472
ret i16 %t2
6573
}
6674
; CHECK-LABEL:sccwule:
67-
; CHECK: if r2 >= r1
75+
; CHECK-V1: if r2 >= r1
76+
; CHECK-V2: if r1 <= r2
6877

6978
define i16 @sccwsgt(i16 %a, i16 %b) nounwind {
7079
%t1 = icmp sgt i16 %a, %b
7180
%t2 = zext i1 %t1 to i16
7281
ret i16 %t2
7382
}
7483
; CHECK-LABEL:sccwsgt:
75-
; CHECK: if r1 s> r2
84+
; CHECK-V1: if r1 s> r2
85+
; CHECK-V2: if r1 s> r2
7686

7787
define i16 @sccwsge(i16 %a, i16 %b) nounwind {
7888
%t1 = icmp sge i16 %a, %b
7989
%t2 = zext i1 %t1 to i16
8090
ret i16 %t2
8191
}
8292
; CHECK-LABEL:sccwsge:
83-
; CHECK: if r1 s>= r2
93+
; CHECK-V1: if r1 s>= r2
94+
; CHECK-V2: if r1 s>= r2
8495

8596
define i16 @sccwslt(i16 %a, i16 %b) nounwind {
8697
%t1 = icmp slt i16 %a, %b
8798
%t2 = zext i1 %t1 to i16
8899
ret i16 %t2
89100
}
90101
; CHECK-LABEL:sccwslt:
91-
; CHECK: if r2 s> r1
102+
; CHECK-V1: if r2 s> r1
103+
; CHECK-V2: if r1 s< r2
92104

93105
define i16 @sccwsle(i16 %a, i16 %b) nounwind {
94106
%t1 = icmp sle i16 %a, %b
95107
%t2 = zext i1 %t1 to i16
96108
ret i16 %t2
97109
}
98110
; CHECK-LABEL:sccwsle:
99-
; CHECK: if r2 s>= r1
111+
; CHECK-V1: if r2 s>= r1
112+
; CHECK-V2: if r1 s<= r2

0 commit comments

Comments
 (0)