History

Merge branch 'libbpf: Support uniform BTF-defined key/value specification across all BPF maps'

Hengqi Chen says: ==================== Currently a bunch of (usually pretty specialized) BPF maps do not support specifying BTF types for they key and value. For such maps, specifying their definition like this: struct { __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY); __type(key, int); __type(value, int); } my_perf_buf SEC(".maps"); Would actually produce warnings about retrying BPF map creation without BTF. Users are forced to know such nuances and use __uint(key_size, 4) instead. This is non-uniform, annoying, and inconvenient. This patch set teaches libbpf to recognize those specialized maps and removes BTF type IDs when creating BPF map. Also, update existing BPF selftests to exericse this change. ====================

Andrii Nakryiko committed 5 years ago

Commit d636c8d2 parents 7bceeb9 bd368cb14 files · +62 −40Browse files

Unified · Split

14 files
  1. tools/lib/bpf/libbpf.c +24 −0
  2. tools/testing/selftests/bpf/progs/kfree_skb.c +2 −2
  3. tools/testing/selftests/bpf/progs/perf_event_stackmap.c +2 −2
  4. tools/testing/selftests/bpf/progs/sockmap_verdict_prog.c +6 −6
  5. tools/testing/selftests/bpf/progs/test_btf_map_in_map.c +7 −7
  6. tools/testing/selftests/bpf/progs/test_map_in_map.c +4 −6
  7. tools/testing/selftests/bpf/progs/test_map_in_map_invalid.c +1 −1
  8. tools/testing/selftests/bpf/progs/test_pe_preserve_elems.c +4 −4
  9. tools/testing/selftests/bpf/progs/test_perf_buffer.c +2 −2
  10. tools/testing/selftests/bpf/progs/test_select_reuseport_kern.c +2 −2
  11. tools/testing/selftests/bpf/progs/test_stacktrace_build_id.c +2 −2
  12. tools/testing/selftests/bpf/progs/test_stacktrace_map.c +2 −2
  13. tools/testing/selftests/bpf/progs/test_tcpnotify_kern.c +2 −2
  14. tools/testing/selftests/bpf/progs/test_xdp_bpf2bpf.c +2 −2
