* [PATCH] samples/bpf: Fix sockex3: missing BPF prog type
@ 2022-10-27 13:33 Rong Tao
2022-10-27 13:38 ` [PATCH bpf-next] " Rong Tao
0 siblings, 1 reply; 12+ messages in thread
From: Rong Tao @ 2022-10-27 13:33 UTC (permalink / raw)
Cc: Rong Tao, Alexei Starovoitov, Daniel Borkmann, Andrii Nakryiko,
Martin KaFai Lau, Song Liu, Yonghong Song, John Fastabend,
KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa,
open list:BPF [GENERAL] (Safe Dynamic Programs and Tools),
open list
From: Rong Tao <rongtao@cestc.cn>
since commit 450b167fb9be("libbpf: clean up SEC() handling"),
sec_def_matches() does not recognize "socket/xxx" as "socket", therefore,
the BPF program type is not recognized, we should add a custom program
type handler for "socket/xxx".
$ cd samples/bpf
$ sudo ./sockex3
libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3'
libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22
libbpf: failed to load object './sockex3_kern.o'
ERROR: loading BPF object file failed
Signed-off-by: Rong Tao <rongtao@cestc.cn>
---
samples/bpf/sockex3_user.c | 15 +++++++++++++++
1 file changed, 15 insertions(+)
diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c
index cd6fa79df900..d18d7a3600b0 100644
--- a/samples/bpf/sockex3_user.c
+++ b/samples/bpf/sockex3_user.c
@@ -22,6 +22,14 @@ struct pair {
__u64 bytes;
};
+static int socket_prog_type_id;
+
+__attribute__((destructor))
+static void unregister_socket_sec_handlers(void)
+{
+ libbpf_unregister_prog_handler(socket_prog_type_id);
+}
+
int main(int argc, char **argv)
{
int i, sock, key, fd, main_prog_fd, jmp_table_fd, hash_map_fd;
@@ -31,6 +39,13 @@ int main(int argc, char **argv)
char filename[256];
FILE *f;
+ LIBBPF_OPTS(libbpf_prog_handler_opts, socket_opts,
+ .cookie = 1,
+ );
+
+ socket_prog_type_id = libbpf_register_prog_handler("socket/",
+ BPF_PROG_TYPE_SOCKET_FILTER, 0, &socket_opts);
+
snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]);
obj = bpf_object__open_file(filename, NULL);
--
2.31.1
^ permalink raw reply related [flat|nested] 12+ messages in thread* [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-27 13:33 [PATCH] samples/bpf: Fix sockex3: missing BPF prog type Rong Tao @ 2022-10-27 13:38 ` Rong Tao 2022-10-27 20:15 ` Andrii Nakryiko 0 siblings, 1 reply; 12+ messages in thread From: Rong Tao @ 2022-10-27 13:38 UTC (permalink / raw) Cc: Rong Tao, Alexei Starovoitov, Daniel Borkmann, Andrii Nakryiko, Martin KaFai Lau, Song Liu, Yonghong Song, John Fastabend, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, open list:BPF [GENERAL] (Safe Dynamic Programs and Tools), open list From: Rong Tao <rongtao@cestc.cn> since commit 450b167fb9be("libbpf: clean up SEC() handling"), sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, the BPF program type is not recognized, we should add a custom program type handler for "socket/xxx". $ cd samples/bpf $ sudo ./sockex3 libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 libbpf: failed to load object './sockex3_kern.o' ERROR: loading BPF object file failed Signed-off-by: Rong Tao <rongtao@cestc.cn> --- samples/bpf/sockex3_user.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c index cd6fa79df900..d18d7a3600b0 100644 --- a/samples/bpf/sockex3_user.c +++ b/samples/bpf/sockex3_user.c @@ -22,6 +22,14 @@ struct pair { __u64 bytes; }; +static int socket_prog_type_id; + +__attribute__((destructor)) +static void unregister_socket_sec_handlers(void) +{ + libbpf_unregister_prog_handler(socket_prog_type_id); +} + int main(int argc, char **argv) { int i, sock, key, fd, main_prog_fd, jmp_table_fd, hash_map_fd; @@ -31,6 +39,13 @@ int main(int argc, char **argv) char filename[256]; FILE *f; + LIBBPF_OPTS(libbpf_prog_handler_opts, socket_opts, + .cookie = 1, + ); + + socket_prog_type_id = libbpf_register_prog_handler("socket/", + BPF_PROG_TYPE_SOCKET_FILTER, 0, &socket_opts); + snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]); obj = bpf_object__open_file(filename, NULL); -- 2.31.1 ^ permalink raw reply related [flat|nested] 12+ messages in thread
* Re: [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-27 13:38 ` [PATCH bpf-next] " Rong Tao @ 2022-10-27 20:15 ` Andrii Nakryiko 2022-10-28 1:01 ` [PATCH] " Rong Tao 0 siblings, 1 reply; 12+ messages in thread From: Andrii Nakryiko @ 2022-10-27 20:15 UTC (permalink / raw) To: Rong Tao Cc: Rong Tao, Alexei Starovoitov, Daniel Borkmann, Andrii Nakryiko, Martin KaFai Lau, Song Liu, Yonghong Song, John Fastabend, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa, open list:BPF [GENERAL] (Safe Dynamic Programs and Tools), open list On Thu, Oct 27, 2022 at 6:38 AM Rong Tao <rtoax@foxmail.com> wrote: > > From: Rong Tao <rongtao@cestc.cn> > > since commit 450b167fb9be("libbpf: clean up SEC() handling"), > sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, > the BPF program type is not recognized, we should add a custom program > type handler for "socket/xxx". I don't think we should, we should just switch to SEC("socket") or whatever the right annotation has to be. Let's fix the BPF-side code. > > $ cd samples/bpf > $ sudo ./sockex3 > libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' > libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 > libbpf: failed to load object './sockex3_kern.o' > ERROR: loading BPF object file failed > > Signed-off-by: Rong Tao <rongtao@cestc.cn> > --- > samples/bpf/sockex3_user.c | 15 +++++++++++++++ > 1 file changed, 15 insertions(+) > > diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c > index cd6fa79df900..d18d7a3600b0 100644 > --- a/samples/bpf/sockex3_user.c > +++ b/samples/bpf/sockex3_user.c > @@ -22,6 +22,14 @@ struct pair { > __u64 bytes; > }; > > +static int socket_prog_type_id; > + > +__attribute__((destructor)) > +static void unregister_socket_sec_handlers(void) > +{ > + libbpf_unregister_prog_handler(socket_prog_type_id); > +} > + > int main(int argc, char **argv) > { > int i, sock, key, fd, main_prog_fd, jmp_table_fd, hash_map_fd; > @@ -31,6 +39,13 @@ int main(int argc, char **argv) > char filename[256]; > FILE *f; > > + LIBBPF_OPTS(libbpf_prog_handler_opts, socket_opts, > + .cookie = 1, > + ); > + > + socket_prog_type_id = libbpf_register_prog_handler("socket/", > + BPF_PROG_TYPE_SOCKET_FILTER, 0, &socket_opts); > + > snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]); > > obj = bpf_object__open_file(filename, NULL); > -- > 2.31.1 > ^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-27 20:15 ` Andrii Nakryiko @ 2022-10-28 1:01 ` Rong Tao 2022-10-28 17:09 ` Andrii Nakryiko 0 siblings, 1 reply; 12+ messages in thread From: Rong Tao @ 2022-10-28 1:01 UTC (permalink / raw) To: andrii.nakryiko Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, rtoax, sdf, song, yhs Thanks for your reply, actually, i tried another method, which can solved this error, recognize "socket/xxx" as "socket". However, it maybe influence other BPF prog or not? What do you think the following patch? --- a/tools/lib/bpf/libbpf.c +++ b/tools/lib/bpf/libbpf.c @@ -8659,7 +8659,7 @@ static bool sec_def_matches(const struct bpf_sec_def *sec_def, const char *sec_n return false; } - return strcmp(sec_name, sec_def->sec) == 0; + return strncmp(sec_name, sec_def->sec, len) == 0; } ^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-28 1:01 ` [PATCH] " Rong Tao @ 2022-10-28 17:09 ` Andrii Nakryiko 2022-10-29 7:53 ` [PATCH bpf-next] " Rong Tao 0 siblings, 1 reply; 12+ messages in thread From: Andrii Nakryiko @ 2022-10-28 17:09 UTC (permalink / raw) To: Rong Tao Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, sdf, song, yhs On Thu, Oct 27, 2022 at 6:01 PM Rong Tao <rtoax@foxmail.com> wrote: > > Thanks for your reply, actually, i tried another method, which can solved > this error, recognize "socket/xxx" as "socket". However, it maybe influence > other BPF prog or not? What do you think the following patch? Don't fix libbpf, it's not broken. Fix the sample. > > --- a/tools/lib/bpf/libbpf.c > +++ b/tools/lib/bpf/libbpf.c > @@ -8659,7 +8659,7 @@ static bool sec_def_matches(const struct bpf_sec_def *sec_def, const char *sec_n > return false; > } > > - return strcmp(sec_name, sec_def->sec) == 0; > + return strncmp(sec_name, sec_def->sec, len) == 0; > } ^ permalink raw reply [flat|nested] 12+ messages in thread
* [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-28 17:09 ` Andrii Nakryiko @ 2022-10-29 7:53 ` Rong Tao 2022-11-03 18:38 ` Andrii Nakryiko 0 siblings, 1 reply; 12+ messages in thread From: Rong Tao @ 2022-10-29 7:53 UTC (permalink / raw) To: andrii.nakryiko Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, rtoax, sdf, song, yhs From: Rong Tao <rongtao@cestc.cn> since commit 450b167fb9be("libbpf: clean up SEC() handling"), sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, the BPF program type is not recognized, set "socket/xxx" to SOCKET_FILTER solves this error. $ cd samples/bpf $ sudo ./sockex3 libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 libbpf: failed to load object './sockex3_kern.o' ERROR: loading BPF object file failed Signed-off-by: Rong Tao <rongtao@cestc.cn> --- samples/bpf/sockex3_user.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c index cd6fa79df900..dc79c17ad195 100644 --- a/samples/bpf/sockex3_user.c +++ b/samples/bpf/sockex3_user.c @@ -39,6 +39,9 @@ int main(int argc, char **argv) return 0; } + bpf_object__for_each_program(prog, obj) + bpf_program__set_type(prog, BPF_PROG_TYPE_SOCKET_FILTER); + /* load BPF program */ if (bpf_object__load(obj)) { fprintf(stderr, "ERROR: loading BPF object file failed\n"); -- 2.31.1 ^ permalink raw reply related [flat|nested] 12+ messages in thread
* Re: [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-10-29 7:53 ` [PATCH bpf-next] " Rong Tao @ 2022-11-03 18:38 ` Andrii Nakryiko 2022-11-04 3:17 ` Rong Tao 0 siblings, 1 reply; 12+ messages in thread From: Andrii Nakryiko @ 2022-11-03 18:38 UTC (permalink / raw) To: Rong Tao Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, sdf, song, yhs On Sat, Oct 29, 2022 at 12:53 AM Rong Tao <rtoax@foxmail.com> wrote: > > From: Rong Tao <rongtao@cestc.cn> > > since commit 450b167fb9be("libbpf: clean up SEC() handling"), > sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, > the BPF program type is not recognized, set "socket/xxx" to SOCKET_FILTER > solves this error. > > $ cd samples/bpf > $ sudo ./sockex3 > libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' > libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 > libbpf: failed to load object './sockex3_kern.o' > ERROR: loading BPF object file failed > > Signed-off-by: Rong Tao <rongtao@cestc.cn> > --- You need to do changes like this: diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c index b363503357e5..db6a93e7ec53 100644 --- a/samples/bpf/sockex3_kern.c +++ b/samples/bpf/sockex3_kern.c @@ -17,7 +17,7 @@ #define IP_MF 0x2000 #define IP_OFFSET 0x1FFF -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F +#define PROG(F) SEC("socket_filter") int bpf_func_##F struct { __uint(type, BPF_MAP_TYPE_PROG_ARRAY); @@ -279,7 +279,7 @@ PROG(PARSE_MPLS)(struct __sk_buff *skb) return 0; } -SEC("socket/0") +SEC("socket_filter") int main_prog(struct __sk_buff *skb) { __u32 nhoff = ETH_HLEN; Why fixing up after the fact at runtime, if you can just make those BPF programs conform to libbpf rules? > samples/bpf/sockex3_user.c | 3 +++ > 1 file changed, 3 insertions(+) > > diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c > index cd6fa79df900..dc79c17ad195 100644 > --- a/samples/bpf/sockex3_user.c > +++ b/samples/bpf/sockex3_user.c > @@ -39,6 +39,9 @@ int main(int argc, char **argv) > return 0; > } > > + bpf_object__for_each_program(prog, obj) > + bpf_program__set_type(prog, BPF_PROG_TYPE_SOCKET_FILTER); > + > /* load BPF program */ > if (bpf_object__load(obj)) { > fprintf(stderr, "ERROR: loading BPF object file failed\n"); > -- > 2.31.1 > ^ permalink raw reply related [flat|nested] 12+ messages in thread
* Re: Re: [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-11-03 18:38 ` Andrii Nakryiko @ 2022-11-04 3:17 ` Rong Tao 2022-11-04 22:53 ` Andrii Nakryiko 0 siblings, 1 reply; 12+ messages in thread From: Rong Tao @ 2022-11-04 3:17 UTC (permalink / raw) To: andrii.nakryiko Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, rtoax, sdf, song, yhs We can not just remove the number of program like: -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F +#define PROG(F) SEC("socket_filter") int bpf_func_##F because "sockex3" use the _NUMBER_ as index(see map "jmp_table"), if we apply the following patch, it's still not recognize "socket_filter/xxx" as "socket_filter", still have "missing BPF prog type" error: diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c index b363503357e5..ab5a7bde66d0 100644 --- a/samples/bpf/sockex3_kern.c +++ b/samples/bpf/sockex3_kern.c @@ -17,7 +17,7 @@ #define IP_MF 0x2000 #define IP_OFFSET 0x1FFF -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F +#define PROG(F) SEC("socket_filter/"__stringify(F)) int bpf_func_##F struct { __uint(type, BPF_MAP_TYPE_PROG_ARRAY); @@ -279,7 +279,7 @@ PROG(PARSE_MPLS)(struct __sk_buff *skb) return 0; } -SEC("socket/0") +SEC("socket_filter/0") int main_prog(struct __sk_buff *skb) { __u32 nhoff = ETH_HLEN; diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c index cd6fa79df900..63fc9a8077b1 100644 --- a/samples/bpf/sockex3_user.c +++ b/samples/bpf/sockex3_user.c @@ -56,7 +56,7 @@ int main(int argc, char **argv) fd = bpf_program__fd(prog); section = bpf_program__section_name(prog); - if (sscanf(section, "socket/%d", &key) != 1) { + if (sscanf(section, "socket_filter/%d", &key) != 1) { fprintf(stderr, "ERROR: finding prog failed\n"); goto cleanup; } For a reason, in sockex3_kern.c only have five PROGs, list all five: #define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F PROG(PARSE_IP)(struct __sk_buff *skb) PROG(PARSE_IPV6)(struct __sk_buff *skb) PROG(PARSE_VLAN)(struct __sk_buff *skb) PROG(PARSE_MPLS)(struct __sk_buff *skb) SEC("socket/0") int main_prog(struct __sk_buff *skb) As you can see, all those PROGs are BPF_PROG_TYPE_SOCKET_FILTER, so we can use the follow patch specify bpf program type as SOCKET_FILTER: https://lore.kernel.org/lkml/tencent_7DD02046A8398BE3324F85E0F56ED41EB105@qq.com/ diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c index cd6fa79df900..dc79c17ad195 100644 --- a/samples/bpf/sockex3_user.c +++ b/samples/bpf/sockex3_user.c @@ -39,6 +39,9 @@ int main(int argc, char **argv) return 0; } + bpf_object__for_each_program(prog, obj) + bpf_program__set_type(prog, BPF_PROG_TYPE_SOCKET_FILTER); + /* load BPF program */ if (bpf_object__load(obj)) { fprintf(stderr, "ERROR: loading BPF object file failed\n"); This patch above totally solved the compile error. ^ permalink raw reply related [flat|nested] 12+ messages in thread
* Re: Re: [PATCH bpf-next] samples/bpf: Fix sockex3: missing BPF prog type 2022-11-04 3:17 ` Rong Tao @ 2022-11-04 22:53 ` Andrii Nakryiko 2022-11-05 6:48 ` [PATCH bpf-next] samples/bpf: Fix sockex3 error: " Rong Tao 0 siblings, 1 reply; 12+ messages in thread From: Andrii Nakryiko @ 2022-11-04 22:53 UTC (permalink / raw) To: Rong Tao Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, sdf, song, yhs On Thu, Nov 3, 2022 at 8:17 PM Rong Tao <rtoax@foxmail.com> wrote: > > We can not just remove the number of program like: > > -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F > +#define PROG(F) SEC("socket_filter") int bpf_func_##F > > because "sockex3" use the _NUMBER_ as index(see map "jmp_table"), if we > apply the following patch, it's still not recognize "socket_filter/xxx" > as "socket_filter", still have "missing BPF prog type" error: Ok, let's keep unwinding this. This is an old and manual way to set up tail call map. Libbpf supports declarative way to do, so sockex3_user.c won't have to do anything at all. See progs/test_prog_array_init.c for an example. Let's convert samples to use this as well. This programmatic setting of program type works, there is no doubt about this. But it's a signal that something is not exactly how it should be. So let's use this as an opportunity to modernize samples, instead of adding workarounds. I hope you sympathize with this goal. > > diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c > index b363503357e5..ab5a7bde66d0 100644 > --- a/samples/bpf/sockex3_kern.c > +++ b/samples/bpf/sockex3_kern.c > @@ -17,7 +17,7 @@ > #define IP_MF 0x2000 > #define IP_OFFSET 0x1FFF > [...] ^ permalink raw reply [flat|nested] 12+ messages in thread
* [PATCH bpf-next] samples/bpf: Fix sockex3 error: missing BPF prog type 2022-11-04 22:53 ` Andrii Nakryiko @ 2022-11-05 6:48 ` Rong Tao 2022-11-08 1:14 ` Andrii Nakryiko 2022-11-08 1:20 ` patchwork-bot+netdevbpf 0 siblings, 2 replies; 12+ messages in thread From: Rong Tao @ 2022-11-05 6:48 UTC (permalink / raw) To: andrii.nakryiko Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, rtoax, sdf, song, yhs From: Rong Tao <rongtao@cestc.cn> since commit 450b167fb9be("libbpf: clean up SEC() handling"), sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, the BPF program type is not recognized. Instead of sockex3_user.c parsing section names to get the BPF program fd. We use the program array map to assign a static index to each BPF program (get inspired by selftests/bpf progs/test_prog_array_init.c). Therefore, use SEC("socket") as section name instead of SEC("socket/xxx"), so that the BPF program is parsed to SOCKET_FILTER type. The "missing BPF prog type" problem is solved. How to reproduce this error: $ cd samples/bpf $ sudo ./sockex3 libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 libbpf: failed to load object './sockex3_kern.o' ERROR: loading BPF object file failed Signed-off-by: Rong Tao <rongtao@cestc.cn> --- samples/bpf/sockex3_kern.c | 95 ++++++++++++++++++++++---------------- samples/bpf/sockex3_user.c | 23 ++++----- 2 files changed, 64 insertions(+), 54 deletions(-) diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c index b363503357e5..26d916834865 100644 --- a/samples/bpf/sockex3_kern.c +++ b/samples/bpf/sockex3_kern.c @@ -17,47 +17,12 @@ #define IP_MF 0x2000 #define IP_OFFSET 0x1FFF -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F - -struct { - __uint(type, BPF_MAP_TYPE_PROG_ARRAY); - __uint(key_size, sizeof(u32)); - __uint(value_size, sizeof(u32)); - __uint(max_entries, 8); -} jmp_table SEC(".maps"); - #define PARSE_VLAN 1 #define PARSE_MPLS 2 #define PARSE_IP 3 #define PARSE_IPV6 4 -/* Protocol dispatch routine. It tail-calls next BPF program depending - * on eth proto. Note, we could have used ... - * - * bpf_tail_call(skb, &jmp_table, proto); - * - * ... but it would need large prog_array and cannot be optimised given - * the map key is not static. - */ -static inline void parse_eth_proto(struct __sk_buff *skb, u32 proto) -{ - switch (proto) { - case ETH_P_8021Q: - case ETH_P_8021AD: - bpf_tail_call(skb, &jmp_table, PARSE_VLAN); - break; - case ETH_P_MPLS_UC: - case ETH_P_MPLS_MC: - bpf_tail_call(skb, &jmp_table, PARSE_MPLS); - break; - case ETH_P_IP: - bpf_tail_call(skb, &jmp_table, PARSE_IP); - break; - case ETH_P_IPV6: - bpf_tail_call(skb, &jmp_table, PARSE_IPV6); - break; - } -} +#define PROG_SOCKET_FILTER SEC("socket") struct vlan_hdr { __be16 h_vlan_TCI; @@ -74,6 +39,8 @@ struct flow_key_record { __u32 ip_proto; }; +static inline void parse_eth_proto(struct __sk_buff *skb, u32 proto); + static inline int ip_is_fragment(struct __sk_buff *ctx, __u64 nhoff) { return load_half(ctx, nhoff + offsetof(struct iphdr, frag_off)) @@ -189,7 +156,8 @@ static __always_inline void parse_ip_proto(struct __sk_buff *skb, } } -PROG(PARSE_IP)(struct __sk_buff *skb) +PROG_SOCKET_FILTER +int bpf_func_ip(struct __sk_buff *skb) { struct globals *g = this_cpu_globals(); __u32 nhoff, verlen, ip_proto; @@ -217,7 +185,8 @@ PROG(PARSE_IP)(struct __sk_buff *skb) return 0; } -PROG(PARSE_IPV6)(struct __sk_buff *skb) +PROG_SOCKET_FILTER +int bpf_func_ipv6(struct __sk_buff *skb) { struct globals *g = this_cpu_globals(); __u32 nhoff, ip_proto; @@ -240,7 +209,8 @@ PROG(PARSE_IPV6)(struct __sk_buff *skb) return 0; } -PROG(PARSE_VLAN)(struct __sk_buff *skb) +PROG_SOCKET_FILTER +int bpf_func_vlan(struct __sk_buff *skb) { __u32 nhoff, proto; @@ -256,7 +226,8 @@ PROG(PARSE_VLAN)(struct __sk_buff *skb) return 0; } -PROG(PARSE_MPLS)(struct __sk_buff *skb) +PROG_SOCKET_FILTER +int bpf_func_mpls(struct __sk_buff *skb) { __u32 nhoff, label; @@ -279,7 +250,49 @@ PROG(PARSE_MPLS)(struct __sk_buff *skb) return 0; } -SEC("socket/0") +struct { + __uint(type, BPF_MAP_TYPE_PROG_ARRAY); + __uint(key_size, sizeof(u32)); + __uint(max_entries, 8); + __array(values, u32 (void *)); +} prog_array_init SEC(".maps") = { + .values = { + [PARSE_VLAN] = (void *)&bpf_func_vlan, + [PARSE_IP] = (void *)&bpf_func_ip, + [PARSE_IPV6] = (void *)&bpf_func_ipv6, + [PARSE_MPLS] = (void *)&bpf_func_mpls, + }, +}; + +/* Protocol dispatch routine. It tail-calls next BPF program depending + * on eth proto. Note, we could have used ... + * + * bpf_tail_call(skb, &prog_array_init, proto); + * + * ... but it would need large prog_array and cannot be optimised given + * the map key is not static. + */ +static inline void parse_eth_proto(struct __sk_buff *skb, u32 proto) +{ + switch (proto) { + case ETH_P_8021Q: + case ETH_P_8021AD: + bpf_tail_call(skb, &prog_array_init, PARSE_VLAN); + break; + case ETH_P_MPLS_UC: + case ETH_P_MPLS_MC: + bpf_tail_call(skb, &prog_array_init, PARSE_MPLS); + break; + case ETH_P_IP: + bpf_tail_call(skb, &prog_array_init, PARSE_IP); + break; + case ETH_P_IPV6: + bpf_tail_call(skb, &prog_array_init, PARSE_IPV6); + break; + } +} + +PROG_SOCKET_FILTER int main_prog(struct __sk_buff *skb) { __u32 nhoff = ETH_HLEN; diff --git a/samples/bpf/sockex3_user.c b/samples/bpf/sockex3_user.c index cd6fa79df900..56044acbd25d 100644 --- a/samples/bpf/sockex3_user.c +++ b/samples/bpf/sockex3_user.c @@ -24,10 +24,9 @@ struct pair { int main(int argc, char **argv) { - int i, sock, key, fd, main_prog_fd, jmp_table_fd, hash_map_fd; + int i, sock, fd, main_prog_fd, hash_map_fd; struct bpf_program *prog; struct bpf_object *obj; - const char *section; char filename[256]; FILE *f; @@ -45,26 +44,24 @@ int main(int argc, char **argv) goto cleanup; } - jmp_table_fd = bpf_object__find_map_fd_by_name(obj, "jmp_table"); hash_map_fd = bpf_object__find_map_fd_by_name(obj, "hash_map"); - if (jmp_table_fd < 0 || hash_map_fd < 0) { + if (hash_map_fd < 0) { fprintf(stderr, "ERROR: finding a map in obj file failed\n"); goto cleanup; } + /* find BPF main program */ + main_prog_fd = 0; bpf_object__for_each_program(prog, obj) { fd = bpf_program__fd(prog); - section = bpf_program__section_name(prog); - if (sscanf(section, "socket/%d", &key) != 1) { - fprintf(stderr, "ERROR: finding prog failed\n"); - goto cleanup; - } - - if (key == 0) + if (!strcmp(bpf_program__name(prog), "main_prog")) main_prog_fd = fd; - else - bpf_map_update_elem(jmp_table_fd, &key, &fd, BPF_ANY); + } + + if (main_prog_fd == 0) { + fprintf(stderr, "ERROR: can't find main_prog\n"); + goto cleanup; } sock = open_raw_sock("lo"); -- 2.31.1 ^ permalink raw reply related [flat|nested] 12+ messages in thread
* Re: [PATCH bpf-next] samples/bpf: Fix sockex3 error: missing BPF prog type 2022-11-05 6:48 ` [PATCH bpf-next] samples/bpf: Fix sockex3 error: " Rong Tao @ 2022-11-08 1:14 ` Andrii Nakryiko 2022-11-08 1:20 ` patchwork-bot+netdevbpf 1 sibling, 0 replies; 12+ messages in thread From: Andrii Nakryiko @ 2022-11-08 1:14 UTC (permalink / raw) To: Rong Tao Cc: andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, sdf, song, yhs On Fri, Nov 4, 2022 at 11:48 PM Rong Tao <rtoax@foxmail.com> wrote: > > From: Rong Tao <rongtao@cestc.cn> > > since commit 450b167fb9be("libbpf: clean up SEC() handling"), > sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, > the BPF program type is not recognized. > > Instead of sockex3_user.c parsing section names to get the BPF program fd. > We use the program array map to assign a static index to each BPF program > (get inspired by selftests/bpf progs/test_prog_array_init.c). > Therefore, use SEC("socket") as section name instead of SEC("socket/xxx"), > so that the BPF program is parsed to SOCKET_FILTER type. The "missing BPF > prog type" problem is solved. > > How to reproduce this error: > $ cd samples/bpf > $ sudo ./sockex3 > libbpf: prog 'bpf_func_PARSE_IP': missing BPF prog type, check ELF section name 'socket/3' > libbpf: prog 'bpf_func_PARSE_IP': failed to load: -22 > libbpf: failed to load object './sockex3_kern.o' > ERROR: loading BPF object file failed > > Signed-off-by: Rong Tao <rongtao@cestc.cn> > --- > samples/bpf/sockex3_kern.c | 95 ++++++++++++++++++++++---------------- > samples/bpf/sockex3_user.c | 23 ++++----- > 2 files changed, 64 insertions(+), 54 deletions(-) > > diff --git a/samples/bpf/sockex3_kern.c b/samples/bpf/sockex3_kern.c > index b363503357e5..26d916834865 100644 > --- a/samples/bpf/sockex3_kern.c > +++ b/samples/bpf/sockex3_kern.c > @@ -17,47 +17,12 @@ > #define IP_MF 0x2000 > #define IP_OFFSET 0x1FFF > > -#define PROG(F) SEC("socket/"__stringify(F)) int bpf_func_##F > - > -struct { > - __uint(type, BPF_MAP_TYPE_PROG_ARRAY); > - __uint(key_size, sizeof(u32)); > - __uint(value_size, sizeof(u32)); > - __uint(max_entries, 8); > -} jmp_table SEC(".maps"); > - > #define PARSE_VLAN 1 > #define PARSE_MPLS 2 > #define PARSE_IP 3 > #define PARSE_IPV6 4 > > -/* Protocol dispatch routine. It tail-calls next BPF program depending > - * on eth proto. Note, we could have used ... > - * > - * bpf_tail_call(skb, &jmp_table, proto); > - * > - * ... but it would need large prog_array and cannot be optimised given > - * the map key is not static. > - */ > -static inline void parse_eth_proto(struct __sk_buff *skb, u32 proto) > -{ > - switch (proto) { > - case ETH_P_8021Q: > - case ETH_P_8021AD: > - bpf_tail_call(skb, &jmp_table, PARSE_VLAN); > - break; > - case ETH_P_MPLS_UC: > - case ETH_P_MPLS_MC: > - bpf_tail_call(skb, &jmp_table, PARSE_MPLS); > - break; > - case ETH_P_IP: > - bpf_tail_call(skb, &jmp_table, PARSE_IP); > - break; > - case ETH_P_IPV6: > - bpf_tail_call(skb, &jmp_table, PARSE_IPV6); > - break; > - } > -} > +#define PROG_SOCKET_FILTER SEC("socket") I dropped this and made SEC("socket") annotations explicit everywhere. Applied to bpf-next, thank. > > struct vlan_hdr { > __be16 h_vlan_TCI; > @@ -74,6 +39,8 @@ struct flow_key_record { > __u32 ip_proto; > }; > [...] ^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH bpf-next] samples/bpf: Fix sockex3 error: missing BPF prog type 2022-11-05 6:48 ` [PATCH bpf-next] samples/bpf: Fix sockex3 error: " Rong Tao 2022-11-08 1:14 ` Andrii Nakryiko @ 2022-11-08 1:20 ` patchwork-bot+netdevbpf 1 sibling, 0 replies; 12+ messages in thread From: patchwork-bot+netdevbpf @ 2022-11-08 1:20 UTC (permalink / raw) To: Rong Tao Cc: andrii.nakryiko, andrii, ast, bpf, daniel, haoluo, john.fastabend, jolsa, kpsingh, linux-kernel, martin.lau, rongtao, sdf, song, yhs Hello: This patch was applied to bpf/bpf-next.git (master) by Andrii Nakryiko <andrii@kernel.org>: On Sat, 5 Nov 2022 14:48:00 +0800 you wrote: > From: Rong Tao <rongtao@cestc.cn> > > since commit 450b167fb9be("libbpf: clean up SEC() handling"), > sec_def_matches() does not recognize "socket/xxx" as "socket", therefore, > the BPF program type is not recognized. > > Instead of sockex3_user.c parsing section names to get the BPF program fd. > We use the program array map to assign a static index to each BPF program > (get inspired by selftests/bpf progs/test_prog_array_init.c). > Therefore, use SEC("socket") as section name instead of SEC("socket/xxx"), > so that the BPF program is parsed to SOCKET_FILTER type. The "missing BPF > prog type" problem is solved. > > [...] Here is the summary with links: - [bpf-next] samples/bpf: Fix sockex3 error: missing BPF prog type https://git.kernel.org/bpf/bpf-next/c/e5659e4e19e4 You are awesome, thank you! -- Deet-doot-dot, I am a bot. https://korg.docs.kernel.org/patchwork/pwbot.html ^ permalink raw reply [flat|nested] 12+ messages in thread
end of thread, other threads:[~2022-11-08 1:20 UTC | newest] Thread overview: 12+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2022-10-27 13:33 [PATCH] samples/bpf: Fix sockex3: missing BPF prog type Rong Tao 2022-10-27 13:38 ` [PATCH bpf-next] " Rong Tao 2022-10-27 20:15 ` Andrii Nakryiko 2022-10-28 1:01 ` [PATCH] " Rong Tao 2022-10-28 17:09 ` Andrii Nakryiko 2022-10-29 7:53 ` [PATCH bpf-next] " Rong Tao 2022-11-03 18:38 ` Andrii Nakryiko 2022-11-04 3:17 ` Rong Tao 2022-11-04 22:53 ` Andrii Nakryiko 2022-11-05 6:48 ` [PATCH bpf-next] samples/bpf: Fix sockex3 error: " Rong Tao 2022-11-08 1:14 ` Andrii Nakryiko 2022-11-08 1:20 ` patchwork-bot+netdevbpf
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox