public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
From: "Jose E. Marchesi" <jose.marchesi@oracle.com>
To: "WanLi Niu" <kiraskyler@163.com>
Cc: Quentin Monnet <qmo@kernel.org>,
	Alexei Starovoitov <ast@kernel.org>,
	Daniel Borkmann <daniel@iogearbox.net>,
	Andrii Nakryiko <andrii@kernel.org>,
	Martin KaFai Lau <martin.lau@linux.dev>,
	Eduard Zingerman <eddyz87@gmail.com>, Song Liu <song@kernel.org>,
	Yonghong Song <yonghong.song@linux.dev>,
	John Fastabend <john.fastabend@gmail.com>,
	KP Singh <kpsingh@kernel.org>,
	Stanislav Fomichev <sdf@fomichev.me>, Hao Luo <haoluo@google.com>,
	Jiri Olsa <jolsa@kernel.org>,
	Menglong Dong <menglong8.dong@gmail.com>, <bpf@vger.kernel.org>,
	<linux-kernel@vger.kernel.org>,
	WanLi Niu <niuwl1@chinatelecom.cn>,
	Menglong Dong <dongml2@chinatelecom.cn>
Subject: Re: [PATCH v4 bpf-next] bpftool: Make skeleton C++ compatible with explicit casts
Date: Mon, 05 Jan 2026 17:05:53 +0100	[thread overview]
Message-ID: <87seckf3j2.fsf@oracle.com> (raw)
In-Reply-To: <7219135.9fee.19b8e385eb5.Coremail.kiraskyler@163.com>


>> FWIW I tested the reproducer with gcc-bpf and got no pointer conversion
>> warnings (not that I was expecting anything different, but just in
>> case):
>>
>>  $ bpf-unknown-none-gcc -std=gnu11 -I./tools/include -g -O2 -c text.bpf.c -o test.bpf.o
>>  $ bpftool gen skeleton test.bpf.o -L > test.bpf.skel.h
>>  $ g++ -c test.cpp -I.
>
> Thanks for testing.
>
> The issue only occurs when bpftool gen skeleton is used in use_loader
> mode (bpftool gen skeleton -L|--use-loader).
>
> Could you double-check if -L was included? I can reproduce the error
> reliably with it — here’s the full output:

I meant to say that I tested the reproducer _with your patch applied_.
It indeed cures the issue :)

Sorry it wasn't clear.

