diff options
author | Wang Nan <wangnan0@huawei.com> | 2015-06-30 22:14:08 -0400 |
---|---|---|
committer | Arnaldo Carvalho de Melo <acme@redhat.com> | 2015-08-07 09:16:59 -0400 |
commit | aa9b1ac33c7979d0d91eff8b70cffc4916f5555c (patch) | |
tree | dbb31262a1ad3ed8385578e9a3783176c34277b5 /tools/lib/bpf | |
parent | 55cffde2e1a41109cb49f8e94de954c8240242b5 (diff) |
bpf tools: Introduce accessors for struct bpf_program
This patch introduces accessors for user of libbpf to retrieve section
name and fd of a opened/loaded eBPF program. 'struct bpf_prog_handler'
is used for that purpose. Accessors of programs section name and file
descriptor are provided. Set/get private data are also impelmented.
Signed-off-by: Wang Nan <wangnan0@huawei.com>
Acked-by: Alexei Starovoitov <ast@plumgrid.com>
Cc: Brendan Gregg <brendan.d.gregg@gmail.com>
Cc: Daniel Borkmann <daniel@iogearbox.net>
Cc: David Ahern <dsahern@gmail.com>
Cc: He Kuang <hekuang@huawei.com>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Kaixu Xia <xiakaixu@huawei.com>
Cc: Masami Hiramatsu <masami.hiramatsu.pt@hitachi.com>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Zefan Li <lizefan@huawei.com>
Link: http://lkml.kernel.org/r/1435716878-189507-21-git-send-email-wangnan0@huawei.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Diffstat (limited to 'tools/lib/bpf')
-rw-r--r-- | tools/lib/bpf/libbpf.c | 72 | ||||
-rw-r--r-- | tools/lib/bpf/libbpf.h | 24 |
2 files changed, 96 insertions, 0 deletions
diff --git a/tools/lib/bpf/libbpf.c b/tools/lib/bpf/libbpf.c index 38447b7d6e73..ae1c5cbd8158 100644 --- a/tools/lib/bpf/libbpf.c +++ b/tools/lib/bpf/libbpf.c | |||
@@ -98,6 +98,10 @@ struct bpf_program { | |||
98 | int nr_reloc; | 98 | int nr_reloc; |
99 | 99 | ||
100 | int fd; | 100 | int fd; |
101 | |||
102 | struct bpf_object *obj; | ||
103 | void *priv; | ||
104 | bpf_program_clear_priv_t clear_priv; | ||
101 | }; | 105 | }; |
102 | 106 | ||
103 | struct bpf_object { | 107 | struct bpf_object { |
@@ -150,6 +154,12 @@ static void bpf_program__exit(struct bpf_program *prog) | |||
150 | if (!prog) | 154 | if (!prog) |
151 | return; | 155 | return; |
152 | 156 | ||
157 | if (prog->clear_priv) | ||
158 | prog->clear_priv(prog, prog->priv); | ||
159 | |||
160 | prog->priv = NULL; | ||
161 | prog->clear_priv = NULL; | ||
162 | |||
153 | bpf_program__unload(prog); | 163 | bpf_program__unload(prog); |
154 | zfree(&prog->section_name); | 164 | zfree(&prog->section_name); |
155 | zfree(&prog->insns); | 165 | zfree(&prog->insns); |
@@ -225,6 +235,7 @@ bpf_object__add_program(struct bpf_object *obj, void *data, size_t size, | |||
225 | pr_debug("found program %s\n", prog.section_name); | 235 | pr_debug("found program %s\n", prog.section_name); |
226 | obj->programs = progs; | 236 | obj->programs = progs; |
227 | obj->nr_programs = nr_progs + 1; | 237 | obj->nr_programs = nr_progs + 1; |
238 | prog.obj = obj; | ||
228 | progs[nr_progs] = prog; | 239 | progs[nr_progs] = prog; |
229 | return 0; | 240 | return 0; |
230 | } | 241 | } |
@@ -931,3 +942,64 @@ void bpf_object__close(struct bpf_object *obj) | |||
931 | 942 | ||
932 | free(obj); | 943 | free(obj); |
933 | } | 944 | } |
945 | |||
946 | struct bpf_program * | ||
947 | bpf_program__next(struct bpf_program *prev, struct bpf_object *obj) | ||
948 | { | ||
949 | size_t idx; | ||
950 | |||
951 | if (!obj->programs) | ||
952 | return NULL; | ||
953 | /* First handler */ | ||
954 | if (prev == NULL) | ||
955 | return &obj->programs[0]; | ||
956 | |||
957 | if (prev->obj != obj) { | ||
958 | pr_warning("error: program handler doesn't match object\n"); | ||
959 | return NULL; | ||
960 | } | ||
961 | |||
962 | idx = (prev - obj->programs) + 1; | ||
963 | if (idx >= obj->nr_programs) | ||
964 | return NULL; | ||
965 | return &obj->programs[idx]; | ||
966 | } | ||
967 | |||
968 | int bpf_program__set_private(struct bpf_program *prog, | ||
969 | void *priv, | ||
970 | bpf_program_clear_priv_t clear_priv) | ||
971 | { | ||
972 | if (prog->priv && prog->clear_priv) | ||
973 | prog->clear_priv(prog, prog->priv); | ||
974 | |||
975 | prog->priv = priv; | ||
976 | prog->clear_priv = clear_priv; | ||
977 | return 0; | ||
978 | } | ||
979 | |||
980 | int bpf_program__get_private(struct bpf_program *prog, void **ppriv) | ||
981 | { | ||
982 | *ppriv = prog->priv; | ||
983 | return 0; | ||
984 | } | ||
985 | |||
986 | const char *bpf_program__title(struct bpf_program *prog, bool dup) | ||
987 | { | ||
988 | const char *title; | ||
989 | |||
990 | title = prog->section_name; | ||
991 | if (dup) { | ||
992 | title = strdup(title); | ||
993 | if (!title) { | ||
994 | pr_warning("failed to strdup program title\n"); | ||
995 | return NULL; | ||
996 | } | ||
997 | } | ||
998 | |||
999 | return title; | ||
1000 | } | ||
1001 | |||
1002 | int bpf_program__fd(struct bpf_program *prog) | ||
1003 | { | ||
1004 | return prog->fd; | ||
1005 | } | ||
diff --git a/tools/lib/bpf/libbpf.h b/tools/lib/bpf/libbpf.h index 3e6960075835..657e497bd586 100644 --- a/tools/lib/bpf/libbpf.h +++ b/tools/lib/bpf/libbpf.h | |||
@@ -9,6 +9,7 @@ | |||
9 | #define __BPF_LIBBPF_H | 9 | #define __BPF_LIBBPF_H |
10 | 10 | ||
11 | #include <stdio.h> | 11 | #include <stdio.h> |
12 | #include <stdbool.h> | ||
12 | 13 | ||
13 | /* | 14 | /* |
14 | * In include/linux/compiler-gcc.h, __printf is defined. However | 15 | * In include/linux/compiler-gcc.h, __printf is defined. However |
@@ -34,6 +35,29 @@ void bpf_object__close(struct bpf_object *object); | |||
34 | int bpf_object__load(struct bpf_object *obj); | 35 | int bpf_object__load(struct bpf_object *obj); |
35 | int bpf_object__unload(struct bpf_object *obj); | 36 | int bpf_object__unload(struct bpf_object *obj); |
36 | 37 | ||
38 | /* Accessors of bpf_program. */ | ||
39 | struct bpf_program; | ||
40 | struct bpf_program *bpf_program__next(struct bpf_program *prog, | ||
41 | struct bpf_object *obj); | ||
42 | |||
43 | #define bpf_object__for_each_program(pos, obj) \ | ||
44 | for ((pos) = bpf_program__next(NULL, (obj)); \ | ||
45 | (pos) != NULL; \ | ||
46 | (pos) = bpf_program__next((pos), (obj))) | ||
47 | |||
48 | typedef void (*bpf_program_clear_priv_t)(struct bpf_program *, | ||
49 | void *); | ||
50 | |||
51 | int bpf_program__set_private(struct bpf_program *prog, void *priv, | ||
52 | bpf_program_clear_priv_t clear_priv); | ||
53 | |||
54 | int bpf_program__get_private(struct bpf_program *prog, | ||
55 | void **ppriv); | ||
56 | |||
57 | const char *bpf_program__title(struct bpf_program *prog, bool dup); | ||
58 | |||
59 | int bpf_program__fd(struct bpf_program *prog); | ||
60 | |||
37 | /* | 61 | /* |
38 | * We don't need __attribute__((packed)) now since it is | 62 | * We don't need __attribute__((packed)) now since it is |
39 | * unnecessary for 'bpf_map_def' because they are all aligned. | 63 | * unnecessary for 'bpf_map_def' because they are all aligned. |