BPF List
 help / color / mirror / Atom feed
From: Yonghong Song <yonghong.song@linux.dev>
To: sashiko-reviews@lists.linux.dev
Cc: bpf@vger.kernel.org
Subject: Re: [PATCH bpf-next v2 06/10] bpf: Allow a global function to return arena pointers by value
Date: Wed, 26 Aug 2026 11:40:59 -0700	[thread overview]
Message-ID: <2074813a-269b-4ddb-82c7-e9b99eaa7f69@linux.dev> (raw)
In-Reply-To: <20260825211254.88DBA1F000E9@smtp.kernel.org>



On 8/25/26 2:12 PM, sashiko-bot@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
> - [High] BPF_PROG_TYPE_EXT (freplace) programs are erroneously rejected when replacing a global function that returns an arena pointer or a struct containing an arena pointer.
> - [High] Callers of global functions returning arena pointers receive a `SCALAR_VALUE` instead of `PTR_TO_ARENA`, causing valid dereferences to be rejected.
> --
>
> commit 9797a7277b67bb03067fdf11db423996a277abbd
> Author: Yonghong Song <yonghong.song@linux.dev>
>
> bpf: Allow a global function to return arena pointers by value
>
> This commit relaxes BTF verification to allow global functions to return
> arena pointers or structures containing arena pointers. It updates the
> verifier's return type validation to recognize these types when processing
> subprograms.
>
>> diff --git a/kernel/bpf/btf.c b/kernel/bpf/btf.c
>> index b1f4ef614d4c4..70481fadacc0f 100644
>> --- a/kernel/bpf/btf.c
>> +++ b/kernel/bpf/btf.c
>> @@ -7972,14 +7972,18 @@ static int btf_validate_return_type(struct bpf_verifier_env *env, struct btf *bt
>>   
>>   	if (btf_type_is_struct(t) && t->size <= 16) {
>>   		/*
>> -		 * A global function's caller models the return as an opaque
>> -		 * scalar pair, so it may only return scalars by value. A local
>> -		 * function is verified inline, so a pointer field stays tracked
>> -		 * and needs no such restriction.
>> +		 * A global function may return a struct with scalar(s) or arena
>> +		 * pointer(s) as its members. A local function is verified inline,
>> +		 * so its caller receives the real register state and any member
>> +		 * is fine.
>>   		 */
>>   		bool local_func = subprog && !is_global;
>> +		u32 member_kinds = BTF_MEMBER_SCALAR;
>>   
>> -		if (local_func || btf_struct_is_composed_of(env, btf, t, BTF_MEMBER_SCALAR))
>> +		if (subprog)
>> +			member_kinds |= BTF_MEMBER_ARENA_PTR;
> [Severity: High]
> Does this subprog condition inadvertently reject valid BPF_PROG_TYPE_EXT
> (freplace) programs?
>
> When replacing a global function that returns an arena pointer, the
> extension's main program must have an identical BTF signature to the target.
> During verification of the extension's main program (where subprog is 0),
> btf_prepare_func_args() is called. Since subprog evaluates to false,
> BTF_MEMBER_ARENA_PTR isn't added to member_kinds, causing the verifier to
> fall back and return -EOPNOTSUPP.

This analysis is correct. The above 'subprog' is not 0 (not for main prog),
so if it wants to return an arena point, the verifier will reject.

>
> [Severity: High]
> Even though this patch allows global functions to return arena pointers,
> won't callers still be unable to dereference them?
>
> In check_func_call() inside kernel/bpf/verifier.c, the return registers of
> global functions are unconditionally marked as unknown scalars:
>
> 	if (!returns_void) {
> 		nregs = bpf_ret_reg_pair(env, subprog) ? 2 : 1;
> 		for (i = 0; i < nregs; i++)
> 			mark_reg_unknown(env, caller->regs, ret_regs[i]);
> 		bpf_diag_mod_end(env);
> 	}
>
> Since the C type returned by the function (void __arena *) matches the type
> in the caller, the compiler doesn't emit an addr_space_cast instruction.
> Without this cast, the scalar is never promoted back to a PTR_TO_ARENA,
> causing check_mem_access() to reject subsequent dereferences with an "invalid
> mem access 'scalar'" error.

We should be okay here. For example, for returning type is a struct and
one of its member is an arena pointer (tagged with __arena). The compiler
will generate proper address_space conversion code due to __arena.

In kernel side, we will have something like below:

                         if (BPF_CLASS(insn->code) == BPF_ALU64) {
                                 if (insn->imm) {
                                         /* off == BPF_ADDR_SPACE_CAST */
                                         mark_reg_unknown(env, regs, insn->dst_reg);
                                         if (insn->imm == 1) /* cast from as(1) to as(0) */
                                                 dst_reg->type = PTR_TO_ARENA;
   	

>
>> +
>> +		if (local_func || btf_struct_is_composed_of(env, btf, t, member_kinds))
>>   			return 0;
>>   	}
>>


  reply	other threads:[~2026-08-26 18:41 UTC|newest]

Thread overview: 27+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-08-25 20:54 [PATCH bpf-next v2 00/10] bpf: Allow arena pointers in by-value returns Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 01/10] bpf: Record each half of a paired return value in verifier diagnostics Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-26 17:08     ` Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 02/10] bpf: Drop the recursion depth argument of btf_type_is_scalar_struct() Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 03/10] bpf: Add btf_type_is_arena_ptr() Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-26 17:28     ` Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 04/10] bpf: Let the by-value struct walk take the kinds of member it accepts Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-26 17:39     ` Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 05/10] bpf: Report which member makes a kfunc return type unsupported Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-26 17:59     ` Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 06/10] bpf: Allow a global function to return arena pointers by value Yonghong Song
2026-08-25 21:12   ` sashiko-bot
2026-08-26 18:40     ` Yonghong Song [this message]
2026-08-25 20:54 ` [PATCH bpf-next v2 07/10] bpf: Allow arena pointers in a by-value kfunc return Yonghong Song
2026-08-25 22:13   ` bot+bpf-ci
2026-08-26 18:57     ` Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 08/10] selftests/bpf: Check the member named for an unsupported kfunc return type Yonghong Song
2026-08-25 20:54 ` [PATCH bpf-next v2 09/10] selftests/bpf: Test global functions returning arena pointers by value Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-27  3:46     ` Yonghong Song
2026-08-25 20:55 ` [PATCH bpf-next v2 10/10] selftests/bpf: Test kfuncs " Yonghong Song
2026-08-25 21:59   ` bot+bpf-ci
2026-08-27  3:58     ` Yonghong Song

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=2074813a-269b-4ddb-82c7-e9b99eaa7f69@linux.dev \
    --to=yonghong.song@linux.dev \
    --cc=bpf@vger.kernel.org \
    --cc=sashiko-reviews@lists.linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox