Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge branch 'use-correct-destructor-kfunc-types'

Sami Tolvanen says:

====================
While running BPF self-tests with CONFIG_CFI (Control Flow
Integrity) enabled, I ran into a couple of failures in
bpf_obj_free_fields() caused by type mismatches between the
btf_dtor_kfunc_t function pointer type and the registered
destructor functions.

It looks like we can't change the argument type for these
functions to match btf_dtor_kfunc_t because the verifier doesn't
like void pointer arguments for functions used in BPF programs,
so this series fixes the issue by adding stubs with correct types
to use as destructors for each instance of this I found in the
kernel tree.

The last patch changes btf_check_dtor_kfuncs() to enforce the
function type when CFI is enabled, so we don't end up registering
destructors that panic the kernel.

v5:
- Rebased on bpf-next/master again.

v4: https://lore.kernel.org/bpf/20251126221724.897221-6-samitolvanen@google.com/
- Rebased on bpf-next/master.
- Renamed CONFIG_CFI_CLANG to CONFIG_CFI.
- Picked up Acked/Tested-by tags.

v3: https://lore.kernel.org/bpf/20250728202656.559071-6-samitolvanen@google.com/
- Renamed the functions and went back to __bpf_kfunc based
on review feedback.

v2: https://lore.kernel.org/bpf/20250725214401.1475224-6-samitolvanen@google.com/
- Annotated the stubs with CFI_NOSEAL to fix issues with IBT
sealing on x86.
- Changed __bpf_kfunc to explicit __used __retain.

v1: https://lore.kernel.org/bpf/20250724223225.1481960-6-samitolvanen@google.com/
====================

Acked-by: Martin KaFai Lau <martin.lau@kernel.org>
Link: https://patch.msgid.link/20260110082548.113748-6-samitolvanen@google.com
Signed-off-by: Alexei Starovoitov <ast@kernel.org>

+28 -3
+7
kernel/bpf/btf.c
··· 8846 8846 */ 8847 8847 if (!t || !btf_type_is_ptr(t)) 8848 8848 return -EINVAL; 8849 + 8850 + if (IS_ENABLED(CONFIG_CFI_CLANG)) { 8851 + /* Ensure the destructor kfunc type matches btf_dtor_kfunc_t */ 8852 + t = btf_type_by_id(btf, t->type); 8853 + if (!btf_type_is_void(t)) 8854 + return -EINVAL; 8855 + } 8849 8856 } 8850 8857 return 0; 8851 8858 }
+7 -1
kernel/bpf/crypto.c
··· 261 261 call_rcu(&ctx->rcu, crypto_free_cb); 262 262 } 263 263 264 + __bpf_kfunc void bpf_crypto_ctx_release_dtor(void *ctx) 265 + { 266 + bpf_crypto_ctx_release(ctx); 267 + } 268 + CFI_NOSEAL(bpf_crypto_ctx_release_dtor); 269 + 264 270 static int bpf_crypto_crypt(const struct bpf_crypto_ctx *ctx, 265 271 const struct bpf_dynptr_kern *src, 266 272 const struct bpf_dynptr_kern *dst, ··· 374 368 375 369 BTF_ID_LIST(bpf_crypto_dtor_ids) 376 370 BTF_ID(struct, bpf_crypto_ctx) 377 - BTF_ID(func, bpf_crypto_ctx_release) 371 + BTF_ID(func, bpf_crypto_ctx_release_dtor) 378 372 379 373 static int __init crypto_kfunc_init(void) 380 374 {
+7 -1
net/sched/bpf_qdisc.c
··· 202 202 kfree_skb(skb); 203 203 } 204 204 205 + __bpf_kfunc void bpf_kfree_skb_dtor(void *skb) 206 + { 207 + bpf_kfree_skb(skb); 208 + } 209 + CFI_NOSEAL(bpf_kfree_skb_dtor); 210 + 205 211 /* bpf_qdisc_skb_drop - Drop an skb by adding it to a deferred free list. 206 212 * @skb: The skb whose reference to be released and dropped. 207 213 * @to_free_list: The list of skbs to be dropped. ··· 455 449 .owner = THIS_MODULE, 456 450 }; 457 451 458 - BTF_ID_LIST_SINGLE(bpf_sk_buff_dtor_ids, func, bpf_kfree_skb) 452 + BTF_ID_LIST_SINGLE(bpf_sk_buff_dtor_ids, func, bpf_kfree_skb_dtor) 459 453 460 454 static int __init bpf_qdisc_kfunc_init(void) 461 455 {
+7 -1
tools/testing/selftests/bpf/test_kmods/bpf_testmod.c
··· 285 285 call_rcu(&ctx->rcu, testmod_free_cb); 286 286 } 287 287 288 + __bpf_kfunc void bpf_testmod_ctx_release_dtor(void *ctx) 289 + { 290 + bpf_testmod_ctx_release(ctx); 291 + } 292 + CFI_NOSEAL(bpf_testmod_ctx_release_dtor); 293 + 288 294 static struct bpf_testmod_ops3 *st_ops3; 289 295 290 296 static int bpf_testmod_test_3(void) ··· 713 707 714 708 BTF_ID_LIST(bpf_testmod_dtor_ids) 715 709 BTF_ID(struct, bpf_testmod_ctx) 716 - BTF_ID(func, bpf_testmod_ctx_release) 710 + BTF_ID(func, bpf_testmod_ctx_release_dtor) 717 711 718 712 static const struct btf_kfunc_id_set bpf_testmod_common_kfunc_set = { 719 713 .owner = THIS_MODULE,