llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT--> @llvm/pr-subscribers-clang Author: None (yonghong-song) <details> <summary>Changes</summary> Alexei added may_goto insn in [1]. The asm syntax for may_goto looks like may_goto <label> The instruction represents a conditional branch but the condition is implicit. Later in bpf kernel verifier, the 'may_goto <label>' insn will be rewritten with an explicit condition. The encoding of 'may_goto' insn is enforced in [2] and is also implemented in this patch. In [3], 'may_goto' insn is encoded with raw bytes. I made the following change ``` --- a/tools/testing/selftests/bpf/bpf_experimental.h +++ b/tools/testing/selftests/bpf/bpf_experimental.h @@ -328,10 +328,7 @@ l_true: \ #define cond_break \ ({ __label__ l_break, l_continue; \ - asm volatile goto("1:.byte 0xe5; \ - .byte 0; \ - .long ((%l[l_break] - 1b - 8) / 8) & 0xffff; \ - .short 0" \ + asm volatile goto("may_goto %l[l_break]" \ :::: l_break); \ goto l_continue; \ l_break: break; ``` and ran the selftest with the latest llvm with this patch. All tests are passed. [1] https://lore.kernel.org/bpf/20240306031929.42666-1-alexei.starovoitov@<!-- -->gmail.com/ [2] https://lore.kernel.org/bpf/20240306031929.42666-2-alexei.starovoitov@<!-- -->gmail.com/ [3] https://lore.kernel.org/bpf/20240306031929.42666-4-alexei.starovoitov@<!-- -->gmail.com/ --- Full diff: https://github.com/llvm/llvm-project/pull/85358.diff 6 Files Affected: - (modified) clang/lib/Basic/Targets/BPF.cpp (+1) - (modified) llvm/lib/Target/BPF/AsmParser/BPFAsmParser.cpp (+1) - (modified) llvm/lib/Target/BPF/BPFInstrFormats.td (+1) - (modified) llvm/lib/Target/BPF/BPFInstrInfo.td (+13) - (modified) llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp (+4-1) - (modified) llvm/test/MC/BPF/insn-unit.s (+2) ``````````diff diff --git a/clang/lib/Basic/Targets/BPF.cpp b/clang/lib/Basic/Targets/BPF.cpp index a90398a362d10a..b5ba11a3bdca9d 100644 --- a/clang/lib/Basic/Targets/BPF.cpp +++ b/clang/lib/Basic/Targets/BPF.cpp @@ -45,6 +45,7 @@ void BPFTargetInfo::getTargetDefines(const LangOptions &Opts, std::string CpuVerNumStr = CPU.substr(1); Builder.defineMacro("__BPF_CPU_VERSION__", CpuVerNumStr); + Builder.defineMacro("__BPF_FEATURE_MAY_GOTO"); int CpuVerNum = std::stoi(CpuVerNumStr); if (CpuVerNum >= 2) diff --git a/llvm/lib/Target/BPF/AsmParser/BPFAsmParser.cpp b/llvm/lib/Target/BPF/AsmParser/BPFAsmParser.cpp index 3145bc3d19f5dc..1688355f427cc7 100644 --- a/llvm/lib/Target/BPF/AsmParser/BPFAsmParser.cpp +++ b/llvm/lib/Target/BPF/AsmParser/BPFAsmParser.cpp @@ -232,6 +232,7 @@ struct BPFOperand : public MCParsedAsmOperand { .Case("callx", true) .Case("goto", true) .Case("gotol", true) + .Case("may_goto", true) .Case("*", true) .Case("exit", true) .Case("lock", true) diff --git a/llvm/lib/Target/BPF/BPFInstrFormats.td b/llvm/lib/Target/BPF/BPFInstrFormats.td index 6ed83d877ac0f2..feffdbc69465ea 100644 --- a/llvm/lib/Target/BPF/BPFInstrFormats.td +++ b/llvm/lib/Target/BPF/BPFInstrFormats.td @@ -73,6 +73,7 @@ def BPF_JLT : BPFJumpOp<0xa>; def BPF_JLE : BPFJumpOp<0xb>; def BPF_JSLT : BPFJumpOp<0xc>; def BPF_JSLE : BPFJumpOp<0xd>; +def BPF_JCOND : BPFJumpOp<0xe>; class BPFWidthModifer<bits<2> val> { bits<2> Value = val; diff --git a/llvm/lib/Target/BPF/BPFInstrInfo.td b/llvm/lib/Target/BPF/BPFInstrInfo.td index 7198e9499bc32a..66c57952a7f10e 100644 --- a/llvm/lib/Target/BPF/BPFInstrInfo.td +++ b/llvm/lib/Target/BPF/BPFInstrInfo.td @@ -215,6 +215,18 @@ class JMP_RI<BPFJumpOp Opc, string OpcodeStr, PatLeaf Cond> let BPFClass = BPF_JMP; } +class JMP_JCOND<BPFJumpOp Opc, string OpcodeStr, list<dag> Pattern> + : TYPE_ALU_JMP<Opc.Value, BPF_K.Value, + (outs), + (ins brtarget:$BrDst), + !strconcat(OpcodeStr, " $BrDst"), + Pattern> { + bits<16> BrDst; + + let Inst{47-32} = BrDst; + let BPFClass = BPF_JMP; +} + class JMP_RR_32<BPFJumpOp Opc, string OpcodeStr, PatLeaf Cond> : TYPE_ALU_JMP<Opc.Value, BPF_X.Value, (outs), @@ -267,6 +279,7 @@ defm JULE : J<BPF_JLE, "<=", BPF_CC_LEU, BPF_CC_LEU_32>; defm JSLT : J<BPF_JSLT, "s<", BPF_CC_LT, BPF_CC_LT_32>; defm JSLE : J<BPF_JSLE, "s<=", BPF_CC_LE, BPF_CC_LE_32>; defm JSET : J<BPF_JSET, "&", NoCond, NoCond>; +def JCOND : JMP_JCOND<BPF_JCOND, "may_goto", []>; } // ALU instructions diff --git a/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp b/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp index 7dad40803d4770..44932383fb43e9 100644 --- a/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp +++ b/llvm/lib/Target/BPF/MCTargetDesc/BPFMCTargetDesc.cpp @@ -81,7 +81,10 @@ class BPFMCInstrAnalysis : public MCInstrAnalysis { // The target is the 3rd operand of cond inst and the 1st of uncond inst. int32_t Imm; if (isConditionalBranch(Inst)) { - Imm = (short)Inst.getOperand(2).getImm(); + if (Inst.getOpcode() == BPF::JCOND) + Imm = (short)Inst.getOperand(0).getImm(); + else + Imm = (short)Inst.getOperand(2).getImm(); } else if (isUnconditionalBranch(Inst)) { if (Inst.getOpcode() == BPF::JMP) Imm = (short)Inst.getOperand(0).getImm(); diff --git a/llvm/test/MC/BPF/insn-unit.s b/llvm/test/MC/BPF/insn-unit.s index 224eb7381aa234..84735d196030d6 100644 --- a/llvm/test/MC/BPF/insn-unit.s +++ b/llvm/test/MC/BPF/insn-unit.s @@ -65,8 +65,10 @@ // CHECK: 8d 02 00 00 00 00 00 00 callx r2 // ======== BPF_JMP Class ======== + may_goto Llabel0 // BPF_JCOND | BPF_K if r1 & r2 goto Llabel0 // BPF_JSET | BPF_X if r1 & 0xffff goto Llabel0 // BPF_JSET | BPF_K +// CHECK: e5 00 1e 00 00 00 00 00 may_goto +30 // CHECK: 4d 21 1d 00 00 00 00 00 if r1 & r2 goto +29 // CHECK: 45 01 1c 00 ff ff 00 00 if r1 & 65535 goto +28 `````````` </details> https://github.com/llvm/llvm-project/pull/85358 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits