[PATCH bpf] bpf, arm64: allocate program buffer using kvcalloc instead of kcalloc

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



It is not necessary to allocate contiguous physical memory for BPF
program buffer using kcalloc. When the BPF program is large more than
memory page size, kcalloc allocates multiple memory pages from buddy
system. If the device can not provide sufficient memory, for example
in low-end android devices[1], memory allocation for BPF program is likely
failed.

Test cases in lib/test_bpf.c all pass on ARM64 QEMU.

[1]
AndroidTestSuit: page allocation failure: order:4,
mode:0x40dc0(GFP_KERNEL|__GFP_COMP|__GFP_ZERO), nodemask=(null),cpuset=foreground,mems_allowed=0
Call trace:
 dump_stack+0xa4/0x114
 warn_alloc+0xf8/0x14c
 __alloc_pages_slowpath+0xac8/0xb14
 __alloc_pages_nodemask+0x194/0x3d0
 kmalloc_order_trace+0x44/0x1e8
 __kmalloc+0x29c/0x66c
 bpf_int_jit_compile+0x17c/0x568
 bpf_prog_select_runtime+0x4c/0x1b0
 bpf_prepare_filter+0x5fc/0x6bc
 bpf_prog_create_from_user+0x118/0x1c0
 seccomp_set_mode_filter+0x1c4/0x7cc
 __do_sys_prctl+0x380/0x1424
 __arm64_sys_prctl+0x20/0x2c
 el0_svc_common+0xc8/0x22c
 el0_svc_handler+0x1c/0x28
 el0_svc+0x8/0x100

Signed-off-by: Aijun Sun <aijun.sun@xxxxxxxxxx>
---
 arch/arm64/net/bpf_jit_comp.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/net/bpf_jit_comp.c b/arch/arm64/net/bpf_jit_comp.c
index 42f2e9a8616c..80918e60387b 100644
--- a/arch/arm64/net/bpf_jit_comp.c
+++ b/arch/arm64/net/bpf_jit_comp.c
@@ -1399,7 +1399,7 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
 	memset(&ctx, 0, sizeof(ctx));
 	ctx.prog = prog;
 
-	ctx.offset = kcalloc(prog->len + 1, sizeof(int), GFP_KERNEL);
+	ctx.offset = kvcalloc(prog->len + 1, sizeof(int), GFP_KERNEL);
 	if (ctx.offset == NULL) {
 		prog = orig_prog;
 		goto out_off;
@@ -1499,7 +1499,7 @@ struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
 			ctx.offset[i] *= AARCH64_INSN_SIZE;
 		bpf_prog_fill_jited_linfo(prog, ctx.offset + 1);
 out_off:
-		kfree(ctx.offset);
+		kvfree(ctx.offset);
 		kfree(jit_data);
 		prog->aux->jit_data = NULL;
 	}
-- 
2.29.0




[Index of Archives]     [Linux Samsung SoC]     [Linux Rockchip SoC]     [Linux Actions SoC]     [Linux for Synopsys ARC Processors]     [Linux NFS]     [Linux NILFS]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]


  Powered by Linux