Re: [PATCH bpf-next v5 06/11] bpf: Add verifier support for 16-byte returns in R0:R2
Eduard Zingerman <[email protected]>
| Newsgroups | org.kernel.vger.bpf |
|---|---|
| Message-ID | <[email protected]> |
On Thu, 2026-08-13 at 13:02 -0700, Yonghong Song wrote: > LLVM 23 added support for returning a value in two registers for an > __int128, or a struct/union whose size is greater than 8 but not more than > 16 bytes. See LLVM patches [1] and [2]. > > Before LLVM 23 the BPF backend could not return these values at all. A > by-value struct or union return (of any size) was rejected at compile time > with: > > error: aggregate returns are not supported > > and an __int128 return failed later in the backend with: > > fatal error: error in backend: unable to allocate function return #1 > > Both are resolved in LLVM 23, which lowers such returns into the R0:R2 > register pair. > > This patch models that pair at calls to global and static BPF subprograms > and at kfunc calls: R2 is marked alongside R0 at the call, propagated out > of a callee at its exit, and held to the same scalar-only and no-stack- > pointer rules that R0 already is. A struct returned by a kfunc must be > composed of scalars, since its bytes reach the program as raw register > contents and a pointer field would otherwise be laundered into a scalar. > > An extension program is the one caller of the convention that cannot take > part in it: its own return value is the program exit code, read out of R0 > alone, so it has no way to hand back an upper half. Replacing a function > whose return value is larger than 8 bytes is therefore rejected with > -EOPNOTSUPP rather than supported. > > [1] https://github.com/llvm/llvm-project/pull/190894 > [2] https://github.com/llvm/llvm-project/pull/206876 > > Signed-off-by: Yonghong Song <[email protected]> > --- Acked-by: Eduard Zingerman <[email protected]> > @@ -19404,6 +19458,13 @@ int bpf_check_attach_target(struct bpf_verifier_log *log, > return -EOPNOTSUPP; > } > > + if (prog_extension && tgt_info->fmodel.ret_size > 8) { > + bpf_log(log, > + "Cannot replace function %s with a >8 byte return value\n", > + tname); > + return -EOPNOTSUPP; > + } > + As commented in v4 [1], this check belongs to btf_check_type_match(). [1] https://lore.kernel.org/bpf/[email protected]/ > /* > * *.multi programs don't need an address during program > * verification, we just take the module ref if needed.