Introduce a new bpf map type 'BPF_MAP_TYPE_PERF_EVENT_ARRAY'. This map will only store the pointer to struct perf_event.
Signed-off-by: Kaixu Xia <[email protected]> --- include/linux/bpf.h | 2 ++ include/uapi/linux/bpf.h | 1 + kernel/bpf/arraymap.c | 40 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 43 insertions(+) diff --git a/include/linux/bpf.h b/include/linux/bpf.h index 4383476..f6a2442 100644 --- a/include/linux/bpf.h +++ b/include/linux/bpf.h @@ -11,6 +11,8 @@ #include <linux/workqueue.h> #include <linux/file.h> +#define MAX_PERF_EVENT_ARRAY_ENTRY (2*NR_CPUS) + struct bpf_map; /* map is generic key/value storage optionally accesible by eBPF programs */ diff --git a/include/uapi/linux/bpf.h b/include/uapi/linux/bpf.h index 29ef6f9..69a1f6b 100644 --- a/include/uapi/linux/bpf.h +++ b/include/uapi/linux/bpf.h @@ -114,6 +114,7 @@ enum bpf_map_type { BPF_MAP_TYPE_HASH, BPF_MAP_TYPE_ARRAY, BPF_MAP_TYPE_PROG_ARRAY, + BPF_MAP_TYPE_PERF_EVENT_ARRAY, }; enum bpf_prog_type { diff --git a/kernel/bpf/arraymap.c b/kernel/bpf/arraymap.c index cb31229..183c1f7 100644 --- a/kernel/bpf/arraymap.c +++ b/kernel/bpf/arraymap.c @@ -255,3 +255,43 @@ static int __init register_prog_array_map(void) return 0; } late_initcall(register_prog_array_map); + +static struct bpf_map *perf_event_array_map_alloc(union bpf_attr *attr) +{ + /* only the pointer to struct perf_event can be stored in + * perf_event_array map + */ + if (attr->value_size != sizeof(void *)) + return ERR_PTR(-EINVAL); + + if (attr->max_entries > MAX_PERF_EVENT_ARRAY_ENTRY) + return ERR_PTR(-EINVAL); + + return array_map_alloc(attr); +} + +static int perf_event_array_map_get_next_key(struct bpf_map *map, void *key, + void *next_key) +{ + return -EINVAL; +} + +static const struct bpf_map_ops perf_event_array_ops = { + .map_alloc = perf_event_array_map_alloc, + .map_free = array_map_free, + .map_get_next_key = perf_event_array_map_get_next_key, + .map_lookup_elem = array_map_lookup_elem, + .map_delete_elem = array_map_delete_elem, +}; + +static struct bpf_map_type_list perf_event_array_type __read_mostly = { + .ops = &perf_event_array_ops, + .type = BPF_MAP_TYPE_PERF_EVENT_ARRAY, +}; + +static int __init register_perf_event_array_map(void) +{ + bpf_register_map_type(&perf_event_array_type); + return 0; +} +late_initcall(register_perf_event_array_map); -- 1.8.3.4 -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [email protected] More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/

