Skip to content

Commit 5f20e6a

Browse files
committed
Alexei Starovoitov says: ==================== pull-request: bpf-next 2024-03-11 We've added 59 non-merge commits during the last 9 day(s) which contain a total of 88 files changed, 4181 insertions(+), 590 deletions(-). The main changes are: 1) Enforce VM_IOREMAP flag and range in ioremap_page_range and introduce VM_SPARSE kind and vm_area_[un]map_pages to be used in bpf_arena, from Alexei. 2) Introduce bpf_arena which is sparse shared memory region between bpf program and user space where structures inside the arena can have pointers to other areas of the arena, and pointers work seamlessly for both user-space programs and bpf programs, from Alexei and Andrii. 3) Introduce may_goto instruction that is a contract between the verifier and the program. The verifier allows the program to loop assuming it's behaving well, but reserves the right to terminate it, from Alexei. 4) Use IETF format for field definitions in the BPF standard document, from Dave. 5) Extend struct_ops libbpf APIs to allow specify version suffixes for stuct_ops map types, share the same BPF program between several map definitions, and other improvements, from Eduard. 6) Enable struct_ops support for more than one page in trampolines, from Kui-Feng. 7) Support kCFI + BPF on riscv64, from Puranjay. 8) Use bpf_prog_pack for arm64 bpf trampoline, from Puranjay. 9) Fix roundup_pow_of_two undefined behavior on 32-bit archs, from Toke. ==================== Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Jakub Kicinski <[email protected]>
2 parents f095fef + 66c8473 commit 5f20e6a

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

88 files changed

+4181
-590
lines changed

Documentation/bpf/standardization/instruction-set.rst

Lines changed: 292 additions & 243 deletions
Large diffs are not rendered by default.

arch/arm/mm/ioremap.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -110,8 +110,8 @@ void __init add_static_vm_early(struct static_vm *svm)
110110
int ioremap_page(unsigned long virt, unsigned long phys,
111111
const struct mem_type *mtype)
112112
{
113-
return ioremap_page_range(virt, virt + PAGE_SIZE, phys,
114-
__pgprot(mtype->prot_pte));
113+
return vmap_page_range(virt, virt + PAGE_SIZE, phys,
114+
__pgprot(mtype->prot_pte));
115115
}
116116
EXPORT_SYMBOL(ioremap_page);
117117

@@ -466,8 +466,8 @@ int pci_remap_iospace(const struct resource *res, phys_addr_t phys_addr)
466466
if (res->end > IO_SPACE_LIMIT)
467467
return -EINVAL;
468468

469-
return ioremap_page_range(vaddr, vaddr + resource_size(res), phys_addr,
470-
__pgprot(get_mem_type(pci_ioremap_mem_type)->prot_pte));
469+
return vmap_page_range(vaddr, vaddr + resource_size(res), phys_addr,
470+
__pgprot(get_mem_type(pci_ioremap_mem_type)->prot_pte));
471471
}
472472
EXPORT_SYMBOL(pci_remap_iospace);
473473

arch/arm64/net/bpf_jit_comp.c

Lines changed: 46 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2076,7 +2076,7 @@ static int prepare_trampoline(struct jit_ctx *ctx, struct bpf_tramp_image *im,
20762076
/* store return value */
20772077
emit(A64_STR64I(A64_R(0), A64_SP, retval_off), ctx);
20782078
/* reserve a nop for bpf_tramp_image_put */
2079-
im->ip_after_call = ctx->image + ctx->idx;
2079+
im->ip_after_call = ctx->ro_image + ctx->idx;
20802080
emit(A64_NOP, ctx);
20812081
}
20822082

@@ -2091,7 +2091,7 @@ static int prepare_trampoline(struct jit_ctx *ctx, struct bpf_tramp_image *im,
20912091
run_ctx_off, false);
20922092

20932093
if (flags & BPF_TRAMP_F_CALL_ORIG) {
2094-
im->ip_epilogue = ctx->image + ctx->idx;
2094+
im->ip_epilogue = ctx->ro_image + ctx->idx;
20952095
emit_addr_mov_i64(A64_R(0), (const u64)im, ctx);
20962096
emit_call((const u64)__bpf_tramp_exit, ctx);
20972097
}
@@ -2124,9 +2124,6 @@ static int prepare_trampoline(struct jit_ctx *ctx, struct bpf_tramp_image *im,
21242124
emit(A64_RET(A64_R(10)), ctx);
21252125
}
21262126

2127-
if (ctx->image)
2128-
bpf_flush_icache(ctx->image, ctx->image + ctx->idx);
2129-
21302127
kfree(branches);
21312128

21322129
return ctx->idx;
@@ -2169,14 +2166,43 @@ int arch_bpf_trampoline_size(const struct btf_func_model *m, u32 flags,
21692166
return ret < 0 ? ret : ret * AARCH64_INSN_SIZE;
21702167
}
21712168

