On Wed, May 6, 2020 at 6:30 AM Jiri Olsa <jolsa@xxxxxxxxxx> wrote: > > This tool takes vmlinux object and whitelist directory on input > and produces C source object with BPF whitelist data. > > The vmlinux object needs to have a BTF information compiled in. > > The whitelist directory is expected to contain files with helper > names, where each file contains list of functions/probes that > helper is allowed to be called from - whitelist. > > The bpfwl tool has following output: > > $ bpfwl vmlinux dir > unsigned long d_path[] __attribute__((section(".BTF_whitelist_d_path"))) = \ > { 24507, 24511, 24537, 24539, 24545, 24588, 24602, 24920 }; why long instead of int? btf_id is 4-byte one. > > Each array are sorted BTF ids of the functions provided in the > helper file. > > Each array will be compiled into kernel and used during the helper > check in verifier. > > Signed-off-by: Jiri Olsa <jolsa@xxxxxxxxxx> > --- > tools/bpf/bpfwl/Build | 11 ++ > tools/bpf/bpfwl/Makefile | 60 +++++++++ > tools/bpf/bpfwl/bpfwl.c | 285 +++++++++++++++++++++++++++++++++++++++ > 3 files changed, 356 insertions(+) > create mode 100644 tools/bpf/bpfwl/Build > create mode 100644 tools/bpf/bpfwl/Makefile > create mode 100644 tools/bpf/bpfwl/bpfwl.c Sorry, I didn't want to nitpick on naming, honestly, but I think this is actually harmful in the long run. bpfwl is incomprehensible name, anyone reading link script would be like "what the hell is bpfwl?" Why not bpf_build_whitelist or something with "whitelist" spelled out in full? > > diff --git a/tools/bpf/bpfwl/Build b/tools/bpf/bpfwl/Build > new file mode 100644 > index 000000000000..667e30d6ce79 > --- /dev/null > +++ b/tools/bpf/bpfwl/Build > @@ -0,0 +1,11 @@ > +bpfwl-y += bpfwl.o > +bpfwl-y += rbtree.o > +bpfwl-y += zalloc.o > + [...] > + > +struct func { > + char *name; > + unsigned long id; as mentioned above, btf_id is 4 byte > + struct rb_node rb_node; > + struct list_head list[]; > +}; > + [...] > + btf = btf__parse_elf(vmlinux, NULL); > + err = libbpf_get_error(btf); > + if (err) { > + fprintf(stderr, "FAILED: load BTF from %s: %s", > + vmlinux, strerror(err)); > + return -1; > + } > + > + nr = btf__get_nr_types(btf); > + > + /* Iterate all the BTF types and resolve all the function IDs. */ > + for (id = 0; id < nr; id++) { It has to be `for (id = 1; id <= nr; id++)`. 0 is VOID type and not included into nr_types. I know it's confusing, but.. life :) > + const struct btf_type *type; > + struct func *func; > + const char *str; > + > + type = btf__type_by_id(btf, id); > + if (!type) > + continue; > + [...]