tools/lib/bpf/libbpf.c+24−0
@@ -4669,6 +4669,30 @@ static int bpf_object__create_map(struct bpf_object *obj, struct bpf_map *map, b · 4668 unmodified lines
46694669 create_attr.inner_map_fd = map->inner_map_fd;
46704670 }
46714671
4672+ switch (def->type) {
4673+ case BPF_MAP_TYPE_PERF_EVENT_ARRAY:
4674+ case BPF_MAP_TYPE_CGROUP_ARRAY:
4675+ case BPF_MAP_TYPE_STACK_TRACE:
4676+ case BPF_MAP_TYPE_ARRAY_OF_MAPS:
4677+ case BPF_MAP_TYPE_HASH_OF_MAPS:
4678+ case BPF_MAP_TYPE_DEVMAP:
4679+ case BPF_MAP_TYPE_DEVMAP_HASH:
4680+ case BPF_MAP_TYPE_CPUMAP:
4681+ case BPF_MAP_TYPE_XSKMAP:
4682+ case BPF_MAP_TYPE_SOCKMAP:
4683+ case BPF_MAP_TYPE_SOCKHASH:
4684+ case BPF_MAP_TYPE_QUEUE:
4685+ case BPF_MAP_TYPE_STACK:
4686+ case BPF_MAP_TYPE_RINGBUF:
4687+ create_attr.btf_fd = 0;
4688+ create_attr.btf_key_type_id = 0;
4689+ create_attr.btf_value_type_id = 0;
4690+ map->btf_key_type_id = 0;
4691+ map->btf_value_type_id = 0;
4692+ default:
4693+ break;
4694+ }
4695+
46724696 if (obj->gen_loader) {
46734697 bpf_gen__map_create(obj->gen_loader, &create_attr, is_inner ? -1 : map - obj->maps);
46744698 /* Pretend to have valid FD to pass various fd >= 0 checks.
tools/testing/selftests/bpf/progs/kfree_skb.c+2−2
@@ -9,8 +9,8 @@ · 8 unmodified lines
99 char _license[] SEC("license") = "GPL";
1010 struct {
1111 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
12− __uint(key_size, sizeof(int));
13− __uint(value_size, sizeof(int));
12+ __type(key, int);
13+ __type(value, int);
1414 } perf_buf_map SEC(".maps");
1515
1616 #define _(P) (__builtin_preserve_access_index(P))
tools/testing/selftests/bpf/progs/perf_event_stackmap.c+2−2
@@ -11,8 +11,8 @@ typedef __u64 stack_trace_t[PERF_MAX_STACK_DEPTH]; · 10 unmodified lines
1111 struct {
1212 __uint(type, BPF_MAP_TYPE_STACK_TRACE);
1313 __uint(max_entries, 16384);
14− __uint(key_size, sizeof(__u32));
15− __uint(value_size, sizeof(stack_trace_t));
14+ __type(key, __u32);
15+ __type(value, stack_trace_t);
1616 } stackmap SEC(".maps");
1717
1818 struct {
tools/testing/selftests/bpf/progs/sockmap_verdict_prog.c+6−6
@@ -7,22 +7,22 @@ int _version SEC("version") = 1; · 6 unmodified lines
77 struct {
88 __uint(type, BPF_MAP_TYPE_SOCKMAP);
99 __uint(max_entries, 20);
10− __uint(key_size, sizeof(int));
11− __uint(value_size, sizeof(int));
10+ __type(key, int);
11+ __type(value, int);
1212 } sock_map_rx SEC(".maps");
1313
1414 struct {
1515 __uint(type, BPF_MAP_TYPE_SOCKMAP);
1616 __uint(max_entries, 20);
17− __uint(key_size, sizeof(int));
18− __uint(value_size, sizeof(int));
17+ __type(key, int);
18+ __type(value, int);
1919 } sock_map_tx SEC(".maps");
2020
2121 struct {
2222 __uint(type, BPF_MAP_TYPE_SOCKMAP);
2323 __uint(max_entries, 20);
24− __uint(key_size, sizeof(int));
25− __uint(value_size, sizeof(int));
24+ __type(key, int);
25+ __type(value, int);
2626 } sock_map_msg SEC(".maps");
2727
2828 struct {
tools/testing/selftests/bpf/progs/test_btf_map_in_map.c+7−7
@@ -21,8 +21,8 @@ struct inner_map_sz2 { · 20 unmodified lines
2121 struct outer_arr {
2222 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
2323 __uint(max_entries, 3);
24− __uint(key_size, sizeof(int));
25− __uint(value_size, sizeof(int));
24+ __type(key, int);
25+ __type(value, int);
2626 /* it's possible to use anonymous struct as inner map definition here */
2727 __array(values, struct {
2828 __uint(type, BPF_MAP_TYPE_ARRAY);
@@ -61,8 +61,8 @@ struct inner_map_sz4 { · 32 unmodified lines
6161 struct outer_arr_dyn {
6262 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
6363 __uint(max_entries, 3);
64− __uint(key_size, sizeof(int));
65− __uint(value_size, sizeof(int));
64+ __type(key, int);
65+ __type(value, int);
6666 __array(values, struct {
6767 __uint(type, BPF_MAP_TYPE_ARRAY);
6868 __uint(map_flags, BPF_F_INNER_MAP);
@@ -81,7 +81,7 @@ struct outer_arr_dyn { · 12 unmodified lines
8181 struct outer_hash {
8282 __uint(type, BPF_MAP_TYPE_HASH_OF_MAPS);
8383 __uint(max_entries, 5);
84− __uint(key_size, sizeof(int));
84+ __type(key, int);
8585 /* Here everything works flawlessly due to reuse of struct inner_map
8686 * and compiler will complain at the attempt to use non-inner_map
8787 * references below. This is great experience.
@@ -111,8 +111,8 @@ struct sockarr_sz2 { · 23 unmodified lines
111111 struct outer_sockarr_sz1 {
112112 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
113113 __uint(max_entries, 1);
114− __uint(key_size, sizeof(int));
115− __uint(value_size, sizeof(int));
114+ __type(key, int);
115+ __type(value, int);
116116 __array(values, struct sockarr_sz1);
117117 } outer_sockarr SEC(".maps") = {
118118 .values = { (void *)&sockarr_sz1 },
tools/testing/selftests/bpf/progs/test_map_in_map.c+4−6
@@ -9,18 +9,16 @@ struct { · 8 unmodified lines
99 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
1010 __uint(max_entries, 1);
1111 __uint(map_flags, 0);
12− __uint(key_size, sizeof(__u32));
13− /* must be sizeof(__u32) for map in map */
14− __uint(value_size, sizeof(__u32));
12+ __type(key, __u32);
13+ __type(value, __u32);
1514 } mim_array SEC(".maps");
1615
1716 struct {
1817 __uint(type, BPF_MAP_TYPE_HASH_OF_MAPS);
1918 __uint(max_entries, 1);
2019 __uint(map_flags, 0);
21− __uint(key_size, sizeof(int));
22− /* must be sizeof(__u32) for map in map */
23− __uint(value_size, sizeof(__u32));
20+ __type(key, int);
21+ __type(value, __u32);
2422 } mim_hash SEC(".maps");
2523
2624 SEC("xdp")
tools/testing/selftests/bpf/progs/test_map_in_map_invalid.c+1−1
@@ -13,7 +13,7 @@ struct inner { · 12 unmodified lines
1313 struct {
1414 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
1515 __uint(max_entries, 0); /* This will make map creation to fail */
16− __uint(key_size, sizeof(__u32));
16+ __type(key, __u32);
1717 __array(values, struct inner);
1818 } mim SEC(".maps");
1919
tools/testing/selftests/bpf/progs/test_pe_preserve_elems.c+4−4
@@ -7,15 +7,15 @@ · 6 unmodified lines
77 struct {
88 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
99 __uint(max_entries, 1);
10− __uint(key_size, sizeof(int));
11− __uint(value_size, sizeof(int));
10+ __type(key, int);
11+ __type(value, int);
1212 } array_1 SEC(".maps");
1313
1414 struct {
1515 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
1616 __uint(max_entries, 1);
17− __uint(key_size, sizeof(int));
18− __uint(value_size, sizeof(int));
17+ __type(key, int);
18+ __type(value, int);
1919 __uint(map_flags, BPF_F_PRESERVE_ELEMS);
2020 } array_2 SEC(".maps");
2121
tools/testing/selftests/bpf/progs/test_perf_buffer.c+2−2
@@ -8,8 +8,8 @@ · 7 unmodified lines
88
99 struct {
1010 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
11− __uint(key_size, sizeof(int));
12− __uint(value_size, sizeof(int));
11+ __type(key, int);
12+ __type(value, int);
1313 } perf_buf_map SEC(".maps");
1414
1515 SEC("tp/raw_syscalls/sys_enter")
tools/testing/selftests/bpf/progs/test_select_reuseport_kern.c+2−2
@@ -24,8 +24,8 @@ int _version SEC("version") = 1; · 23 unmodified lines
2424 struct {
2525 __uint(type, BPF_MAP_TYPE_ARRAY_OF_MAPS);
2626 __uint(max_entries, 1);
27− __uint(key_size, sizeof(__u32));
28− __uint(value_size, sizeof(__u32));
27+ __type(key, __u32);
28+ __type(value, __u32);
2929 } outer_map SEC(".maps");
3030
3131 struct {
tools/testing/selftests/bpf/progs/test_stacktrace_build_id.c+2−2
@@ -28,8 +28,8 @@ struct { · 27 unmodified lines
2828 __uint(type, BPF_MAP_TYPE_STACK_TRACE);
2929 __uint(max_entries, 128);
3030 __uint(map_flags, BPF_F_STACK_BUILD_ID);
31− __uint(key_size, sizeof(__u32));
32− __uint(value_size, sizeof(stack_trace_t));
31+ __type(key, __u32);
32+ __type(value, stack_trace_t);
3333 } stackmap SEC(".maps");
3434
3535 struct {
tools/testing/selftests/bpf/progs/test_stacktrace_map.c+2−2
@@ -27,8 +27,8 @@ typedef __u64 stack_trace_t[PERF_MAX_STACK_DEPTH]; · 26 unmodified lines
2727 struct {
2828 __uint(type, BPF_MAP_TYPE_STACK_TRACE);
2929 __uint(max_entries, 16384);
30− __uint(key_size, sizeof(__u32));
31− __uint(value_size, sizeof(stack_trace_t));
30+ __type(key, __u32);
31+ __type(value, stack_trace_t);
3232 } stackmap SEC(".maps");
3333
3434 struct {
tools/testing/selftests/bpf/progs/test_tcpnotify_kern.c+2−2
@@ -24,8 +24,8 @@ struct { · 23 unmodified lines
2424 struct {
2525 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
2626 __uint(max_entries, 2);
27− __uint(key_size, sizeof(int));
28− __uint(value_size, sizeof(__u32));
27+ __type(key, int);
28+ __type(value, __u32);
2929 } perf_event_map SEC(".maps");
3030
3131 int _version SEC("version") = 1;
tools/testing/selftests/bpf/progs/test_xdp_bpf2bpf.c+2−2
@@ -36,8 +36,8 @@ struct meta { · 35 unmodified lines
3636
3737 struct {
3838 __uint(type, BPF_MAP_TYPE_PERF_EVENT_ARRAY);
39− __uint(key_size, sizeof(int));
40− __uint(value_size, sizeof(int));
39+ __type(key, int);
40+ __type(value, int);
4141 } perf_buf_map SEC(".maps");
4242
4343 __u64 test_result_fentry = 0;