2172-
int arch_prepare_bpf_trampoline(struct bpf_tramp_image *im, void *image,
2173-
void *image_end, const struct btf_func_model *m,
2169+
void *arch_alloc_bpf_trampoline(unsigned int size)
2170+
{
2171+
return bpf_prog_pack_alloc(size, jit_fill_hole);
2172+
}
2173+
2174+
void arch_free_bpf_trampoline(void *image, unsigned int size)
2175+
{
2176+
bpf_prog_pack_free(image, size);
2177+
}
2178+
2179+
void arch_protect_bpf_trampoline(void *image, unsigned int size)
2180+
{
2181+
}
2182+
2183+
void arch_unprotect_bpf_trampoline(void *image, unsigned int size)
2184+
{
2185+
}
2186+
2187+
int arch_prepare_bpf_trampoline(struct bpf_tramp_image *im, void *ro_image,
2188+
void *ro_image_end, const struct btf_func_model *m,
21742189
u32 flags, struct bpf_tramp_links *tlinks,
21752190
void *func_addr)
21762191
{
21772192
int ret, nregs;
2193+
void *image, *tmp;
2194+
u32 size = ro_image_end - ro_image;
2195+
2196+
/* image doesn't need to be in module memory range, so we can
2197+
* use kvmalloc.
2198+
*/
2199+
image = kvmalloc(size, GFP_KERNEL);
2200+
if (!image)
2201+
return -ENOMEM;
2202+
21782203
struct jit_ctx ctx = {
21792204
.image = image,
2205+
.ro_image = ro_image,
21802206
.idx = 0,
21812207
};
21822208

@@ -2185,15 +2211,26 @@ int arch_prepare_bpf_trampoline(struct bpf_tramp_image *im, void *image,
21852211
if (nregs > 8)
21862212
return -ENOTSUPP;
21872213

2188-
jit_fill_hole(image, (unsigned int)(image_end - image));
2214+
jit_fill_hole(image, (unsigned int)(ro_image_end - ro_image));
21892215
ret = prepare_trampoline(&ctx, im, tlinks, func_addr, nregs, flags);
21902216

2191-
if (ret > 0 && validate_code(&ctx) < 0)
2217+
if (ret > 0 && validate_code(&ctx) < 0) {
21922218
ret = -EINVAL;
2219+
goto out;
2220+
}
21932221

21942222
if (ret > 0)
21952223
ret *= AARCH64_INSN_SIZE;
21962224

2225+
tmp = bpf_arch_text_copy(ro_image, image, size);
2226+
if (IS_ERR(tmp)) {
2227+
ret = PTR_ERR(tmp);
2228+
goto out;
2229+
}
2230+
2231+
bpf_flush_icache(ro_image, ro_image + size);
2232+
out:
2233+
kvfree(image);
21972234
return ret;
21982235
}
21992236

arch/loongarch/kernel/setup.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -490,7 +490,7 @@ static int __init add_legacy_isa_io(struct fwnode_handle *fwnode,
490490
}
491491

492492
vaddr = (unsigned long)(PCI_IOBASE + range->io_start);
493-
ioremap_page_range(vaddr, vaddr + size, hw_start, pgprot_device(PAGE_KERNEL));
493+
vmap_page_range(vaddr, vaddr + size, hw_start, pgprot_device(PAGE_KERNEL));
494494

495495
return 0;
496496
}

arch/mips/loongson64/init.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,7 +180,7 @@ static int __init add_legacy_isa_io(struct fwnode_handle *fwnode, resource_size_
180180

181181
vaddr = PCI_IOBASE + range->io_start;
182182

183-
ioremap_page_range(vaddr, vaddr + size, hw_start, pgprot_device(PAGE_KERNEL));
183+
vmap_page_range(vaddr, vaddr + size, hw_start, pgprot_device(PAGE_KERNEL));
184184

185185
return 0;
186186
}

arch/powerpc/kernel/isa-bridge.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,8 @@ static void remap_isa_base(phys_addr_t pa, unsigned long size)
4646
WARN_ON_ONCE(size & ~PAGE_MASK);
4747

4848
if (slab_is_available()) {
49-
if (ioremap_page_range(ISA_IO_BASE, ISA_IO_BASE + size, pa,
50-
pgprot_noncached(PAGE_KERNEL)))
49+
if (vmap_page_range(ISA_IO_BASE, ISA_IO_BASE + size, pa,
50+
pgprot_noncached(PAGE_KERNEL)))
5151
vunmap_range(ISA_IO_BASE, ISA_IO_BASE + size);
5252
} else {
5353
early_ioremap_range(ISA_IO_BASE, pa, size,

arch/riscv/include/asm/cfi.h

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,28 @@ struct pt_regs;
1313

1414
#ifdef CONFIG_CFI_CLANG
1515
enum bug_trap_type handle_cfi_failure(struct pt_regs *regs);
16+
#define __bpfcall
17+
static inline int cfi_get_offset(void)
18+
{
19+
return 4;
20+
}
21+
22+
#define cfi_get_offset cfi_get_offset
23+
extern u32 cfi_bpf_hash;
24+
extern u32 cfi_bpf_subprog_hash;
25+
extern u32 cfi_get_func_hash(void *func);
1626
#else
1727
static inline enum bug_trap_type handle_cfi_failure(struct pt_regs *regs)
1828
{
1929
return BUG_TRAP_TYPE_NONE;
2030
}
31+
32+
#define cfi_bpf_hash 0U
33+
#define cfi_bpf_subprog_hash 0U
34+
static inline u32 cfi_get_func_hash(void *func)
35+
{
36+
return 0;
37+
}
2138
#endif /* CONFIG_CFI_CLANG */
2239

2340
#endif /* _ASM_RISCV_CFI_H */

arch/riscv/kernel/cfi.c

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,3 +75,56 @@ enum bug_trap_type handle_cfi_failure(struct pt_regs *regs)
7575

7676
return report_cfi_failure(regs, regs->epc, &target, type);
7777
}
78+
79+
#ifdef CONFIG_CFI_CLANG
80+
struct bpf_insn;
81+
82+
/* Must match bpf_func_t / DEFINE_BPF_PROG_RUN() */
83+
extern unsigned int __bpf_prog_runX(const void *ctx,
84+
const struct bpf_insn *insn);
85+
86+
/*
87+
* Force a reference to the external symbol so the compiler generates
88+
* __kcfi_typid.
89+
*/
90+
__ADDRESSABLE(__bpf_prog_runX);
91+
92+
/* u32 __ro_after_init cfi_bpf_hash = __kcfi_typeid___bpf_prog_runX; */
93+
asm (
94+
" .pushsection .data..ro_after_init,\"aw\",@progbits \n"
95+
" .type cfi_bpf_hash,@object \n"
96+
" .globl cfi_bpf_hash \n"
97+
" .p2align 2, 0x0 \n"
98+
"cfi_bpf_hash: \n"
99+
" .word __kcfi_typeid___bpf_prog_runX \n"
100+
" .size cfi_bpf_hash, 4 \n"
101+
" .popsection \n"
102+
);
103+
104+
/* Must match bpf_callback_t */
105+
extern u64 __bpf_callback_fn(u64, u64, u64, u64, u64);
106+
107+
__ADDRESSABLE(__bpf_callback_fn);
108+
109+
/* u32 __ro_after_init cfi_bpf_subprog_hash = __kcfi_typeid___bpf_callback_fn; */
110+
asm (
111+
" .pushsection .data..ro_after_init,\"aw\",@progbits \n"
112+
" .type cfi_bpf_subprog_hash,@object \n"
113+
" .globl cfi_bpf_subprog_hash \n"
114+
" .p2align 2, 0x0 \n"
115+
"cfi_bpf_subprog_hash: \n"
116+
" .word __kcfi_typeid___bpf_callback_fn \n"
117+
" .size cfi_bpf_subprog_hash, 4 \n"
118+
" .popsection \n"
119+
);
120+
121+
u32 cfi_get_func_hash(void *func)
122+
{
123+
u32 hash;
124+
125+
if (get_kernel_nofault(hash, func - cfi_get_offset()))
126+
return 0;
127+
128+
return hash;
129+
}
130+
#endif

arch/riscv/net/bpf_jit.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1223,7 +1223,7 @@ static inline void emit_bswap(u8 rd, s32 imm, struct rv_jit_context *ctx)
12231223

12241224
#endif /* __riscv_xlen == 64 */
12251225

1226-
void bpf_jit_build_prologue(struct rv_jit_context *ctx);
1226+
void bpf_jit_build_prologue(struct rv_jit_context *ctx, bool is_subprog);
12271227
void bpf_jit_build_epilogue(struct rv_jit_context *ctx);
12281228

12291229
int bpf_jit_emit_insn(const struct bpf_insn *insn, struct rv_jit_context *ctx,

arch/riscv/net/bpf_jit_comp32.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1301,7 +1301,7 @@ int bpf_jit_emit_insn(const struct bpf_insn *insn, struct rv_jit_context *ctx,
13011301
return 0;
13021302
}
13031303

1304-
void bpf_jit_build_prologue(struct rv_jit_context *ctx)
1304+
void bpf_jit_build_prologue(struct rv_jit_context *ctx, bool is_subprog)
13051305
{
13061306
const s8 *fp = bpf2rv32[BPF_REG_FP];
13071307
const s8 *r1 = bpf2rv32[BPF_REG_1];

0 commit comments

Comments
 (0)