Re: [PATCH dwarves v7 0/5] pahole: Encode true signatures in kernel BTF
Yonghong Song <[email protected]> Tue, 23 Jun 2026 09:58:09 -0700
| Newsgroups | org.kernel.vger.dwarves,org.kernel.vger.bpf |
|---|---|
| Message-ID | <[email protected]> |
On 6/23/26 9:02 AM, Alan Maguire wrote:
> On 23/06/2026 14:11, Alan Maguire wrote:
>> On 23/06/2026 13:28, Jiri Olsa wrote:
>>> On Mon, Jun 22, 2026 at 09:07:04PM -0700, Yonghong Song wrote:
>>>> Current vmlinux BTF encoding is based on the source level signatures.
>>>> But the compiler may do some optimization and changed the signature.
>>>> If the user tried with source level signature, their initial implementation
>>>> may have wrong results and then the user need to check what is the
>>>> problem and work around it, e.g. through kprobe since kprobe does not
>>>> need vmlinux BTF.
>>>>
>>>> Majority of changed signatures are due to dead argument elimination.
>>>> The following is a more complex one. The original source signature:
>>>> typedef struct {
>>>> union {
>>>> void *kernel;
>>>> void __user *user;
>>>> };
>>>> bool is_kernel : 1;
>>>> } sockptr_t;
>>>> typedef sockptr_t bpfptr_t;
>>>> static int map_create(union bpf_attr *attr, bpfptr_t uattr) { ... }
>>>> After compiler optimization, the signature becomes:
>>>> static int map_create(union bpf_attr *attr, bool uattr__is_kernel) { ... }
>>>> In the above, uattr__is_kernel corresponds to 'is_kernel' field in sockptr_t.
>>>> This makes it easier for developers to understand what changed.
>>>>
>>>> The new signature needs to properly follow ABI specification based on
>>>> locations. Otherwise, that signature should be discarded. For example,
>>>>
>>>> 0x0242f1f7: DW_TAG_subprogram
>>>> DW_AT_name ("memblock_find_in_range")
>>>> DW_AT_calling_convention (DW_CC_nocall)
>>>> DW_AT_type (0x0242decc "phys_addr_t")
>>>> ...
>>>> 0x0242f22e: DW_TAG_formal_parameter
>>>> DW_AT_location (indexed (0x14a) loclist = 0x005595bc:
>>>> [0xffffffff87a000f9, 0xffffffff87a00178): DW_OP_reg5 RDI
>>>> [0xffffffff87a00178, 0xffffffff87a001be): DW_OP_reg14 R14
>>>> [0xffffffff87a001be, 0xffffffff87a001c7): DW_OP_entry_value(DW_OP_reg5 RDI), DW_OP_stack_value
>>>> [0xffffffff87a001c7, 0xffffffff87a00214): DW_OP_reg14 R14)
>>>> DW_AT_name ("start")
>>>> DW_AT_type (0x0242decc "phys_addr_t")
>>>> ...
>>>> 0x0242f239: DW_TAG_formal_parameter
>>>> DW_AT_location (indexed (0x14b) loclist = 0x005595e6:
>>>> [0xffffffff87a000f9, 0xffffffff87a00175): DW_OP_reg4 RSI
>>>> [0xffffffff87a00175, 0xffffffff87a001b8): DW_OP_reg3 RBX
>>>> [0xffffffff87a001b8, 0xffffffff87a001c7): DW_OP_entry_value(DW_OP_reg4 RSI), DW_OP_stack_value
>>>> [0xffffffff87a001c7, 0xffffffff87a00214): DW_OP_reg3 RBX)
>>>> DW_AT_name ("end")
>>>> DW_AT_type (0x0242decc "phys_addr_t")
>>>> ...
>>>> 0x0242f245: DW_TAG_formal_parameter
>>>> DW_AT_location (indexed (0x14c) loclist = 0x00559610:
>>>> [0xffffffff87a001e3, 0xffffffff87a001ef): DW_OP_breg4 RSI+0)
>>>> DW_AT_name ("size")
>>>> DW_AT_type (0x0242decc "phys_addr_t")
>>>> ...
>>>> 0x0242f250: DW_TAG_formal_parameter
>>>> DW_AT_const_value (4096)
>>>> DW_AT_name ("align")
>>>> DW_AT_type (0x0242decc "phys_addr_t")
>>>> ...
>>>>
>>>> The third argument should correspond to RDX for x86_64. But the location suggests that
>>>> the parameter value is stored in the address with 'RSI + 0'. It is not clear whether
>>>> the parameter value is stored in RDX or not. So we have to discard this funciton in
>>>> vmlinux BTF to avoid incorrect true signatures.
>>>>
>>>> For llvm, any function having
>>>> DW_AT_calling_convention (DW_CC_nocall)
>>>> in dwarf DW_TAG_subprogram will indicate that this function has signature changed.
>>>> I did experiment with latest bpf-next. For x86_64, there are 69103 kernel functions
>>>> and 875 kernel functions having signature changed. A series of patches are intended
>>>> to ensure true signatures are properly represented. Eventually, only 20 functions
>>>> cannot have true signatures due to locations.
>>> hi,
>>> I tried to get the numbers from my setup and noticed that some new
>>> functions were included in BTF compared to the current version
>>> (functions diff attached below)
>>>
>>> like for "arp_process" function the current pahole gives me:
>>>
>>> arp_process : skipping BTF encoding of function due to unexpected register usage for parameter
>>>
>>> but it's included in BTF generated with the new pahole.
>>>
>>> in addition to your explanation above also one of the commit says:
>>>
>>> - a parameter with no location, a constant value, or (for non-clang) no
>>> register found is marked optimized out
>>>
>>> please check below, it seems like 2nd argument of arp_process has no location,
>>> so iiuc it should not be included in BTF, right?
>>>
>>> thanks,
>>> jirka
>>>
>>>
>> thanks for catching this; it looks like we return a bit early before detecting
>> missing locations in the non-true-signature code. If you get a chance, would you
>> mind trying the attached patch to see if it fixes the problem?
>>
>> If the fix works and Yonghong is happy with it we can add it as a followup
>> and land the true signature series to save another round.
> actually sorry that patch leaked true signature partial names for gcc; updated
> patch attached.
The whole clang signature_changed thing can be removed.
I want to see whether cu->producer_clang can be removed in
} else if (pos->has_const_value && !cu->producer_clang) {
pos->optimized = 1;
} else if (true_sig_enabled) {
if (regs_available &&
ftype__next_parameter_preserves_slots(ftype, pos, reg_idx, slots, cu)) {
reg_idx += slots;
continue;
}
pos->optimized = 1;
consumes_register = false;
}
For clang, we cannot just do pos->optimized = 1 just due to pos->has_const_value though.