>
> $ rpm -qf `which bpf-unknown-none-gcc`
> gcc-bpf-unknown-none-15.2.1-1.fc42.x86_64
> $ bpf-unknown-none-gcc -std=gnu11 -I/usr/include -g -O2 -c test.bpf.c -o test.bpf.o
> $ bpftool gen skeleton test.bpf.o -L > test.bpf.skel.h
> libbpf: elf: skipping section(2) .data (size 0)
> libbpf: elf: skipping unrecognized data section(7) .comment
> libbpf: prog 'handle': missing .BTF.ext line info for the main program, skipping all of .BTF.ext line info.
> $ g++ -c test.cpp -I.
> In file included from test.cpp:4:
> test.bpf.skel.h: In function ‘test_bpf* test_bpf__open()’:
> test.bpf.skel.h:65:26: error: invalid conversion from ‘void*’ to ‘test_bpf*’ [-fpermissive]
>    65 |         skel = skel_alloc(sizeof(*skel));
>       |                ~~~~~~~~~~^~~~~~~~~~~~~~~
>       |                          |
>       |                          void*
> test.bpf.skel.h:68:55: error: invalid use of ‘void’
>    68 |         skel->ctx.sz = (void *)&skel->links - (void *)skel;
>       |                                                       ^~~~
> test.bpf.skel.h:73:47: error: invalid conversion from ‘void*’ to ‘test_bpf::test_bpf__bss*’ [-fpermissive]
>    73 |                 skel->bss = skel_prep_map_data((void *)data, 4096,
>       |                             ~~~~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~
>       |                                               |
>       |                                               void*
>    74 |                                                 sizeof(data) - 1);
>       |                                                 ~~~~~~~~~~~~~~~~~
> test.bpf.skel.h: In function ‘int test_bpf__load(test_bpf*)’:
> test.bpf.skel.h:196:43: error: invalid conversion from ‘void*’ to ‘test_bpf::test_bpf__bss*’ [-fpermissive]
>   196 |         skel->bss = skel_finalize_map_data(&skel->maps.bss.initial_value,
>       |                     ~~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>       |                                           |
>       |                                           void*
>   197 |                                         4096, PROT_READ | PROT_WRITE, skel->maps.bss.map_fd);
>       |                                         ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> $ cat test.bpf.skel.h 
> /* SPDX-License-Identifier: (LGPL-2.1 OR BSD-2-Clause) */
> /* THIS FILE IS AUTOGENERATED BY BPFTOOL! */
> #ifndef __TEST_BPF_SKEL_H__
> #define __TEST_BPF_SKEL_H__
>
> #include <bpf/skel_internal.h>
>
> struct test_bpf {
>         struct bpf_loader_ctx ctx;
>         struct {
>                 struct bpf_map_desc bss;
>         } maps;
>         struct {
>                 struct bpf_prog_desc handle;
>         } progs;
>         struct {
>                 int handle_fd;
>         } links;
>         struct test_bpf__bss {
>                 int val;
>         } *bss;
> };
>
> static inline int
> test_bpf__handle__attach(struct test_bpf *skel)
> {
>         int prog_fd = skel->progs.handle.prog_fd;
>         int fd = skel_raw_tracepoint_open("sched_wakeup_new", prog_fd);
>
>         if (fd > 0)
>                 skel->links.handle_fd = fd;
>         return fd;
> }
>
> static inline int
> test_bpf__attach(struct test_bpf *skel)
> {
>         int ret = 0;
>
>         ret = ret < 0 ? ret : test_bpf__handle__attach(skel);
>         return ret < 0 ? ret : 0;
> }
>
> static inline void
> test_bpf__detach(struct test_bpf *skel)
> {
>         skel_closenz(skel->links.handle_fd);
> }
> static void
> test_bpf__destroy(struct test_bpf *skel)
> {
>         if (!skel)
>                 return;
>         test_bpf__detach(skel);
>         skel_closenz(skel->progs.handle.prog_fd);
>         skel_free_map_data(skel->bss, skel->maps.bss.initial_value, 4096);
>         skel_closenz(skel->maps.bss.map_fd);
>         skel_free(skel);
> }
> static inline struct test_bpf *
> test_bpf__open(void)
> {
>         struct test_bpf *skel;
>
>         skel = skel_alloc(sizeof(*skel));
>         if (!skel)
>                 goto cleanup;
>         skel->ctx.sz = (void *)&skel->links - (void *)skel;
>         {
>                 static const char data[] __attribute__((__aligned__(8))) = "\
> \0\0\0\0";
>
>                 skel->bss = skel_prep_map_data((void *)data, 4096,
>                                                 sizeof(data) - 1);
>                 if (!skel->bss)
>                         goto cleanup;
>                 skel->maps.bss.initial_value = (__u64) (long) skel->bss;
>         }
>         return skel;
> cleanup:
>         test_bpf__destroy(skel);
>         return NULL;
> }
>
> static inline int
> test_bpf__load(struct test_bpf *skel)
> {
>         struct bpf_load_and_run_opts opts = {};
>         int err;
>         static const char opts_data[] __attribute__((__aligned__(8))) = "\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x9f\xeb\x01\0\
> \x18\0\0\0\0\0\0\0\x64\0\0\0\x64\0\0\0\x41\0\0\0\0\0\0\0\x01\0\0\x0d\x02\0\0\0\
> \x18\0\0\0\x03\0\0\0\x08\0\0\0\0\0\0\x01\x04\0\0\0\x20\0\0\x01\0\0\0\0\0\0\0\
> \x02\0\0\0\0\x13\0\0\0\0\0\0\x0e\x02\0\0\0\x01\0\0\0\x0c\0\0\0\x01\0\0\x0c\x01\
> \0\0\0\x3c\0\0\0\x01\0\0\x0f\x04\0\0\0\x04\0\0\0\0\0\0\0\x04\0\0\0\0\x68\x61\
> \x6e\x64\x6c\x65\0\x69\x6e\x74\0\x68\x61\x6e\x64\x6c\x65\0\x76\x61\x6c\0\0\x63\
> \x74\x78\0\x72\x61\x77\x5f\x74\x72\x61\x63\x65\x70\x6f\x69\x6e\x74\x2f\x73\x63\
> \x68\x65\x64\x5f\x77\x61\x6b\x65\x75\x70\x5f\x6e\x65\x77\0\x2e\x62\x73\x73\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\xbd\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x02\0\0\
> \0\x04\0\0\0\x04\0\0\0\x01\0\0\0\0\x04\0\0\0\0\0\0\0\0\0\0\x74\x65\x73\x74\x5f\
> \x62\x70\x66\x2e\x62\x73\x73\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x06\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\xb7\0\0\0\0\0\0\0\x95\0\0\0\
> \0\0\0\0\0\0\0\0\x05\0\0\0\x11\0\0\0\x02\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x68\x61\x6e\x64\x6c\x65\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x08\0\0\0\0\0\0\0\0\0\0\0\x01\0\0\0\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
> \0\0\0\x10\0\0\0\0\0\0\0";
>         static const char opts_insn[] __attribute__((__aligned__(8))) = "\
> \xbf\x16\0\0\0\0\0\0\xbf\xa1\0\0\0\0\0\0\x07\x01\0\0\x78\xff\xff\xff\xb7\x02\0\
> \0\x88\0\0\0\xb7\x03\0\0\0\0\0\0\x85\0\0\0\x71\0\0\0\x05\0\x11\0\0\0\0\0\x61\
> \xa1\x78\xff\0\0\0\0\xd5\x01\x01\0\0\0\0\0\x85\0\0\0\xa8\0\0\0\x61\xa1\x7c\xff\
> \0\0\0\0\xd5\x01\x01\0\0\0\0\0\x85\0\0\0\xa8\0\0\0\x61\xa1\x80\xff\0\0\0\0\xd5\
> \x01\x01\0\0\0\0\0\x85\0\0\0\xa8\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x61\
> \x01\0\0\0\0\0\0\xd5\x01\x02\0\0\0\0\0\xbf\x19\0\0\0\0\0\0\x85\0\0\0\xa8\0\0\0\
> \xbf\x70\0\0\0\0\0\0\x95\0\0\0\0\0\0\0\x61\x60\x08\0\0\0\0\0\x18\x61\0\0\0\0\0\
> \0\0\0\0\0\xd8\x05\0\0\x63\x01\0\0\0\0\0\0\x61\x60\x0c\0\0\0\0\0\x18\x61\0\0\0\
> \0\0\0\0\0\0\0\xd4\x05\0\0\x63\x01\0\0\0\0\0\0\x79\x60\x10\0\0\0\0\0\x18\x61\0\
> \0\0\0\0\0\0\0\0\0\xc8\x05\0\0\x7b\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\
> \0\x05\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\xc0\x05\0\0\x7b\x01\0\0\0\0\0\0\xb7\x01\
> \0\0\x12\0\0\0\x18\x62\0\0\0\0\0\0\0\0\0\0\xc0\x05\0\0\xb7\x03\0\0\x1c\0\0\0\
> \x85\0\0\0\xa6\0\0\0\xbf\x07\0\0\0\0\0\0\xc5\x07\xd7\xff\0\0\0\0\x63\x7a\x78\
> \xff\0\0\0\0\x61\xa0\x78\xff\0\0\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\x10\x06\0\0\
> \x63\x01\0\0\0\0\0\0\x61\x60\x1c\0\0\0\0\0\x15\0\x03\0\0\0\0\0\x18\x61\0\0\0\0\
> \0\0\0\0\0\0\xec\x05\0\0\x63\x01\0\0\0\0\0\0\xb7\x01\0\0\0\0\0\0\x18\x62\0\0\0\
> \0\0\0\0\0\0\0\xe0\x05\0\0\xb7\x03\0\0\x48\0\0\0\x85\0\0\0\xa6\0\0\0\xbf\x07\0\
> \0\0\0\0\0\xc5\x07\xc6\xff\0\0\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x63\x71\
> \0\0\0\0\0\0\x79\x63\x20\0\0\0\0\0\x15\x03\x08\0\0\0\0\0\x18\x61\0\0\0\0\0\0\0\
> \0\0\0\x28\x06\0\0\xb7\x02\0\0\x04\0\0\0\x61\x60\x04\0\0\0\0\0\x45\0\x02\0\x01\
> \0\0\0\x85\0\0\0\x94\0\0\0\x05\0\x01\0\0\0\0\0\x85\0\0\0\x71\0\0\0\x18\x62\0\0\
> \0\0\0\0\0\0\0\0\0\0\0\0\x61\x20\0\0\0\0\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\x38\
> \x06\0\0\x63\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\x30\x06\0\0\x18\x61\0\
> \0\0\0\0\0\0\0\0\0\x40\x06\0\0\x7b\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\
> \x28\x06\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\x48\x06\0\0\x7b\x01\0\0\0\0\0\0\xb7\
> \x01\0\0\x02\0\0\0\x18\x62\0\0\0\0\0\0\0\0\0\0\x38\x06\0\0\xb7\x03\0\0\x20\0\0\
> \0\x85\0\0\0\xa6\0\0\0\xbf\x07\0\0\0\0\0\0\xc5\x07\xa2\xff\0\0\0\0\x18\x60\0\0\
> \0\0\0\0\0\0\0\0\x58\x06\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\x88\x06\0\0\x7b\x01\0\
> \0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\x60\x06\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\
> \x80\x06\0\0\x7b\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\x70\x06\0\0\x18\
> \x61\0\0\0\0\0\0\0\0\0\0\xc8\x06\0\0\x7b\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\
> \0\0\0\x78\x06\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\xd8\x06\0\0\x7b\x01\0\0\0\0\0\0\
> \x18\x60\0\0\0\0\0\0\0\0\0\0\x78\x06\0\0\x18\x61\0\0\0\0\0\0\0\0\0\0\xf8\x06\0\
> \0\x7b\x01\0\0\0\0\0\0\x18\x60\0\0\0\0\0\0\0\0\0\0\0\0\0\0\x18\x61\0\0\0\0\0\0\
> \0\0\0\0\xf0\x06\0\0\x7b\x01\0\0\0\0\0\0\x61\x60\x08\0\0\0\0\0\x18\x61\0\0\0\0\
> \0\0\0\0\0\0\x90\x06\0\0\x63\x01\0\0\0\0\0\0\x61\x60\x0c\0\0\0\0\0\x18\x61\0\0\
> \0\0\0\0\0\0\0\0\x94\x06\0\0\x63\x01\0\0\0\0\0\0\x79\x60\x10\0\0\0\0\0\x18\x61\
> \0\0\0\0\0\0\0\0\0\0\x98\x06\0\0\x7b\x01\0\0\0\0\0\0\x61\xa0\x78\xff\0\0\0\0\
> \x18\x61\0\0\0\0\0\0\0\0\0\0\xc0\x06\0\0\x63\x01\0\0\0\0\0\0\xb7\x01\0\0\x05\0\
> \0\0\x18\x62\0\0\0\0\0\0\0\0\0\0\x78\x06\0\0\xb7\x03\0\0\x8c\0\0\0\x85\0\0\0\
> \xa6\0\0\0\xbf\x07\0\0\0\0\0\0\xc5\x07\x6d\xff\0\0\0\0\x63\x7a\x80\xff\0\0\0\0\
> \x61\xa1\x78\xff\0\0\0\0\xd5\x01\x02\0\0\0\0\0\xbf\x19\0\0\0\0\0\0\x85\0\0\0\
> \xa8\0\0\0\x61\xa0\x80\xff\0\0\0\0\x63\x06\x28\0\0\0\0\0\x18\x61\0\0\0\0\0\0\0\
> \0\0\0\0\0\0\0\x61\x10\0\0\0\0\0\0\x63\x06\x18\0\0\0\0\0\xb7\0\0\0\0\0\0\0\x95\
> \0\0\0\0\0\0\0";
>         opts.ctx = (struct bpf_loader_ctx *)skel;
>         opts.data_sz = sizeof(opts_data) - 1;
>         opts.data = (void *)opts_data;
>         opts.insns_sz = sizeof(opts_insn) - 1;
>         opts.insns = (void *)opts_insn;
>
>         err = bpf_load_and_run(&opts);
>         if (err < 0)
>                 return err;
>         skel->bss = skel_finalize_map_data(&skel->maps.bss.initial_value,
>                                         4096, PROT_READ | PROT_WRITE, skel->maps.bss.map_fd);
>         if (!skel->bss)
>                 return -ENOMEM;
>         return 0;
> }
>
> static inline struct test_bpf *
> test_bpf__open_and_load(void)
> {
>         struct test_bpf *skel;
>
>         skel = test_bpf__open();
>         if (!skel)
>                 return NULL;
>         if (test_bpf__load(skel)) {
>                 test_bpf__destroy(skel);
>                 return NULL;
>         }
>         return skel;
> }
>
> __attribute__((unused)) static void
> test_bpf__assert(struct test_bpf *s __attribute__((unused)))
> {
> #ifdef __cplusplus
> #define _Static_assert static_assert
> #endif
>         _Static_assert(sizeof(s->bss->val) == 4, "unexpected size of 'val'");
> #ifdef __cplusplus
> #undef _Static_assert
> #endif
> }
>
> #endif /* __TEST_BPF_SKEL_H__ */
>
> At 2026-01-05 19:50:25, "Jose E. Marchesi" <jose.marchesi@oracle.com> wrote:
>>
>>FWIW I tested the reproducer with gcc-bpf and got no pointer conversion
>>warnings (not that I was expecting anything different, but just in
>>case):
>>
>> $ bpf-unknown-none-gcc -std=gnu11 -I./tools/include -g -O2 -c text.bpf.c -o test.bpf.o
>> $ bpftool gen skeleton test.bpf.o -L > test.bpf.skel.h
>> $ g++ -c test.cpp -I.
>>
>>> From: WanLi Niu <niuwl1@chinatelecom.cn>
>>>
>>> Fix C++ compilation errors in generated skeleton by adding explicit
>>> pointer casts and using integer subtraction for offset calculation.
>>>
>>> Use struct outer::inner syntax under __cplusplus to access nested skeleton map
>>> structs, ensuring C++ compilation compatibility while preserving C support
>>>
>>> error: invalid conversion from 'void*' to '<obj_name>*' [-fpermissive]
>>>       |         skel = skel_alloc(sizeof(*skel));
>>>       |                ~~~~~~~~~~^~~~~~~~~~~~~~~
>>>       |                          |
>>>       |                          void*
>>>
>>> error: arithmetic on pointers to void
>>>       |         skel->ctx.sz = (void *)&skel->links - (void *)skel;
>>>       |                        ~~~~~~~~~~~~~~~~~~~~ ^ ~~~~~~~~~~~~
>>>
>>> error: assigning to 'struct <obj_name>__<ident> *' from incompatible type 'void *'
>>>       |                 skel-><ident> = skel_prep_map_data((void *)data, 4096,
>>>       |                             ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>>>       |                                                 sizeof(data) - 1);
>>>       |                                                 ~~~~~~~~~~~~~~~~~
>>>
>>> error: assigning to 'struct <obj_name>__<ident> *' from incompatible type 'void *'
>>>       |         skel-><ident> = skel_finalize_map_data(&skel->maps.<ident>.initial_value,
>>>       |                     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>>>       |                                         4096, PROT_READ | PROT_WRITE, skel->maps.<ident>.map_fd);
>>>       |                                         ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>>>
>>> Minimum reproducer:
>>>
>>> 	$ cat test.bpf.c
>>> 	int val; // placed in .bss section
>>>
>>> 	#include "vmlinux.h"
>>> 	#include <bpf/bpf_helpers.h>
>>>
>>> 	SEC("raw_tracepoint/sched_wakeup_new") int handle(void *ctx) { return 0; }
>>>
>>> 	$ cat test.cpp
>>> 	#include <cerrno>
>>>
>>> 	extern "C" {
>>> 	#include "test.bpf.skel.h"
>>> 	}
>>>
>>> 	$ bpftool btf dump file /sys/kernel/btf/vmlinux format c > vmlinux.h
>>> 	$ clang -g -O2 -target bpf -c test.bpf.c -o test.bpf.o
>>> 	$ bpftool gen skeleton test.bpf.o -L  > test.bpf.skel.h
>>> 	$ g++ -c test.cpp -I.
>>>
>>> Signed-off-by: WanLi Niu <niuwl1@chinatelecom.cn>
>>> Co-developed-by: Menglong Dong <dongml2@chinatelecom.cn>
>>> Signed-off-by: Menglong Dong <dongml2@chinatelecom.cn>
>>> ---
>>> changelog:
>>> v4:
>>> - Add a minimum reproducer to demonstrate the issue, as suggested by Yonghong Song
>>>
>>> v3: https://lore.kernel.org/all/20260104021402.2968-1-kiraskyler@163.com/
>>> - Fix two additional <obj_name>__<ident> type mismatches as suggested by Yonghong Song
>>>
>>> v2: https://lore.kernel.org/all/20251231102929.3843-1-kiraskyler@163.com/
>>> - Use generic (struct %1$s *) instead of project-specific (struct trace_bpf *)
>>>
>>> v1: https://lore.kernel.org/all/20251231092541.3352-1-kiraskyler@163.com/
>>> ---
>>>  tools/bpf/bpftool/gen.c | 16 ++++++++++++----
>>>  1 file changed, 12 insertions(+), 4 deletions(-)
>>>
>>> diff --git a/tools/bpf/bpftool/gen.c b/tools/bpf/bpftool/gen.c
>>> index 993c7d9484a4..010861b7d0ea 100644
>>> --- a/tools/bpf/bpftool/gen.c
>>> +++ b/tools/bpf/bpftool/gen.c
>>> @@ -731,10 +731,10 @@ static int gen_trace(struct bpf_object *obj, const char *obj_name, const char *h
>>>  		{							    \n\
>>>  			struct %1$s *skel;				    \n\
>>>  									    \n\
>>> -			skel = skel_alloc(sizeof(*skel));		    \n\
>>> +			skel = (struct %1$s *)skel_alloc(sizeof(*skel));    \n\
>>>  			if (!skel)					    \n\
>>>  				goto cleanup;				    \n\
>>> -			skel->ctx.sz = (void *)&skel->links - (void *)skel; \n\
>>> +			skel->ctx.sz = (__u64)&skel->links - (__u64)skel;   \n\
>>>  		",
>>>  		obj_name, opts.data_sz);
>>>  	bpf_object__for_each_map(map, obj) {
>>> @@ -755,13 +755,17 @@ static int gen_trace(struct bpf_object *obj, const char *obj_name, const char *h
>>>  		\n\
>>>  		\";							    \n\
>>>  									    \n\
>>> +		#ifdef __cplusplus                                          \n\
>>> +				skel->%1$s = (struct %3$s::%3$s__%1$s *)skel_prep_map_data((void *)data, %2$zd,\n\
>>> +		#else                                                       \n\
>>>  				skel->%1$s = skel_prep_map_data((void *)data, %2$zd,\n\
>>> +		#endif							    \n\
>>>  								sizeof(data) - 1);\n\
>>>  				if (!skel->%1$s)			    \n\
>>>  					goto cleanup;			    \n\
>>>  				skel->maps.%1$s.initial_value = (__u64) (long) skel->%1$s;\n\
>>>  			}						    \n\
>>> -			", ident, bpf_map_mmap_sz(map));
>>> +			", ident, bpf_map_mmap_sz(map), obj_name);
>>>  	}
>>>  	codegen("\
>>>  		\n\
>>> @@ -857,12 +861,16 @@ static int gen_trace(struct bpf_object *obj, const char *obj_name, const char *h
>>>  
>>>  		codegen("\
>>>  		\n\
>>> +		#ifdef __cplusplus					    \n\
>>> +			skel->%1$s = (struct %4$s::%4$s__%1$s *)skel_finalize_map_data(&skel->maps.%1$s.initial_value,\n\
>>> +		#else							    \n\
>>>  			skel->%1$s = skel_finalize_map_data(&skel->maps.%1$s.initial_value,  \n\
>>> +		#endif							    \n\
>>>  							%2$zd, %3$s, skel->maps.%1$s.map_fd);\n\
>>>  			if (!skel->%1$s)				    \n\
>>>  				return -ENOMEM;				    \n\
>>>  			",
>>> -		       ident, bpf_map_mmap_sz(map), mmap_flags);
>>> +		       ident, bpf_map_mmap_sz(map), mmap_flags, obj_name);
>>>  	}
>>>  	codegen("\
>>>  		\n\

  reply	other threads:[~2026-01-05 16:07 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2025-12-31  9:25 [PATCH bpf-next] bpftool: Make skeleton C++ compatible with explicit casts WanLi Niu
2025-12-31  9:48 ` bot+bpf-ci
2025-12-31 10:29 ` [PATCH v2 " WanLi Niu
2026-01-02 19:35   ` Yonghong Song
2026-01-04  2:14   ` [PATCH v3 " WanLi Niu
2026-01-05  5:27     ` Yonghong Song
2026-01-05  7:12     ` [PATCH v4 " WanLi Niu
2026-01-05 10:39       ` Quentin Monnet
2026-01-05 11:50       ` Jose E. Marchesi
2026-01-05 12:53         ` WanLi Niu
2026-01-05 16:05           ` Jose E. Marchesi [this message]
2026-01-06  2:31       ` [PATCH v5 " WanLi Niu
2026-01-09 19:00         ` patchwork-bot+netdevbpf
2026-01-06  0:46     ` [PATCH v3 " Andrii Nakryiko

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=87seckf3j2.fsf@oracle.com \
    --to=jose.marchesi@oracle.com \
    --cc=andrii@kernel.org \
    --cc=ast@kernel.org \
    --cc=bpf@vger.kernel.org \
    --cc=daniel@iogearbox.net \
    --cc=dongml2@chinatelecom.cn \
    --cc=eddyz87@gmail.com \
    --cc=haoluo@google.com \
    --cc=john.fastabend@gmail.com \
    --cc=jolsa@kernel.org \
    --cc=kiraskyler@163.com \
    --cc=kpsingh@kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=martin.lau@linux.dev \
    --cc=menglong8.dong@gmail.com \
    --cc=niuwl1@chinatelecom.cn \
    --cc=qmo@kernel.org \
    --cc=sdf@fomichev.me \
    --cc=song@kernel.org \
    --cc=yonghong.song@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