From: Abhishek Dubey On loading the BPF program, the verifier might adjust/omit some instructions. The adjusted instruction offset is accounted in the map containing original instruction -> xlated mapping. This patch add ppc64 JIT support to additionally build the xlated->jitted mapping for every instruction present in instruction array. This change is needed to enable support for indirect jumps, added in a subsequent patch. Invoke bpf_prog_update_insn_ptrs() with offset pair of xlated_offset and jited_offset. The offset mapping is already available, which is being used for bpf_prog_fill_jited_linfo() and can be directly used for bpf_prog_update_insn_ptrs() as well. Additional details present at: commit b4ce5923e780 ("bpf, x86: add new map type: instructions array") Signed-off-by: Abhishek Dubey --- arch/powerpc/net/bpf_jit_comp.c | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/arch/powerpc/net/bpf_jit_comp.c b/arch/powerpc/net/bpf_jit_comp.c index 9ec5ab9b020e..620667c3400b 100644 --- a/arch/powerpc/net/bpf_jit_comp.c +++ b/arch/powerpc/net/bpf_jit_comp.c @@ -373,6 +373,16 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *fp) goto out_addrs; } bpf_prog_fill_jited_linfo(fp, addrs); + /* + * On ABI V1, executable code starts after the function + * descriptor, so adjust base accordingly. + */ +#ifdef CONFIG_PPC64_ELF_ABI_V1 + bpf_prog_update_insn_ptrs(fp, addrs, + (void *)fimage + FUNCTION_DESCR_SIZE); +#else + bpf_prog_update_insn_ptrs(fp, addrs, fimage); +#endif out_addrs: if (!image && priv_stack_ptr) { fp->aux->priv_stack_ptr = NULL; -- 2.52.0 From: Abhishek Dubey With instruction array now supported, enable corresponding bpf selftest for powerpc. Signed-off-by: Abhishek Dubey --- tools/testing/selftests/bpf/prog_tests/bpf_insn_array.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/testing/selftests/bpf/prog_tests/bpf_insn_array.c b/tools/testing/selftests/bpf/prog_tests/bpf_insn_array.c index 93166c2da8e7..57ce6943fcfd 100644 --- a/tools/testing/selftests/bpf/prog_tests/bpf_insn_array.c +++ b/tools/testing/selftests/bpf/prog_tests/bpf_insn_array.c @@ -3,7 +3,7 @@ #include #include -#if defined(__x86_64__) || defined(__aarch64__) +#if defined(__x86_64__) || defined(__aarch64__) || defined(__powerpc64__) static int map_create(__u32 map_type, __u32 max_entries) { const char *map_name = "insn_array"; -- 2.52.0 From: Abhishek Dubey Add support for a new instruction BPF_JMP|BPF_X|BPF_JA, SRC=0, DST=Rx, off=0, imm=0 which does an indirect jump to a location stored in Rx. The register Rx should have type PTR_TO_INSN. This new type ensures that the Rx register contains a value (or a range of values) loaded from a correct jump table – map of type instruction array. Support indirect jump to all registers in powerpc64 JIT using the ctr register. Move Rx content to ctr register, then invoke bctr instruction to branch to address stored in ctr register. Skip save and restore of TOC as the jump is always within the program context. Signed-off-by: Abhishek Dubey --- arch/powerpc/net/bpf_jit_comp64.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/arch/powerpc/net/bpf_jit_comp64.c b/arch/powerpc/net/bpf_jit_comp64.c index c1d011046d8b..2cb550ca1dec 100644 --- a/arch/powerpc/net/bpf_jit_comp64.c +++ b/arch/powerpc/net/bpf_jit_comp64.c @@ -1627,6 +1627,14 @@ int bpf_jit_build_body(struct bpf_prog *fp, u32 *image, u32 *fimage, struct code addrs[++i] = ctx->idx * 4; break; + /* + * JUMP reg + */ + case BPF_JMP | BPF_JA | BPF_X: + EMIT(PPC_RAW_MTCTR(dst_reg)); + EMIT(PPC_RAW_BCTR()); + break; + /* * Return/Exit */ -- 2.52.0 From: Abhishek Dubey With gotox instruction and jumptable now supported, enable corresponding bpf selftest on powerpc. Signed-off-by: Abhishek Dubey --- tools/testing/selftests/bpf/progs/verifier_gotox.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tools/testing/selftests/bpf/progs/verifier_gotox.c b/tools/testing/selftests/bpf/progs/verifier_gotox.c index 607dad058ca1..0f43b56ec2bc 100644 --- a/tools/testing/selftests/bpf/progs/verifier_gotox.c +++ b/tools/testing/selftests/bpf/progs/verifier_gotox.c @@ -6,7 +6,7 @@ #include "bpf_misc.h" #include "../../../include/linux/filter.h" -#if defined(__TARGET_ARCH_x86) || defined(__TARGET_ARCH_arm64) +#if defined(__TARGET_ARCH_x86) || defined(__TARGET_ARCH_arm64) || defined(__TARGET_ARCH_powerpc) #define DEFINE_SIMPLE_JUMP_TABLE_PROG(NAME, SRC_REG, OFF, IMM, OUTCOME) \ \ @@ -384,6 +384,6 @@ jt0_%=: \ : __clobber_all); } -#endif /* __TARGET_ARCH_x86 || __TARGET_ARCH_arm64 */ +#endif /* __TARGET_ARCH_x86 || __TARGET_ARCH_arm64 || __TARGET_ARCH_powerpc*/ char _license[] SEC("license") = "GPL"; -- 2.52.0