bpf, arm64: save 4 bytes in prologue when ebpf insns came from cbpf

We can trivially save 4 bytes in prologue for cBPF since tail calls
can never be used from there. The register push/pop is pairwise,
here, x25 (fp) and x26 (tcc), so no point in changing that, only
reset to zero is not needed.

Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
Signed-off-by: Alexei Starovoitov <ast@kernel.org>
This commit is contained in:
Daniel Borkmann 2018-05-14 23:22:33 +02:00 committed by Alexei Starovoitov
parent 6d2eea6fb0
commit 56ea6a8b49

View file

@ -185,7 +185,7 @@ static inline int epilogue_offset(const struct jit_ctx *ctx)
/* Tail call offset to jump into */ /* Tail call offset to jump into */
#define PROLOGUE_OFFSET 7 #define PROLOGUE_OFFSET 7
static int build_prologue(struct jit_ctx *ctx) static int build_prologue(struct jit_ctx *ctx, bool ebpf_from_cbpf)
{ {
const struct bpf_prog *prog = ctx->prog; const struct bpf_prog *prog = ctx->prog;
const u8 r6 = bpf2a64[BPF_REG_6]; const u8 r6 = bpf2a64[BPF_REG_6];
@ -232,14 +232,16 @@ static int build_prologue(struct jit_ctx *ctx)
/* Set up BPF prog stack base register */ /* Set up BPF prog stack base register */
emit(A64_MOV(1, fp, A64_SP), ctx); emit(A64_MOV(1, fp, A64_SP), ctx);
/* Initialize tail_call_cnt */ if (!ebpf_from_cbpf) {
emit(A64_MOVZ(1, tcc, 0, 0), ctx); /* Initialize tail_call_cnt */
emit(A64_MOVZ(1, tcc, 0, 0), ctx);
cur_offset = ctx->idx - idx0; cur_offset = ctx->idx - idx0;
if (cur_offset != PROLOGUE_OFFSET) { if (cur_offset != PROLOGUE_OFFSET) {
pr_err_once("PROLOGUE_OFFSET = %d, expected %d!\n", pr_err_once("PROLOGUE_OFFSET = %d, expected %d!\n",
cur_offset, PROLOGUE_OFFSET); cur_offset, PROLOGUE_OFFSET);
return -1; return -1;
}
} }
ctx->stack_size = STACK_ALIGN(prog->aux->stack_depth); ctx->stack_size = STACK_ALIGN(prog->aux->stack_depth);
@ -806,6 +808,7 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
struct bpf_prog *tmp, *orig_prog = prog; struct bpf_prog *tmp, *orig_prog = prog;
struct bpf_binary_header *header; struct bpf_binary_header *header;
struct arm64_jit_data *jit_data; struct arm64_jit_data *jit_data;
bool was_classic = bpf_prog_was_classic(prog);
bool tmp_blinded = false; bool tmp_blinded = false;
bool extra_pass = false; bool extra_pass = false;
struct jit_ctx ctx; struct jit_ctx ctx;
@ -860,7 +863,7 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
goto out_off; goto out_off;
} }
if (build_prologue(&ctx)) { if (build_prologue(&ctx, was_classic)) {
prog = orig_prog; prog = orig_prog;
goto out_off; goto out_off;
} }
@ -883,7 +886,7 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
skip_init_ctx: skip_init_ctx:
ctx.idx = 0; ctx.idx = 0;
build_prologue(&ctx); build_prologue(&ctx, was_classic);
if (build_body(&ctx)) { if (build_body(&ctx)) {
bpf_jit_binary_free(header); bpf_jit_binary_free(header);