summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPuranjay Mohan <puranjay@kernel.org>2025-07-22 13:34:09 +0000
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2025-08-15 12:16:37 +0200
commite23184725dbb72d5d02940222eee36dbba2aa422 (patch)
treea2e348025e71aec361eb8ad493880190dce9de6a
parent64eb83167df318daad509334da75881d37d4d734 (diff)
bpf, arm64: Fix fp initialization for exception boundary
[ Upstream commit b114fcee766d5101eada1aca7bb5fd0a86c89b35 ] In the ARM64 BPF JIT when prog->aux->exception_boundary is set for a BPF program, find_used_callee_regs() is not called because for a program acting as exception boundary, all callee saved registers are saved. find_used_callee_regs() sets `ctx->fp_used = true;` when it sees FP being used in any of the instructions. For programs acting as exception boundary, ctx->fp_used remains false even if frame pointer is used by the program and therefore, FP is not set-up for such programs in the prologue. This can cause the kernel to crash due to a pagefault. Fix it by setting ctx->fp_used = true for exception boundary programs as fp is always saved in such programs. Fixes: 5d4fa9ec5643 ("bpf, arm64: Avoid blindly saving/restoring all callee-saved registers") Signed-off-by: Puranjay Mohan <puranjay@kernel.org> Signed-off-by: Daniel Borkmann <daniel@iogearbox.net> Acked-by: Xu Kuohai <xukuohai@huawei.com> Link: https://lore.kernel.org/bpf/20250722133410.54161-2-puranjay@kernel.org Signed-off-by: Sasha Levin <sashal@kernel.org>
-rw-r--r--arch/arm64/net/bpf_jit_comp.c1
1 files changed, 1 insertions, 0 deletions
diff --git a/arch/arm64/net/bpf_jit_comp.c b/arch/arm64/net/bpf_jit_comp.c
index 634d78422adb..a85236d0afee 100644
--- a/arch/arm64/net/bpf_jit_comp.c
+++ b/arch/arm64/net/bpf_jit_comp.c
@@ -412,6 +412,7 @@ static void push_callee_regs(struct jit_ctx *ctx)
emit(A64_PUSH(A64_R(23), A64_R(24), A64_SP), ctx);
emit(A64_PUSH(A64_R(25), A64_R(26), A64_SP), ctx);
emit(A64_PUSH(A64_R(27), A64_R(28), A64_SP), ctx);
+ ctx->fp_used = true;
} else {
find_used_callee_regs(ctx);
for (i = 0; i + 1 < ctx->nr_used_callee_reg; i += 2) {