Merge tag 'icc-5.2-rc1' of https://git.linaro.org/people/georgi.djakov/linux into...
[sfrench/cifs-2.6.git] / tools / testing / selftests / bpf / test_btf.c
1 /* SPDX-License-Identifier: GPL-2.0 */
2 /* Copyright (c) 2018 Facebook */
3
4 #include <linux/bpf.h>
5 #include <linux/btf.h>
6 #include <linux/err.h>
7 #include <linux/kernel.h>
8 #include <linux/filter.h>
9 #include <linux/unistd.h>
10 #include <bpf/bpf.h>
11 #include <sys/resource.h>
12 #include <libelf.h>
13 #include <gelf.h>
14 #include <string.h>
15 #include <stdlib.h>
16 #include <stdio.h>
17 #include <stdarg.h>
18 #include <unistd.h>
19 #include <fcntl.h>
20 #include <errno.h>
21 #include <assert.h>
22 #include <bpf/libbpf.h>
23 #include <bpf/btf.h>
24
25 #include "bpf_rlimit.h"
26 #include "bpf_util.h"
27
28 #define MAX_INSNS       512
29 #define MAX_SUBPROGS    16
30
31 static uint32_t pass_cnt;
32 static uint32_t error_cnt;
33 static uint32_t skip_cnt;
34
35 #define CHECK(condition, format...) ({                                  \
36         int __ret = !!(condition);                                      \
37         if (__ret) {                                                    \
38                 fprintf(stderr, "%s:%d:FAIL ", __func__, __LINE__);     \
39                 fprintf(stderr, format);                                \
40         }                                                               \
41         __ret;                                                          \
42 })
43
44 static int count_result(int err)
45 {
46         if (err)
47                 error_cnt++;
48         else
49                 pass_cnt++;
50
51         fprintf(stderr, "\n");
52         return err;
53 }
54
55 static int __base_pr(enum libbpf_print_level level __attribute__((unused)),
56                      const char *format, va_list args)
57 {
58         return vfprintf(stderr, format, args);
59 }
60
61 #define BTF_INFO_ENC(kind, kind_flag, vlen)                     \
62         ((!!(kind_flag) << 31) | ((kind) << 24) | ((vlen) & BTF_MAX_VLEN))
63
64 #define BTF_TYPE_ENC(name, info, size_or_type)  \
65         (name), (info), (size_or_type)
66
67 #define BTF_INT_ENC(encoding, bits_offset, nr_bits)     \
68         ((encoding) << 24 | (bits_offset) << 16 | (nr_bits))
69 #define BTF_TYPE_INT_ENC(name, encoding, bits_offset, bits, sz) \
70         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_INT, 0, 0), sz),       \
71         BTF_INT_ENC(encoding, bits_offset, bits)
72
73 #define BTF_FWD_ENC(name, kind_flag) \
74         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_FWD, kind_flag, 0), 0)
75
76 #define BTF_ARRAY_ENC(type, index_type, nr_elems)       \
77         (type), (index_type), (nr_elems)
78 #define BTF_TYPE_ARRAY_ENC(type, index_type, nr_elems) \
79         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ARRAY, 0, 0), 0), \
80         BTF_ARRAY_ENC(type, index_type, nr_elems)
81
82 #define BTF_STRUCT_ENC(name, nr_elems, sz)      \
83         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, nr_elems), sz)
84
85 #define BTF_UNION_ENC(name, nr_elems, sz)       \
86         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_UNION, 0, nr_elems), sz)
87
88 #define BTF_MEMBER_ENC(name, type, bits_offset) \
89         (name), (type), (bits_offset)
90 #define BTF_ENUM_ENC(name, val) (name), (val)
91 #define BTF_MEMBER_OFFSET(bitfield_size, bits_offset) \
92         ((bitfield_size) << 24 | (bits_offset))
93
94 #define BTF_TYPEDEF_ENC(name, type) \
95         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_TYPEDEF, 0, 0), type)
96
97 #define BTF_PTR_ENC(type) \
98         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), type)
99
100 #define BTF_CONST_ENC(type) \
101         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), type)
102
103 #define BTF_VOLATILE_ENC(type) \
104         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_VOLATILE, 0, 0), type)
105
106 #define BTF_RESTRICT_ENC(type) \
107         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_RESTRICT, 0, 0), type)
108
109 #define BTF_FUNC_PROTO_ENC(ret_type, nargs) \
110         BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_FUNC_PROTO, 0, nargs), ret_type)
111
112 #define BTF_FUNC_PROTO_ARG_ENC(name, type) \
113         (name), (type)
114
115 #define BTF_FUNC_ENC(name, func_proto) \
116         BTF_TYPE_ENC(name, BTF_INFO_ENC(BTF_KIND_FUNC, 0, 0), func_proto)
117
118 #define BTF_END_RAW 0xdeadbeef
119 #define NAME_TBD 0xdeadb33f
120
121 #define NAME_NTH(N) (0xffff0000 | N)
122 #define IS_NAME_NTH(X) ((X & 0xffff0000) == 0xffff0000)
123 #define GET_NAME_NTH_IDX(X) (X & 0x0000ffff)
124
125 #define MAX_NR_RAW_U32 1024
126 #define BTF_LOG_BUF_SIZE 65535
127
128 static struct args {
129         unsigned int raw_test_num;
130         unsigned int file_test_num;
131         unsigned int get_info_test_num;
132         unsigned int info_raw_test_num;
133         unsigned int dedup_test_num;
134         bool raw_test;
135         bool file_test;
136         bool get_info_test;
137         bool pprint_test;
138         bool always_log;
139         bool info_raw_test;
140         bool dedup_test;
141 } args;
142
143 static char btf_log_buf[BTF_LOG_BUF_SIZE];
144
145 static struct btf_header hdr_tmpl = {
146         .magic = BTF_MAGIC,
147         .version = BTF_VERSION,
148         .hdr_len = sizeof(struct btf_header),
149 };
150
151 /* several different mapv kinds(types) supported by pprint */
152 enum pprint_mapv_kind_t {
153         PPRINT_MAPV_KIND_BASIC = 0,
154         PPRINT_MAPV_KIND_INT128,
155 };
156
157 struct btf_raw_test {
158         const char *descr;
159         const char *str_sec;
160         const char *map_name;
161         const char *err_str;
162         __u32 raw_types[MAX_NR_RAW_U32];
163         __u32 str_sec_size;
164         enum bpf_map_type map_type;
165         __u32 key_size;
166         __u32 value_size;
167         __u32 key_type_id;
168         __u32 value_type_id;
169         __u32 max_entries;
170         bool btf_load_err;
171         bool map_create_err;
172         bool ordered_map;
173         bool lossless_map;
174         bool percpu_map;
175         int hdr_len_delta;
176         int type_off_delta;
177         int str_off_delta;
178         int str_len_delta;
179         enum pprint_mapv_kind_t mapv_kind;
180 };
181
182 #define BTF_STR_SEC(str) \
183         .str_sec = str, .str_sec_size = sizeof(str)
184
185 static struct btf_raw_test raw_tests[] = {
186 /* enum E {
187  *     E0,
188  *     E1,
189  * };
190  *
191  * struct A {
192  *      unsigned long long m;
193  *      int n;
194  *      char o;
195  *      [3 bytes hole]
196  *      int p[8];
197  *      int q[4][8];
198  *      enum E r;
199  * };
200  */
201 {
202         .descr = "struct test #1",
203         .raw_types = {
204                 /* int */
205                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
206                 /* unsigned long long */
207                 BTF_TYPE_INT_ENC(0, 0, 0, 64, 8),               /* [2] */
208                 /* char */
209                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 8, 1),   /* [3] */
210                 /* int[8] */
211                 BTF_TYPE_ARRAY_ENC(1, 1, 8),                    /* [4] */
212                 /* struct A { */                                /* [5] */
213                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 6), 180),
214                 BTF_MEMBER_ENC(NAME_TBD, 2, 0), /* unsigned long long m;*/
215                 BTF_MEMBER_ENC(NAME_TBD, 1, 64),/* int n;               */
216                 BTF_MEMBER_ENC(NAME_TBD, 3, 96),/* char o;              */
217                 BTF_MEMBER_ENC(NAME_TBD, 4, 128),/* int p[8]            */
218                 BTF_MEMBER_ENC(NAME_TBD, 6, 384),/* int q[4][8]         */
219                 BTF_MEMBER_ENC(NAME_TBD, 7, 1408), /* enum E r          */
220                 /* } */
221                 /* int[4][8] */
222                 BTF_TYPE_ARRAY_ENC(4, 1, 4),                    /* [6] */
223                 /* enum E */                                    /* [7] */
224                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 2), sizeof(int)),
225                 BTF_ENUM_ENC(NAME_TBD, 0),
226                 BTF_ENUM_ENC(NAME_TBD, 1),
227                 BTF_END_RAW,
228         },
229         .str_sec = "\0A\0m\0n\0o\0p\0q\0r\0E\0E0\0E1",
230         .str_sec_size = sizeof("\0A\0m\0n\0o\0p\0q\0r\0E\0E0\0E1"),
231         .map_type = BPF_MAP_TYPE_ARRAY,
232         .map_name = "struct_test1_map",
233         .key_size = sizeof(int),
234         .value_size = 180,
235         .key_type_id = 1,
236         .value_type_id = 5,
237         .max_entries = 4,
238 },
239
240 /* typedef struct b Struct_B;
241  *
242  * struct A {
243  *     int m;
244  *     struct b n[4];
245  *     const Struct_B o[4];
246  * };
247  *
248  * struct B {
249  *     int m;
250  *     int n;
251  * };
252  */
253 {
254         .descr = "struct test #2",
255         .raw_types = {
256                 /* int */                                       /* [1] */
257                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
258                 /* struct b [4] */                              /* [2] */
259                 BTF_TYPE_ARRAY_ENC(4, 1, 4),
260
261                 /* struct A { */                                /* [3] */
262                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 3), 68),
263                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m;               */
264                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* struct B n[4]        */
265                 BTF_MEMBER_ENC(NAME_TBD, 8, 288),/* const Struct_B o[4];*/
266                 /* } */
267
268                 /* struct B { */                                /* [4] */
269                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), 8),
270                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m; */
271                 BTF_MEMBER_ENC(NAME_TBD, 1, 32),/* int n; */
272                 /* } */
273
274                 /* const int */                                 /* [5] */
275                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 1),
276                 /* typedef struct b Struct_B */ /* [6] */
277                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_TYPEDEF, 0, 0), 4),
278                 /* const Struct_B */                            /* [7] */
279                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 6),
280                 /* const Struct_B [4] */                        /* [8] */
281                 BTF_TYPE_ARRAY_ENC(7, 1, 4),
282                 BTF_END_RAW,
283         },
284         .str_sec = "\0A\0m\0n\0o\0B\0m\0n\0Struct_B",
285         .str_sec_size = sizeof("\0A\0m\0n\0o\0B\0m\0n\0Struct_B"),
286         .map_type = BPF_MAP_TYPE_ARRAY,
287         .map_name = "struct_test2_map",
288         .key_size = sizeof(int),
289         .value_size = 68,
290         .key_type_id = 1,
291         .value_type_id = 3,
292         .max_entries = 4,
293 },
294
295 {
296         .descr = "struct test #3 Invalid member offset",
297         .raw_types = {
298                 /* int */                                       /* [1] */
299                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
300                 /* int64 */                                     /* [2] */
301                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 64, 8),
302
303                 /* struct A { */                                /* [3] */
304                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), 16),
305                 BTF_MEMBER_ENC(NAME_TBD, 1, 64),        /* int m;               */
306                 BTF_MEMBER_ENC(NAME_TBD, 2, 0),         /* int64 n; */
307                 /* } */
308                 BTF_END_RAW,
309         },
310         .str_sec = "\0A\0m\0n\0",
311         .str_sec_size = sizeof("\0A\0m\0n\0"),
312         .map_type = BPF_MAP_TYPE_ARRAY,
313         .map_name = "struct_test3_map",
314         .key_size = sizeof(int),
315         .value_size = 16,
316         .key_type_id = 1,
317         .value_type_id = 3,
318         .max_entries = 4,
319         .btf_load_err = true,
320         .err_str = "Invalid member bits_offset",
321 },
322
323 /* Test member exceeds the size of struct.
324  *
325  * struct A {
326  *     int m;
327  *     int n;
328  * };
329  */
330 {
331         .descr = "size check test #1",
332         .raw_types = {
333                 /* int */                                       /* [1] */
334                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
335                 /* struct A { */                                /* [2] */
336                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), sizeof(int) * 2 -  1),
337                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m; */
338                 BTF_MEMBER_ENC(NAME_TBD, 1, 32),/* int n; */
339                 /* } */
340                 BTF_END_RAW,
341         },
342         .str_sec = "\0A\0m\0n",
343         .str_sec_size = sizeof("\0A\0m\0n"),
344         .map_type = BPF_MAP_TYPE_ARRAY,
345         .map_name = "size_check1_map",
346         .key_size = sizeof(int),
347         .value_size = 1,
348         .key_type_id = 1,
349         .value_type_id = 2,
350         .max_entries = 4,
351         .btf_load_err = true,
352         .err_str = "Member exceeds struct_size",
353 },
354
355 /* Test member exeeds the size of struct
356  *
357  * struct A {
358  *     int m;
359  *     int n[2];
360  * };
361  */
362 {
363         .descr = "size check test #2",
364         .raw_types = {
365                 /* int */                                       /* [1] */
366                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, sizeof(int)),
367                 /* int[2] */                                    /* [2] */
368                 BTF_TYPE_ARRAY_ENC(1, 1, 2),
369                 /* struct A { */                                /* [3] */
370                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), sizeof(int) * 3 - 1),
371                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m; */
372                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* int n[2]; */
373                 /* } */
374                 BTF_END_RAW,
375         },
376         .str_sec = "\0A\0m\0n",
377         .str_sec_size = sizeof("\0A\0m\0n"),
378         .map_type = BPF_MAP_TYPE_ARRAY,
379         .map_name = "size_check2_map",
380         .key_size = sizeof(int),
381         .value_size = 1,
382         .key_type_id = 1,
383         .value_type_id = 3,
384         .max_entries = 4,
385         .btf_load_err = true,
386         .err_str = "Member exceeds struct_size",
387 },
388
389 /* Test member exeeds the size of struct
390  *
391  * struct A {
392  *     int m;
393  *     void *n;
394  * };
395  */
396 {
397         .descr = "size check test #3",
398         .raw_types = {
399                 /* int */                                       /* [1] */
400                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, sizeof(int)),
401                 /* void* */                                     /* [2] */
402                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 0),
403                 /* struct A { */                                /* [3] */
404                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), sizeof(int) + sizeof(void *) - 1),
405                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m; */
406                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* void *n; */
407                 /* } */
408                 BTF_END_RAW,
409         },
410         .str_sec = "\0A\0m\0n",
411         .str_sec_size = sizeof("\0A\0m\0n"),
412         .map_type = BPF_MAP_TYPE_ARRAY,
413         .map_name = "size_check3_map",
414         .key_size = sizeof(int),
415         .value_size = 1,
416         .key_type_id = 1,
417         .value_type_id = 3,
418         .max_entries = 4,
419         .btf_load_err = true,
420         .err_str = "Member exceeds struct_size",
421 },
422
423 /* Test member exceeds the size of struct
424  *
425  * enum E {
426  *     E0,
427  *     E1,
428  * };
429  *
430  * struct A {
431  *     int m;
432  *     enum E n;
433  * };
434  */
435 {
436         .descr = "size check test #4",
437         .raw_types = {
438                 /* int */                       /* [1] */
439                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, sizeof(int)),
440                 /* enum E { */                  /* [2] */
441                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 2), sizeof(int)),
442                 BTF_ENUM_ENC(NAME_TBD, 0),
443                 BTF_ENUM_ENC(NAME_TBD, 1),
444                 /* } */
445                 /* struct A { */                /* [3] */
446                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), sizeof(int) * 2 - 1),
447                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int m; */
448                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* enum E n; */
449                 /* } */
450                 BTF_END_RAW,
451         },
452         .str_sec = "\0E\0E0\0E1\0A\0m\0n",
453         .str_sec_size = sizeof("\0E\0E0\0E1\0A\0m\0n"),
454         .map_type = BPF_MAP_TYPE_ARRAY,
455         .map_name = "size_check4_map",
456         .key_size = sizeof(int),
457         .value_size = 1,
458         .key_type_id = 1,
459         .value_type_id = 3,
460         .max_entries = 4,
461         .btf_load_err = true,
462         .err_str = "Member exceeds struct_size",
463 },
464
465 /* typedef const void * const_void_ptr;
466  * struct A {
467  *      const_void_ptr m;
468  * };
469  */
470 {
471         .descr = "void test #1",
472         .raw_types = {
473                 /* int */               /* [1] */
474                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
475                 /* const void */        /* [2] */
476                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
477                 /* const void* */       /* [3] */
478                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 2),
479                 /* typedef const void * const_void_ptr */
480                 BTF_TYPEDEF_ENC(NAME_TBD, 3),   /* [4] */
481                 /* struct A { */        /* [5] */
482                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), sizeof(void *)),
483                 /* const_void_ptr m; */
484                 BTF_MEMBER_ENC(NAME_TBD, 4, 0),
485                 /* } */
486                 BTF_END_RAW,
487         },
488         .str_sec = "\0const_void_ptr\0A\0m",
489         .str_sec_size = sizeof("\0const_void_ptr\0A\0m"),
490         .map_type = BPF_MAP_TYPE_ARRAY,
491         .map_name = "void_test1_map",
492         .key_size = sizeof(int),
493         .value_size = sizeof(void *),
494         .key_type_id = 1,
495         .value_type_id = 4,
496         .max_entries = 4,
497 },
498
499 /* struct A {
500  *     const void m;
501  * };
502  */
503 {
504         .descr = "void test #2",
505         .raw_types = {
506                 /* int */               /* [1] */
507                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
508                 /* const void */        /* [2] */
509                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
510                 /* struct A { */        /* [3] */
511                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 8),
512                 /* const void m; */
513                 BTF_MEMBER_ENC(NAME_TBD, 2, 0),
514                 /* } */
515                 BTF_END_RAW,
516         },
517         .str_sec = "\0A\0m",
518         .str_sec_size = sizeof("\0A\0m"),
519         .map_type = BPF_MAP_TYPE_ARRAY,
520         .map_name = "void_test2_map",
521         .key_size = sizeof(int),
522         .value_size = sizeof(void *),
523         .key_type_id = 1,
524         .value_type_id = 3,
525         .max_entries = 4,
526         .btf_load_err = true,
527         .err_str = "Invalid member",
528 },
529
530 /* typedef const void * const_void_ptr;
531  * const_void_ptr[4]
532  */
533 {
534         .descr = "void test #3",
535         .raw_types = {
536                 /* int */               /* [1] */
537                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
538                 /* const void */        /* [2] */
539                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
540                 /* const void* */       /* [3] */
541                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 2),
542                 /* typedef const void * const_void_ptr */
543                 BTF_TYPEDEF_ENC(NAME_TBD, 3),   /* [4] */
544                 /* const_void_ptr[4] */
545                 BTF_TYPE_ARRAY_ENC(4, 1, 4),    /* [5] */
546                 BTF_END_RAW,
547         },
548         .str_sec = "\0const_void_ptr",
549         .str_sec_size = sizeof("\0const_void_ptr"),
550         .map_type = BPF_MAP_TYPE_ARRAY,
551         .map_name = "void_test3_map",
552         .key_size = sizeof(int),
553         .value_size = sizeof(void *) * 4,
554         .key_type_id = 1,
555         .value_type_id = 5,
556         .max_entries = 4,
557 },
558
559 /* const void[4]  */
560 {
561         .descr = "void test #4",
562         .raw_types = {
563                 /* int */               /* [1] */
564                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
565                 /* const void */        /* [2] */
566                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
567                 /* const void[4] */     /* [3] */
568                 BTF_TYPE_ARRAY_ENC(2, 1, 4),
569                 BTF_END_RAW,
570         },
571         .str_sec = "\0A\0m",
572         .str_sec_size = sizeof("\0A\0m"),
573         .map_type = BPF_MAP_TYPE_ARRAY,
574         .map_name = "void_test4_map",
575         .key_size = sizeof(int),
576         .value_size = sizeof(void *) * 4,
577         .key_type_id = 1,
578         .value_type_id = 3,
579         .max_entries = 4,
580         .btf_load_err = true,
581         .err_str = "Invalid elem",
582 },
583
584 /* Array_A  <------------------+
585  *     elem_type == Array_B    |
586  *                    |        |
587  *                    |        |
588  * Array_B  <-------- +        |
589  *      elem_type == Array A --+
590  */
591 {
592         .descr = "loop test #1",
593         .raw_types = {
594                 /* int */                       /* [1] */
595                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
596                 /* Array_A */                   /* [2] */
597                 BTF_TYPE_ARRAY_ENC(3, 1, 8),
598                 /* Array_B */                   /* [3] */
599                 BTF_TYPE_ARRAY_ENC(2, 1, 8),
600                 BTF_END_RAW,
601         },
602         .str_sec = "",
603         .str_sec_size = sizeof(""),
604         .map_type = BPF_MAP_TYPE_ARRAY,
605         .map_name = "loop_test1_map",
606         .key_size = sizeof(int),
607         .value_size = sizeof(sizeof(int) * 8),
608         .key_type_id = 1,
609         .value_type_id = 2,
610         .max_entries = 4,
611         .btf_load_err = true,
612         .err_str = "Loop detected",
613 },
614
615 /* typedef is _before_ the BTF type of Array_A and Array_B
616  *
617  * typedef Array_B int_array;
618  *
619  * Array_A  <------------------+
620  *     elem_type == int_array  |
621  *                    |        |
622  *                    |        |
623  * Array_B  <-------- +        |
624  *      elem_type == Array_A --+
625  */
626 {
627         .descr = "loop test #2",
628         .raw_types = {
629                 /* int */
630                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
631                 /* typedef Array_B int_array */
632                 BTF_TYPEDEF_ENC(1, 4),                          /* [2] */
633                 /* Array_A */
634                 BTF_TYPE_ARRAY_ENC(2, 1, 8),                    /* [3] */
635                 /* Array_B */
636                 BTF_TYPE_ARRAY_ENC(3, 1, 8),                    /* [4] */
637                 BTF_END_RAW,
638         },
639         .str_sec = "\0int_array\0",
640         .str_sec_size = sizeof("\0int_array"),
641         .map_type = BPF_MAP_TYPE_ARRAY,
642         .map_name = "loop_test2_map",
643         .key_size = sizeof(int),
644         .value_size = sizeof(sizeof(int) * 8),
645         .key_type_id = 1,
646         .value_type_id = 2,
647         .max_entries = 4,
648         .btf_load_err = true,
649         .err_str = "Loop detected",
650 },
651
652 /* Array_A  <------------------+
653  *     elem_type == Array_B    |
654  *                    |        |
655  *                    |        |
656  * Array_B  <-------- +        |
657  *      elem_type == Array_A --+
658  */
659 {
660         .descr = "loop test #3",
661         .raw_types = {
662                 /* int */                               /* [1] */
663                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
664                 /* Array_A */                           /* [2] */
665                 BTF_TYPE_ARRAY_ENC(3, 1, 8),
666                 /* Array_B */                           /* [3] */
667                 BTF_TYPE_ARRAY_ENC(2, 1, 8),
668                 BTF_END_RAW,
669         },
670         .str_sec = "",
671         .str_sec_size = sizeof(""),
672         .map_type = BPF_MAP_TYPE_ARRAY,
673         .map_name = "loop_test3_map",
674         .key_size = sizeof(int),
675         .value_size = sizeof(sizeof(int) * 8),
676         .key_type_id = 1,
677         .value_type_id = 2,
678         .max_entries = 4,
679         .btf_load_err = true,
680         .err_str = "Loop detected",
681 },
682
683 /* typedef is _between_ the BTF type of Array_A and Array_B
684  *
685  * typedef Array_B int_array;
686  *
687  * Array_A  <------------------+
688  *     elem_type == int_array  |
689  *                    |        |
690  *                    |        |
691  * Array_B  <-------- +        |
692  *      elem_type == Array_A --+
693  */
694 {
695         .descr = "loop test #4",
696         .raw_types = {
697                 /* int */                               /* [1] */
698                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
699                 /* Array_A */                           /* [2] */
700                 BTF_TYPE_ARRAY_ENC(3, 1, 8),
701                 /* typedef Array_B int_array */         /* [3] */
702                 BTF_TYPEDEF_ENC(NAME_TBD, 4),
703                 /* Array_B */                           /* [4] */
704                 BTF_TYPE_ARRAY_ENC(2, 1, 8),
705                 BTF_END_RAW,
706         },
707         .str_sec = "\0int_array\0",
708         .str_sec_size = sizeof("\0int_array"),
709         .map_type = BPF_MAP_TYPE_ARRAY,
710         .map_name = "loop_test4_map",
711         .key_size = sizeof(int),
712         .value_size = sizeof(sizeof(int) * 8),
713         .key_type_id = 1,
714         .value_type_id = 2,
715         .max_entries = 4,
716         .btf_load_err = true,
717         .err_str = "Loop detected",
718 },
719
720 /* typedef struct B Struct_B
721  *
722  * struct A {
723  *     int x;
724  *     Struct_B y;
725  * };
726  *
727  * struct B {
728  *     int x;
729  *     struct A y;
730  * };
731  */
732 {
733         .descr = "loop test #5",
734         .raw_types = {
735                 /* int */
736                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
737                 /* struct A */                                  /* [2] */
738                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), 8),
739                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int x;       */
740                 BTF_MEMBER_ENC(NAME_TBD, 3, 32),/* Struct_B y;  */
741                 /* typedef struct B Struct_B */
742                 BTF_TYPEDEF_ENC(NAME_TBD, 4),                   /* [3] */
743                 /* struct B */                                  /* [4] */
744                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), 8),
745                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int x;       */
746                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* struct A y;  */
747                 BTF_END_RAW,
748         },
749         .str_sec = "\0A\0x\0y\0Struct_B\0B\0x\0y",
750         .str_sec_size = sizeof("\0A\0x\0y\0Struct_B\0B\0x\0y"),
751         .map_type = BPF_MAP_TYPE_ARRAY,
752         .map_name = "loop_test5_map",
753         .key_size = sizeof(int),
754         .value_size = 8,
755         .key_type_id = 1,
756         .value_type_id = 2,
757         .max_entries = 4,
758         .btf_load_err = true,
759         .err_str = "Loop detected",
760 },
761
762 /* struct A {
763  *     int x;
764  *     struct A array_a[4];
765  * };
766  */
767 {
768         .descr = "loop test #6",
769         .raw_types = {
770                 /* int */
771                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
772                 BTF_TYPE_ARRAY_ENC(3, 1, 4),                    /* [2] */
773                 /* struct A */                                  /* [3] */
774                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 2), 8),
775                 BTF_MEMBER_ENC(NAME_TBD, 1, 0), /* int x;               */
776                 BTF_MEMBER_ENC(NAME_TBD, 2, 32),/* struct A array_a[4]; */
777                 BTF_END_RAW,
778         },
779         .str_sec = "\0A\0x\0y",
780         .str_sec_size = sizeof("\0A\0x\0y"),
781         .map_type = BPF_MAP_TYPE_ARRAY,
782         .map_name = "loop_test6_map",
783         .key_size = sizeof(int),
784         .value_size = 8,
785         .key_type_id = 1,
786         .value_type_id = 2,
787         .max_entries = 4,
788         .btf_load_err = true,
789         .err_str = "Loop detected",
790 },
791
792 {
793         .descr = "loop test #7",
794         .raw_types = {
795                 /* int */                               /* [1] */
796                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
797                 /* struct A { */                        /* [2] */
798                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), sizeof(void *)),
799                 /*     const void *m;   */
800                 BTF_MEMBER_ENC(NAME_TBD, 3, 0),
801                 /* CONST type_id=3      */              /* [3] */
802                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 4),
803                 /* PTR type_id=2        */              /* [4] */
804                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 3),
805                 BTF_END_RAW,
806         },
807         .str_sec = "\0A\0m",
808         .str_sec_size = sizeof("\0A\0m"),
809         .map_type = BPF_MAP_TYPE_ARRAY,
810         .map_name = "loop_test7_map",
811         .key_size = sizeof(int),
812         .value_size = sizeof(void *),
813         .key_type_id = 1,
814         .value_type_id = 2,
815         .max_entries = 4,
816         .btf_load_err = true,
817         .err_str = "Loop detected",
818 },
819
820 {
821         .descr = "loop test #8",
822         .raw_types = {
823                 /* int */                               /* [1] */
824                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
825                 /* struct A { */                        /* [2] */
826                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), sizeof(void *)),
827                 /*     const void *m;   */
828                 BTF_MEMBER_ENC(NAME_TBD, 4, 0),
829                 /* struct B { */                        /* [3] */
830                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), sizeof(void *)),
831                 /*     const void *n;   */
832                 BTF_MEMBER_ENC(NAME_TBD, 6, 0),
833                 /* CONST type_id=5      */              /* [4] */
834                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 5),
835                 /* PTR type_id=6        */              /* [5] */
836                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 6),
837                 /* CONST type_id=7      */              /* [6] */
838                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 7),
839                 /* PTR type_id=4        */              /* [7] */
840                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 4),
841                 BTF_END_RAW,
842         },
843         .str_sec = "\0A\0m\0B\0n",
844         .str_sec_size = sizeof("\0A\0m\0B\0n"),
845         .map_type = BPF_MAP_TYPE_ARRAY,
846         .map_name = "loop_test8_map",
847         .key_size = sizeof(int),
848         .value_size = sizeof(void *),
849         .key_type_id = 1,
850         .value_type_id = 2,
851         .max_entries = 4,
852         .btf_load_err = true,
853         .err_str = "Loop detected",
854 },
855
856 {
857         .descr = "string section does not end with null",
858         .raw_types = {
859                 /* int */                               /* [1] */
860                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
861                 BTF_END_RAW,
862         },
863         .str_sec = "\0int",
864         .str_sec_size = sizeof("\0int") - 1,
865         .map_type = BPF_MAP_TYPE_ARRAY,
866         .map_name = "hdr_test_map",
867         .key_size = sizeof(int),
868         .value_size = sizeof(int),
869         .key_type_id = 1,
870         .value_type_id = 1,
871         .max_entries = 4,
872         .btf_load_err = true,
873         .err_str = "Invalid string section",
874 },
875
876 {
877         .descr = "empty string section",
878         .raw_types = {
879                 /* int */                               /* [1] */
880                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
881                 BTF_END_RAW,
882         },
883         .str_sec = "",
884         .str_sec_size = 0,
885         .map_type = BPF_MAP_TYPE_ARRAY,
886         .map_name = "hdr_test_map",
887         .key_size = sizeof(int),
888         .value_size = sizeof(int),
889         .key_type_id = 1,
890         .value_type_id = 1,
891         .max_entries = 4,
892         .btf_load_err = true,
893         .err_str = "Invalid string section",
894 },
895
896 {
897         .descr = "empty type section",
898         .raw_types = {
899                 BTF_END_RAW,
900         },
901         .str_sec = "\0int",
902         .str_sec_size = sizeof("\0int"),
903         .map_type = BPF_MAP_TYPE_ARRAY,
904         .map_name = "hdr_test_map",
905         .key_size = sizeof(int),
906         .value_size = sizeof(int),
907         .key_type_id = 1,
908         .value_type_id = 1,
909         .max_entries = 4,
910         .btf_load_err = true,
911         .err_str = "No type found",
912 },
913
914 {
915         .descr = "btf_header test. Longer hdr_len",
916         .raw_types = {
917                 /* int */                               /* [1] */
918                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
919                 BTF_END_RAW,
920         },
921         .str_sec = "\0int",
922         .str_sec_size = sizeof("\0int"),
923         .map_type = BPF_MAP_TYPE_ARRAY,
924         .map_name = "hdr_test_map",
925         .key_size = sizeof(int),
926         .value_size = sizeof(int),
927         .key_type_id = 1,
928         .value_type_id = 1,
929         .max_entries = 4,
930         .btf_load_err = true,
931         .hdr_len_delta = 4,
932         .err_str = "Unsupported btf_header",
933 },
934
935 {
936         .descr = "btf_header test. Gap between hdr and type",
937         .raw_types = {
938                 /* int */                               /* [1] */
939                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
940                 BTF_END_RAW,
941         },
942         .str_sec = "\0int",
943         .str_sec_size = sizeof("\0int"),
944         .map_type = BPF_MAP_TYPE_ARRAY,
945         .map_name = "hdr_test_map",
946         .key_size = sizeof(int),
947         .value_size = sizeof(int),
948         .key_type_id = 1,
949         .value_type_id = 1,
950         .max_entries = 4,
951         .btf_load_err = true,
952         .type_off_delta = 4,
953         .err_str = "Unsupported section found",
954 },
955
956 {
957         .descr = "btf_header test. Gap between type and str",
958         .raw_types = {
959                 /* int */                               /* [1] */
960                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
961                 BTF_END_RAW,
962         },
963         .str_sec = "\0int",
964         .str_sec_size = sizeof("\0int"),
965         .map_type = BPF_MAP_TYPE_ARRAY,
966         .map_name = "hdr_test_map",
967         .key_size = sizeof(int),
968         .value_size = sizeof(int),
969         .key_type_id = 1,
970         .value_type_id = 1,
971         .max_entries = 4,
972         .btf_load_err = true,
973         .str_off_delta = 4,
974         .err_str = "Unsupported section found",
975 },
976
977 {
978         .descr = "btf_header test. Overlap between type and str",
979         .raw_types = {
980                 /* int */                               /* [1] */
981                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
982                 BTF_END_RAW,
983         },
984         .str_sec = "\0int",
985         .str_sec_size = sizeof("\0int"),
986         .map_type = BPF_MAP_TYPE_ARRAY,
987         .map_name = "hdr_test_map",
988         .key_size = sizeof(int),
989         .value_size = sizeof(int),
990         .key_type_id = 1,
991         .value_type_id = 1,
992         .max_entries = 4,
993         .btf_load_err = true,
994         .str_off_delta = -4,
995         .err_str = "Section overlap found",
996 },
997
998 {
999         .descr = "btf_header test. Larger BTF size",
1000         .raw_types = {
1001                 /* int */                               /* [1] */
1002                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
1003                 BTF_END_RAW,
1004         },
1005         .str_sec = "\0int",
1006         .str_sec_size = sizeof("\0int"),
1007         .map_type = BPF_MAP_TYPE_ARRAY,
1008         .map_name = "hdr_test_map",
1009         .key_size = sizeof(int),
1010         .value_size = sizeof(int),
1011         .key_type_id = 1,
1012         .value_type_id = 1,
1013         .max_entries = 4,
1014         .btf_load_err = true,
1015         .str_len_delta = -4,
1016         .err_str = "Unsupported section found",
1017 },
1018
1019 {
1020         .descr = "btf_header test. Smaller BTF size",
1021         .raw_types = {
1022                 /* int */                               /* [1] */
1023                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
1024                 BTF_END_RAW,
1025         },
1026         .str_sec = "\0int",
1027         .str_sec_size = sizeof("\0int"),
1028         .map_type = BPF_MAP_TYPE_ARRAY,
1029         .map_name = "hdr_test_map",
1030         .key_size = sizeof(int),
1031         .value_size = sizeof(int),
1032         .key_type_id = 1,
1033         .value_type_id = 1,
1034         .max_entries = 4,
1035         .btf_load_err = true,
1036         .str_len_delta = 4,
1037         .err_str = "Total section length too long",
1038 },
1039
1040 {
1041         .descr = "array test. index_type/elem_type \"int\"",
1042         .raw_types = {
1043                 /* int */                               /* [1] */
1044                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1045                 /* int[16] */                           /* [2] */
1046                 BTF_TYPE_ARRAY_ENC(1, 1, 16),
1047                 BTF_END_RAW,
1048         },
1049         .str_sec = "",
1050         .str_sec_size = sizeof(""),
1051         .map_type = BPF_MAP_TYPE_ARRAY,
1052         .map_name = "array_test_map",
1053         .key_size = sizeof(int),
1054         .value_size = sizeof(int),
1055         .key_type_id = 1,
1056         .value_type_id = 1,
1057         .max_entries = 4,
1058 },
1059
1060 {
1061         .descr = "array test. index_type/elem_type \"const int\"",
1062         .raw_types = {
1063                 /* int */                               /* [1] */
1064                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1065                 /* int[16] */                           /* [2] */
1066                 BTF_TYPE_ARRAY_ENC(3, 3, 16),
1067                 /* CONST type_id=1 */                   /* [3] */
1068                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 1),
1069                 BTF_END_RAW,
1070         },
1071         .str_sec = "",
1072         .str_sec_size = sizeof(""),
1073         .map_type = BPF_MAP_TYPE_ARRAY,
1074         .map_name = "array_test_map",
1075         .key_size = sizeof(int),
1076         .value_size = sizeof(int),
1077         .key_type_id = 1,
1078         .value_type_id = 1,
1079         .max_entries = 4,
1080 },
1081
1082 {
1083         .descr = "array test. index_type \"const int:31\"",
1084         .raw_types = {
1085                 /* int */                               /* [1] */
1086                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1087                 /* int:31 */                            /* [2] */
1088                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 31, 4),
1089                 /* int[16] */                           /* [3] */
1090                 BTF_TYPE_ARRAY_ENC(1, 4, 16),
1091                 /* CONST type_id=2 */                   /* [4] */
1092                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 2),
1093                 BTF_END_RAW,
1094         },
1095         .str_sec = "",
1096         .str_sec_size = sizeof(""),
1097         .map_type = BPF_MAP_TYPE_ARRAY,
1098         .map_name = "array_test_map",
1099         .key_size = sizeof(int),
1100         .value_size = sizeof(int),
1101         .key_type_id = 1,
1102         .value_type_id = 1,
1103         .max_entries = 4,
1104         .btf_load_err = true,
1105         .err_str = "Invalid index",
1106 },
1107
1108 {
1109         .descr = "array test. elem_type \"const int:31\"",
1110         .raw_types = {
1111                 /* int */                               /* [1] */
1112                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1113                 /* int:31 */                            /* [2] */
1114                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 31, 4),
1115                 /* int[16] */                           /* [3] */
1116                 BTF_TYPE_ARRAY_ENC(4, 1, 16),
1117                 /* CONST type_id=2 */                   /* [4] */
1118                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 2),
1119                 BTF_END_RAW,
1120         },
1121         .str_sec = "",
1122         .str_sec_size = sizeof(""),
1123         .map_type = BPF_MAP_TYPE_ARRAY,
1124         .map_name = "array_test_map",
1125         .key_size = sizeof(int),
1126         .value_size = sizeof(int),
1127         .key_type_id = 1,
1128         .value_type_id = 1,
1129         .max_entries = 4,
1130         .btf_load_err = true,
1131         .err_str = "Invalid array of int",
1132 },
1133
1134 {
1135         .descr = "array test. index_type \"void\"",
1136         .raw_types = {
1137                 /* int */                               /* [1] */
1138                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1139                 /* int[16] */                           /* [2] */
1140                 BTF_TYPE_ARRAY_ENC(1, 0, 16),
1141                 BTF_END_RAW,
1142         },
1143         .str_sec = "",
1144         .str_sec_size = sizeof(""),
1145         .map_type = BPF_MAP_TYPE_ARRAY,
1146         .map_name = "array_test_map",
1147         .key_size = sizeof(int),
1148         .value_size = sizeof(int),
1149         .key_type_id = 1,
1150         .value_type_id = 1,
1151         .max_entries = 4,
1152         .btf_load_err = true,
1153         .err_str = "Invalid index",
1154 },
1155
1156 {
1157         .descr = "array test. index_type \"const void\"",
1158         .raw_types = {
1159                 /* int */                               /* [1] */
1160                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1161                 /* int[16] */                           /* [2] */
1162                 BTF_TYPE_ARRAY_ENC(1, 3, 16),
1163                 /* CONST type_id=0 (void) */            /* [3] */
1164                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
1165                 BTF_END_RAW,
1166         },
1167         .str_sec = "",
1168         .str_sec_size = sizeof(""),
1169         .map_type = BPF_MAP_TYPE_ARRAY,
1170         .map_name = "array_test_map",
1171         .key_size = sizeof(int),
1172         .value_size = sizeof(int),
1173         .key_type_id = 1,
1174         .value_type_id = 1,
1175         .max_entries = 4,
1176         .btf_load_err = true,
1177         .err_str = "Invalid index",
1178 },
1179
1180 {
1181         .descr = "array test. elem_type \"const void\"",
1182         .raw_types = {
1183                 /* int */                               /* [1] */
1184                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1185                 /* int[16] */                           /* [2] */
1186                 BTF_TYPE_ARRAY_ENC(3, 1, 16),
1187                 /* CONST type_id=0 (void) */            /* [3] */
1188                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 0),
1189                 BTF_END_RAW,
1190         },
1191         .str_sec = "",
1192         .str_sec_size = sizeof(""),
1193         .map_type = BPF_MAP_TYPE_ARRAY,
1194         .map_name = "array_test_map",
1195         .key_size = sizeof(int),
1196         .value_size = sizeof(int),
1197         .key_type_id = 1,
1198         .value_type_id = 1,
1199         .max_entries = 4,
1200         .btf_load_err = true,
1201         .err_str = "Invalid elem",
1202 },
1203
1204 {
1205         .descr = "array test. elem_type \"const void *\"",
1206         .raw_types = {
1207                 /* int */                               /* [1] */
1208                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1209                 /* const void *[16] */                  /* [2] */
1210                 BTF_TYPE_ARRAY_ENC(3, 1, 16),
1211                 /* CONST type_id=4 */                   /* [3] */
1212                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 4),
1213                 /* void* */                             /* [4] */
1214                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 0),
1215                 BTF_END_RAW,
1216         },
1217         .str_sec = "",
1218         .str_sec_size = sizeof(""),
1219         .map_type = BPF_MAP_TYPE_ARRAY,
1220         .map_name = "array_test_map",
1221         .key_size = sizeof(int),
1222         .value_size = sizeof(int),
1223         .key_type_id = 1,
1224         .value_type_id = 1,
1225         .max_entries = 4,
1226 },
1227
1228 {
1229         .descr = "array test. index_type \"const void *\"",
1230         .raw_types = {
1231                 /* int */                               /* [1] */
1232                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1233                 /* const void *[16] */                  /* [2] */
1234                 BTF_TYPE_ARRAY_ENC(3, 3, 16),
1235                 /* CONST type_id=4 */                   /* [3] */
1236                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 4),
1237                 /* void* */                             /* [4] */
1238                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 0),
1239                 BTF_END_RAW,
1240         },
1241         .str_sec = "",
1242         .str_sec_size = sizeof(""),
1243         .map_type = BPF_MAP_TYPE_ARRAY,
1244         .map_name = "array_test_map",
1245         .key_size = sizeof(int),
1246         .value_size = sizeof(int),
1247         .key_type_id = 1,
1248         .value_type_id = 1,
1249         .max_entries = 4,
1250         .btf_load_err = true,
1251         .err_str = "Invalid index",
1252 },
1253
1254 {
1255         .descr = "array test. t->size != 0\"",
1256         .raw_types = {
1257                 /* int */                               /* [1] */
1258                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1259                 /* int[16] */                           /* [2] */
1260                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ARRAY, 0, 0), 1),
1261                 BTF_ARRAY_ENC(1, 1, 16),
1262                 BTF_END_RAW,
1263         },
1264         .str_sec = "",
1265         .str_sec_size = sizeof(""),
1266         .map_type = BPF_MAP_TYPE_ARRAY,
1267         .map_name = "array_test_map",
1268         .key_size = sizeof(int),
1269         .value_size = sizeof(int),
1270         .key_type_id = 1,
1271         .value_type_id = 1,
1272         .max_entries = 4,
1273         .btf_load_err = true,
1274         .err_str = "size != 0",
1275 },
1276
1277 {
1278         .descr = "int test. invalid int_data",
1279         .raw_types = {
1280                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_INT, 0, 0), 4),
1281                 0x10000000,
1282                 BTF_END_RAW,
1283         },
1284         .str_sec = "",
1285         .str_sec_size = sizeof(""),
1286         .map_type = BPF_MAP_TYPE_ARRAY,
1287         .map_name = "array_test_map",
1288         .key_size = sizeof(int),
1289         .value_size = sizeof(int),
1290         .key_type_id = 1,
1291         .value_type_id = 1,
1292         .max_entries = 4,
1293         .btf_load_err = true,
1294         .err_str = "Invalid int_data",
1295 },
1296
1297 {
1298         .descr = "invalid BTF_INFO",
1299         .raw_types = {
1300                 /* int */                               /* [1] */
1301                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1302                 BTF_TYPE_ENC(0, 0x10000000, 4),
1303                 BTF_END_RAW,
1304         },
1305         .str_sec = "",
1306         .str_sec_size = sizeof(""),
1307         .map_type = BPF_MAP_TYPE_ARRAY,
1308         .map_name = "array_test_map",
1309         .key_size = sizeof(int),
1310         .value_size = sizeof(int),
1311         .key_type_id = 1,
1312         .value_type_id = 1,
1313         .max_entries = 4,
1314         .btf_load_err = true,
1315         .err_str = "Invalid btf_info",
1316 },
1317
1318 {
1319         .descr = "fwd test. t->type != 0\"",
1320         .raw_types = {
1321                 /* int */                               /* [1] */
1322                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1323                 /* fwd type */                          /* [2] */
1324                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_FWD, 0, 0), 1),
1325                 BTF_END_RAW,
1326         },
1327         .str_sec = "",
1328         .str_sec_size = sizeof(""),
1329         .map_type = BPF_MAP_TYPE_ARRAY,
1330         .map_name = "fwd_test_map",
1331         .key_size = sizeof(int),
1332         .value_size = sizeof(int),
1333         .key_type_id = 1,
1334         .value_type_id = 1,
1335         .max_entries = 4,
1336         .btf_load_err = true,
1337         .err_str = "type != 0",
1338 },
1339
1340 {
1341         .descr = "typedef (invalid name, name_off = 0)",
1342         .raw_types = {
1343                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1344                 BTF_TYPEDEF_ENC(0, 1),                          /* [2] */
1345                 BTF_END_RAW,
1346         },
1347         .str_sec = "\0__int",
1348         .str_sec_size = sizeof("\0__int"),
1349         .map_type = BPF_MAP_TYPE_ARRAY,
1350         .map_name = "typedef_check_btf",
1351         .key_size = sizeof(int),
1352         .value_size = sizeof(int),
1353         .key_type_id = 1,
1354         .value_type_id = 1,
1355         .max_entries = 4,
1356         .btf_load_err = true,
1357         .err_str = "Invalid name",
1358 },
1359
1360 {
1361         .descr = "typedef (invalid name, invalid identifier)",
1362         .raw_types = {
1363                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1364                 BTF_TYPEDEF_ENC(NAME_TBD, 1),                   /* [2] */
1365                 BTF_END_RAW,
1366         },
1367         .str_sec = "\0__!int",
1368         .str_sec_size = sizeof("\0__!int"),
1369         .map_type = BPF_MAP_TYPE_ARRAY,
1370         .map_name = "typedef_check_btf",
1371         .key_size = sizeof(int),
1372         .value_size = sizeof(int),
1373         .key_type_id = 1,
1374         .value_type_id = 1,
1375         .max_entries = 4,
1376         .btf_load_err = true,
1377         .err_str = "Invalid name",
1378 },
1379
1380 {
1381         .descr = "ptr type (invalid name, name_off <> 0)",
1382         .raw_types = {
1383                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1384                 BTF_TYPE_ENC(NAME_TBD,
1385                              BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 1),      /* [2] */
1386                 BTF_END_RAW,
1387         },
1388         .str_sec = "\0__int",
1389         .str_sec_size = sizeof("\0__int"),
1390         .map_type = BPF_MAP_TYPE_ARRAY,
1391         .map_name = "ptr_type_check_btf",
1392         .key_size = sizeof(int),
1393         .value_size = sizeof(int),
1394         .key_type_id = 1,
1395         .value_type_id = 1,
1396         .max_entries = 4,
1397         .btf_load_err = true,
1398         .err_str = "Invalid name",
1399 },
1400
1401 {
1402         .descr = "volatile type (invalid name, name_off <> 0)",
1403         .raw_types = {
1404                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1405                 BTF_TYPE_ENC(NAME_TBD,
1406                              BTF_INFO_ENC(BTF_KIND_VOLATILE, 0, 0), 1), /* [2] */
1407                 BTF_END_RAW,
1408         },
1409         .str_sec = "\0__int",
1410         .str_sec_size = sizeof("\0__int"),
1411         .map_type = BPF_MAP_TYPE_ARRAY,
1412         .map_name = "volatile_type_check_btf",
1413         .key_size = sizeof(int),
1414         .value_size = sizeof(int),
1415         .key_type_id = 1,
1416         .value_type_id = 1,
1417         .max_entries = 4,
1418         .btf_load_err = true,
1419         .err_str = "Invalid name",
1420 },
1421
1422 {
1423         .descr = "const type (invalid name, name_off <> 0)",
1424         .raw_types = {
1425                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1426                 BTF_TYPE_ENC(NAME_TBD,
1427                              BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 1),    /* [2] */
1428                 BTF_END_RAW,
1429         },
1430         .str_sec = "\0__int",
1431         .str_sec_size = sizeof("\0__int"),
1432         .map_type = BPF_MAP_TYPE_ARRAY,
1433         .map_name = "const_type_check_btf",
1434         .key_size = sizeof(int),
1435         .value_size = sizeof(int),
1436         .key_type_id = 1,
1437         .value_type_id = 1,
1438         .max_entries = 4,
1439         .btf_load_err = true,
1440         .err_str = "Invalid name",
1441 },
1442
1443 {
1444         .descr = "restrict type (invalid name, name_off <> 0)",
1445         .raw_types = {
1446                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1447                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 0, 0), 1),   /* [2] */
1448                 BTF_TYPE_ENC(NAME_TBD,
1449                              BTF_INFO_ENC(BTF_KIND_RESTRICT, 0, 0), 2), /* [3] */
1450                 BTF_END_RAW,
1451         },
1452         .str_sec = "\0__int",
1453         .str_sec_size = sizeof("\0__int"),
1454         .map_type = BPF_MAP_TYPE_ARRAY,
1455         .map_name = "restrict_type_check_btf",
1456         .key_size = sizeof(int),
1457         .value_size = sizeof(int),
1458         .key_type_id = 1,
1459         .value_type_id = 1,
1460         .max_entries = 4,
1461         .btf_load_err = true,
1462         .err_str = "Invalid name",
1463 },
1464
1465 {
1466         .descr = "fwd type (invalid name, name_off = 0)",
1467         .raw_types = {
1468                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1469                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_FWD, 0, 0), 0),   /* [2] */
1470                 BTF_END_RAW,
1471         },
1472         .str_sec = "\0__skb",
1473         .str_sec_size = sizeof("\0__skb"),
1474         .map_type = BPF_MAP_TYPE_ARRAY,
1475         .map_name = "fwd_type_check_btf",
1476         .key_size = sizeof(int),
1477         .value_size = sizeof(int),
1478         .key_type_id = 1,
1479         .value_type_id = 1,
1480         .max_entries = 4,
1481         .btf_load_err = true,
1482         .err_str = "Invalid name",
1483 },
1484
1485 {
1486         .descr = "fwd type (invalid name, invalid identifier)",
1487         .raw_types = {
1488                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1489                 BTF_TYPE_ENC(NAME_TBD,
1490                              BTF_INFO_ENC(BTF_KIND_FWD, 0, 0), 0),      /* [2] */
1491                 BTF_END_RAW,
1492         },
1493         .str_sec = "\0__!skb",
1494         .str_sec_size = sizeof("\0__!skb"),
1495         .map_type = BPF_MAP_TYPE_ARRAY,
1496         .map_name = "fwd_type_check_btf",
1497         .key_size = sizeof(int),
1498         .value_size = sizeof(int),
1499         .key_type_id = 1,
1500         .value_type_id = 1,
1501         .max_entries = 4,
1502         .btf_load_err = true,
1503         .err_str = "Invalid name",
1504 },
1505
1506 {
1507         .descr = "array type (invalid name, name_off <> 0)",
1508         .raw_types = {
1509                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1510                 BTF_TYPE_ENC(NAME_TBD,
1511                              BTF_INFO_ENC(BTF_KIND_ARRAY, 0, 0), 0),    /* [2] */
1512                 BTF_ARRAY_ENC(1, 1, 4),
1513                 BTF_END_RAW,
1514         },
1515         .str_sec = "\0__skb",
1516         .str_sec_size = sizeof("\0__skb"),
1517         .map_type = BPF_MAP_TYPE_ARRAY,
1518         .map_name = "array_type_check_btf",
1519         .key_size = sizeof(int),
1520         .value_size = sizeof(int),
1521         .key_type_id = 1,
1522         .value_type_id = 1,
1523         .max_entries = 4,
1524         .btf_load_err = true,
1525         .err_str = "Invalid name",
1526 },
1527
1528 {
1529         .descr = "struct type (name_off = 0)",
1530         .raw_types = {
1531                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1532                 BTF_TYPE_ENC(0,
1533                              BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 4),   /* [2] */
1534                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
1535                 BTF_END_RAW,
1536         },
1537         .str_sec = "\0A",
1538         .str_sec_size = sizeof("\0A"),
1539         .map_type = BPF_MAP_TYPE_ARRAY,
1540         .map_name = "struct_type_check_btf",
1541         .key_size = sizeof(int),
1542         .value_size = sizeof(int),
1543         .key_type_id = 1,
1544         .value_type_id = 1,
1545         .max_entries = 4,
1546 },
1547
1548 {
1549         .descr = "struct type (invalid name, invalid identifier)",
1550         .raw_types = {
1551                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1552                 BTF_TYPE_ENC(NAME_TBD,
1553                              BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 4),   /* [2] */
1554                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
1555                 BTF_END_RAW,
1556         },
1557         .str_sec = "\0A!\0B",
1558         .str_sec_size = sizeof("\0A!\0B"),
1559         .map_type = BPF_MAP_TYPE_ARRAY,
1560         .map_name = "struct_type_check_btf",
1561         .key_size = sizeof(int),
1562         .value_size = sizeof(int),
1563         .key_type_id = 1,
1564         .value_type_id = 1,
1565         .max_entries = 4,
1566         .btf_load_err = true,
1567         .err_str = "Invalid name",
1568 },
1569
1570 {
1571         .descr = "struct member (name_off = 0)",
1572         .raw_types = {
1573                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1574                 BTF_TYPE_ENC(0,
1575                              BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 4),   /* [2] */
1576                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
1577                 BTF_END_RAW,
1578         },
1579         .str_sec = "\0A",
1580         .str_sec_size = sizeof("\0A"),
1581         .map_type = BPF_MAP_TYPE_ARRAY,
1582         .map_name = "struct_type_check_btf",
1583         .key_size = sizeof(int),
1584         .value_size = sizeof(int),
1585         .key_type_id = 1,
1586         .value_type_id = 1,
1587         .max_entries = 4,
1588 },
1589
1590 {
1591         .descr = "struct member (invalid name, invalid identifier)",
1592         .raw_types = {
1593                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1594                 BTF_TYPE_ENC(NAME_TBD,
1595                              BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 4),   /* [2] */
1596                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
1597                 BTF_END_RAW,
1598         },
1599         .str_sec = "\0A\0B*",
1600         .str_sec_size = sizeof("\0A\0B*"),
1601         .map_type = BPF_MAP_TYPE_ARRAY,
1602         .map_name = "struct_type_check_btf",
1603         .key_size = sizeof(int),
1604         .value_size = sizeof(int),
1605         .key_type_id = 1,
1606         .value_type_id = 1,
1607         .max_entries = 4,
1608         .btf_load_err = true,
1609         .err_str = "Invalid name",
1610 },
1611
1612 {
1613         .descr = "enum type (name_off = 0)",
1614         .raw_types = {
1615                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1616                 BTF_TYPE_ENC(0,
1617                              BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1),
1618                              sizeof(int)),                              /* [2] */
1619                 BTF_ENUM_ENC(NAME_TBD, 0),
1620                 BTF_END_RAW,
1621         },
1622         .str_sec = "\0A\0B",
1623         .str_sec_size = sizeof("\0A\0B"),
1624         .map_type = BPF_MAP_TYPE_ARRAY,
1625         .map_name = "enum_type_check_btf",
1626         .key_size = sizeof(int),
1627         .value_size = sizeof(int),
1628         .key_type_id = 1,
1629         .value_type_id = 1,
1630         .max_entries = 4,
1631 },
1632
1633 {
1634         .descr = "enum type (invalid name, invalid identifier)",
1635         .raw_types = {
1636                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1637                 BTF_TYPE_ENC(NAME_TBD,
1638                              BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1),
1639                              sizeof(int)),                              /* [2] */
1640                 BTF_ENUM_ENC(NAME_TBD, 0),
1641                 BTF_END_RAW,
1642         },
1643         .str_sec = "\0A!\0B",
1644         .str_sec_size = sizeof("\0A!\0B"),
1645         .map_type = BPF_MAP_TYPE_ARRAY,
1646         .map_name = "enum_type_check_btf",
1647         .key_size = sizeof(int),
1648         .value_size = sizeof(int),
1649         .key_type_id = 1,
1650         .value_type_id = 1,
1651         .max_entries = 4,
1652         .btf_load_err = true,
1653         .err_str = "Invalid name",
1654 },
1655
1656 {
1657         .descr = "enum member (invalid name, name_off = 0)",
1658         .raw_types = {
1659                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1660                 BTF_TYPE_ENC(0,
1661                              BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1),
1662                              sizeof(int)),                              /* [2] */
1663                 BTF_ENUM_ENC(0, 0),
1664                 BTF_END_RAW,
1665         },
1666         .str_sec = "",
1667         .str_sec_size = sizeof(""),
1668         .map_type = BPF_MAP_TYPE_ARRAY,
1669         .map_name = "enum_type_check_btf",
1670         .key_size = sizeof(int),
1671         .value_size = sizeof(int),
1672         .key_type_id = 1,
1673         .value_type_id = 1,
1674         .max_entries = 4,
1675         .btf_load_err = true,
1676         .err_str = "Invalid name",
1677 },
1678
1679 {
1680         .descr = "enum member (invalid name, invalid identifier)",
1681         .raw_types = {
1682                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
1683                 BTF_TYPE_ENC(0,
1684                              BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1),
1685                              sizeof(int)),                              /* [2] */
1686                 BTF_ENUM_ENC(NAME_TBD, 0),
1687                 BTF_END_RAW,
1688         },
1689         .str_sec = "\0A!",
1690         .str_sec_size = sizeof("\0A!"),
1691         .map_type = BPF_MAP_TYPE_ARRAY,
1692         .map_name = "enum_type_check_btf",
1693         .key_size = sizeof(int),
1694         .value_size = sizeof(int),
1695         .key_type_id = 1,
1696         .value_type_id = 1,
1697         .max_entries = 4,
1698         .btf_load_err = true,
1699         .err_str = "Invalid name",
1700 },
1701 {
1702         .descr = "arraymap invalid btf key (a bit field)",
1703         .raw_types = {
1704                 /* int */                               /* [1] */
1705                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1706                 /* 32 bit int with 32 bit offset */     /* [2] */
1707                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 32, 32, 8),
1708                 BTF_END_RAW,
1709         },
1710         .str_sec = "",
1711         .str_sec_size = sizeof(""),
1712         .map_type = BPF_MAP_TYPE_ARRAY,
1713         .map_name = "array_map_check_btf",
1714         .key_size = sizeof(int),
1715         .value_size = sizeof(int),
1716         .key_type_id = 2,
1717         .value_type_id = 1,
1718         .max_entries = 4,
1719         .map_create_err = true,
1720 },
1721
1722 {
1723         .descr = "arraymap invalid btf key (!= 32 bits)",
1724         .raw_types = {
1725                 /* int */                               /* [1] */
1726                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1727                 /* 16 bit int with 0 bit offset */      /* [2] */
1728                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 16, 2),
1729                 BTF_END_RAW,
1730         },
1731         .str_sec = "",
1732         .str_sec_size = sizeof(""),
1733         .map_type = BPF_MAP_TYPE_ARRAY,
1734         .map_name = "array_map_check_btf",
1735         .key_size = sizeof(int),
1736         .value_size = sizeof(int),
1737         .key_type_id = 2,
1738         .value_type_id = 1,
1739         .max_entries = 4,
1740         .map_create_err = true,
1741 },
1742
1743 {
1744         .descr = "arraymap invalid btf value (too small)",
1745         .raw_types = {
1746                 /* int */                               /* [1] */
1747                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1748                 BTF_END_RAW,
1749         },
1750         .str_sec = "",
1751         .str_sec_size = sizeof(""),
1752         .map_type = BPF_MAP_TYPE_ARRAY,
1753         .map_name = "array_map_check_btf",
1754         .key_size = sizeof(int),
1755         /* btf_value_size < map->value_size */
1756         .value_size = sizeof(__u64),
1757         .key_type_id = 1,
1758         .value_type_id = 1,
1759         .max_entries = 4,
1760         .map_create_err = true,
1761 },
1762
1763 {
1764         .descr = "arraymap invalid btf value (too big)",
1765         .raw_types = {
1766                 /* int */                               /* [1] */
1767                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
1768                 BTF_END_RAW,
1769         },
1770         .str_sec = "",
1771         .str_sec_size = sizeof(""),
1772         .map_type = BPF_MAP_TYPE_ARRAY,
1773         .map_name = "array_map_check_btf",
1774         .key_size = sizeof(int),
1775         /* btf_value_size > map->value_size */
1776         .value_size = sizeof(__u16),
1777         .key_type_id = 1,
1778         .value_type_id = 1,
1779         .max_entries = 4,
1780         .map_create_err = true,
1781 },
1782
1783 {
1784         .descr = "func proto (int (*)(int, unsigned int))",
1785         .raw_types = {
1786                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4), /* [1] */
1787                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1788                 /* int (*)(int, unsigned int) */
1789                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [3] */
1790                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
1791                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
1792                 BTF_END_RAW,
1793         },
1794         .str_sec = "",
1795         .str_sec_size = sizeof(""),
1796         .map_type = BPF_MAP_TYPE_ARRAY,
1797         .map_name = "func_proto_type_check_btf",
1798         .key_size = sizeof(int),
1799         .value_size = sizeof(int),
1800         .key_type_id = 1,
1801         .value_type_id = 1,
1802         .max_entries = 4,
1803 },
1804
1805 {
1806         .descr = "func proto (vararg)",
1807         .raw_types = {
1808                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1809                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1810                 /* void (*)(int, unsigned int, ...) */
1811                 BTF_FUNC_PROTO_ENC(0, 3),                       /* [3] */
1812                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
1813                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
1814                         BTF_FUNC_PROTO_ARG_ENC(0, 0),
1815                 BTF_END_RAW,
1816         },
1817         .str_sec = "",
1818         .str_sec_size = sizeof(""),
1819         .map_type = BPF_MAP_TYPE_ARRAY,
1820         .map_name = "func_proto_type_check_btf",
1821         .key_size = sizeof(int),
1822         .value_size = sizeof(int),
1823         .key_type_id = 1,
1824         .value_type_id = 1,
1825         .max_entries = 4,
1826 },
1827
1828 {
1829         .descr = "func proto (vararg with name)",
1830         .raw_types = {
1831                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1832                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1833                 /* void (*)(int a, unsigned int b, ... c) */
1834                 BTF_FUNC_PROTO_ENC(0, 3),                       /* [3] */
1835                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
1836                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
1837                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 0),
1838                 BTF_END_RAW,
1839         },
1840         .str_sec = "\0a\0b\0c",
1841         .str_sec_size = sizeof("\0a\0b\0c"),
1842         .map_type = BPF_MAP_TYPE_ARRAY,
1843         .map_name = "func_proto_type_check_btf",
1844         .key_size = sizeof(int),
1845         .value_size = sizeof(int),
1846         .key_type_id = 1,
1847         .value_type_id = 1,
1848         .max_entries = 4,
1849         .btf_load_err = true,
1850         .err_str = "Invalid arg#3",
1851 },
1852
1853 {
1854         .descr = "func proto (arg after vararg)",
1855         .raw_types = {
1856                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1857                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1858                 /* void (*)(int a, ..., unsigned int b) */
1859                 BTF_FUNC_PROTO_ENC(0, 3),                       /* [3] */
1860                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
1861                         BTF_FUNC_PROTO_ARG_ENC(0, 0),
1862                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
1863                 BTF_END_RAW,
1864         },
1865         .str_sec = "\0a\0b",
1866         .str_sec_size = sizeof("\0a\0b"),
1867         .map_type = BPF_MAP_TYPE_ARRAY,
1868         .map_name = "func_proto_type_check_btf",
1869         .key_size = sizeof(int),
1870         .value_size = sizeof(int),
1871         .key_type_id = 1,
1872         .value_type_id = 1,
1873         .max_entries = 4,
1874         .btf_load_err = true,
1875         .err_str = "Invalid arg#2",
1876 },
1877
1878 {
1879         .descr = "func proto (CONST=>TYPEDEF=>PTR=>FUNC_PROTO)",
1880         .raw_types = {
1881                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1882                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1883                 /* typedef void (*func_ptr)(int, unsigned int) */
1884                 BTF_TYPEDEF_ENC(NAME_TBD, 5),                   /* [3] */
1885                 /* const func_ptr */
1886                 BTF_CONST_ENC(3),                               /* [4] */
1887                 BTF_PTR_ENC(6),                                 /* [5] */
1888                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [6] */
1889                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
1890                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
1891                 BTF_END_RAW,
1892         },
1893         .str_sec = "\0func_ptr",
1894         .str_sec_size = sizeof("\0func_ptr"),
1895         .map_type = BPF_MAP_TYPE_ARRAY,
1896         .map_name = "func_proto_type_check_btf",
1897         .key_size = sizeof(int),
1898         .value_size = sizeof(int),
1899         .key_type_id = 1,
1900         .value_type_id = 1,
1901         .max_entries = 4,
1902 },
1903
1904 {
1905         .descr = "func proto (TYPEDEF=>FUNC_PROTO)",
1906         .raw_types = {
1907                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1908                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1909                 BTF_TYPEDEF_ENC(NAME_TBD, 4),                   /* [3] */
1910                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [4] */
1911                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
1912                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
1913                 BTF_END_RAW,
1914         },
1915         .str_sec = "\0func_typedef",
1916         .str_sec_size = sizeof("\0func_typedef"),
1917         .map_type = BPF_MAP_TYPE_ARRAY,
1918         .map_name = "func_proto_type_check_btf",
1919         .key_size = sizeof(int),
1920         .value_size = sizeof(int),
1921         .key_type_id = 1,
1922         .value_type_id = 1,
1923         .max_entries = 4,
1924 },
1925
1926 {
1927         .descr = "func proto (btf_resolve(arg))",
1928         .raw_types = {
1929                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1930                 /* void (*)(const void *) */
1931                 BTF_FUNC_PROTO_ENC(0, 1),                       /* [2] */
1932                         BTF_FUNC_PROTO_ARG_ENC(0, 3),
1933                 BTF_CONST_ENC(4),                               /* [3] */
1934                 BTF_PTR_ENC(0),                                 /* [4] */
1935                 BTF_END_RAW,
1936         },
1937         .str_sec = "",
1938         .str_sec_size = sizeof(""),
1939         .map_type = BPF_MAP_TYPE_ARRAY,
1940         .map_name = "func_proto_type_check_btf",
1941         .key_size = sizeof(int),
1942         .value_size = sizeof(int),
1943         .key_type_id = 1,
1944         .value_type_id = 1,
1945         .max_entries = 4,
1946 },
1947
1948 {
1949         .descr = "func proto (Not all arg has name)",
1950         .raw_types = {
1951                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1952                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1953                 /* void (*)(int, unsigned int b) */
1954                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
1955                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
1956                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
1957                 BTF_END_RAW,
1958         },
1959         .str_sec = "\0b",
1960         .str_sec_size = sizeof("\0b"),
1961         .map_type = BPF_MAP_TYPE_ARRAY,
1962         .map_name = "func_proto_type_check_btf",
1963         .key_size = sizeof(int),
1964         .value_size = sizeof(int),
1965         .key_type_id = 1,
1966         .value_type_id = 1,
1967         .max_entries = 4,
1968 },
1969
1970 {
1971         .descr = "func proto (Bad arg name_off)",
1972         .raw_types = {
1973                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1974                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1975                 /* void (*)(int a, unsigned int <bad_name_off>) */
1976                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
1977                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
1978                         BTF_FUNC_PROTO_ARG_ENC(0x0fffffff, 2),
1979                 BTF_END_RAW,
1980         },
1981         .str_sec = "\0a",
1982         .str_sec_size = sizeof("\0a"),
1983         .map_type = BPF_MAP_TYPE_ARRAY,
1984         .map_name = "func_proto_type_check_btf",
1985         .key_size = sizeof(int),
1986         .value_size = sizeof(int),
1987         .key_type_id = 1,
1988         .value_type_id = 1,
1989         .max_entries = 4,
1990         .btf_load_err = true,
1991         .err_str = "Invalid arg#2",
1992 },
1993
1994 {
1995         .descr = "func proto (Bad arg name)",
1996         .raw_types = {
1997                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
1998                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
1999                 /* void (*)(int a, unsigned int !!!) */
2000                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2001                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2002                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
2003                 BTF_END_RAW,
2004         },
2005         .str_sec = "\0a\0!!!",
2006         .str_sec_size = sizeof("\0a\0!!!"),
2007         .map_type = BPF_MAP_TYPE_ARRAY,
2008         .map_name = "func_proto_type_check_btf",
2009         .key_size = sizeof(int),
2010         .value_size = sizeof(int),
2011         .key_type_id = 1,
2012         .value_type_id = 1,
2013         .max_entries = 4,
2014         .btf_load_err = true,
2015         .err_str = "Invalid arg#2",
2016 },
2017
2018 {
2019         .descr = "func proto (Invalid return type)",
2020         .raw_types = {
2021                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2022                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2023                 /* <bad_ret_type> (*)(int, unsigned int) */
2024                 BTF_FUNC_PROTO_ENC(100, 2),                     /* [3] */
2025                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
2026                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
2027                 BTF_END_RAW,
2028         },
2029         .str_sec = "",
2030         .str_sec_size = sizeof(""),
2031         .map_type = BPF_MAP_TYPE_ARRAY,
2032         .map_name = "func_proto_type_check_btf",
2033         .key_size = sizeof(int),
2034         .value_size = sizeof(int),
2035         .key_type_id = 1,
2036         .value_type_id = 1,
2037         .max_entries = 4,
2038         .btf_load_err = true,
2039         .err_str = "Invalid return type",
2040 },
2041
2042 {
2043         .descr = "func proto (with func name)",
2044         .raw_types = {
2045                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2046                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2047                 /* void func_proto(int, unsigned int) */
2048                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_FUNC_PROTO, 0, 2), 0),     /* [3] */
2049                         BTF_FUNC_PROTO_ARG_ENC(0, 1),
2050                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
2051                 BTF_END_RAW,
2052         },
2053         .str_sec = "\0func_proto",
2054         .str_sec_size = sizeof("\0func_proto"),
2055         .map_type = BPF_MAP_TYPE_ARRAY,
2056         .map_name = "func_proto_type_check_btf",
2057         .key_size = sizeof(int),
2058         .value_size = sizeof(int),
2059         .key_type_id = 1,
2060         .value_type_id = 1,
2061         .max_entries = 4,
2062         .btf_load_err = true,
2063         .err_str = "Invalid name",
2064 },
2065
2066 {
2067         .descr = "func proto (const void arg)",
2068         .raw_types = {
2069                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2070                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2071                 /* void (*)(const void) */
2072                 BTF_FUNC_PROTO_ENC(0, 1),                       /* [3] */
2073                         BTF_FUNC_PROTO_ARG_ENC(0, 4),
2074                 BTF_CONST_ENC(0),                               /* [4] */
2075                 BTF_END_RAW,
2076         },
2077         .str_sec = "",
2078         .str_sec_size = sizeof(""),
2079         .map_type = BPF_MAP_TYPE_ARRAY,
2080         .map_name = "func_proto_type_check_btf",
2081         .key_size = sizeof(int),
2082         .value_size = sizeof(int),
2083         .key_type_id = 1,
2084         .value_type_id = 1,
2085         .max_entries = 4,
2086         .btf_load_err = true,
2087         .err_str = "Invalid arg#1",
2088 },
2089
2090 {
2091         .descr = "func (void func(int a, unsigned int b))",
2092         .raw_types = {
2093                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2094                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2095                 /* void (*)(int a, unsigned int b) */
2096                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2097                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2098                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
2099                 /* void func(int a, unsigned int b) */
2100                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [4] */
2101                 BTF_END_RAW,
2102         },
2103         .str_sec = "\0a\0b\0func",
2104         .str_sec_size = sizeof("\0a\0b\0func"),
2105         .map_type = BPF_MAP_TYPE_ARRAY,
2106         .map_name = "func_type_check_btf",
2107         .key_size = sizeof(int),
2108         .value_size = sizeof(int),
2109         .key_type_id = 1,
2110         .value_type_id = 1,
2111         .max_entries = 4,
2112 },
2113
2114 {
2115         .descr = "func (No func name)",
2116         .raw_types = {
2117                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2118                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2119                 /* void (*)(int a, unsigned int b) */
2120                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2121                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2122                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
2123                 /* void <no_name>(int a, unsigned int b) */
2124                 BTF_FUNC_ENC(0, 3),                             /* [4] */
2125                 BTF_END_RAW,
2126         },
2127         .str_sec = "\0a\0b",
2128         .str_sec_size = sizeof("\0a\0b"),
2129         .map_type = BPF_MAP_TYPE_ARRAY,
2130         .map_name = "func_type_check_btf",
2131         .key_size = sizeof(int),
2132         .value_size = sizeof(int),
2133         .key_type_id = 1,
2134         .value_type_id = 1,
2135         .max_entries = 4,
2136         .btf_load_err = true,
2137         .err_str = "Invalid name",
2138 },
2139
2140 {
2141         .descr = "func (Invalid func name)",
2142         .raw_types = {
2143                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2144                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2145                 /* void (*)(int a, unsigned int b) */
2146                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2147                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2148                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
2149                 /* void !!!(int a, unsigned int b) */
2150                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [4] */
2151                 BTF_END_RAW,
2152         },
2153         .str_sec = "\0a\0b\0!!!",
2154         .str_sec_size = sizeof("\0a\0b\0!!!"),
2155         .map_type = BPF_MAP_TYPE_ARRAY,
2156         .map_name = "func_type_check_btf",
2157         .key_size = sizeof(int),
2158         .value_size = sizeof(int),
2159         .key_type_id = 1,
2160         .value_type_id = 1,
2161         .max_entries = 4,
2162         .btf_load_err = true,
2163         .err_str = "Invalid name",
2164 },
2165
2166 {
2167         .descr = "func (Some arg has no name)",
2168         .raw_types = {
2169                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2170                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2171                 /* void (*)(int a, unsigned int) */
2172                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2173                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2174                         BTF_FUNC_PROTO_ARG_ENC(0, 2),
2175                 /* void func(int a, unsigned int) */
2176                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [4] */
2177                 BTF_END_RAW,
2178         },
2179         .str_sec = "\0a\0func",
2180         .str_sec_size = sizeof("\0a\0func"),
2181         .map_type = BPF_MAP_TYPE_ARRAY,
2182         .map_name = "func_type_check_btf",
2183         .key_size = sizeof(int),
2184         .value_size = sizeof(int),
2185         .key_type_id = 1,
2186         .value_type_id = 1,
2187         .max_entries = 4,
2188         .btf_load_err = true,
2189         .err_str = "Invalid arg#2",
2190 },
2191
2192 {
2193         .descr = "func (Non zero vlen)",
2194         .raw_types = {
2195                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2196                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),               /* [2] */
2197                 /* void (*)(int a, unsigned int b) */
2198                 BTF_FUNC_PROTO_ENC(0, 2),                       /* [3] */
2199                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
2200                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
2201                 /* void func(int a, unsigned int b) */
2202                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_FUNC, 0, 2), 3),   /* [4] */
2203                 BTF_END_RAW,
2204         },
2205         .str_sec = "\0a\0b\0func",
2206         .str_sec_size = sizeof("\0a\0b\0func"),
2207         .map_type = BPF_MAP_TYPE_ARRAY,
2208         .map_name = "func_type_check_btf",
2209         .key_size = sizeof(int),
2210         .value_size = sizeof(int),
2211         .key_type_id = 1,
2212         .value_type_id = 1,
2213         .max_entries = 4,
2214         .btf_load_err = true,
2215         .err_str = "vlen != 0",
2216 },
2217
2218 {
2219         .descr = "func (Not referring to FUNC_PROTO)",
2220         .raw_types = {
2221                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),  /* [1] */
2222                 BTF_FUNC_ENC(NAME_TBD, 1),                      /* [2] */
2223                 BTF_END_RAW,
2224         },
2225         .str_sec = "\0func",
2226         .str_sec_size = sizeof("\0func"),
2227         .map_type = BPF_MAP_TYPE_ARRAY,
2228         .map_name = "func_type_check_btf",
2229         .key_size = sizeof(int),
2230         .value_size = sizeof(int),
2231         .key_type_id = 1,
2232         .value_type_id = 1,
2233         .max_entries = 4,
2234         .btf_load_err = true,
2235         .err_str = "Invalid type_id",
2236 },
2237
2238 {
2239         .descr = "invalid int kind_flag",
2240         .raw_types = {
2241                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2242                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_INT, 1, 0), 4),   /* [2] */
2243                 BTF_INT_ENC(0, 0, 32),
2244                 BTF_END_RAW,
2245         },
2246         BTF_STR_SEC(""),
2247         .map_type = BPF_MAP_TYPE_ARRAY,
2248         .map_name = "int_type_check_btf",
2249         .key_size = sizeof(int),
2250         .value_size = sizeof(int),
2251         .key_type_id = 1,
2252         .value_type_id = 1,
2253         .max_entries = 4,
2254         .btf_load_err = true,
2255         .err_str = "Invalid btf_info kind_flag",
2256 },
2257
2258 {
2259         .descr = "invalid ptr kind_flag",
2260         .raw_types = {
2261                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2262                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_PTR, 1, 0), 1),   /* [2] */
2263                 BTF_END_RAW,
2264         },
2265         BTF_STR_SEC(""),
2266         .map_type = BPF_MAP_TYPE_ARRAY,
2267         .map_name = "ptr_type_check_btf",
2268         .key_size = sizeof(int),
2269         .value_size = sizeof(int),
2270         .key_type_id = 1,
2271         .value_type_id = 1,
2272         .max_entries = 4,
2273         .btf_load_err = true,
2274         .err_str = "Invalid btf_info kind_flag",
2275 },
2276
2277 {
2278         .descr = "invalid array kind_flag",
2279         .raw_types = {
2280                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2281                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ARRAY, 1, 0), 0), /* [2] */
2282                 BTF_ARRAY_ENC(1, 1, 1),
2283                 BTF_END_RAW,
2284         },
2285         BTF_STR_SEC(""),
2286         .map_type = BPF_MAP_TYPE_ARRAY,
2287         .map_name = "array_type_check_btf",
2288         .key_size = sizeof(int),
2289         .value_size = sizeof(int),
2290         .key_type_id = 1,
2291         .value_type_id = 1,
2292         .max_entries = 4,
2293         .btf_load_err = true,
2294         .err_str = "Invalid btf_info kind_flag",
2295 },
2296
2297 {
2298         .descr = "invalid enum kind_flag",
2299         .raw_types = {
2300                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2301                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 1, 1), 4),  /* [2] */
2302                 BTF_ENUM_ENC(NAME_TBD, 0),
2303                 BTF_END_RAW,
2304         },
2305         BTF_STR_SEC("\0A"),
2306         .map_type = BPF_MAP_TYPE_ARRAY,
2307         .map_name = "enum_type_check_btf",
2308         .key_size = sizeof(int),
2309         .value_size = sizeof(int),
2310         .key_type_id = 1,
2311         .value_type_id = 1,
2312         .max_entries = 4,
2313         .btf_load_err = true,
2314         .err_str = "Invalid btf_info kind_flag",
2315 },
2316
2317 {
2318         .descr = "valid fwd kind_flag",
2319         .raw_types = {
2320                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2321                 BTF_TYPE_ENC(NAME_TBD,
2322                              BTF_INFO_ENC(BTF_KIND_FWD, 1, 0), 0),      /* [2] */
2323                 BTF_END_RAW,
2324         },
2325         BTF_STR_SEC("\0A"),
2326         .map_type = BPF_MAP_TYPE_ARRAY,
2327         .map_name = "fwd_type_check_btf",
2328         .key_size = sizeof(int),
2329         .value_size = sizeof(int),
2330         .key_type_id = 1,
2331         .value_type_id = 1,
2332         .max_entries = 4,
2333 },
2334
2335 {
2336         .descr = "invalid typedef kind_flag",
2337         .raw_types = {
2338                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2339                 BTF_TYPE_ENC(NAME_TBD,
2340                              BTF_INFO_ENC(BTF_KIND_TYPEDEF, 1, 0), 1),  /* [2] */
2341                 BTF_END_RAW,
2342         },
2343         BTF_STR_SEC("\0A"),
2344         .map_type = BPF_MAP_TYPE_ARRAY,
2345         .map_name = "typedef_type_check_btf",
2346         .key_size = sizeof(int),
2347         .value_size = sizeof(int),
2348         .key_type_id = 1,
2349         .value_type_id = 1,
2350         .max_entries = 4,
2351         .btf_load_err = true,
2352         .err_str = "Invalid btf_info kind_flag",
2353 },
2354
2355 {
2356         .descr = "invalid volatile kind_flag",
2357         .raw_types = {
2358                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2359                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_VOLATILE, 1, 0), 1),      /* [2] */
2360                 BTF_END_RAW,
2361         },
2362         BTF_STR_SEC(""),
2363         .map_type = BPF_MAP_TYPE_ARRAY,
2364         .map_name = "volatile_type_check_btf",
2365         .key_size = sizeof(int),
2366         .value_size = sizeof(int),
2367         .key_type_id = 1,
2368         .value_type_id = 1,
2369         .max_entries = 4,
2370         .btf_load_err = true,
2371         .err_str = "Invalid btf_info kind_flag",
2372 },
2373
2374 {
2375         .descr = "invalid const kind_flag",
2376         .raw_types = {
2377                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2378                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 1, 0), 1), /* [2] */
2379                 BTF_END_RAW,
2380         },
2381         BTF_STR_SEC(""),
2382         .map_type = BPF_MAP_TYPE_ARRAY,
2383         .map_name = "const_type_check_btf",
2384         .key_size = sizeof(int),
2385         .value_size = sizeof(int),
2386         .key_type_id = 1,
2387         .value_type_id = 1,
2388         .max_entries = 4,
2389         .btf_load_err = true,
2390         .err_str = "Invalid btf_info kind_flag",
2391 },
2392
2393 {
2394         .descr = "invalid restrict kind_flag",
2395         .raw_types = {
2396                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2397                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_RESTRICT, 1, 0), 1),      /* [2] */
2398                 BTF_END_RAW,
2399         },
2400         BTF_STR_SEC(""),
2401         .map_type = BPF_MAP_TYPE_ARRAY,
2402         .map_name = "restrict_type_check_btf",
2403         .key_size = sizeof(int),
2404         .value_size = sizeof(int),
2405         .key_type_id = 1,
2406         .value_type_id = 1,
2407         .max_entries = 4,
2408         .btf_load_err = true,
2409         .err_str = "Invalid btf_info kind_flag",
2410 },
2411
2412 {
2413         .descr = "invalid func kind_flag",
2414         .raw_types = {
2415                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2416                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_FUNC_PROTO, 0, 0), 0),    /* [2] */
2417                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_FUNC, 1, 0), 2),   /* [3] */
2418                 BTF_END_RAW,
2419         },
2420         BTF_STR_SEC("\0A"),
2421         .map_type = BPF_MAP_TYPE_ARRAY,
2422         .map_name = "func_type_check_btf",
2423         .key_size = sizeof(int),
2424         .value_size = sizeof(int),
2425         .key_type_id = 1,
2426         .value_type_id = 1,
2427         .max_entries = 4,
2428         .btf_load_err = true,
2429         .err_str = "Invalid btf_info kind_flag",
2430 },
2431
2432 {
2433         .descr = "invalid func_proto kind_flag",
2434         .raw_types = {
2435                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2436                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_FUNC_PROTO, 1, 0), 0),    /* [2] */
2437                 BTF_END_RAW,
2438         },
2439         BTF_STR_SEC(""),
2440         .map_type = BPF_MAP_TYPE_ARRAY,
2441         .map_name = "func_proto_type_check_btf",
2442         .key_size = sizeof(int),
2443         .value_size = sizeof(int),
2444         .key_type_id = 1,
2445         .value_type_id = 1,
2446         .max_entries = 4,
2447         .btf_load_err = true,
2448         .err_str = "Invalid btf_info kind_flag",
2449 },
2450
2451 {
2452         .descr = "valid struct, kind_flag, bitfield_size = 0",
2453         .raw_types = {
2454                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2455                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 8),        /* [2] */
2456                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(0, 0)),
2457                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(0, 32)),
2458                 BTF_END_RAW,
2459         },
2460         BTF_STR_SEC("\0A\0B"),
2461         .map_type = BPF_MAP_TYPE_ARRAY,
2462         .map_name = "struct_type_check_btf",
2463         .key_size = sizeof(int),
2464         .value_size = sizeof(int),
2465         .key_type_id = 1,
2466         .value_type_id = 1,
2467         .max_entries = 4,
2468 },
2469
2470 {
2471         .descr = "valid struct, kind_flag, int member, bitfield_size != 0",
2472         .raw_types = {
2473                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2474                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),        /* [2] */
2475                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(4, 0)),
2476                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(4, 4)),
2477                 BTF_END_RAW,
2478         },
2479         BTF_STR_SEC("\0A\0B"),
2480         .map_type = BPF_MAP_TYPE_ARRAY,
2481         .map_name = "struct_type_check_btf",
2482         .key_size = sizeof(int),
2483         .value_size = sizeof(int),
2484         .key_type_id = 1,
2485         .value_type_id = 1,
2486         .max_entries = 4,
2487 },
2488
2489 {
2490         .descr = "valid union, kind_flag, int member, bitfield_size != 0",
2491         .raw_types = {
2492                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2493                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 1, 2), 4), /* [2] */
2494                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(4, 0)),
2495                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(4, 0)),
2496                 BTF_END_RAW,
2497         },
2498         BTF_STR_SEC("\0A\0B"),
2499         .map_type = BPF_MAP_TYPE_ARRAY,
2500         .map_name = "union_type_check_btf",
2501         .key_size = sizeof(int),
2502         .value_size = sizeof(int),
2503         .key_type_id = 1,
2504         .value_type_id = 1,
2505         .max_entries = 4,
2506 },
2507
2508 {
2509         .descr = "valid struct, kind_flag, enum member, bitfield_size != 0",
2510         .raw_types = {
2511                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2512                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),  /* [2] */
2513                 BTF_ENUM_ENC(NAME_TBD, 0),
2514                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),/* [3] */
2515                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(4, 0)),
2516                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(4, 4)),
2517                 BTF_END_RAW,
2518         },
2519         BTF_STR_SEC("\0A\0B\0C"),
2520         .map_type = BPF_MAP_TYPE_ARRAY,
2521         .map_name = "struct_type_check_btf",
2522         .key_size = sizeof(int),
2523         .value_size = sizeof(int),
2524         .key_type_id = 1,
2525         .value_type_id = 1,
2526         .max_entries = 4,
2527 },
2528
2529 {
2530         .descr = "valid union, kind_flag, enum member, bitfield_size != 0",
2531         .raw_types = {
2532                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2533                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),  /* [2] */
2534                 BTF_ENUM_ENC(NAME_TBD, 0),
2535                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 1, 2), 4), /* [3] */
2536                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(4, 0)),
2537                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(4, 0)),
2538                 BTF_END_RAW,
2539         },
2540         BTF_STR_SEC("\0A\0B\0C"),
2541         .map_type = BPF_MAP_TYPE_ARRAY,
2542         .map_name = "union_type_check_btf",
2543         .key_size = sizeof(int),
2544         .value_size = sizeof(int),
2545         .key_type_id = 1,
2546         .value_type_id = 1,
2547         .max_entries = 4,
2548 },
2549
2550 {
2551         .descr = "valid struct, kind_flag, typedef member, bitfield_size != 0",
2552         .raw_types = {
2553                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2554                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),  /* [2] */
2555                 BTF_ENUM_ENC(NAME_TBD, 0),
2556                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),/* [3] */
2557                 BTF_MEMBER_ENC(NAME_TBD, 4, BTF_MEMBER_OFFSET(4, 0)),
2558                 BTF_MEMBER_ENC(NAME_TBD, 5, BTF_MEMBER_OFFSET(4, 4)),
2559                 BTF_TYPEDEF_ENC(NAME_TBD, 1),                           /* [4] */
2560                 BTF_TYPEDEF_ENC(NAME_TBD, 2),                           /* [5] */
2561                 BTF_END_RAW,
2562         },
2563         BTF_STR_SEC("\0A\0B\0C\0D\0E"),
2564         .map_type = BPF_MAP_TYPE_ARRAY,
2565         .map_name = "struct_type_check_btf",
2566         .key_size = sizeof(int),
2567         .value_size = sizeof(int),
2568         .key_type_id = 1,
2569         .value_type_id = 1,
2570         .max_entries = 4,
2571 },
2572
2573 {
2574         .descr = "valid union, kind_flag, typedef member, bitfield_size != 0",
2575         .raw_types = {
2576                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2577                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),  /* [2] */
2578                 BTF_ENUM_ENC(NAME_TBD, 0),
2579                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 1, 2), 4), /* [3] */
2580                 BTF_MEMBER_ENC(NAME_TBD, 4, BTF_MEMBER_OFFSET(4, 0)),
2581                 BTF_MEMBER_ENC(NAME_TBD, 5, BTF_MEMBER_OFFSET(4, 0)),
2582                 BTF_TYPEDEF_ENC(NAME_TBD, 1),                           /* [4] */
2583                 BTF_TYPEDEF_ENC(NAME_TBD, 2),                           /* [5] */
2584                 BTF_END_RAW,
2585         },
2586         BTF_STR_SEC("\0A\0B\0C\0D\0E"),
2587         .map_type = BPF_MAP_TYPE_ARRAY,
2588         .map_name = "union_type_check_btf",
2589         .key_size = sizeof(int),
2590         .value_size = sizeof(int),
2591         .key_type_id = 1,
2592         .value_type_id = 1,
2593         .max_entries = 4,
2594 },
2595
2596 {
2597         .descr = "invalid struct, kind_flag, bitfield_size greater than struct size",
2598         .raw_types = {
2599                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2600                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),        /* [2] */
2601                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(20, 0)),
2602                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(20, 20)),
2603                 BTF_END_RAW,
2604         },
2605         BTF_STR_SEC("\0A\0B"),
2606         .map_type = BPF_MAP_TYPE_ARRAY,
2607         .map_name = "struct_type_check_btf",
2608         .key_size = sizeof(int),
2609         .value_size = sizeof(int),
2610         .key_type_id = 1,
2611         .value_type_id = 1,
2612         .max_entries = 4,
2613         .btf_load_err = true,
2614         .err_str = "Member exceeds struct_size",
2615 },
2616
2617 {
2618         .descr = "invalid struct, kind_flag, bitfield base_type int not regular",
2619         .raw_types = {
2620                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2621                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 20, 4),                  /* [2] */
2622                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),        /* [3] */
2623                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(20, 0)),
2624                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(20, 20)),
2625                 BTF_END_RAW,
2626         },
2627         BTF_STR_SEC("\0A\0B"),
2628         .map_type = BPF_MAP_TYPE_ARRAY,
2629         .map_name = "struct_type_check_btf",
2630         .key_size = sizeof(int),
2631         .value_size = sizeof(int),
2632         .key_type_id = 1,
2633         .value_type_id = 1,
2634         .max_entries = 4,
2635         .btf_load_err = true,
2636         .err_str = "Invalid member base type",
2637 },
2638
2639 {
2640         .descr = "invalid struct, kind_flag, base_type int not regular",
2641         .raw_types = {
2642                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2643                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 12, 4),                  /* [2] */
2644                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 4),        /* [3] */
2645                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(8, 0)),
2646                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(8, 8)),
2647                 BTF_END_RAW,
2648         },
2649         BTF_STR_SEC("\0A\0B"),
2650         .map_type = BPF_MAP_TYPE_ARRAY,
2651         .map_name = "struct_type_check_btf",
2652         .key_size = sizeof(int),
2653         .value_size = sizeof(int),
2654         .key_type_id = 1,
2655         .value_type_id = 1,
2656         .max_entries = 4,
2657         .btf_load_err = true,
2658         .err_str = "Invalid member base type",
2659 },
2660
2661 {
2662         .descr = "invalid union, kind_flag, bitfield_size greater than struct size",
2663         .raw_types = {
2664                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),          /* [1] */
2665                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 1, 2), 2), /* [2] */
2666                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(8, 0)),
2667                 BTF_MEMBER_ENC(NAME_TBD, 1, BTF_MEMBER_OFFSET(20, 0)),
2668                 BTF_END_RAW,
2669         },
2670         BTF_STR_SEC("\0A\0B"),
2671         .map_type = BPF_MAP_TYPE_ARRAY,
2672         .map_name = "union_type_check_btf",
2673         .key_size = sizeof(int),
2674         .value_size = sizeof(int),
2675         .key_type_id = 1,
2676         .value_type_id = 1,
2677         .max_entries = 4,
2678         .btf_load_err = true,
2679         .err_str = "Member exceeds struct_size",
2680 },
2681
2682 {
2683         .descr = "invalid struct, kind_flag, int member, bitfield_size = 0, wrong byte alignment",
2684         .raw_types = {
2685                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2686                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [2] */
2687                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 12),       /* [3] */
2688                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 0)),
2689                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 36)),
2690                 BTF_END_RAW,
2691         },
2692         BTF_STR_SEC("\0A\0B"),
2693         .map_type = BPF_MAP_TYPE_ARRAY,
2694         .map_name = "struct_type_check_btf",
2695         .key_size = sizeof(int),
2696         .value_size = sizeof(int),
2697         .key_type_id = 1,
2698         .value_type_id = 1,
2699         .max_entries = 4,
2700         .btf_load_err = true,
2701         .err_str = "Invalid member offset",
2702 },
2703
2704 {
2705         .descr = "invalid struct, kind_flag, enum member, bitfield_size = 0, wrong byte alignment",
2706         .raw_types = {
2707                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2708                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [2] */
2709                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),  /* [2] */
2710                 BTF_ENUM_ENC(NAME_TBD, 0),
2711                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 2), 12),       /* [3] */
2712                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 0)),
2713                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 36)),
2714                 BTF_END_RAW,
2715         },
2716         BTF_STR_SEC("\0A\0B\0C"),
2717         .map_type = BPF_MAP_TYPE_ARRAY,
2718         .map_name = "struct_type_check_btf",
2719         .key_size = sizeof(int),
2720         .value_size = sizeof(int),
2721         .key_type_id = 1,
2722         .value_type_id = 1,
2723         .max_entries = 4,
2724         .btf_load_err = true,
2725         .err_str = "Invalid member offset",
2726 },
2727
2728 {
2729         .descr = "128-bit int",
2730         .raw_types = {
2731                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2732                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 128, 16),                /* [2] */
2733                 BTF_END_RAW,
2734         },
2735         BTF_STR_SEC("\0A"),
2736         .map_type = BPF_MAP_TYPE_ARRAY,
2737         .map_name = "int_type_check_btf",
2738         .key_size = sizeof(int),
2739         .value_size = sizeof(int),
2740         .key_type_id = 1,
2741         .value_type_id = 1,
2742         .max_entries = 4,
2743 },
2744
2745 {
2746         .descr = "struct, 128-bit int member",
2747         .raw_types = {
2748                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2749                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 128, 16),                /* [2] */
2750                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 16),       /* [3] */
2751                 BTF_MEMBER_ENC(NAME_TBD, 2, 0),
2752                 BTF_END_RAW,
2753         },
2754         BTF_STR_SEC("\0A"),
2755         .map_type = BPF_MAP_TYPE_ARRAY,
2756         .map_name = "struct_type_check_btf",
2757         .key_size = sizeof(int),
2758         .value_size = sizeof(int),
2759         .key_type_id = 1,
2760         .value_type_id = 1,
2761         .max_entries = 4,
2762 },
2763
2764 {
2765         .descr = "struct, 120-bit int member bitfield",
2766         .raw_types = {
2767                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2768                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 120, 16),                /* [2] */
2769                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 1), 16),       /* [3] */
2770                 BTF_MEMBER_ENC(NAME_TBD, 2, 0),
2771                 BTF_END_RAW,
2772         },
2773         BTF_STR_SEC("\0A"),
2774         .map_type = BPF_MAP_TYPE_ARRAY,
2775         .map_name = "struct_type_check_btf",
2776         .key_size = sizeof(int),
2777         .value_size = sizeof(int),
2778         .key_type_id = 1,
2779         .value_type_id = 1,
2780         .max_entries = 4,
2781 },
2782
2783 {
2784         .descr = "struct, kind_flag, 128-bit int member",
2785         .raw_types = {
2786                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2787                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 128, 16),                /* [2] */
2788                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 1), 16),       /* [3] */
2789                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 0)),
2790                 BTF_END_RAW,
2791         },
2792         BTF_STR_SEC("\0A"),
2793         .map_type = BPF_MAP_TYPE_ARRAY,
2794         .map_name = "struct_type_check_btf",
2795         .key_size = sizeof(int),
2796         .value_size = sizeof(int),
2797         .key_type_id = 1,
2798         .value_type_id = 1,
2799         .max_entries = 4,
2800 },
2801
2802 {
2803         .descr = "struct, kind_flag, 120-bit int member bitfield",
2804         .raw_types = {
2805                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),                  /* [1] */
2806                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 128, 16),                /* [2] */
2807                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 1), 16),       /* [3] */
2808                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(120, 0)),
2809                 BTF_END_RAW,
2810         },
2811         BTF_STR_SEC("\0A"),
2812         .map_type = BPF_MAP_TYPE_ARRAY,
2813         .map_name = "struct_type_check_btf",
2814         .key_size = sizeof(int),
2815         .value_size = sizeof(int),
2816         .key_type_id = 1,
2817         .value_type_id = 1,
2818         .max_entries = 4,
2819 },
2820
2821 }; /* struct btf_raw_test raw_tests[] */
2822
2823 static const char *get_next_str(const char *start, const char *end)
2824 {
2825         return start < end - 1 ? start + 1 : NULL;
2826 }
2827
2828 static int get_raw_sec_size(const __u32 *raw_types)
2829 {
2830         int i;
2831
2832         for (i = MAX_NR_RAW_U32 - 1;
2833              i >= 0 && raw_types[i] != BTF_END_RAW;
2834              i--)
2835                 ;
2836
2837         return i < 0 ? i : i * sizeof(raw_types[0]);
2838 }
2839
2840 static void *btf_raw_create(const struct btf_header *hdr,
2841                             const __u32 *raw_types,
2842                             const char *str,
2843                             unsigned int str_sec_size,
2844                             unsigned int *btf_size,
2845                             const char **ret_next_str)
2846 {
2847         const char *next_str = str, *end_str = str + str_sec_size;
2848         const char **strs_idx = NULL, **tmp_strs_idx;
2849         int strs_cap = 0, strs_cnt = 0, next_str_idx = 0;
2850         unsigned int size_needed, offset;
2851         struct btf_header *ret_hdr;
2852         int i, type_sec_size, err = 0;
2853         uint32_t *ret_types;
2854         void *raw_btf = NULL;
2855
2856         type_sec_size = get_raw_sec_size(raw_types);
2857         if (CHECK(type_sec_size < 0, "Cannot get nr_raw_types"))
2858                 return NULL;
2859
2860         size_needed = sizeof(*hdr) + type_sec_size + str_sec_size;
2861         raw_btf = malloc(size_needed);
2862         if (CHECK(!raw_btf, "Cannot allocate memory for raw_btf"))
2863                 return NULL;
2864
2865         /* Copy header */
2866         memcpy(raw_btf, hdr, sizeof(*hdr));
2867         offset = sizeof(*hdr);
2868
2869         /* Index strings */
2870         while ((next_str = get_next_str(next_str, end_str))) {
2871                 if (strs_cnt == strs_cap) {
2872                         strs_cap += max(16, strs_cap / 2);
2873                         tmp_strs_idx = realloc(strs_idx,
2874                                                sizeof(*strs_idx) * strs_cap);
2875                         if (CHECK(!tmp_strs_idx,
2876                                   "Cannot allocate memory for strs_idx")) {
2877                                 err = -1;
2878                                 goto done;
2879                         }
2880                         strs_idx = tmp_strs_idx;
2881                 }
2882                 strs_idx[strs_cnt++] = next_str;
2883                 next_str += strlen(next_str);
2884         }
2885
2886         /* Copy type section */
2887         ret_types = raw_btf + offset;
2888         for (i = 0; i < type_sec_size / sizeof(raw_types[0]); i++) {
2889                 if (raw_types[i] == NAME_TBD) {
2890                         if (CHECK(next_str_idx == strs_cnt,
2891                                   "Error in getting next_str #%d",
2892                                   next_str_idx)) {
2893                                 err = -1;
2894                                 goto done;
2895                         }
2896                         ret_types[i] = strs_idx[next_str_idx++] - str;
2897                 } else if (IS_NAME_NTH(raw_types[i])) {
2898                         int idx = GET_NAME_NTH_IDX(raw_types[i]);
2899
2900                         if (CHECK(idx <= 0 || idx > strs_cnt,
2901                                   "Error getting string #%d, strs_cnt:%d",
2902                                   idx, strs_cnt)) {
2903                                 err = -1;
2904                                 goto done;
2905                         }
2906                         ret_types[i] = strs_idx[idx-1] - str;
2907                 } else {
2908                         ret_types[i] = raw_types[i];
2909                 }
2910         }
2911         offset += type_sec_size;
2912
2913         /* Copy string section */
2914         memcpy(raw_btf + offset, str, str_sec_size);
2915
2916         ret_hdr = (struct btf_header *)raw_btf;
2917         ret_hdr->type_len = type_sec_size;
2918         ret_hdr->str_off = type_sec_size;
2919         ret_hdr->str_len = str_sec_size;
2920
2921         *btf_size = size_needed;
2922         if (ret_next_str)
2923                 *ret_next_str =
2924                         next_str_idx < strs_cnt ? strs_idx[next_str_idx] : NULL;
2925
2926 done:
2927         if (err) {
2928                 if (raw_btf)
2929                         free(raw_btf);
2930                 if (strs_idx)
2931                         free(strs_idx);
2932                 return NULL;
2933         }
2934         return raw_btf;
2935 }
2936
2937 static int do_test_raw(unsigned int test_num)
2938 {
2939         struct btf_raw_test *test = &raw_tests[test_num - 1];
2940         struct bpf_create_map_attr create_attr = {};
2941         int map_fd = -1, btf_fd = -1;
2942         unsigned int raw_btf_size;
2943         struct btf_header *hdr;
2944         void *raw_btf;
2945         int err;
2946
2947         fprintf(stderr, "BTF raw test[%u] (%s): ", test_num, test->descr);
2948         raw_btf = btf_raw_create(&hdr_tmpl,
2949                                  test->raw_types,
2950                                  test->str_sec,
2951                                  test->str_sec_size,
2952                                  &raw_btf_size, NULL);
2953
2954         if (!raw_btf)
2955                 return -1;
2956
2957         hdr = raw_btf;
2958
2959         hdr->hdr_len = (int)hdr->hdr_len + test->hdr_len_delta;
2960         hdr->type_off = (int)hdr->type_off + test->type_off_delta;
2961         hdr->str_off = (int)hdr->str_off + test->str_off_delta;
2962         hdr->str_len = (int)hdr->str_len + test->str_len_delta;
2963
2964         *btf_log_buf = '\0';
2965         btf_fd = bpf_load_btf(raw_btf, raw_btf_size,
2966                               btf_log_buf, BTF_LOG_BUF_SIZE,
2967                               args.always_log);
2968         free(raw_btf);
2969
2970         err = ((btf_fd == -1) != test->btf_load_err);
2971         if (CHECK(err, "btf_fd:%d test->btf_load_err:%u",
2972                   btf_fd, test->btf_load_err) ||
2973             CHECK(test->err_str && !strstr(btf_log_buf, test->err_str),
2974                   "expected err_str:%s", test->err_str)) {
2975                 err = -1;
2976                 goto done;
2977         }
2978
2979         if (err || btf_fd == -1)
2980                 goto done;
2981
2982         create_attr.name = test->map_name;
2983         create_attr.map_type = test->map_type;
2984         create_attr.key_size = test->key_size;
2985         create_attr.value_size = test->value_size;
2986         create_attr.max_entries = test->max_entries;
2987         create_attr.btf_fd = btf_fd;
2988         create_attr.btf_key_type_id = test->key_type_id;
2989         create_attr.btf_value_type_id = test->value_type_id;
2990
2991         map_fd = bpf_create_map_xattr(&create_attr);
2992
2993         err = ((map_fd == -1) != test->map_create_err);
2994         CHECK(err, "map_fd:%d test->map_create_err:%u",
2995               map_fd, test->map_create_err);
2996
2997 done:
2998         if (!err)
2999                 fprintf(stderr, "OK");
3000
3001         if (*btf_log_buf && (err || args.always_log))
3002                 fprintf(stderr, "\n%s", btf_log_buf);
3003
3004         if (btf_fd != -1)
3005                 close(btf_fd);
3006         if (map_fd != -1)
3007                 close(map_fd);
3008
3009         return err;
3010 }
3011
3012 static int test_raw(void)
3013 {
3014         unsigned int i;
3015         int err = 0;
3016
3017         if (args.raw_test_num)
3018                 return count_result(do_test_raw(args.raw_test_num));
3019
3020         for (i = 1; i <= ARRAY_SIZE(raw_tests); i++)
3021                 err |= count_result(do_test_raw(i));
3022
3023         return err;
3024 }
3025
3026 struct btf_get_info_test {
3027         const char *descr;
3028         const char *str_sec;
3029         __u32 raw_types[MAX_NR_RAW_U32];
3030         __u32 str_sec_size;
3031         int btf_size_delta;
3032         int (*special_test)(unsigned int test_num);
3033 };
3034
3035 static int test_big_btf_info(unsigned int test_num);
3036 static int test_btf_id(unsigned int test_num);
3037
3038 const struct btf_get_info_test get_info_tests[] = {
3039 {
3040         .descr = "== raw_btf_size+1",
3041         .raw_types = {
3042                 /* int */                               /* [1] */
3043                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
3044                 BTF_END_RAW,
3045         },
3046         .str_sec = "",
3047         .str_sec_size = sizeof(""),
3048         .btf_size_delta = 1,
3049 },
3050 {
3051         .descr = "== raw_btf_size-3",
3052         .raw_types = {
3053                 /* int */                               /* [1] */
3054                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
3055                 BTF_END_RAW,
3056         },
3057         .str_sec = "",
3058         .str_sec_size = sizeof(""),
3059         .btf_size_delta = -3,
3060 },
3061 {
3062         .descr = "Large bpf_btf_info",
3063         .raw_types = {
3064                 /* int */                               /* [1] */
3065                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
3066                 BTF_END_RAW,
3067         },
3068         .str_sec = "",
3069         .str_sec_size = sizeof(""),
3070         .special_test = test_big_btf_info,
3071 },
3072 {
3073         .descr = "BTF ID",
3074         .raw_types = {
3075                 /* int */                               /* [1] */
3076                 BTF_TYPE_INT_ENC(0, BTF_INT_SIGNED, 0, 32, 4),
3077                 /* unsigned int */                      /* [2] */
3078                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),
3079                 BTF_END_RAW,
3080         },
3081         .str_sec = "",
3082         .str_sec_size = sizeof(""),
3083         .special_test = test_btf_id,
3084 },
3085 };
3086
3087 static inline __u64 ptr_to_u64(const void *ptr)
3088 {
3089         return (__u64)(unsigned long)ptr;
3090 }
3091
3092 static int test_big_btf_info(unsigned int test_num)
3093 {
3094         const struct btf_get_info_test *test = &get_info_tests[test_num - 1];
3095         uint8_t *raw_btf = NULL, *user_btf = NULL;
3096         unsigned int raw_btf_size;
3097         struct {
3098                 struct bpf_btf_info info;
3099                 uint64_t garbage;
3100         } info_garbage;
3101         struct bpf_btf_info *info;
3102         int btf_fd = -1, err;
3103         uint32_t info_len;
3104
3105         raw_btf = btf_raw_create(&hdr_tmpl,
3106                                  test->raw_types,
3107                                  test->str_sec,
3108                                  test->str_sec_size,
3109                                  &raw_btf_size, NULL);
3110
3111         if (!raw_btf)
3112                 return -1;
3113
3114         *btf_log_buf = '\0';
3115
3116         user_btf = malloc(raw_btf_size);
3117         if (CHECK(!user_btf, "!user_btf")) {
3118                 err = -1;
3119                 goto done;
3120         }
3121
3122         btf_fd = bpf_load_btf(raw_btf, raw_btf_size,
3123                               btf_log_buf, BTF_LOG_BUF_SIZE,
3124                               args.always_log);
3125         if (CHECK(btf_fd == -1, "errno:%d", errno)) {
3126                 err = -1;
3127                 goto done;
3128         }
3129
3130         /*
3131          * GET_INFO should error out if the userspace info
3132          * has non zero tailing bytes.
3133          */
3134         info = &info_garbage.info;
3135         memset(info, 0, sizeof(*info));
3136         info_garbage.garbage = 0xdeadbeef;
3137         info_len = sizeof(info_garbage);
3138         info->btf = ptr_to_u64(user_btf);
3139         info->btf_size = raw_btf_size;
3140
3141         err = bpf_obj_get_info_by_fd(btf_fd, info, &info_len);
3142         if (CHECK(!err, "!err")) {
3143                 err = -1;
3144                 goto done;
3145         }
3146
3147         /*
3148          * GET_INFO should succeed even info_len is larger than
3149          * the kernel supported as long as tailing bytes are zero.
3150          * The kernel supported info len should also be returned
3151          * to userspace.
3152          */
3153         info_garbage.garbage = 0;
3154         err = bpf_obj_get_info_by_fd(btf_fd, info, &info_len);
3155         if (CHECK(err || info_len != sizeof(*info),
3156                   "err:%d errno:%d info_len:%u sizeof(*info):%lu",
3157                   err, errno, info_len, sizeof(*info))) {
3158                 err = -1;
3159                 goto done;
3160         }
3161
3162         fprintf(stderr, "OK");
3163
3164 done:
3165         if (*btf_log_buf && (err || args.always_log))
3166                 fprintf(stderr, "\n%s", btf_log_buf);
3167
3168         free(raw_btf);
3169         free(user_btf);
3170
3171         if (btf_fd != -1)
3172                 close(btf_fd);
3173
3174         return err;
3175 }
3176
3177 static int test_btf_id(unsigned int test_num)
3178 {
3179         const struct btf_get_info_test *test = &get_info_tests[test_num - 1];
3180         struct bpf_create_map_attr create_attr = {};
3181         uint8_t *raw_btf = NULL, *user_btf[2] = {};
3182         int btf_fd[2] = {-1, -1}, map_fd = -1;
3183         struct bpf_map_info map_info = {};
3184         struct bpf_btf_info info[2] = {};
3185         unsigned int raw_btf_size;
3186         uint32_t info_len;
3187         int err, i, ret;
3188
3189         raw_btf = btf_raw_create(&hdr_tmpl,
3190                                  test->raw_types,
3191                                  test->str_sec,
3192                                  test->str_sec_size,
3193                                  &raw_btf_size, NULL);
3194
3195         if (!raw_btf)
3196                 return -1;
3197
3198         *btf_log_buf = '\0';
3199
3200         for (i = 0; i < 2; i++) {
3201                 user_btf[i] = malloc(raw_btf_size);
3202                 if (CHECK(!user_btf[i], "!user_btf[%d]", i)) {
3203                         err = -1;
3204                         goto done;
3205                 }
3206                 info[i].btf = ptr_to_u64(user_btf[i]);
3207                 info[i].btf_size = raw_btf_size;
3208         }
3209
3210         btf_fd[0] = bpf_load_btf(raw_btf, raw_btf_size,
3211                                  btf_log_buf, BTF_LOG_BUF_SIZE,
3212                                  args.always_log);
3213         if (CHECK(btf_fd[0] == -1, "errno:%d", errno)) {
3214                 err = -1;
3215                 goto done;
3216         }
3217
3218         /* Test BPF_OBJ_GET_INFO_BY_ID on btf_id */
3219         info_len = sizeof(info[0]);
3220         err = bpf_obj_get_info_by_fd(btf_fd[0], &info[0], &info_len);
3221         if (CHECK(err, "errno:%d", errno)) {
3222                 err = -1;
3223                 goto done;
3224         }
3225
3226         btf_fd[1] = bpf_btf_get_fd_by_id(info[0].id);
3227         if (CHECK(btf_fd[1] == -1, "errno:%d", errno)) {
3228                 err = -1;
3229                 goto done;
3230         }
3231
3232         ret = 0;
3233         err = bpf_obj_get_info_by_fd(btf_fd[1], &info[1], &info_len);
3234         if (CHECK(err || info[0].id != info[1].id ||
3235                   info[0].btf_size != info[1].btf_size ||
3236                   (ret = memcmp(user_btf[0], user_btf[1], info[0].btf_size)),
3237                   "err:%d errno:%d id0:%u id1:%u btf_size0:%u btf_size1:%u memcmp:%d",
3238                   err, errno, info[0].id, info[1].id,
3239                   info[0].btf_size, info[1].btf_size, ret)) {
3240                 err = -1;
3241                 goto done;
3242         }
3243
3244         /* Test btf members in struct bpf_map_info */
3245         create_attr.name = "test_btf_id";
3246         create_attr.map_type = BPF_MAP_TYPE_ARRAY;
3247         create_attr.key_size = sizeof(int);
3248         create_attr.value_size = sizeof(unsigned int);
3249         create_attr.max_entries = 4;
3250         create_attr.btf_fd = btf_fd[0];
3251         create_attr.btf_key_type_id = 1;
3252         create_attr.btf_value_type_id = 2;
3253
3254         map_fd = bpf_create_map_xattr(&create_attr);
3255         if (CHECK(map_fd == -1, "errno:%d", errno)) {
3256                 err = -1;
3257                 goto done;
3258         }
3259
3260         info_len = sizeof(map_info);
3261         err = bpf_obj_get_info_by_fd(map_fd, &map_info, &info_len);
3262         if (CHECK(err || map_info.btf_id != info[0].id ||
3263                   map_info.btf_key_type_id != 1 || map_info.btf_value_type_id != 2,
3264                   "err:%d errno:%d info.id:%u btf_id:%u btf_key_type_id:%u btf_value_type_id:%u",
3265                   err, errno, info[0].id, map_info.btf_id, map_info.btf_key_type_id,
3266                   map_info.btf_value_type_id)) {
3267                 err = -1;
3268                 goto done;
3269         }
3270
3271         for (i = 0; i < 2; i++) {
3272                 close(btf_fd[i]);
3273                 btf_fd[i] = -1;
3274         }
3275
3276         /* Test BTF ID is removed from the kernel */
3277         btf_fd[0] = bpf_btf_get_fd_by_id(map_info.btf_id);
3278         if (CHECK(btf_fd[0] == -1, "errno:%d", errno)) {
3279                 err = -1;
3280                 goto done;
3281         }
3282         close(btf_fd[0]);
3283         btf_fd[0] = -1;
3284
3285         /* The map holds the last ref to BTF and its btf_id */
3286         close(map_fd);
3287         map_fd = -1;
3288         btf_fd[0] = bpf_btf_get_fd_by_id(map_info.btf_id);
3289         if (CHECK(btf_fd[0] != -1, "BTF lingers")) {
3290                 err = -1;
3291                 goto done;
3292         }
3293
3294         fprintf(stderr, "OK");
3295
3296 done:
3297         if (*btf_log_buf && (err || args.always_log))
3298                 fprintf(stderr, "\n%s", btf_log_buf);
3299
3300         free(raw_btf);
3301         if (map_fd != -1)
3302                 close(map_fd);
3303         for (i = 0; i < 2; i++) {
3304                 free(user_btf[i]);
3305                 if (btf_fd[i] != -1)
3306                         close(btf_fd[i]);
3307         }
3308
3309         return err;
3310 }
3311
3312 static int do_test_get_info(unsigned int test_num)
3313 {
3314         const struct btf_get_info_test *test = &get_info_tests[test_num - 1];
3315         unsigned int raw_btf_size, user_btf_size, expected_nbytes;
3316         uint8_t *raw_btf = NULL, *user_btf = NULL;
3317         struct bpf_btf_info info = {};
3318         int btf_fd = -1, err, ret;
3319         uint32_t info_len;
3320
3321         fprintf(stderr, "BTF GET_INFO test[%u] (%s): ",
3322                 test_num, test->descr);
3323
3324         if (test->special_test)
3325                 return test->special_test(test_num);
3326
3327         raw_btf = btf_raw_create(&hdr_tmpl,
3328                                  test->raw_types,
3329                                  test->str_sec,
3330                                  test->str_sec_size,
3331                                  &raw_btf_size, NULL);
3332
3333         if (!raw_btf)
3334                 return -1;
3335
3336         *btf_log_buf = '\0';
3337
3338         user_btf = malloc(raw_btf_size);
3339         if (CHECK(!user_btf, "!user_btf")) {
3340                 err = -1;
3341                 goto done;
3342         }
3343
3344         btf_fd = bpf_load_btf(raw_btf, raw_btf_size,
3345                               btf_log_buf, BTF_LOG_BUF_SIZE,
3346                               args.always_log);
3347         if (CHECK(btf_fd == -1, "errno:%d", errno)) {
3348                 err = -1;
3349                 goto done;
3350         }
3351
3352         user_btf_size = (int)raw_btf_size + test->btf_size_delta;
3353         expected_nbytes = min(raw_btf_size, user_btf_size);
3354         if (raw_btf_size > expected_nbytes)
3355                 memset(user_btf + expected_nbytes, 0xff,
3356                        raw_btf_size - expected_nbytes);
3357
3358         info_len = sizeof(info);
3359         info.btf = ptr_to_u64(user_btf);
3360         info.btf_size = user_btf_size;
3361
3362         ret = 0;
3363         err = bpf_obj_get_info_by_fd(btf_fd, &info, &info_len);
3364         if (CHECK(err || !info.id || info_len != sizeof(info) ||
3365                   info.btf_size != raw_btf_size ||
3366                   (ret = memcmp(raw_btf, user_btf, expected_nbytes)),
3367                   "err:%d errno:%d info.id:%u info_len:%u sizeof(info):%lu raw_btf_size:%u info.btf_size:%u expected_nbytes:%u memcmp:%d",
3368                   err, errno, info.id, info_len, sizeof(info),
3369                   raw_btf_size, info.btf_size, expected_nbytes, ret)) {
3370                 err = -1;
3371                 goto done;
3372         }
3373
3374         while (expected_nbytes < raw_btf_size) {
3375                 fprintf(stderr, "%u...", expected_nbytes);
3376                 if (CHECK(user_btf[expected_nbytes++] != 0xff,
3377                           "user_btf[%u]:%x != 0xff", expected_nbytes - 1,
3378                           user_btf[expected_nbytes - 1])) {
3379                         err = -1;
3380                         goto done;
3381                 }
3382         }
3383
3384         fprintf(stderr, "OK");
3385
3386 done:
3387         if (*btf_log_buf && (err || args.always_log))
3388                 fprintf(stderr, "\n%s", btf_log_buf);
3389
3390         free(raw_btf);
3391         free(user_btf);
3392
3393         if (btf_fd != -1)
3394                 close(btf_fd);
3395
3396         return err;
3397 }
3398
3399 static int test_get_info(void)
3400 {
3401         unsigned int i;
3402         int err = 0;
3403
3404         if (args.get_info_test_num)
3405                 return count_result(do_test_get_info(args.get_info_test_num));
3406
3407         for (i = 1; i <= ARRAY_SIZE(get_info_tests); i++)
3408                 err |= count_result(do_test_get_info(i));
3409
3410         return err;
3411 }
3412
3413 struct btf_file_test {
3414         const char *file;
3415         bool btf_kv_notfound;
3416 };
3417
3418 static struct btf_file_test file_tests[] = {
3419 {
3420         .file = "test_btf_haskv.o",
3421 },
3422 {
3423         .file = "test_btf_nokv.o",
3424         .btf_kv_notfound = true,
3425 },
3426 };
3427
3428 static int file_has_btf_elf(const char *fn, bool *has_btf_ext)
3429 {
3430         Elf_Scn *scn = NULL;
3431         GElf_Ehdr ehdr;
3432         int ret = 0;
3433         int elf_fd;
3434         Elf *elf;
3435
3436         if (CHECK(elf_version(EV_CURRENT) == EV_NONE,
3437                   "elf_version(EV_CURRENT) == EV_NONE"))
3438                 return -1;
3439
3440         elf_fd = open(fn, O_RDONLY);
3441         if (CHECK(elf_fd == -1, "open(%s): errno:%d", fn, errno))
3442                 return -1;
3443
3444         elf = elf_begin(elf_fd, ELF_C_READ, NULL);
3445         if (CHECK(!elf, "elf_begin(%s): %s", fn, elf_errmsg(elf_errno()))) {
3446                 ret = -1;
3447                 goto done;
3448         }
3449
3450         if (CHECK(!gelf_getehdr(elf, &ehdr), "!gelf_getehdr(%s)", fn)) {
3451                 ret = -1;
3452                 goto done;
3453         }
3454
3455         while ((scn = elf_nextscn(elf, scn))) {
3456                 const char *sh_name;
3457                 GElf_Shdr sh;
3458
3459                 if (CHECK(gelf_getshdr(scn, &sh) != &sh,
3460                           "file:%s gelf_getshdr != &sh", fn)) {
3461                         ret = -1;
3462                         goto done;
3463                 }
3464
3465                 sh_name = elf_strptr(elf, ehdr.e_shstrndx, sh.sh_name);
3466                 if (!strcmp(sh_name, BTF_ELF_SEC))
3467                         ret = 1;
3468                 if (!strcmp(sh_name, BTF_EXT_ELF_SEC))
3469                         *has_btf_ext = true;
3470         }
3471
3472 done:
3473         close(elf_fd);
3474         elf_end(elf);
3475         return ret;
3476 }
3477
3478 static int do_test_file(unsigned int test_num)
3479 {
3480         const struct btf_file_test *test = &file_tests[test_num - 1];
3481         const char *expected_fnames[] = {"_dummy_tracepoint",
3482                                          "test_long_fname_1",
3483                                          "test_long_fname_2"};
3484         struct bpf_prog_info info = {};
3485         struct bpf_object *obj = NULL;
3486         struct bpf_func_info *finfo;
3487         struct bpf_program *prog;
3488         __u32 info_len, rec_size;
3489         bool has_btf_ext = false;
3490         struct btf *btf = NULL;
3491         void *func_info = NULL;
3492         struct bpf_map *map;
3493         int i, err, prog_fd;
3494
3495         fprintf(stderr, "BTF libbpf test[%u] (%s): ", test_num,
3496                 test->file);
3497
3498         err = file_has_btf_elf(test->file, &has_btf_ext);
3499         if (err == -1)
3500                 return err;
3501
3502         if (err == 0) {
3503                 fprintf(stderr, "SKIP. No ELF %s found", BTF_ELF_SEC);
3504                 skip_cnt++;
3505                 return 0;
3506         }
3507
3508         obj = bpf_object__open(test->file);
3509         if (CHECK(IS_ERR(obj), "obj: %ld", PTR_ERR(obj)))
3510                 return PTR_ERR(obj);
3511
3512         err = bpf_object__btf_fd(obj);
3513         if (CHECK(err == -1, "bpf_object__btf_fd: -1"))
3514                 goto done;
3515
3516         prog = bpf_program__next(NULL, obj);
3517         if (CHECK(!prog, "Cannot find bpf_prog")) {
3518                 err = -1;
3519                 goto done;
3520         }
3521
3522         bpf_program__set_type(prog, BPF_PROG_TYPE_TRACEPOINT);
3523         err = bpf_object__load(obj);
3524         if (CHECK(err < 0, "bpf_object__load: %d", err))
3525                 goto done;
3526         prog_fd = bpf_program__fd(prog);
3527
3528         map = bpf_object__find_map_by_name(obj, "btf_map");
3529         if (CHECK(!map, "btf_map not found")) {
3530                 err = -1;
3531                 goto done;
3532         }
3533
3534         err = (bpf_map__btf_key_type_id(map) == 0 || bpf_map__btf_value_type_id(map) == 0)
3535                 != test->btf_kv_notfound;
3536         if (CHECK(err, "btf_key_type_id:%u btf_value_type_id:%u test->btf_kv_notfound:%u",
3537                   bpf_map__btf_key_type_id(map), bpf_map__btf_value_type_id(map),
3538                   test->btf_kv_notfound))
3539                 goto done;
3540
3541         if (!has_btf_ext)
3542                 goto skip;
3543
3544         /* get necessary program info */
3545         info_len = sizeof(struct bpf_prog_info);
3546         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
3547
3548         if (CHECK(err == -1, "invalid get info (1st) errno:%d", errno)) {
3549                 fprintf(stderr, "%s\n", btf_log_buf);
3550                 err = -1;
3551                 goto done;
3552         }
3553         if (CHECK(info.nr_func_info != 3,
3554                   "incorrect info.nr_func_info (1st) %d",
3555                   info.nr_func_info)) {
3556                 err = -1;
3557                 goto done;
3558         }
3559         rec_size = info.func_info_rec_size;
3560         if (CHECK(rec_size != sizeof(struct bpf_func_info),
3561                   "incorrect info.func_info_rec_size (1st) %d\n", rec_size)) {
3562                 err = -1;
3563                 goto done;
3564         }
3565
3566         func_info = malloc(info.nr_func_info * rec_size);
3567         if (CHECK(!func_info, "out of memory")) {
3568                 err = -1;
3569                 goto done;
3570         }
3571
3572         /* reset info to only retrieve func_info related data */
3573         memset(&info, 0, sizeof(info));
3574         info.nr_func_info = 3;
3575         info.func_info_rec_size = rec_size;
3576         info.func_info = ptr_to_u64(func_info);
3577
3578         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
3579
3580         if (CHECK(err == -1, "invalid get info (2nd) errno:%d", errno)) {
3581                 fprintf(stderr, "%s\n", btf_log_buf);
3582                 err = -1;
3583                 goto done;
3584         }
3585         if (CHECK(info.nr_func_info != 3,
3586                   "incorrect info.nr_func_info (2nd) %d",
3587                   info.nr_func_info)) {
3588                 err = -1;
3589                 goto done;
3590         }
3591         if (CHECK(info.func_info_rec_size != rec_size,
3592                   "incorrect info.func_info_rec_size (2nd) %d",
3593                   info.func_info_rec_size)) {
3594                 err = -1;
3595                 goto done;
3596         }
3597
3598         err = btf__get_from_id(info.btf_id, &btf);
3599         if (CHECK(err, "cannot get btf from kernel, err: %d", err))
3600                 goto done;
3601
3602         /* check three functions */
3603         finfo = func_info;
3604         for (i = 0; i < 3; i++) {
3605                 const struct btf_type *t;
3606                 const char *fname;
3607
3608                 t = btf__type_by_id(btf, finfo->type_id);
3609                 if (CHECK(!t, "btf__type_by_id failure: id %u",
3610                           finfo->type_id)) {
3611                         err = -1;
3612                         goto done;
3613                 }
3614
3615                 fname = btf__name_by_offset(btf, t->name_off);
3616                 err = strcmp(fname, expected_fnames[i]);
3617                 /* for the second and third functions in .text section,
3618                  * the compiler may order them either way.
3619                  */
3620                 if (i && err)
3621                         err = strcmp(fname, expected_fnames[3 - i]);
3622                 if (CHECK(err, "incorrect fname %s", fname ? : "")) {
3623                         err = -1;
3624                         goto done;
3625                 }
3626
3627                 finfo = (void *)finfo + rec_size;
3628         }
3629
3630 skip:
3631         fprintf(stderr, "OK");
3632
3633 done:
3634         free(func_info);
3635         bpf_object__close(obj);
3636         return err;
3637 }
3638
3639 static int test_file(void)
3640 {
3641         unsigned int i;
3642         int err = 0;
3643
3644         if (args.file_test_num)
3645                 return count_result(do_test_file(args.file_test_num));
3646
3647         for (i = 1; i <= ARRAY_SIZE(file_tests); i++)
3648                 err |= count_result(do_test_file(i));
3649
3650         return err;
3651 }
3652
3653 const char *pprint_enum_str[] = {
3654         "ENUM_ZERO",
3655         "ENUM_ONE",
3656         "ENUM_TWO",
3657         "ENUM_THREE",
3658 };
3659
3660 struct pprint_mapv {
3661         uint32_t ui32;
3662         uint16_t ui16;
3663         /* 2 bytes hole */
3664         int32_t si32;
3665         uint32_t unused_bits2a:2,
3666                 bits28:28,
3667                 unused_bits2b:2;
3668         union {
3669                 uint64_t ui64;
3670                 uint8_t ui8a[8];
3671         };
3672         enum {
3673                 ENUM_ZERO,
3674                 ENUM_ONE,
3675                 ENUM_TWO,
3676                 ENUM_THREE,
3677         } aenum;
3678         uint32_t ui32b;
3679         uint32_t bits2c:2;
3680 };
3681
3682 #ifdef __SIZEOF_INT128__
3683 struct pprint_mapv_int128 {
3684         __int128 si128a;
3685         __int128 si128b;
3686         unsigned __int128 bits3:3;
3687         unsigned __int128 bits80:80;
3688         unsigned __int128 ui128;
3689 };
3690 #endif
3691
3692 static struct btf_raw_test pprint_test_template[] = {
3693 {
3694         .raw_types = {
3695                 /* unsighed char */                     /* [1] */
3696                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 8, 1),
3697                 /* unsigned short */                    /* [2] */
3698                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 16, 2),
3699                 /* unsigned int */                      /* [3] */
3700                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),
3701                 /* int */                               /* [4] */
3702                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
3703                 /* unsigned long long */                /* [5] */
3704                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 64, 8),
3705                 /* 2 bits */                            /* [6] */
3706                 BTF_TYPE_INT_ENC(0, 0, 0, 2, 2),
3707                 /* 28 bits */                           /* [7] */
3708                 BTF_TYPE_INT_ENC(0, 0, 0, 28, 4),
3709                 /* uint8_t[8] */                        /* [8] */
3710                 BTF_TYPE_ARRAY_ENC(9, 1, 8),
3711                 /* typedef unsigned char uint8_t */     /* [9] */
3712                 BTF_TYPEDEF_ENC(NAME_TBD, 1),
3713                 /* typedef unsigned short uint16_t */   /* [10] */
3714                 BTF_TYPEDEF_ENC(NAME_TBD, 2),
3715                 /* typedef unsigned int uint32_t */     /* [11] */
3716                 BTF_TYPEDEF_ENC(NAME_TBD, 3),
3717                 /* typedef int int32_t */               /* [12] */
3718                 BTF_TYPEDEF_ENC(NAME_TBD, 4),
3719                 /* typedef unsigned long long uint64_t *//* [13] */
3720                 BTF_TYPEDEF_ENC(NAME_TBD, 5),
3721                 /* union (anon) */                      /* [14] */
3722                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 0, 2), 8),
3723                 BTF_MEMBER_ENC(NAME_TBD, 13, 0),/* uint64_t ui64; */
3724                 BTF_MEMBER_ENC(NAME_TBD, 8, 0), /* uint8_t ui8a[8]; */
3725                 /* enum (anon) */                       /* [15] */
3726                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 4), 4),
3727                 BTF_ENUM_ENC(NAME_TBD, 0),
3728                 BTF_ENUM_ENC(NAME_TBD, 1),
3729                 BTF_ENUM_ENC(NAME_TBD, 2),
3730                 BTF_ENUM_ENC(NAME_TBD, 3),
3731                 /* struct pprint_mapv */                /* [16] */
3732                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 0, 10), 40),
3733                 BTF_MEMBER_ENC(NAME_TBD, 11, 0),        /* uint32_t ui32 */
3734                 BTF_MEMBER_ENC(NAME_TBD, 10, 32),       /* uint16_t ui16 */
3735                 BTF_MEMBER_ENC(NAME_TBD, 12, 64),       /* int32_t si32 */
3736                 BTF_MEMBER_ENC(NAME_TBD, 6, 96),        /* unused_bits2a */
3737                 BTF_MEMBER_ENC(NAME_TBD, 7, 98),        /* bits28 */
3738                 BTF_MEMBER_ENC(NAME_TBD, 6, 126),       /* unused_bits2b */
3739                 BTF_MEMBER_ENC(0, 14, 128),             /* union (anon) */
3740                 BTF_MEMBER_ENC(NAME_TBD, 15, 192),      /* aenum */
3741                 BTF_MEMBER_ENC(NAME_TBD, 11, 224),      /* uint32_t ui32b */
3742                 BTF_MEMBER_ENC(NAME_TBD, 6, 256),       /* bits2c */
3743                 BTF_END_RAW,
3744         },
3745         BTF_STR_SEC("\0unsigned char\0unsigned short\0unsigned int\0int\0unsigned long long\0uint8_t\0uint16_t\0uint32_t\0int32_t\0uint64_t\0ui64\0ui8a\0ENUM_ZERO\0ENUM_ONE\0ENUM_TWO\0ENUM_THREE\0pprint_mapv\0ui32\0ui16\0si32\0unused_bits2a\0bits28\0unused_bits2b\0aenum\0ui32b\0bits2c"),
3746         .key_size = sizeof(unsigned int),
3747         .value_size = sizeof(struct pprint_mapv),
3748         .key_type_id = 3,       /* unsigned int */
3749         .value_type_id = 16,    /* struct pprint_mapv */
3750         .max_entries = 128 * 1024,
3751 },
3752
3753 {
3754         /* this type will have the same type as the
3755          * first .raw_types definition, but struct type will
3756          * be encoded with kind_flag set.
3757          */
3758         .raw_types = {
3759                 /* unsighed char */                     /* [1] */
3760                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 8, 1),
3761                 /* unsigned short */                    /* [2] */
3762                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 16, 2),
3763                 /* unsigned int */                      /* [3] */
3764                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),
3765                 /* int */                               /* [4] */
3766                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
3767                 /* unsigned long long */                /* [5] */
3768                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 64, 8),
3769                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),       /* [6] */
3770                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),       /* [7] */
3771                 /* uint8_t[8] */                        /* [8] */
3772                 BTF_TYPE_ARRAY_ENC(9, 1, 8),
3773                 /* typedef unsigned char uint8_t */     /* [9] */
3774                 BTF_TYPEDEF_ENC(NAME_TBD, 1),
3775                 /* typedef unsigned short uint16_t */   /* [10] */
3776                 BTF_TYPEDEF_ENC(NAME_TBD, 2),
3777                 /* typedef unsigned int uint32_t */     /* [11] */
3778                 BTF_TYPEDEF_ENC(NAME_TBD, 3),
3779                 /* typedef int int32_t */               /* [12] */
3780                 BTF_TYPEDEF_ENC(NAME_TBD, 4),
3781                 /* typedef unsigned long long uint64_t *//* [13] */
3782                 BTF_TYPEDEF_ENC(NAME_TBD, 5),
3783                 /* union (anon) */                      /* [14] */
3784                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 0, 2), 8),
3785                 BTF_MEMBER_ENC(NAME_TBD, 13, 0),/* uint64_t ui64; */
3786                 BTF_MEMBER_ENC(NAME_TBD, 8, 0), /* uint8_t ui8a[8]; */
3787                 /* enum (anon) */                       /* [15] */
3788                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 4), 4),
3789                 BTF_ENUM_ENC(NAME_TBD, 0),
3790                 BTF_ENUM_ENC(NAME_TBD, 1),
3791                 BTF_ENUM_ENC(NAME_TBD, 2),
3792                 BTF_ENUM_ENC(NAME_TBD, 3),
3793                 /* struct pprint_mapv */                /* [16] */
3794                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 10), 40),
3795                 BTF_MEMBER_ENC(NAME_TBD, 11, BTF_MEMBER_OFFSET(0, 0)),  /* uint32_t ui32 */
3796                 BTF_MEMBER_ENC(NAME_TBD, 10, BTF_MEMBER_OFFSET(0, 32)), /* uint16_t ui16 */
3797                 BTF_MEMBER_ENC(NAME_TBD, 12, BTF_MEMBER_OFFSET(0, 64)), /* int32_t si32 */
3798                 BTF_MEMBER_ENC(NAME_TBD, 6, BTF_MEMBER_OFFSET(2, 96)),  /* unused_bits2a */
3799                 BTF_MEMBER_ENC(NAME_TBD, 7, BTF_MEMBER_OFFSET(28, 98)), /* bits28 */
3800                 BTF_MEMBER_ENC(NAME_TBD, 6, BTF_MEMBER_OFFSET(2, 126)), /* unused_bits2b */
3801                 BTF_MEMBER_ENC(0, 14, BTF_MEMBER_OFFSET(0, 128)),       /* union (anon) */
3802                 BTF_MEMBER_ENC(NAME_TBD, 15, BTF_MEMBER_OFFSET(0, 192)),        /* aenum */
3803                 BTF_MEMBER_ENC(NAME_TBD, 11, BTF_MEMBER_OFFSET(0, 224)),        /* uint32_t ui32b */
3804                 BTF_MEMBER_ENC(NAME_TBD, 6, BTF_MEMBER_OFFSET(2, 256)), /* bits2c */
3805                 BTF_END_RAW,
3806         },
3807         BTF_STR_SEC("\0unsigned char\0unsigned short\0unsigned int\0int\0unsigned long long\0uint8_t\0uint16_t\0uint32_t\0int32_t\0uint64_t\0ui64\0ui8a\0ENUM_ZERO\0ENUM_ONE\0ENUM_TWO\0ENUM_THREE\0pprint_mapv\0ui32\0ui16\0si32\0unused_bits2a\0bits28\0unused_bits2b\0aenum\0ui32b\0bits2c"),
3808         .key_size = sizeof(unsigned int),
3809         .value_size = sizeof(struct pprint_mapv),
3810         .key_type_id = 3,       /* unsigned int */
3811         .value_type_id = 16,    /* struct pprint_mapv */
3812         .max_entries = 128 * 1024,
3813 },
3814
3815 {
3816         /* this type will have the same layout as the
3817          * first .raw_types definition. The struct type will
3818          * be encoded with kind_flag set, bitfield members
3819          * are added typedef/const/volatile, and bitfield members
3820          * will have both int and enum types.
3821          */
3822         .raw_types = {
3823                 /* unsighed char */                     /* [1] */
3824                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 8, 1),
3825                 /* unsigned short */                    /* [2] */
3826                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 16, 2),
3827                 /* unsigned int */                      /* [3] */
3828                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),
3829                 /* int */                               /* [4] */
3830                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),
3831                 /* unsigned long long */                /* [5] */
3832                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 64, 8),
3833                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),       /* [6] */
3834                 BTF_TYPE_INT_ENC(0, 0, 0, 32, 4),       /* [7] */
3835                 /* uint8_t[8] */                        /* [8] */
3836                 BTF_TYPE_ARRAY_ENC(9, 1, 8),
3837                 /* typedef unsigned char uint8_t */     /* [9] */
3838                 BTF_TYPEDEF_ENC(NAME_TBD, 1),
3839                 /* typedef unsigned short uint16_t */   /* [10] */
3840                 BTF_TYPEDEF_ENC(NAME_TBD, 2),
3841                 /* typedef unsigned int uint32_t */     /* [11] */
3842                 BTF_TYPEDEF_ENC(NAME_TBD, 3),
3843                 /* typedef int int32_t */               /* [12] */
3844                 BTF_TYPEDEF_ENC(NAME_TBD, 4),
3845                 /* typedef unsigned long long uint64_t *//* [13] */
3846                 BTF_TYPEDEF_ENC(NAME_TBD, 5),
3847                 /* union (anon) */                      /* [14] */
3848                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_UNION, 0, 2), 8),
3849                 BTF_MEMBER_ENC(NAME_TBD, 13, 0),/* uint64_t ui64; */
3850                 BTF_MEMBER_ENC(NAME_TBD, 8, 0), /* uint8_t ui8a[8]; */
3851                 /* enum (anon) */                       /* [15] */
3852                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 4), 4),
3853                 BTF_ENUM_ENC(NAME_TBD, 0),
3854                 BTF_ENUM_ENC(NAME_TBD, 1),
3855                 BTF_ENUM_ENC(NAME_TBD, 2),
3856                 BTF_ENUM_ENC(NAME_TBD, 3),
3857                 /* struct pprint_mapv */                /* [16] */
3858                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 10), 40),
3859                 BTF_MEMBER_ENC(NAME_TBD, 11, BTF_MEMBER_OFFSET(0, 0)),  /* uint32_t ui32 */
3860                 BTF_MEMBER_ENC(NAME_TBD, 10, BTF_MEMBER_OFFSET(0, 32)), /* uint16_t ui16 */
3861                 BTF_MEMBER_ENC(NAME_TBD, 12, BTF_MEMBER_OFFSET(0, 64)), /* int32_t si32 */
3862                 BTF_MEMBER_ENC(NAME_TBD, 17, BTF_MEMBER_OFFSET(2, 96)), /* unused_bits2a */
3863                 BTF_MEMBER_ENC(NAME_TBD, 7, BTF_MEMBER_OFFSET(28, 98)), /* bits28 */
3864                 BTF_MEMBER_ENC(NAME_TBD, 19, BTF_MEMBER_OFFSET(2, 126)),/* unused_bits2b */
3865                 BTF_MEMBER_ENC(0, 14, BTF_MEMBER_OFFSET(0, 128)),       /* union (anon) */
3866                 BTF_MEMBER_ENC(NAME_TBD, 15, BTF_MEMBER_OFFSET(0, 192)),        /* aenum */
3867                 BTF_MEMBER_ENC(NAME_TBD, 11, BTF_MEMBER_OFFSET(0, 224)),        /* uint32_t ui32b */
3868                 BTF_MEMBER_ENC(NAME_TBD, 17, BTF_MEMBER_OFFSET(2, 256)),        /* bits2c */
3869                 /* typedef unsigned int ___int */       /* [17] */
3870                 BTF_TYPEDEF_ENC(NAME_TBD, 18),
3871                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_VOLATILE, 0, 0), 6),      /* [18] */
3872                 BTF_TYPE_ENC(0, BTF_INFO_ENC(BTF_KIND_CONST, 0, 0), 15),        /* [19] */
3873                 BTF_END_RAW,
3874         },
3875         BTF_STR_SEC("\0unsigned char\0unsigned short\0unsigned int\0int\0unsigned long long\0uint8_t\0uint16_t\0uint32_t\0int32_t\0uint64_t\0ui64\0ui8a\0ENUM_ZERO\0ENUM_ONE\0ENUM_TWO\0ENUM_THREE\0pprint_mapv\0ui32\0ui16\0si32\0unused_bits2a\0bits28\0unused_bits2b\0aenum\0ui32b\0bits2c\0___int"),
3876         .key_size = sizeof(unsigned int),
3877         .value_size = sizeof(struct pprint_mapv),
3878         .key_type_id = 3,       /* unsigned int */
3879         .value_type_id = 16,    /* struct pprint_mapv */
3880         .max_entries = 128 * 1024,
3881 },
3882
3883 #ifdef __SIZEOF_INT128__
3884 {
3885         /* test int128 */
3886         .raw_types = {
3887                 /* unsigned int */                              /* [1] */
3888                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),
3889                 /* __int128 */                                  /* [2] */
3890                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 128, 16),
3891                 /* unsigned __int128 */                         /* [3] */
3892                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 128, 16),
3893                 /* struct pprint_mapv_int128 */                 /* [4] */
3894                 BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_STRUCT, 1, 5), 64),
3895                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 0)),           /* si128a */
3896                 BTF_MEMBER_ENC(NAME_TBD, 2, BTF_MEMBER_OFFSET(0, 128)),         /* si128b */
3897                 BTF_MEMBER_ENC(NAME_TBD, 3, BTF_MEMBER_OFFSET(3, 256)),         /* bits3 */
3898                 BTF_MEMBER_ENC(NAME_TBD, 3, BTF_MEMBER_OFFSET(80, 259)),        /* bits80 */
3899                 BTF_MEMBER_ENC(NAME_TBD, 3, BTF_MEMBER_OFFSET(0, 384)),         /* ui128 */
3900                 BTF_END_RAW,
3901         },
3902         BTF_STR_SEC("\0unsigned int\0__int128\0unsigned __int128\0pprint_mapv_int128\0si128a\0si128b\0bits3\0bits80\0ui128"),
3903         .key_size = sizeof(unsigned int),
3904         .value_size = sizeof(struct pprint_mapv_int128),
3905         .key_type_id = 1,
3906         .value_type_id = 4,
3907         .max_entries = 128 * 1024,
3908         .mapv_kind = PPRINT_MAPV_KIND_INT128,
3909 },
3910 #endif
3911
3912 };
3913
3914 static struct btf_pprint_test_meta {
3915         const char *descr;
3916         enum bpf_map_type map_type;
3917         const char *map_name;
3918         bool ordered_map;
3919         bool lossless_map;
3920         bool percpu_map;
3921 } pprint_tests_meta[] = {
3922 {
3923         .descr = "BTF pretty print array",
3924         .map_type = BPF_MAP_TYPE_ARRAY,
3925         .map_name = "pprint_test_array",
3926         .ordered_map = true,
3927         .lossless_map = true,
3928         .percpu_map = false,
3929 },
3930
3931 {
3932         .descr = "BTF pretty print hash",
3933         .map_type = BPF_MAP_TYPE_HASH,
3934         .map_name = "pprint_test_hash",
3935         .ordered_map = false,
3936         .lossless_map = true,
3937         .percpu_map = false,
3938 },
3939
3940 {
3941         .descr = "BTF pretty print lru hash",
3942         .map_type = BPF_MAP_TYPE_LRU_HASH,
3943         .map_name = "pprint_test_lru_hash",
3944         .ordered_map = false,
3945         .lossless_map = false,
3946         .percpu_map = false,
3947 },
3948
3949 {
3950         .descr = "BTF pretty print percpu array",
3951         .map_type = BPF_MAP_TYPE_PERCPU_ARRAY,
3952         .map_name = "pprint_test_percpu_array",
3953         .ordered_map = true,
3954         .lossless_map = true,
3955         .percpu_map = true,
3956 },
3957
3958 {
3959         .descr = "BTF pretty print percpu hash",
3960         .map_type = BPF_MAP_TYPE_PERCPU_HASH,
3961         .map_name = "pprint_test_percpu_hash",
3962         .ordered_map = false,
3963         .lossless_map = true,
3964         .percpu_map = true,
3965 },
3966
3967 {
3968         .descr = "BTF pretty print lru percpu hash",
3969         .map_type = BPF_MAP_TYPE_LRU_PERCPU_HASH,
3970         .map_name = "pprint_test_lru_percpu_hash",
3971         .ordered_map = false,
3972         .lossless_map = false,
3973         .percpu_map = true,
3974 },
3975
3976 };
3977
3978 static size_t get_pprint_mapv_size(enum pprint_mapv_kind_t mapv_kind)
3979 {
3980         if (mapv_kind == PPRINT_MAPV_KIND_BASIC)
3981                 return sizeof(struct pprint_mapv);
3982
3983 #ifdef __SIZEOF_INT128__
3984         if (mapv_kind == PPRINT_MAPV_KIND_INT128)
3985                 return sizeof(struct pprint_mapv_int128);
3986 #endif
3987
3988         assert(0);
3989 }
3990
3991 static void set_pprint_mapv(enum pprint_mapv_kind_t mapv_kind,
3992                             void *mapv, uint32_t i,
3993                             int num_cpus, int rounded_value_size)
3994 {
3995         int cpu;
3996
3997         if (mapv_kind == PPRINT_MAPV_KIND_BASIC) {
3998                 struct pprint_mapv *v = mapv;
3999
4000                 for (cpu = 0; cpu < num_cpus; cpu++) {
4001                         v->ui32 = i + cpu;
4002                         v->si32 = -i;
4003                         v->unused_bits2a = 3;
4004                         v->bits28 = i;
4005                         v->unused_bits2b = 3;
4006                         v->ui64 = i;
4007                         v->aenum = i & 0x03;
4008                         v->ui32b = 4;
4009                         v->bits2c = 1;
4010                         v = (void *)v + rounded_value_size;
4011                 }
4012         }
4013
4014 #ifdef __SIZEOF_INT128__
4015         if (mapv_kind == PPRINT_MAPV_KIND_INT128) {
4016                 struct pprint_mapv_int128 *v = mapv;
4017
4018                 for (cpu = 0; cpu < num_cpus; cpu++) {
4019                         v->si128a = i;
4020                         v->si128b = -i;
4021                         v->bits3 = i & 0x07;
4022                         v->bits80 = (((unsigned __int128)1) << 64) + i;
4023                         v->ui128 = (((unsigned __int128)2) << 64) + i;
4024                         v = (void *)v + rounded_value_size;
4025                 }
4026         }
4027 #endif
4028 }
4029
4030 ssize_t get_pprint_expected_line(enum pprint_mapv_kind_t mapv_kind,
4031                                  char *expected_line, ssize_t line_size,
4032                                  bool percpu_map, unsigned int next_key,
4033                                  int cpu, void *mapv)
4034 {
4035         ssize_t nexpected_line = -1;
4036
4037         if (mapv_kind == PPRINT_MAPV_KIND_BASIC) {
4038                 struct pprint_mapv *v = mapv;
4039
4040                 nexpected_line = snprintf(expected_line, line_size,
4041                                           "%s%u: {%u,0,%d,0x%x,0x%x,0x%x,"
4042                                           "{%lu|[%u,%u,%u,%u,%u,%u,%u,%u]},%s,"
4043                                           "%u,0x%x}\n",
4044                                           percpu_map ? "\tcpu" : "",
4045                                           percpu_map ? cpu : next_key,
4046                                           v->ui32, v->si32,
4047                                           v->unused_bits2a,
4048                                           v->bits28,
4049                                           v->unused_bits2b,
4050                                           v->ui64,
4051                                           v->ui8a[0], v->ui8a[1],
4052                                           v->ui8a[2], v->ui8a[3],
4053                                           v->ui8a[4], v->ui8a[5],
4054                                           v->ui8a[6], v->ui8a[7],
4055                                           pprint_enum_str[v->aenum],
4056                                           v->ui32b,
4057                                           v->bits2c);
4058         }
4059
4060 #ifdef __SIZEOF_INT128__
4061         if (mapv_kind == PPRINT_MAPV_KIND_INT128) {
4062                 struct pprint_mapv_int128 *v = mapv;
4063
4064                 nexpected_line = snprintf(expected_line, line_size,
4065                                           "%s%u: {0x%lx,0x%lx,0x%lx,"
4066                                           "0x%lx%016lx,0x%lx%016lx}\n",
4067                                           percpu_map ? "\tcpu" : "",
4068                                           percpu_map ? cpu : next_key,
4069                                           (uint64_t)v->si128a,
4070                                           (uint64_t)v->si128b,
4071                                           (uint64_t)v->bits3,
4072                                           (uint64_t)(v->bits80 >> 64),
4073                                           (uint64_t)v->bits80,
4074                                           (uint64_t)(v->ui128 >> 64),
4075                                           (uint64_t)v->ui128);
4076         }
4077 #endif
4078
4079         return nexpected_line;
4080 }
4081
4082 static int check_line(const char *expected_line, int nexpected_line,
4083                       int expected_line_len, const char *line)
4084 {
4085         if (CHECK(nexpected_line == expected_line_len,
4086                   "expected_line is too long"))
4087                 return -1;
4088
4089         if (strcmp(expected_line, line)) {
4090                 fprintf(stderr, "unexpected pprint output\n");
4091                 fprintf(stderr, "expected: %s", expected_line);
4092                 fprintf(stderr, "    read: %s", line);
4093                 return -1;
4094         }
4095
4096         return 0;
4097 }
4098
4099
4100 static int do_test_pprint(int test_num)
4101 {
4102         const struct btf_raw_test *test = &pprint_test_template[test_num];
4103         enum pprint_mapv_kind_t mapv_kind = test->mapv_kind;
4104         struct bpf_create_map_attr create_attr = {};
4105         bool ordered_map, lossless_map, percpu_map;
4106         int err, ret, num_cpus, rounded_value_size;
4107         unsigned int key, nr_read_elems;
4108         int map_fd = -1, btf_fd = -1;
4109         unsigned int raw_btf_size;
4110         char expected_line[255];
4111         FILE *pin_file = NULL;
4112         char pin_path[255];
4113         size_t line_len = 0;
4114         char *line = NULL;
4115         void *mapv = NULL;
4116         uint8_t *raw_btf;
4117         ssize_t nread;
4118
4119         fprintf(stderr, "%s(#%d)......", test->descr, test_num);
4120         raw_btf = btf_raw_create(&hdr_tmpl, test->raw_types,
4121                                  test->str_sec, test->str_sec_size,
4122                                  &raw_btf_size, NULL);
4123
4124         if (!raw_btf)
4125                 return -1;
4126
4127         *btf_log_buf = '\0';
4128         btf_fd = bpf_load_btf(raw_btf, raw_btf_size,
4129                               btf_log_buf, BTF_LOG_BUF_SIZE,
4130                               args.always_log);
4131         free(raw_btf);
4132
4133         if (CHECK(btf_fd == -1, "errno:%d", errno)) {
4134                 err = -1;
4135                 goto done;
4136         }
4137
4138         create_attr.name = test->map_name;
4139         create_attr.map_type = test->map_type;
4140         create_attr.key_size = test->key_size;
4141         create_attr.value_size = test->value_size;
4142         create_attr.max_entries = test->max_entries;
4143         create_attr.btf_fd = btf_fd;
4144         create_attr.btf_key_type_id = test->key_type_id;
4145         create_attr.btf_value_type_id = test->value_type_id;
4146
4147         map_fd = bpf_create_map_xattr(&create_attr);
4148         if (CHECK(map_fd == -1, "errno:%d", errno)) {
4149                 err = -1;
4150                 goto done;
4151         }
4152
4153         ret = snprintf(pin_path, sizeof(pin_path), "%s/%s",
4154                        "/sys/fs/bpf", test->map_name);
4155
4156         if (CHECK(ret == sizeof(pin_path), "pin_path %s/%s is too long",
4157                   "/sys/fs/bpf", test->map_name)) {
4158                 err = -1;
4159                 goto done;
4160         }
4161
4162         err = bpf_obj_pin(map_fd, pin_path);
4163         if (CHECK(err, "bpf_obj_pin(%s): errno:%d.", pin_path, errno))
4164                 goto done;
4165
4166         percpu_map = test->percpu_map;
4167         num_cpus = percpu_map ? bpf_num_possible_cpus() : 1;
4168         rounded_value_size = round_up(get_pprint_mapv_size(mapv_kind), 8);
4169         mapv = calloc(num_cpus, rounded_value_size);
4170         if (CHECK(!mapv, "mapv allocation failure")) {
4171                 err = -1;
4172                 goto done;
4173         }
4174
4175         for (key = 0; key < test->max_entries; key++) {
4176                 set_pprint_mapv(mapv_kind, mapv, key, num_cpus, rounded_value_size);
4177                 bpf_map_update_elem(map_fd, &key, mapv, 0);
4178         }
4179
4180         pin_file = fopen(pin_path, "r");
4181         if (CHECK(!pin_file, "fopen(%s): errno:%d", pin_path, errno)) {
4182                 err = -1;
4183                 goto done;
4184         }
4185
4186         /* Skip lines start with '#' */
4187         while ((nread = getline(&line, &line_len, pin_file)) > 0 &&
4188                *line == '#')
4189                 ;
4190
4191         if (CHECK(nread <= 0, "Unexpected EOF")) {
4192                 err = -1;
4193                 goto done;
4194         }
4195
4196         nr_read_elems = 0;
4197         ordered_map = test->ordered_map;
4198         lossless_map = test->lossless_map;
4199         do {
4200                 ssize_t nexpected_line;
4201                 unsigned int next_key;
4202                 void *cmapv;
4203                 int cpu;
4204
4205                 next_key = ordered_map ? nr_read_elems : atoi(line);
4206                 set_pprint_mapv(mapv_kind, mapv, next_key, num_cpus, rounded_value_size);
4207                 cmapv = mapv;
4208
4209                 for (cpu = 0; cpu < num_cpus; cpu++) {
4210                         if (percpu_map) {
4211                                 /* for percpu map, the format looks like:
4212                                  * <key>: {
4213                                  *      cpu0: <value_on_cpu0>
4214                                  *      cpu1: <value_on_cpu1>
4215                                  *      ...
4216                                  *      cpun: <value_on_cpun>
4217                                  * }
4218                                  *
4219                                  * let us verify the line containing the key here.
4220                                  */
4221                                 if (cpu == 0) {
4222                                         nexpected_line = snprintf(expected_line,
4223                                                                   sizeof(expected_line),
4224                                                                   "%u: {\n",
4225                                                                   next_key);
4226
4227                                         err = check_line(expected_line, nexpected_line,
4228                                                          sizeof(expected_line), line);
4229                                         if (err == -1)
4230                                                 goto done;
4231                                 }
4232
4233                                 /* read value@cpu */
4234                                 nread = getline(&line, &line_len, pin_file);
4235                                 if (nread < 0)
4236                                         break;
4237                         }
4238
4239                         nexpected_line = get_pprint_expected_line(mapv_kind, expected_line,
4240                                                                   sizeof(expected_line),
4241                                                                   percpu_map, next_key,
4242                                                                   cpu, cmapv);
4243                         err = check_line(expected_line, nexpected_line,
4244                                          sizeof(expected_line), line);
4245                         if (err == -1)
4246                                 goto done;
4247
4248                         cmapv = cmapv + rounded_value_size;
4249                 }
4250
4251                 if (percpu_map) {
4252                         /* skip the last bracket for the percpu map */
4253                         nread = getline(&line, &line_len, pin_file);
4254                         if (nread < 0)
4255                                 break;
4256                 }
4257
4258                 nread = getline(&line, &line_len, pin_file);
4259         } while (++nr_read_elems < test->max_entries && nread > 0);
4260
4261         if (lossless_map &&
4262             CHECK(nr_read_elems < test->max_entries,
4263                   "Unexpected EOF. nr_read_elems:%u test->max_entries:%u",
4264                   nr_read_elems, test->max_entries)) {
4265                 err = -1;
4266                 goto done;
4267         }
4268
4269         if (CHECK(nread > 0, "Unexpected extra pprint output: %s", line)) {
4270                 err = -1;
4271                 goto done;
4272         }
4273
4274         err = 0;
4275
4276 done:
4277         if (mapv)
4278                 free(mapv);
4279         if (!err)
4280                 fprintf(stderr, "OK");
4281         if (*btf_log_buf && (err || args.always_log))
4282                 fprintf(stderr, "\n%s", btf_log_buf);
4283         if (btf_fd != -1)
4284                 close(btf_fd);
4285         if (map_fd != -1)
4286                 close(map_fd);
4287         if (pin_file)
4288                 fclose(pin_file);
4289         unlink(pin_path);
4290         free(line);
4291
4292         return err;
4293 }
4294
4295 static int test_pprint(void)
4296 {
4297         unsigned int i;
4298         int err = 0;
4299
4300         /* test various maps with the first test template */
4301         for (i = 0; i < ARRAY_SIZE(pprint_tests_meta); i++) {
4302                 pprint_test_template[0].descr = pprint_tests_meta[i].descr;
4303                 pprint_test_template[0].map_type = pprint_tests_meta[i].map_type;
4304                 pprint_test_template[0].map_name = pprint_tests_meta[i].map_name;
4305                 pprint_test_template[0].ordered_map = pprint_tests_meta[i].ordered_map;
4306                 pprint_test_template[0].lossless_map = pprint_tests_meta[i].lossless_map;
4307                 pprint_test_template[0].percpu_map = pprint_tests_meta[i].percpu_map;
4308
4309                 err |= count_result(do_test_pprint(0));
4310         }
4311
4312         /* test rest test templates with the first map */
4313         for (i = 1; i < ARRAY_SIZE(pprint_test_template); i++) {
4314                 pprint_test_template[i].descr = pprint_tests_meta[0].descr;
4315                 pprint_test_template[i].map_type = pprint_tests_meta[0].map_type;
4316                 pprint_test_template[i].map_name = pprint_tests_meta[0].map_name;
4317                 pprint_test_template[i].ordered_map = pprint_tests_meta[0].ordered_map;
4318                 pprint_test_template[i].lossless_map = pprint_tests_meta[0].lossless_map;
4319                 pprint_test_template[i].percpu_map = pprint_tests_meta[0].percpu_map;
4320                 err |= count_result(do_test_pprint(i));
4321         }
4322
4323         return err;
4324 }
4325
4326 #define BPF_LINE_INFO_ENC(insn_off, file_off, line_off, line_num, line_col) \
4327         (insn_off), (file_off), (line_off), ((line_num) << 10 | ((line_col) & 0x3ff))
4328
4329 static struct prog_info_raw_test {
4330         const char *descr;
4331         const char *str_sec;
4332         const char *err_str;
4333         __u32 raw_types[MAX_NR_RAW_U32];
4334         __u32 str_sec_size;
4335         struct bpf_insn insns[MAX_INSNS];
4336         __u32 prog_type;
4337         __u32 func_info[MAX_SUBPROGS][2];
4338         __u32 func_info_rec_size;
4339         __u32 func_info_cnt;
4340         __u32 line_info[MAX_NR_RAW_U32];
4341         __u32 line_info_rec_size;
4342         __u32 nr_jited_ksyms;
4343         bool expected_prog_load_failure;
4344         __u32 dead_code_cnt;
4345         __u32 dead_code_mask;
4346         __u32 dead_func_cnt;
4347         __u32 dead_func_mask;
4348 } info_raw_tests[] = {
4349 {
4350         .descr = "func_type (main func + one sub)",
4351         .raw_types = {
4352                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4353                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),        /* [2] */
4354                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [3] */
4355                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4356                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4357                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [4] */
4358                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4359                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4360                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [5] */
4361                 BTF_FUNC_ENC(NAME_TBD, 4),                      /* [6] */
4362                 BTF_END_RAW,
4363         },
4364         .str_sec = "\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB",
4365         .str_sec_size = sizeof("\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB"),
4366         .insns = {
4367                 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 1, 0, 2),
4368                 BPF_MOV64_IMM(BPF_REG_0, 1),
4369                 BPF_EXIT_INSN(),
4370                 BPF_MOV64_IMM(BPF_REG_0, 2),
4371                 BPF_EXIT_INSN(),
4372         },
4373         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4374         .func_info = { {0, 5}, {3, 6} },
4375         .func_info_rec_size = 8,
4376         .func_info_cnt = 2,
4377         .line_info = { BTF_END_RAW },
4378 },
4379
4380 {
4381         .descr = "func_type (Incorrect func_info_rec_size)",
4382         .raw_types = {
4383                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4384                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),        /* [2] */
4385                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [3] */
4386                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4387                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4388                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [4] */
4389                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4390                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4391                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [5] */
4392                 BTF_FUNC_ENC(NAME_TBD, 4),                      /* [6] */
4393                 BTF_END_RAW,
4394         },
4395         .str_sec = "\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB",
4396         .str_sec_size = sizeof("\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB"),
4397         .insns = {
4398                 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 1, 0, 2),
4399                 BPF_MOV64_IMM(BPF_REG_0, 1),
4400                 BPF_EXIT_INSN(),
4401                 BPF_MOV64_IMM(BPF_REG_0, 2),
4402                 BPF_EXIT_INSN(),
4403         },
4404         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4405         .func_info = { {0, 5}, {3, 6} },
4406         .func_info_rec_size = 4,
4407         .func_info_cnt = 2,
4408         .line_info = { BTF_END_RAW },
4409         .expected_prog_load_failure = true,
4410 },
4411
4412 {
4413         .descr = "func_type (Incorrect func_info_cnt)",
4414         .raw_types = {
4415                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4416                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),        /* [2] */
4417                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [3] */
4418                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4419                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4420                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [4] */
4421                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4422                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4423                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [5] */
4424                 BTF_FUNC_ENC(NAME_TBD, 4),                      /* [6] */
4425                 BTF_END_RAW,
4426         },
4427         .str_sec = "\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB",
4428         .str_sec_size = sizeof("\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB"),
4429         .insns = {
4430                 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 1, 0, 2),
4431                 BPF_MOV64_IMM(BPF_REG_0, 1),
4432                 BPF_EXIT_INSN(),
4433                 BPF_MOV64_IMM(BPF_REG_0, 2),
4434                 BPF_EXIT_INSN(),
4435         },
4436         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4437         .func_info = { {0, 5}, {3, 6} },
4438         .func_info_rec_size = 8,
4439         .func_info_cnt = 1,
4440         .line_info = { BTF_END_RAW },
4441         .expected_prog_load_failure = true,
4442 },
4443
4444 {
4445         .descr = "func_type (Incorrect bpf_func_info.insn_off)",
4446         .raw_types = {
4447                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4448                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 32, 4),        /* [2] */
4449                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [3] */
4450                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4451                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4452                 BTF_FUNC_PROTO_ENC(1, 2),                       /* [4] */
4453                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 2),
4454                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4455                 BTF_FUNC_ENC(NAME_TBD, 3),                      /* [5] */
4456                 BTF_FUNC_ENC(NAME_TBD, 4),                      /* [6] */
4457                 BTF_END_RAW,
4458         },
4459         .str_sec = "\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB",
4460         .str_sec_size = sizeof("\0int\0unsigned int\0a\0b\0c\0d\0funcA\0funcB"),
4461         .insns = {
4462                 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 1, 0, 2),
4463                 BPF_MOV64_IMM(BPF_REG_0, 1),
4464                 BPF_EXIT_INSN(),
4465                 BPF_MOV64_IMM(BPF_REG_0, 2),
4466                 BPF_EXIT_INSN(),
4467         },
4468         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4469         .func_info = { {0, 5}, {2, 6} },
4470         .func_info_rec_size = 8,
4471         .func_info_cnt = 2,
4472         .line_info = { BTF_END_RAW },
4473         .expected_prog_load_failure = true,
4474 },
4475
4476 {
4477         .descr = "line_info (No subprog)",
4478         .raw_types = {
4479                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4480                 BTF_END_RAW,
4481         },
4482         BTF_STR_SEC("\0int\0int a=1;\0int b=2;\0return a + b;\0return a + b;"),
4483         .insns = {
4484                 BPF_MOV64_IMM(BPF_REG_0, 1),
4485                 BPF_MOV64_IMM(BPF_REG_1, 2),
4486                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4487                 BPF_EXIT_INSN(),
4488         },
4489         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4490         .func_info_cnt = 0,
4491         .line_info = {
4492                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4493                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 9),
4494                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8),
4495                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 7),
4496                 BTF_END_RAW,
4497         },
4498         .line_info_rec_size = sizeof(struct bpf_line_info),
4499         .nr_jited_ksyms = 1,
4500 },
4501
4502 {
4503         .descr = "line_info (No subprog. insn_off >= prog->len)",
4504         .raw_types = {
4505                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4506                 BTF_END_RAW,
4507         },
4508         BTF_STR_SEC("\0int\0int a=1;\0int b=2;\0return a + b;\0return a + b;"),
4509         .insns = {
4510                 BPF_MOV64_IMM(BPF_REG_0, 1),
4511                 BPF_MOV64_IMM(BPF_REG_1, 2),
4512                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4513                 BPF_EXIT_INSN(),
4514         },
4515         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4516         .func_info_cnt = 0,
4517         .line_info = {
4518                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4519                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 9),
4520                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8),
4521                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 7),
4522                 BPF_LINE_INFO_ENC(4, 0, 0, 5, 6),
4523                 BTF_END_RAW,
4524         },
4525         .line_info_rec_size = sizeof(struct bpf_line_info),
4526         .nr_jited_ksyms = 1,
4527         .err_str = "line_info[4].insn_off",
4528         .expected_prog_load_failure = true,
4529 },
4530
4531 {
4532         .descr = "line_info (Zero bpf insn code)",
4533         .raw_types = {
4534                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4535                 BTF_TYPE_INT_ENC(NAME_TBD, 0, 0, 64, 8),        /* [2] */
4536                 BTF_TYPEDEF_ENC(NAME_TBD, 2),                   /* [3] */
4537                 BTF_END_RAW,
4538         },
4539         BTF_STR_SEC("\0int\0unsigned long\0u64\0u64 a=1;\0return a;"),
4540         .insns = {
4541                 BPF_LD_IMM64(BPF_REG_0, 1),
4542                 BPF_EXIT_INSN(),
4543         },
4544         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4545         .func_info_cnt = 0,
4546         .line_info = {
4547                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4548                 BPF_LINE_INFO_ENC(1, 0, 0, 2, 9),
4549                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8),
4550                 BTF_END_RAW,
4551         },
4552         .line_info_rec_size = sizeof(struct bpf_line_info),
4553         .nr_jited_ksyms = 1,
4554         .err_str = "Invalid insn code at line_info[1]",
4555         .expected_prog_load_failure = true,
4556 },
4557
4558 {
4559         .descr = "line_info (No subprog. zero tailing line_info",
4560         .raw_types = {
4561                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4562                 BTF_END_RAW,
4563         },
4564         BTF_STR_SEC("\0int\0int a=1;\0int b=2;\0return a + b;\0return a + b;"),
4565         .insns = {
4566                 BPF_MOV64_IMM(BPF_REG_0, 1),
4567                 BPF_MOV64_IMM(BPF_REG_1, 2),
4568                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4569                 BPF_EXIT_INSN(),
4570         },
4571         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4572         .func_info_cnt = 0,
4573         .line_info = {
4574                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10), 0,
4575                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 9), 0,
4576                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8), 0,
4577                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 7), 0,
4578                 BTF_END_RAW,
4579         },
4580         .line_info_rec_size = sizeof(struct bpf_line_info) + sizeof(__u32),
4581         .nr_jited_ksyms = 1,
4582 },
4583
4584 {
4585         .descr = "line_info (No subprog. nonzero tailing line_info)",
4586         .raw_types = {
4587                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4588                 BTF_END_RAW,
4589         },
4590         BTF_STR_SEC("\0int\0int a=1;\0int b=2;\0return a + b;\0return a + b;"),
4591         .insns = {
4592                 BPF_MOV64_IMM(BPF_REG_0, 1),
4593                 BPF_MOV64_IMM(BPF_REG_1, 2),
4594                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4595                 BPF_EXIT_INSN(),
4596         },
4597         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4598         .func_info_cnt = 0,
4599         .line_info = {
4600                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10), 0,
4601                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 9), 0,
4602                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8), 0,
4603                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 7), 1,
4604                 BTF_END_RAW,
4605         },
4606         .line_info_rec_size = sizeof(struct bpf_line_info) + sizeof(__u32),
4607         .nr_jited_ksyms = 1,
4608         .err_str = "nonzero tailing record in line_info",
4609         .expected_prog_load_failure = true,
4610 },
4611
4612 {
4613         .descr = "line_info (subprog)",
4614         .raw_types = {
4615                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4616                 BTF_END_RAW,
4617         },
4618         BTF_STR_SEC("\0int\0int a=1+1;\0return func(a);\0b+=1;\0return b;"),
4619         .insns = {
4620                 BPF_MOV64_IMM(BPF_REG_2, 1),
4621                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4622                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4623                 BPF_CALL_REL(1),
4624                 BPF_EXIT_INSN(),
4625                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4626                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4627                 BPF_EXIT_INSN(),
4628         },
4629         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4630         .func_info_cnt = 0,
4631         .line_info = {
4632                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4633                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 2, 9),
4634                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 3, 8),
4635                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 4, 7),
4636                 BTF_END_RAW,
4637         },
4638         .line_info_rec_size = sizeof(struct bpf_line_info),
4639         .nr_jited_ksyms = 2,
4640 },
4641
4642 {
4643         .descr = "line_info (subprog + func_info)",
4644         .raw_types = {
4645                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4646                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
4647                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4648                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
4649                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
4650                 BTF_END_RAW,
4651         },
4652         BTF_STR_SEC("\0int\0x\0sub\0main\0int a=1+1;\0return func(a);\0b+=1;\0return b;"),
4653         .insns = {
4654                 BPF_MOV64_IMM(BPF_REG_2, 1),
4655                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4656                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4657                 BPF_CALL_REL(1),
4658                 BPF_EXIT_INSN(),
4659                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4660                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4661                 BPF_EXIT_INSN(),
4662         },
4663         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4664         .func_info_cnt = 2,
4665         .func_info_rec_size = 8,
4666         .func_info = { {0, 4}, {5, 3} },
4667         .line_info = {
4668                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4669                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 2, 9),
4670                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 3, 8),
4671                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 4, 7),
4672                 BTF_END_RAW,
4673         },
4674         .line_info_rec_size = sizeof(struct bpf_line_info),
4675         .nr_jited_ksyms = 2,
4676 },
4677
4678 {
4679         .descr = "line_info (subprog. missing 1st func line info)",
4680         .raw_types = {
4681                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4682                 BTF_END_RAW,
4683         },
4684         BTF_STR_SEC("\0int\0int a=1+1;\0return func(a);\0b+=1;\0return b;"),
4685         .insns = {
4686                 BPF_MOV64_IMM(BPF_REG_2, 1),
4687                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4688                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4689                 BPF_CALL_REL(1),
4690                 BPF_EXIT_INSN(),
4691                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4692                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4693                 BPF_EXIT_INSN(),
4694         },
4695         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4696         .func_info_cnt = 0,
4697         .line_info = {
4698                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 1, 10),
4699                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 2, 9),
4700                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 3, 8),
4701                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 4, 7),
4702                 BTF_END_RAW,
4703         },
4704         .line_info_rec_size = sizeof(struct bpf_line_info),
4705         .nr_jited_ksyms = 2,
4706         .err_str = "missing bpf_line_info for func#0",
4707         .expected_prog_load_failure = true,
4708 },
4709
4710 {
4711         .descr = "line_info (subprog. missing 2nd func line info)",
4712         .raw_types = {
4713                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4714                 BTF_END_RAW,
4715         },
4716         BTF_STR_SEC("\0int\0int a=1+1;\0return func(a);\0b+=1;\0return b;"),
4717         .insns = {
4718                 BPF_MOV64_IMM(BPF_REG_2, 1),
4719                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4720                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4721                 BPF_CALL_REL(1),
4722                 BPF_EXIT_INSN(),
4723                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4724                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4725                 BPF_EXIT_INSN(),
4726         },
4727         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4728         .func_info_cnt = 0,
4729         .line_info = {
4730                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4731                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 2, 9),
4732                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 3, 8),
4733                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 4, 7),
4734                 BTF_END_RAW,
4735         },
4736         .line_info_rec_size = sizeof(struct bpf_line_info),
4737         .nr_jited_ksyms = 2,
4738         .err_str = "missing bpf_line_info for func#1",
4739         .expected_prog_load_failure = true,
4740 },
4741
4742 {
4743         .descr = "line_info (subprog. unordered insn offset)",
4744         .raw_types = {
4745                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4746                 BTF_END_RAW,
4747         },
4748         BTF_STR_SEC("\0int\0int a=1+1;\0return func(a);\0b+=1;\0return b;"),
4749         .insns = {
4750                 BPF_MOV64_IMM(BPF_REG_2, 1),
4751                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4752                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4753                 BPF_CALL_REL(1),
4754                 BPF_EXIT_INSN(),
4755                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4756                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4757                 BPF_EXIT_INSN(),
4758         },
4759         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4760         .func_info_cnt = 0,
4761         .line_info = {
4762                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4763                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 2, 9),
4764                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8),
4765                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 4, 7),
4766                 BTF_END_RAW,
4767         },
4768         .line_info_rec_size = sizeof(struct bpf_line_info),
4769         .nr_jited_ksyms = 2,
4770         .err_str = "Invalid line_info[2].insn_off",
4771         .expected_prog_load_failure = true,
4772 },
4773
4774 {
4775         .descr = "line_info (dead start)",
4776         .raw_types = {
4777                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4778                 BTF_END_RAW,
4779         },
4780         BTF_STR_SEC("\0int\0/* dead jmp */\0int a=1;\0int b=2;\0return a + b;\0return a + b;"),
4781         .insns = {
4782                 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
4783                 BPF_MOV64_IMM(BPF_REG_0, 1),
4784                 BPF_MOV64_IMM(BPF_REG_1, 2),
4785                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4786                 BPF_EXIT_INSN(),
4787         },
4788         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4789         .func_info_cnt = 0,
4790         .line_info = {
4791                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4792                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 9),
4793                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 8),
4794                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 7),
4795                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 5, 6),
4796                 BTF_END_RAW,
4797         },
4798         .line_info_rec_size = sizeof(struct bpf_line_info),
4799         .nr_jited_ksyms = 1,
4800         .dead_code_cnt = 1,
4801         .dead_code_mask = 0x01,
4802 },
4803
4804 {
4805         .descr = "line_info (dead end)",
4806         .raw_types = {
4807                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4808                 BTF_END_RAW,
4809         },
4810         BTF_STR_SEC("\0int\0int a=1;\0int b=2;\0return a + b;\0/* dead jmp */\0return a + b;\0/* dead exit */"),
4811         .insns = {
4812                 BPF_MOV64_IMM(BPF_REG_0, 1),
4813                 BPF_MOV64_IMM(BPF_REG_1, 2),
4814                 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4815                 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 10, 1),
4816                 BPF_EXIT_INSN(),
4817                 BPF_EXIT_INSN(),
4818         },
4819         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4820         .func_info_cnt = 0,
4821         .line_info = {
4822                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 12),
4823                 BPF_LINE_INFO_ENC(1, 0, NAME_TBD, 2, 11),
4824                 BPF_LINE_INFO_ENC(2, 0, NAME_TBD, 3, 10),
4825                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 4, 9),
4826                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 5, 8),
4827                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 6, 7),
4828                 BTF_END_RAW,
4829         },
4830         .line_info_rec_size = sizeof(struct bpf_line_info),
4831         .nr_jited_ksyms = 1,
4832         .dead_code_cnt = 2,
4833         .dead_code_mask = 0x28,
4834 },
4835
4836 {
4837         .descr = "line_info (dead code + subprog + func_info)",
4838         .raw_types = {
4839                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4840                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
4841                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4842                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
4843                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
4844                 BTF_END_RAW,
4845         },
4846         BTF_STR_SEC("\0int\0x\0sub\0main\0int a=1+1;\0/* dead jmp */"
4847                     "\0/* dead */\0/* dead */\0/* dead */\0/* dead */"
4848                     "\0/* dead */\0/* dead */\0/* dead */\0/* dead */"
4849                     "\0return func(a);\0b+=1;\0return b;"),
4850         .insns = {
4851                 BPF_MOV64_IMM(BPF_REG_2, 1),
4852                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
4853                 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4854                 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 8),
4855                 BPF_MOV64_IMM(BPF_REG_2, 1),
4856                 BPF_MOV64_IMM(BPF_REG_2, 1),
4857                 BPF_MOV64_IMM(BPF_REG_2, 1),
4858                 BPF_MOV64_IMM(BPF_REG_2, 1),
4859                 BPF_MOV64_IMM(BPF_REG_2, 1),
4860                 BPF_MOV64_IMM(BPF_REG_2, 1),
4861                 BPF_MOV64_IMM(BPF_REG_2, 1),
4862                 BPF_MOV64_IMM(BPF_REG_2, 1),
4863                 BPF_CALL_REL(1),
4864                 BPF_EXIT_INSN(),
4865                 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
4866                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4867                 BPF_EXIT_INSN(),
4868         },
4869         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4870         .func_info_cnt = 2,
4871         .func_info_rec_size = 8,
4872         .func_info = { {0, 4}, {14, 3} },
4873         .line_info = {
4874                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4875                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 1, 10),
4876                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 1, 10),
4877                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 1, 10),
4878                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
4879                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 1, 10),
4880                 BPF_LINE_INFO_ENC(8, 0, NAME_TBD, 1, 10),
4881                 BPF_LINE_INFO_ENC(9, 0, NAME_TBD, 1, 10),
4882                 BPF_LINE_INFO_ENC(10, 0, NAME_TBD, 1, 10),
4883                 BPF_LINE_INFO_ENC(11, 0, NAME_TBD, 2, 9),
4884                 BPF_LINE_INFO_ENC(12, 0, NAME_TBD, 2, 9),
4885                 BPF_LINE_INFO_ENC(14, 0, NAME_TBD, 3, 8),
4886                 BPF_LINE_INFO_ENC(16, 0, NAME_TBD, 4, 7),
4887                 BTF_END_RAW,
4888         },
4889         .line_info_rec_size = sizeof(struct bpf_line_info),
4890         .nr_jited_ksyms = 2,
4891         .dead_code_cnt = 9,
4892         .dead_code_mask = 0x3fe,
4893 },
4894
4895 {
4896         .descr = "line_info (dead subprog)",
4897         .raw_types = {
4898                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4899                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
4900                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4901                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
4902                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
4903                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [5] */
4904                 BTF_END_RAW,
4905         },
4906         BTF_STR_SEC("\0int\0x\0dead\0main\0func\0int a=1+1;\0/* live call */"
4907                     "\0return 0;\0return 0;\0/* dead */\0/* dead */"
4908                     "\0/* dead */\0return bla + 1;\0return bla + 1;"
4909                     "\0return bla + 1;\0return func(a);\0b+=1;\0return b;"),
4910         .insns = {
4911                 BPF_MOV64_IMM(BPF_REG_2, 1),
4912                 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
4913                 BPF_CALL_REL(3),
4914                 BPF_CALL_REL(5),
4915                 BPF_MOV64_IMM(BPF_REG_0, 0),
4916                 BPF_EXIT_INSN(),
4917                 BPF_MOV64_IMM(BPF_REG_0, 0),
4918                 BPF_CALL_REL(1),
4919                 BPF_EXIT_INSN(),
4920                 BPF_MOV64_REG(BPF_REG_0, 2),
4921                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
4922                 BPF_EXIT_INSN(),
4923         },
4924         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4925         .func_info_cnt = 3,
4926         .func_info_rec_size = 8,
4927                 .func_info = { {0, 4}, {6, 3}, {9, 5} },
4928         .line_info = {
4929                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4930                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 1, 10),
4931                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 1, 10),
4932                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 1, 10),
4933                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
4934                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 1, 10),
4935                 BPF_LINE_INFO_ENC(8, 0, NAME_TBD, 1, 10),
4936                 BPF_LINE_INFO_ENC(9, 0, NAME_TBD, 1, 10),
4937                 BPF_LINE_INFO_ENC(10, 0, NAME_TBD, 1, 10),
4938                 BPF_LINE_INFO_ENC(11, 0, NAME_TBD, 2, 9),
4939                 BTF_END_RAW,
4940         },
4941         .line_info_rec_size = sizeof(struct bpf_line_info),
4942         .nr_jited_ksyms = 2,
4943         .dead_code_cnt = 3,
4944         .dead_code_mask = 0x70,
4945         .dead_func_cnt = 1,
4946         .dead_func_mask = 0x2,
4947 },
4948
4949 {
4950         .descr = "line_info (dead last subprog)",
4951         .raw_types = {
4952                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4953                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
4954                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4955                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
4956                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [5] */
4957                 BTF_END_RAW,
4958         },
4959         BTF_STR_SEC("\0int\0x\0dead\0main\0int a=1+1;\0/* live call */"
4960                     "\0return 0;\0/* dead */\0/* dead */"),
4961         .insns = {
4962                 BPF_MOV64_IMM(BPF_REG_2, 1),
4963                 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
4964                 BPF_CALL_REL(2),
4965                 BPF_MOV64_IMM(BPF_REG_0, 0),
4966                 BPF_EXIT_INSN(),
4967                 BPF_MOV64_IMM(BPF_REG_0, 0),
4968                 BPF_EXIT_INSN(),
4969         },
4970         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4971         .func_info_cnt = 2,
4972         .func_info_rec_size = 8,
4973                 .func_info = { {0, 4}, {5, 3} },
4974         .line_info = {
4975                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
4976                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 1, 10),
4977                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 1, 10),
4978                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 1, 10),
4979                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
4980                 BTF_END_RAW,
4981         },
4982         .line_info_rec_size = sizeof(struct bpf_line_info),
4983         .nr_jited_ksyms = 1,
4984         .dead_code_cnt = 2,
4985         .dead_code_mask = 0x18,
4986         .dead_func_cnt = 1,
4987         .dead_func_mask = 0x2,
4988 },
4989
4990 {
4991         .descr = "line_info (dead subprog + dead start)",
4992         .raw_types = {
4993                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
4994                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
4995                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
4996                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
4997                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
4998                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [5] */
4999                 BTF_END_RAW,
5000         },
5001         BTF_STR_SEC("\0int\0x\0dead\0main\0func\0int a=1+1;\0/* dead */"
5002                     "\0return 0;\0return 0;\0return 0;"
5003                     "\0/* dead */\0/* dead */\0/* dead */\0/* dead */"
5004                     "\0return b + 1;\0return b + 1;\0return b + 1;"),
5005         .insns = {
5006                 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
5007                 BPF_MOV64_IMM(BPF_REG_2, 1),
5008                 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
5009                 BPF_CALL_REL(3),
5010                 BPF_CALL_REL(5),
5011                 BPF_MOV64_IMM(BPF_REG_0, 0),
5012                 BPF_EXIT_INSN(),
5013                 BPF_MOV64_IMM(BPF_REG_0, 0),
5014                 BPF_CALL_REL(1),
5015                 BPF_EXIT_INSN(),
5016                 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
5017                 BPF_MOV64_REG(BPF_REG_0, 2),
5018                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
5019                 BPF_EXIT_INSN(),
5020         },
5021         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5022         .func_info_cnt = 3,
5023         .func_info_rec_size = 8,
5024                 .func_info = { {0, 4}, {7, 3}, {10, 5} },
5025         .line_info = {
5026                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
5027                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 1, 10),
5028                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 1, 10),
5029                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 1, 10),
5030                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
5031                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 1, 10),
5032                 BPF_LINE_INFO_ENC(8, 0, NAME_TBD, 1, 10),
5033                 BPF_LINE_INFO_ENC(9, 0, NAME_TBD, 1, 10),
5034                 BPF_LINE_INFO_ENC(10, 0, NAME_TBD, 1, 10),
5035                 BPF_LINE_INFO_ENC(11, 0, NAME_TBD, 2, 9),
5036                 BPF_LINE_INFO_ENC(12, 0, NAME_TBD, 2, 9),
5037                 BPF_LINE_INFO_ENC(13, 0, NAME_TBD, 2, 9),
5038                 BTF_END_RAW,
5039         },
5040         .line_info_rec_size = sizeof(struct bpf_line_info),
5041         .nr_jited_ksyms = 2,
5042         .dead_code_cnt = 5,
5043         .dead_code_mask = 0x1e2,
5044         .dead_func_cnt = 1,
5045         .dead_func_mask = 0x2,
5046 },
5047
5048 {
5049         .descr = "line_info (dead subprog + dead start w/ move)",
5050         .raw_types = {
5051                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
5052                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
5053                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
5054                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
5055                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
5056                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [5] */
5057                 BTF_END_RAW,
5058         },
5059         BTF_STR_SEC("\0int\0x\0dead\0main\0func\0int a=1+1;\0/* live call */"
5060                     "\0return 0;\0return 0;\0/* dead */\0/* dead */"
5061                     "\0/* dead */\0return bla + 1;\0return bla + 1;"
5062                     "\0return bla + 1;\0return func(a);\0b+=1;\0return b;"),
5063         .insns = {
5064                 BPF_MOV64_IMM(BPF_REG_2, 1),
5065                 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
5066                 BPF_CALL_REL(3),
5067                 BPF_CALL_REL(5),
5068                 BPF_MOV64_IMM(BPF_REG_0, 0),
5069                 BPF_EXIT_INSN(),
5070                 BPF_MOV64_IMM(BPF_REG_0, 0),
5071                 BPF_CALL_REL(1),
5072                 BPF_EXIT_INSN(),
5073                 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
5074                 BPF_MOV64_REG(BPF_REG_0, 2),
5075                 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
5076                 BPF_EXIT_INSN(),
5077         },
5078         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5079         .func_info_cnt = 3,
5080         .func_info_rec_size = 8,
5081                 .func_info = { {0, 4}, {6, 3}, {9, 5} },
5082         .line_info = {
5083                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
5084                 BPF_LINE_INFO_ENC(3, 0, NAME_TBD, 1, 10),
5085                 BPF_LINE_INFO_ENC(4, 0, NAME_TBD, 1, 10),
5086                 BPF_LINE_INFO_ENC(5, 0, NAME_TBD, 1, 10),
5087                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
5088                 BPF_LINE_INFO_ENC(7, 0, NAME_TBD, 1, 10),
5089                 BPF_LINE_INFO_ENC(8, 0, NAME_TBD, 1, 10),
5090                 BPF_LINE_INFO_ENC(9, 0, NAME_TBD, 1, 10),
5091                 BPF_LINE_INFO_ENC(11, 0, NAME_TBD, 1, 10),
5092                 BPF_LINE_INFO_ENC(12, 0, NAME_TBD, 2, 9),
5093                 BTF_END_RAW,
5094         },
5095         .line_info_rec_size = sizeof(struct bpf_line_info),
5096         .nr_jited_ksyms = 2,
5097         .dead_code_cnt = 3,
5098         .dead_code_mask = 0x70,
5099         .dead_func_cnt = 1,
5100         .dead_func_mask = 0x2,
5101 },
5102
5103 {
5104         .descr = "line_info (dead end + subprog start w/ no linfo)",
5105         .raw_types = {
5106                 BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 4),   /* [1] */
5107                 BTF_FUNC_PROTO_ENC(1, 1),                       /* [2] */
5108                         BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
5109                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [3] */
5110                 BTF_FUNC_ENC(NAME_TBD, 2),                      /* [4] */
5111                 BTF_END_RAW,
5112         },
5113         BTF_STR_SEC("\0int\0x\0main\0func\0/* main linfo */\0/* func linfo */"),
5114         .insns = {
5115                 BPF_MOV64_IMM(BPF_REG_0, 0),
5116                 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 1, 3),
5117                 BPF_CALL_REL(3),
5118                 BPF_MOV64_IMM(BPF_REG_0, 0),
5119                 BPF_EXIT_INSN(),
5120                 BPF_EXIT_INSN(),
5121                 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
5122                 BPF_EXIT_INSN(),
5123         },
5124         .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5125         .func_info_cnt = 2,
5126         .func_info_rec_size = 8,
5127         .func_info = { {0, 3}, {6, 4}, },
5128         .line_info = {
5129                 BPF_LINE_INFO_ENC(0, 0, NAME_TBD, 1, 10),
5130                 BPF_LINE_INFO_ENC(6, 0, NAME_TBD, 1, 10),
5131                 BTF_END_RAW,
5132         },
5133         .line_info_rec_size = sizeof(struct bpf_line_info),
5134         .nr_jited_ksyms = 2,
5135 },
5136
5137 };
5138
5139 static size_t probe_prog_length(const struct bpf_insn *fp)
5140 {
5141         size_t len;
5142
5143         for (len = MAX_INSNS - 1; len > 0; --len)
5144                 if (fp[len].code != 0 || fp[len].imm != 0)
5145                         break;
5146         return len + 1;
5147 }
5148
5149 static __u32 *patch_name_tbd(const __u32 *raw_u32,
5150                              const char *str, __u32 str_off,
5151                              unsigned int str_sec_size,
5152                              unsigned int *ret_size)
5153 {
5154         int i, raw_u32_size = get_raw_sec_size(raw_u32);
5155         const char *end_str = str + str_sec_size;
5156         const char *next_str = str + str_off;
5157         __u32 *new_u32 = NULL;
5158
5159         if (raw_u32_size == -1)
5160                 return ERR_PTR(-EINVAL);
5161
5162         if (!raw_u32_size) {
5163                 *ret_size = 0;
5164                 return NULL;
5165         }
5166
5167         new_u32 = malloc(raw_u32_size);
5168         if (!new_u32)
5169                 return ERR_PTR(-ENOMEM);
5170
5171         for (i = 0; i < raw_u32_size / sizeof(raw_u32[0]); i++) {
5172                 if (raw_u32[i] == NAME_TBD) {
5173                         next_str = get_next_str(next_str, end_str);
5174                         if (CHECK(!next_str, "Error in getting next_str\n")) {
5175                                 free(new_u32);
5176                                 return ERR_PTR(-EINVAL);
5177                         }
5178                         new_u32[i] = next_str - str;
5179                         next_str += strlen(next_str);
5180                 } else {
5181                         new_u32[i] = raw_u32[i];
5182                 }
5183         }
5184
5185         *ret_size = raw_u32_size;
5186         return new_u32;
5187 }
5188
5189 static int test_get_finfo(const struct prog_info_raw_test *test,
5190                           int prog_fd)
5191 {
5192         struct bpf_prog_info info = {};
5193         struct bpf_func_info *finfo;
5194         __u32 info_len, rec_size, i;
5195         void *func_info = NULL;
5196         __u32 nr_func_info;
5197         int err;
5198
5199         /* get necessary lens */
5200         info_len = sizeof(struct bpf_prog_info);
5201         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
5202         if (CHECK(err == -1, "invalid get info (1st) errno:%d", errno)) {
5203                 fprintf(stderr, "%s\n", btf_log_buf);
5204                 return -1;
5205         }
5206         nr_func_info = test->func_info_cnt - test->dead_func_cnt;
5207         if (CHECK(info.nr_func_info != nr_func_info,
5208                   "incorrect info.nr_func_info (1st) %d",
5209                   info.nr_func_info)) {
5210                 return -1;
5211         }
5212
5213         rec_size = info.func_info_rec_size;
5214         if (CHECK(rec_size != sizeof(struct bpf_func_info),
5215                   "incorrect info.func_info_rec_size (1st) %d", rec_size)) {
5216                 return -1;
5217         }
5218
5219         if (!info.nr_func_info)
5220                 return 0;
5221
5222         func_info = malloc(info.nr_func_info * rec_size);
5223         if (CHECK(!func_info, "out of memory"))
5224                 return -1;
5225
5226         /* reset info to only retrieve func_info related data */
5227         memset(&info, 0, sizeof(info));
5228         info.nr_func_info = nr_func_info;
5229         info.func_info_rec_size = rec_size;
5230         info.func_info = ptr_to_u64(func_info);
5231         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
5232         if (CHECK(err == -1, "invalid get info (2nd) errno:%d", errno)) {
5233                 fprintf(stderr, "%s\n", btf_log_buf);
5234                 err = -1;
5235                 goto done;
5236         }
5237         if (CHECK(info.nr_func_info != nr_func_info,
5238                   "incorrect info.nr_func_info (2nd) %d",
5239                   info.nr_func_info)) {
5240                 err = -1;
5241                 goto done;
5242         }
5243         if (CHECK(info.func_info_rec_size != rec_size,
5244                   "incorrect info.func_info_rec_size (2nd) %d",
5245                   info.func_info_rec_size)) {
5246                 err = -1;
5247                 goto done;
5248         }
5249
5250         finfo = func_info;
5251         for (i = 0; i < nr_func_info; i++) {
5252                 if (test->dead_func_mask & (1 << i))
5253                         continue;
5254                 if (CHECK(finfo->type_id != test->func_info[i][1],
5255                           "incorrect func_type %u expected %u",
5256                           finfo->type_id, test->func_info[i][1])) {
5257                         err = -1;
5258                         goto done;
5259                 }
5260                 finfo = (void *)finfo + rec_size;
5261         }
5262
5263         err = 0;
5264
5265 done:
5266         free(func_info);
5267         return err;
5268 }
5269
5270 static int test_get_linfo(const struct prog_info_raw_test *test,
5271                           const void *patched_linfo,
5272                           __u32 cnt, int prog_fd)
5273 {
5274         __u32 i, info_len, nr_jited_ksyms, nr_jited_func_lens;
5275         __u64 *jited_linfo = NULL, *jited_ksyms = NULL;
5276         __u32 rec_size, jited_rec_size, jited_cnt;
5277         struct bpf_line_info *linfo = NULL;
5278         __u32 cur_func_len, ksyms_found;
5279         struct bpf_prog_info info = {};
5280         __u32 *jited_func_lens = NULL;
5281         __u64 cur_func_ksyms;
5282         __u32 dead_insns;
5283         int err;
5284
5285         jited_cnt = cnt;
5286         rec_size = sizeof(*linfo);
5287         jited_rec_size = sizeof(*jited_linfo);
5288         if (test->nr_jited_ksyms)
5289                 nr_jited_ksyms = test->nr_jited_ksyms;
5290         else
5291                 nr_jited_ksyms = test->func_info_cnt - test->dead_func_cnt;
5292         nr_jited_func_lens = nr_jited_ksyms;
5293
5294         info_len = sizeof(struct bpf_prog_info);
5295         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
5296         if (CHECK(err == -1, "err:%d errno:%d", err, errno)) {
5297                 err = -1;
5298                 goto done;
5299         }
5300
5301         if (!info.jited_prog_len) {
5302                 /* prog is not jited */
5303                 jited_cnt = 0;
5304                 nr_jited_ksyms = 1;
5305                 nr_jited_func_lens = 1;
5306         }
5307
5308         if (CHECK(info.nr_line_info != cnt ||
5309                   info.nr_jited_line_info != jited_cnt ||
5310                   info.nr_jited_ksyms != nr_jited_ksyms ||
5311                   info.nr_jited_func_lens != nr_jited_func_lens ||
5312                   (!info.nr_line_info && info.nr_jited_line_info),
5313                   "info: nr_line_info:%u(expected:%u) nr_jited_line_info:%u(expected:%u) nr_jited_ksyms:%u(expected:%u) nr_jited_func_lens:%u(expected:%u)",
5314                   info.nr_line_info, cnt,
5315                   info.nr_jited_line_info, jited_cnt,
5316                   info.nr_jited_ksyms, nr_jited_ksyms,
5317                   info.nr_jited_func_lens, nr_jited_func_lens)) {
5318                 err = -1;
5319                 goto done;
5320         }
5321
5322         if (CHECK(info.line_info_rec_size != sizeof(struct bpf_line_info) ||
5323                   info.jited_line_info_rec_size != sizeof(__u64),
5324                   "info: line_info_rec_size:%u(userspace expected:%u) jited_line_info_rec_size:%u(userspace expected:%u)",
5325                   info.line_info_rec_size, rec_size,
5326                   info.jited_line_info_rec_size, jited_rec_size)) {
5327                 err = -1;
5328                 goto done;
5329         }
5330
5331         if (!cnt)
5332                 return 0;
5333
5334         rec_size = info.line_info_rec_size;
5335         jited_rec_size = info.jited_line_info_rec_size;
5336
5337         memset(&info, 0, sizeof(info));
5338
5339         linfo = calloc(cnt, rec_size);
5340         if (CHECK(!linfo, "!linfo")) {
5341                 err = -1;
5342                 goto done;
5343         }
5344         info.nr_line_info = cnt;
5345         info.line_info_rec_size = rec_size;
5346         info.line_info = ptr_to_u64(linfo);
5347
5348         if (jited_cnt) {
5349                 jited_linfo = calloc(jited_cnt, jited_rec_size);
5350                 jited_ksyms = calloc(nr_jited_ksyms, sizeof(*jited_ksyms));
5351                 jited_func_lens = calloc(nr_jited_func_lens,
5352                                          sizeof(*jited_func_lens));
5353                 if (CHECK(!jited_linfo || !jited_ksyms || !jited_func_lens,
5354                           "jited_linfo:%p jited_ksyms:%p jited_func_lens:%p",
5355                           jited_linfo, jited_ksyms, jited_func_lens)) {
5356                         err = -1;
5357                         goto done;
5358                 }
5359
5360                 info.nr_jited_line_info = jited_cnt;
5361                 info.jited_line_info_rec_size = jited_rec_size;
5362                 info.jited_line_info = ptr_to_u64(jited_linfo);
5363                 info.nr_jited_ksyms = nr_jited_ksyms;
5364                 info.jited_ksyms = ptr_to_u64(jited_ksyms);
5365                 info.nr_jited_func_lens = nr_jited_func_lens;
5366                 info.jited_func_lens = ptr_to_u64(jited_func_lens);
5367         }
5368
5369         err = bpf_obj_get_info_by_fd(prog_fd, &info, &info_len);
5370
5371         /*
5372          * Only recheck the info.*line_info* fields.
5373          * Other fields are not the concern of this test.
5374          */
5375         if (CHECK(err == -1 ||
5376                   info.nr_line_info != cnt ||
5377                   (jited_cnt && !info.jited_line_info) ||
5378                   info.nr_jited_line_info != jited_cnt ||
5379                   info.line_info_rec_size != rec_size ||
5380                   info.jited_line_info_rec_size != jited_rec_size,
5381                   "err:%d errno:%d info: nr_line_info:%u(expected:%u) nr_jited_line_info:%u(expected:%u) line_info_rec_size:%u(expected:%u) jited_linfo_rec_size:%u(expected:%u) line_info:%p jited_line_info:%p",
5382                   err, errno,
5383                   info.nr_line_info, cnt,
5384                   info.nr_jited_line_info, jited_cnt,
5385                   info.line_info_rec_size, rec_size,
5386                   info.jited_line_info_rec_size, jited_rec_size,
5387                   (void *)(long)info.line_info,
5388                   (void *)(long)info.jited_line_info)) {
5389                 err = -1;
5390                 goto done;
5391         }
5392
5393         dead_insns = 0;
5394         while (test->dead_code_mask & (1 << dead_insns))
5395                 dead_insns++;
5396
5397         CHECK(linfo[0].insn_off, "linfo[0].insn_off:%u",
5398               linfo[0].insn_off);
5399         for (i = 1; i < cnt; i++) {
5400                 const struct bpf_line_info *expected_linfo;
5401
5402                 while (test->dead_code_mask & (1 << (i + dead_insns)))
5403                         dead_insns++;
5404
5405                 expected_linfo = patched_linfo +
5406                         ((i + dead_insns) * test->line_info_rec_size);
5407                 if (CHECK(linfo[i].insn_off <= linfo[i - 1].insn_off,
5408                           "linfo[%u].insn_off:%u <= linfo[%u].insn_off:%u",
5409                           i, linfo[i].insn_off,
5410                           i - 1, linfo[i - 1].insn_off)) {
5411                         err = -1;
5412                         goto done;
5413                 }
5414                 if (CHECK(linfo[i].file_name_off != expected_linfo->file_name_off ||
5415                           linfo[i].line_off != expected_linfo->line_off ||
5416                           linfo[i].line_col != expected_linfo->line_col,
5417                           "linfo[%u] (%u, %u, %u) != (%u, %u, %u)", i,
5418                           linfo[i].file_name_off,
5419                           linfo[i].line_off,
5420                           linfo[i].line_col,
5421                           expected_linfo->file_name_off,
5422                           expected_linfo->line_off,
5423                           expected_linfo->line_col)) {
5424                         err = -1;
5425                         goto done;
5426                 }
5427         }
5428
5429         if (!jited_cnt) {
5430                 fprintf(stderr, "not jited. skipping jited_line_info check. ");
5431                 err = 0;
5432                 goto done;
5433         }
5434
5435         if (CHECK(jited_linfo[0] != jited_ksyms[0],
5436                   "jited_linfo[0]:%lx != jited_ksyms[0]:%lx",
5437                   (long)(jited_linfo[0]), (long)(jited_ksyms[0]))) {
5438                 err = -1;
5439                 goto done;
5440         }
5441
5442         ksyms_found = 1;
5443         cur_func_len = jited_func_lens[0];
5444         cur_func_ksyms = jited_ksyms[0];
5445         for (i = 1; i < jited_cnt; i++) {
5446                 if (ksyms_found < nr_jited_ksyms &&
5447                     jited_linfo[i] == jited_ksyms[ksyms_found]) {
5448                         cur_func_ksyms = jited_ksyms[ksyms_found];
5449                         cur_func_len = jited_ksyms[ksyms_found];
5450                         ksyms_found++;
5451                         continue;
5452                 }
5453
5454                 if (CHECK(jited_linfo[i] <= jited_linfo[i - 1],
5455                           "jited_linfo[%u]:%lx <= jited_linfo[%u]:%lx",
5456                           i, (long)jited_linfo[i],
5457                           i - 1, (long)(jited_linfo[i - 1]))) {
5458                         err = -1;
5459                         goto done;
5460                 }
5461
5462                 if (CHECK(jited_linfo[i] - cur_func_ksyms > cur_func_len,
5463                           "jited_linfo[%u]:%lx - %lx > %u",
5464                           i, (long)jited_linfo[i], (long)cur_func_ksyms,
5465                           cur_func_len)) {
5466                         err = -1;
5467                         goto done;
5468                 }
5469         }
5470
5471         if (CHECK(ksyms_found != nr_jited_ksyms,
5472                   "ksyms_found:%u != nr_jited_ksyms:%u",
5473                   ksyms_found, nr_jited_ksyms)) {
5474                 err = -1;
5475                 goto done;
5476         }
5477
5478         err = 0;
5479
5480 done:
5481         free(linfo);
5482         free(jited_linfo);
5483         free(jited_ksyms);
5484         free(jited_func_lens);
5485         return err;
5486 }
5487
5488 static int do_test_info_raw(unsigned int test_num)
5489 {
5490         const struct prog_info_raw_test *test = &info_raw_tests[test_num - 1];
5491         unsigned int raw_btf_size, linfo_str_off, linfo_size;
5492         int btf_fd = -1, prog_fd = -1, err = 0;
5493         void *raw_btf, *patched_linfo = NULL;
5494         const char *ret_next_str;
5495         union bpf_attr attr = {};
5496
5497         fprintf(stderr, "BTF prog info raw test[%u] (%s): ", test_num, test->descr);
5498         raw_btf = btf_raw_create(&hdr_tmpl, test->raw_types,
5499                                  test->str_sec, test->str_sec_size,
5500                                  &raw_btf_size, &ret_next_str);
5501
5502         if (!raw_btf)
5503                 return -1;
5504
5505         *btf_log_buf = '\0';
5506         btf_fd = bpf_load_btf(raw_btf, raw_btf_size,
5507                               btf_log_buf, BTF_LOG_BUF_SIZE,
5508                               args.always_log);
5509         free(raw_btf);
5510
5511         if (CHECK(btf_fd == -1, "invalid btf_fd errno:%d", errno)) {
5512                 err = -1;
5513                 goto done;
5514         }
5515
5516         if (*btf_log_buf && args.always_log)
5517                 fprintf(stderr, "\n%s", btf_log_buf);
5518         *btf_log_buf = '\0';
5519
5520         linfo_str_off = ret_next_str - test->str_sec;
5521         patched_linfo = patch_name_tbd(test->line_info,
5522                                        test->str_sec, linfo_str_off,
5523                                        test->str_sec_size, &linfo_size);
5524         if (IS_ERR(patched_linfo)) {
5525                 fprintf(stderr, "error in creating raw bpf_line_info");
5526                 err = -1;
5527                 goto done;
5528         }
5529
5530         attr.prog_type = test->prog_type;
5531         attr.insns = ptr_to_u64(test->insns);
5532         attr.insn_cnt = probe_prog_length(test->insns);
5533         attr.license = ptr_to_u64("GPL");
5534         attr.prog_btf_fd = btf_fd;
5535         attr.func_info_rec_size = test->func_info_rec_size;
5536         attr.func_info_cnt = test->func_info_cnt;
5537         attr.func_info = ptr_to_u64(test->func_info);
5538         attr.log_buf = ptr_to_u64(btf_log_buf);
5539         attr.log_size = BTF_LOG_BUF_SIZE;
5540         attr.log_level = 1;
5541         if (linfo_size) {
5542                 attr.line_info_rec_size = test->line_info_rec_size;
5543                 attr.line_info = ptr_to_u64(patched_linfo);
5544                 attr.line_info_cnt = linfo_size / attr.line_info_rec_size;
5545         }
5546
5547         prog_fd = syscall(__NR_bpf, BPF_PROG_LOAD, &attr, sizeof(attr));
5548         err = ((prog_fd == -1) != test->expected_prog_load_failure);
5549         if (CHECK(err, "prog_fd:%d expected_prog_load_failure:%u errno:%d",
5550                   prog_fd, test->expected_prog_load_failure, errno) ||
5551             CHECK(test->err_str && !strstr(btf_log_buf, test->err_str),
5552                   "expected err_str:%s", test->err_str)) {
5553                 err = -1;
5554                 goto done;
5555         }
5556
5557         if (prog_fd == -1)
5558                 goto done;
5559
5560         err = test_get_finfo(test, prog_fd);
5561         if (err)
5562                 goto done;
5563
5564         err = test_get_linfo(test, patched_linfo,
5565                              attr.line_info_cnt - test->dead_code_cnt,
5566                              prog_fd);
5567         if (err)
5568                 goto done;
5569
5570 done:
5571         if (!err)
5572                 fprintf(stderr, "OK");
5573
5574         if (*btf_log_buf && (err || args.always_log))
5575                 fprintf(stderr, "\n%s", btf_log_buf);
5576
5577         if (btf_fd != -1)
5578                 close(btf_fd);
5579         if (prog_fd != -1)
5580                 close(prog_fd);
5581
5582         if (!IS_ERR(patched_linfo))
5583                 free(patched_linfo);
5584
5585         return err;
5586 }
5587
5588 static int test_info_raw(void)
5589 {
5590         unsigned int i;
5591         int err = 0;
5592
5593         if (args.info_raw_test_num)
5594                 return count_result(do_test_info_raw(args.info_raw_test_num));
5595
5596         for (i = 1; i <= ARRAY_SIZE(info_raw_tests); i++)
5597                 err |= count_result(do_test_info_raw(i));
5598
5599         return err;
5600 }
5601
5602 struct btf_raw_data {
5603         __u32 raw_types[MAX_NR_RAW_U32];
5604         const char *str_sec;
5605         __u32 str_sec_size;
5606 };
5607
5608 struct btf_dedup_test {
5609         const char *descr;
5610         struct btf_raw_data input;
5611         struct btf_raw_data expect;
5612         struct btf_dedup_opts opts;
5613 };
5614
5615 const struct btf_dedup_test dedup_tests[] = {
5616
5617 {
5618         .descr = "dedup: unused strings filtering",
5619         .input = {
5620                 .raw_types = {
5621                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 32, 4),
5622                         BTF_TYPE_INT_ENC(NAME_NTH(5), BTF_INT_SIGNED, 0, 64, 8),
5623                         BTF_END_RAW,
5624                 },
5625                 BTF_STR_SEC("\0unused\0int\0foo\0bar\0long"),
5626         },
5627         .expect = {
5628                 .raw_types = {
5629                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),
5630                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 64, 8),
5631                         BTF_END_RAW,
5632                 },
5633                 BTF_STR_SEC("\0int\0long"),
5634         },
5635         .opts = {
5636                 .dont_resolve_fwds = false,
5637         },
5638 },
5639 {
5640         .descr = "dedup: strings deduplication",
5641         .input = {
5642                 .raw_types = {
5643                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),
5644                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 64, 8),
5645                         BTF_TYPE_INT_ENC(NAME_NTH(3), BTF_INT_SIGNED, 0, 32, 4),
5646                         BTF_TYPE_INT_ENC(NAME_NTH(4), BTF_INT_SIGNED, 0, 64, 8),
5647                         BTF_TYPE_INT_ENC(NAME_NTH(5), BTF_INT_SIGNED, 0, 32, 4),
5648                         BTF_END_RAW,
5649                 },
5650                 BTF_STR_SEC("\0int\0long int\0int\0long int\0int"),
5651         },
5652         .expect = {
5653                 .raw_types = {
5654                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),
5655                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 64, 8),
5656                         BTF_END_RAW,
5657                 },
5658                 BTF_STR_SEC("\0int\0long int"),
5659         },
5660         .opts = {
5661                 .dont_resolve_fwds = false,
5662         },
5663 },
5664 {
5665         .descr = "dedup: struct example #1",
5666         /*
5667          * struct s {
5668          *      struct s *next;
5669          *      const int *a;
5670          *      int b[16];
5671          *      int c;
5672          * }
5673          */
5674         .input = {
5675                 .raw_types = {
5676                         /* int */
5677                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),        /* [1] */
5678                         /* int[16] */
5679                         BTF_TYPE_ARRAY_ENC(1, 1, 16),                                   /* [2] */
5680                         /* struct s { */
5681                         BTF_STRUCT_ENC(NAME_NTH(2), 4, 84),                             /* [3] */
5682                                 BTF_MEMBER_ENC(NAME_NTH(3), 4, 0),      /* struct s *next;      */
5683                                 BTF_MEMBER_ENC(NAME_NTH(4), 5, 64),     /* const int *a;        */
5684                                 BTF_MEMBER_ENC(NAME_NTH(5), 2, 128),    /* int b[16];           */
5685                                 BTF_MEMBER_ENC(NAME_NTH(6), 1, 640),    /* int c;               */
5686                         /* ptr -> [3] struct s */
5687                         BTF_PTR_ENC(3),                                                 /* [4] */
5688                         /* ptr -> [6] const int */
5689                         BTF_PTR_ENC(6),                                                 /* [5] */
5690                         /* const -> [1] int */
5691                         BTF_CONST_ENC(1),                                               /* [6] */
5692
5693                         /* full copy of the above */
5694                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),        /* [7] */
5695                         BTF_TYPE_ARRAY_ENC(7, 7, 16),                                   /* [8] */
5696                         BTF_STRUCT_ENC(NAME_NTH(2), 4, 84),                             /* [9] */
5697                                 BTF_MEMBER_ENC(NAME_NTH(3), 10, 0),
5698                                 BTF_MEMBER_ENC(NAME_NTH(4), 11, 64),
5699                                 BTF_MEMBER_ENC(NAME_NTH(5), 8, 128),
5700                                 BTF_MEMBER_ENC(NAME_NTH(6), 7, 640),
5701                         BTF_PTR_ENC(9),                                                 /* [10] */
5702                         BTF_PTR_ENC(12),                                                /* [11] */
5703                         BTF_CONST_ENC(7),                                               /* [12] */
5704                         BTF_END_RAW,
5705                 },
5706                 BTF_STR_SEC("\0int\0s\0next\0a\0b\0c\0"),
5707         },
5708         .expect = {
5709                 .raw_types = {
5710                         /* int */
5711                         BTF_TYPE_INT_ENC(NAME_NTH(4), BTF_INT_SIGNED, 0, 32, 4),        /* [1] */
5712                         /* int[16] */
5713                         BTF_TYPE_ARRAY_ENC(1, 1, 16),                                   /* [2] */
5714                         /* struct s { */
5715                         BTF_STRUCT_ENC(NAME_NTH(6), 4, 84),                             /* [3] */
5716                                 BTF_MEMBER_ENC(NAME_NTH(5), 4, 0),      /* struct s *next;      */
5717                                 BTF_MEMBER_ENC(NAME_NTH(1), 5, 64),     /* const int *a;        */
5718                                 BTF_MEMBER_ENC(NAME_NTH(2), 2, 128),    /* int b[16];           */
5719                                 BTF_MEMBER_ENC(NAME_NTH(3), 1, 640),    /* int c;               */
5720                         /* ptr -> [3] struct s */
5721                         BTF_PTR_ENC(3),                                                 /* [4] */
5722                         /* ptr -> [6] const int */
5723                         BTF_PTR_ENC(6),                                                 /* [5] */
5724                         /* const -> [1] int */
5725                         BTF_CONST_ENC(1),                                               /* [6] */
5726                         BTF_END_RAW,
5727                 },
5728                 BTF_STR_SEC("\0a\0b\0c\0int\0next\0s"),
5729         },
5730         .opts = {
5731                 .dont_resolve_fwds = false,
5732         },
5733 },
5734 {
5735         .descr = "dedup: struct <-> fwd resolution w/ hash collision",
5736         /*
5737          * // CU 1:
5738          * struct x;
5739          * struct s {
5740          *      struct x *x;
5741          * };
5742          * // CU 2:
5743          * struct x {};
5744          * struct s {
5745          *      struct x *x;
5746          * };
5747          */
5748         .input = {
5749                 .raw_types = {
5750                         /* CU 1 */
5751                         BTF_FWD_ENC(NAME_TBD, 0 /* struct fwd */),      /* [1] fwd x      */
5752                         BTF_PTR_ENC(1),                                 /* [2] ptr -> [1] */
5753                         BTF_STRUCT_ENC(NAME_TBD, 1, 8),                 /* [3] struct s   */
5754                                 BTF_MEMBER_ENC(NAME_TBD, 2, 0),
5755                         /* CU 2 */
5756                         BTF_STRUCT_ENC(NAME_TBD, 0, 0),                 /* [4] struct x   */
5757                         BTF_PTR_ENC(4),                                 /* [5] ptr -> [4] */
5758                         BTF_STRUCT_ENC(NAME_TBD, 1, 8),                 /* [6] struct s   */
5759                                 BTF_MEMBER_ENC(NAME_TBD, 5, 0),
5760                         BTF_END_RAW,
5761                 },
5762                 BTF_STR_SEC("\0x\0s\0x\0x\0s\0x\0"),
5763         },
5764         .expect = {
5765                 .raw_types = {
5766                         BTF_PTR_ENC(3),                                 /* [1] ptr -> [3] */
5767                         BTF_STRUCT_ENC(NAME_TBD, 1, 8),                 /* [2] struct s   */
5768                                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
5769                         BTF_STRUCT_ENC(NAME_NTH(2), 0, 0),              /* [3] struct x   */
5770                         BTF_END_RAW,
5771                 },
5772                 BTF_STR_SEC("\0s\0x"),
5773         },
5774         .opts = {
5775                 .dont_resolve_fwds = false,
5776                 .dedup_table_size = 1, /* force hash collisions */
5777         },
5778 },
5779 {
5780         .descr = "dedup: void equiv check",
5781         /*
5782          * // CU 1:
5783          * struct s {
5784          *      struct {} *x;
5785          * };
5786          * // CU 2:
5787          * struct s {
5788          *      int *x;
5789          * };
5790          */
5791         .input = {
5792                 .raw_types = {
5793                         /* CU 1 */
5794                         BTF_STRUCT_ENC(0, 0, 1),                                /* [1] struct {}  */
5795                         BTF_PTR_ENC(1),                                         /* [2] ptr -> [1] */
5796                         BTF_STRUCT_ENC(NAME_NTH(1), 1, 8),                      /* [3] struct s   */
5797                                 BTF_MEMBER_ENC(NAME_NTH(2), 2, 0),
5798                         /* CU 2 */
5799                         BTF_PTR_ENC(0),                                         /* [4] ptr -> void */
5800                         BTF_STRUCT_ENC(NAME_NTH(1), 1, 8),                      /* [5] struct s   */
5801                                 BTF_MEMBER_ENC(NAME_NTH(2), 4, 0),
5802                         BTF_END_RAW,
5803                 },
5804                 BTF_STR_SEC("\0s\0x"),
5805         },
5806         .expect = {
5807                 .raw_types = {
5808                         /* CU 1 */
5809                         BTF_STRUCT_ENC(0, 0, 1),                                /* [1] struct {}  */
5810                         BTF_PTR_ENC(1),                                         /* [2] ptr -> [1] */
5811                         BTF_STRUCT_ENC(NAME_NTH(1), 1, 8),                      /* [3] struct s   */
5812                                 BTF_MEMBER_ENC(NAME_NTH(2), 2, 0),
5813                         /* CU 2 */
5814                         BTF_PTR_ENC(0),                                         /* [4] ptr -> void */
5815                         BTF_STRUCT_ENC(NAME_NTH(1), 1, 8),                      /* [5] struct s   */
5816                                 BTF_MEMBER_ENC(NAME_NTH(2), 4, 0),
5817                         BTF_END_RAW,
5818                 },
5819                 BTF_STR_SEC("\0s\0x"),
5820         },
5821         .opts = {
5822                 .dont_resolve_fwds = false,
5823                 .dedup_table_size = 1, /* force hash collisions */
5824         },
5825 },
5826 {
5827         .descr = "dedup: all possible kinds (no duplicates)",
5828         .input = {
5829                 .raw_types = {
5830                         BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 8),           /* [1] int */
5831                         BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 2), 4),   /* [2] enum */
5832                                 BTF_ENUM_ENC(NAME_TBD, 0),
5833                                 BTF_ENUM_ENC(NAME_TBD, 1),
5834                         BTF_FWD_ENC(NAME_TBD, 1 /* union kind_flag */),                 /* [3] fwd */
5835                         BTF_TYPE_ARRAY_ENC(2, 1, 7),                                    /* [4] array */
5836                         BTF_STRUCT_ENC(NAME_TBD, 1, 4),                                 /* [5] struct */
5837                                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
5838                         BTF_UNION_ENC(NAME_TBD, 1, 4),                                  /* [6] union */
5839                                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
5840                         BTF_TYPEDEF_ENC(NAME_TBD, 1),                                   /* [7] typedef */
5841                         BTF_PTR_ENC(0),                                                 /* [8] ptr */
5842                         BTF_CONST_ENC(8),                                               /* [9] const */
5843                         BTF_VOLATILE_ENC(8),                                            /* [10] volatile */
5844                         BTF_RESTRICT_ENC(8),                                            /* [11] restrict */
5845                         BTF_FUNC_PROTO_ENC(1, 2),                                       /* [12] func_proto */
5846                                 BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
5847                                 BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 8),
5848                         BTF_FUNC_ENC(NAME_TBD, 12),                                     /* [13] func */
5849                         BTF_END_RAW,
5850                 },
5851                 BTF_STR_SEC("\0A\0B\0C\0D\0E\0F\0G\0H\0I\0J\0K\0L\0M"),
5852         },
5853         .expect = {
5854                 .raw_types = {
5855                         BTF_TYPE_INT_ENC(NAME_TBD, BTF_INT_SIGNED, 0, 32, 8),           /* [1] int */
5856                         BTF_TYPE_ENC(NAME_TBD, BTF_INFO_ENC(BTF_KIND_ENUM, 0, 2), 4),   /* [2] enum */
5857                                 BTF_ENUM_ENC(NAME_TBD, 0),
5858                                 BTF_ENUM_ENC(NAME_TBD, 1),
5859                         BTF_FWD_ENC(NAME_TBD, 1 /* union kind_flag */),                 /* [3] fwd */
5860                         BTF_TYPE_ARRAY_ENC(2, 1, 7),                                    /* [4] array */
5861                         BTF_STRUCT_ENC(NAME_TBD, 1, 4),                                 /* [5] struct */
5862                                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
5863                         BTF_UNION_ENC(NAME_TBD, 1, 4),                                  /* [6] union */
5864                                 BTF_MEMBER_ENC(NAME_TBD, 1, 0),
5865                         BTF_TYPEDEF_ENC(NAME_TBD, 1),                                   /* [7] typedef */
5866                         BTF_PTR_ENC(0),                                                 /* [8] ptr */
5867                         BTF_CONST_ENC(8),                                               /* [9] const */
5868                         BTF_VOLATILE_ENC(8),                                            /* [10] volatile */
5869                         BTF_RESTRICT_ENC(8),                                            /* [11] restrict */
5870                         BTF_FUNC_PROTO_ENC(1, 2),                                       /* [12] func_proto */
5871                                 BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 1),
5872                                 BTF_FUNC_PROTO_ARG_ENC(NAME_TBD, 8),
5873                         BTF_FUNC_ENC(NAME_TBD, 12),                                     /* [13] func */
5874                         BTF_END_RAW,
5875                 },
5876                 BTF_STR_SEC("\0A\0B\0C\0D\0E\0F\0G\0H\0I\0J\0K\0L\0M"),
5877         },
5878         .opts = {
5879                 .dont_resolve_fwds = false,
5880         },
5881 },
5882 {
5883         .descr = "dedup: no int duplicates",
5884         .input = {
5885                 .raw_types = {
5886                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 8),
5887                         /* different name */
5888                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 32, 8),
5889                         /* different encoding */
5890                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_CHAR, 0, 32, 8),
5891                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_BOOL, 0, 32, 8),
5892                         /* different bit offset */
5893                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 8, 32, 8),
5894                         /* different bit size */
5895                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 27, 8),
5896                         /* different byte size */
5897                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),
5898                         BTF_END_RAW,
5899                 },
5900                 BTF_STR_SEC("\0int\0some other int"),
5901         },
5902         .expect = {
5903                 .raw_types = {
5904                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 8),
5905                         /* different name */
5906                         BTF_TYPE_INT_ENC(NAME_NTH(2), BTF_INT_SIGNED, 0, 32, 8),
5907                         /* different encoding */
5908                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_CHAR, 0, 32, 8),
5909                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_BOOL, 0, 32, 8),
5910                         /* different bit offset */
5911                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 8, 32, 8),
5912                         /* different bit size */
5913                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 27, 8),
5914                         /* different byte size */
5915                         BTF_TYPE_INT_ENC(NAME_NTH(1), BTF_INT_SIGNED, 0, 32, 4),
5916                         BTF_END_RAW,
5917                 },
5918                 BTF_STR_SEC("\0int\0some other int"),
5919         },
5920         .opts = {
5921                 .dont_resolve_fwds = false,
5922         },
5923 },
5924 {
5925         .descr = "dedup: enum fwd resolution",
5926         .input = {
5927                 .raw_types = {
5928                         /* [1] fwd enum 'e1' before full enum */
5929                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 0), 4),
5930                         /* [2] full enum 'e1' after fwd */
5931                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5932                                 BTF_ENUM_ENC(NAME_NTH(2), 123),
5933                         /* [3] full enum 'e2' before fwd */
5934                         BTF_TYPE_ENC(NAME_NTH(3), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5935                                 BTF_ENUM_ENC(NAME_NTH(4), 456),
5936                         /* [4] fwd enum 'e2' after full enum */
5937                         BTF_TYPE_ENC(NAME_NTH(3), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 0), 4),
5938                         /* [5] incompatible fwd enum with different size */
5939                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 0), 1),
5940                         /* [6] incompatible full enum with different value */
5941                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5942                                 BTF_ENUM_ENC(NAME_NTH(2), 321),
5943                         BTF_END_RAW,
5944                 },
5945                 BTF_STR_SEC("\0e1\0e1_val\0e2\0e2_val"),
5946         },
5947         .expect = {
5948                 .raw_types = {
5949                         /* [1] full enum 'e1' */
5950                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5951                                 BTF_ENUM_ENC(NAME_NTH(2), 123),
5952                         /* [2] full enum 'e2' */
5953                         BTF_TYPE_ENC(NAME_NTH(3), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5954                                 BTF_ENUM_ENC(NAME_NTH(4), 456),
5955                         /* [3] incompatible fwd enum with different size */
5956                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 0), 1),
5957                         /* [4] incompatible full enum with different value */
5958                         BTF_TYPE_ENC(NAME_NTH(1), BTF_INFO_ENC(BTF_KIND_ENUM, 0, 1), 4),
5959                                 BTF_ENUM_ENC(NAME_NTH(2), 321),
5960                         BTF_END_RAW,
5961                 },
5962                 BTF_STR_SEC("\0e1\0e1_val\0e2\0e2_val"),
5963         },
5964         .opts = {
5965                 .dont_resolve_fwds = false,
5966         },
5967 },
5968
5969 };
5970
5971 static int btf_type_size(const struct btf_type *t)
5972 {
5973         int base_size = sizeof(struct btf_type);
5974         __u16 vlen = BTF_INFO_VLEN(t->info);
5975         __u16 kind = BTF_INFO_KIND(t->info);
5976
5977         switch (kind) {
5978         case BTF_KIND_FWD:
5979         case BTF_KIND_CONST:
5980         case BTF_KIND_VOLATILE:
5981         case BTF_KIND_RESTRICT:
5982         case BTF_KIND_PTR:
5983         case BTF_KIND_TYPEDEF:
5984         case BTF_KIND_FUNC:
5985                 return base_size;
5986         case BTF_KIND_INT:
5987                 return base_size + sizeof(__u32);
5988         case BTF_KIND_ENUM:
5989                 return base_size + vlen * sizeof(struct btf_enum);
5990         case BTF_KIND_ARRAY:
5991                 return base_size + sizeof(struct btf_array);
5992         case BTF_KIND_STRUCT:
5993         case BTF_KIND_UNION:
5994                 return base_size + vlen * sizeof(struct btf_member);
5995         case BTF_KIND_FUNC_PROTO:
5996                 return base_size + vlen * sizeof(struct btf_param);
5997         default:
5998                 fprintf(stderr, "Unsupported BTF_KIND:%u\n", kind);
5999                 return -EINVAL;
6000         }
6001 }
6002
6003 static void dump_btf_strings(const char *strs, __u32 len)
6004 {
6005         const char *cur = strs;
6006         int i = 0;
6007
6008         while (cur < strs + len) {
6009                 fprintf(stderr, "string #%d: '%s'\n", i, cur);
6010                 cur += strlen(cur) + 1;
6011                 i++;
6012         }
6013 }
6014
6015 static int do_test_dedup(unsigned int test_num)
6016 {
6017         const struct btf_dedup_test *test = &dedup_tests[test_num - 1];
6018         __u32 test_nr_types, expect_nr_types, test_btf_size, expect_btf_size;
6019         const struct btf_header *test_hdr, *expect_hdr;
6020         struct btf *test_btf = NULL, *expect_btf = NULL;
6021         const void *test_btf_data, *expect_btf_data;
6022         const char *ret_test_next_str, *ret_expect_next_str;
6023         const char *test_strs, *expect_strs;
6024         const char *test_str_cur, *test_str_end;
6025         const char *expect_str_cur, *expect_str_end;
6026         unsigned int raw_btf_size;
6027         void *raw_btf;
6028         int err = 0, i;
6029
6030         fprintf(stderr, "BTF dedup test[%u] (%s):", test_num, test->descr);
6031
6032         raw_btf = btf_raw_create(&hdr_tmpl, test->input.raw_types,
6033                                  test->input.str_sec, test->input.str_sec_size,
6034                                  &raw_btf_size, &ret_test_next_str);
6035         if (!raw_btf)
6036                 return -1;
6037         test_btf = btf__new((__u8 *)raw_btf, raw_btf_size);
6038         free(raw_btf);
6039         if (CHECK(IS_ERR(test_btf), "invalid test_btf errno:%ld",
6040                   PTR_ERR(test_btf))) {
6041                 err = -1;
6042                 goto done;
6043         }
6044
6045         raw_btf = btf_raw_create(&hdr_tmpl, test->expect.raw_types,
6046                                  test->expect.str_sec,
6047                                  test->expect.str_sec_size,
6048                                  &raw_btf_size, &ret_expect_next_str);
6049         if (!raw_btf)
6050                 return -1;
6051         expect_btf = btf__new((__u8 *)raw_btf, raw_btf_size);
6052         free(raw_btf);
6053         if (CHECK(IS_ERR(expect_btf), "invalid expect_btf errno:%ld",
6054                   PTR_ERR(expect_btf))) {
6055                 err = -1;
6056                 goto done;
6057         }
6058
6059         err = btf__dedup(test_btf, NULL, &test->opts);
6060         if (CHECK(err, "btf_dedup failed errno:%d", err)) {
6061                 err = -1;
6062                 goto done;
6063         }
6064
6065         test_btf_data = btf__get_raw_data(test_btf, &test_btf_size);
6066         expect_btf_data = btf__get_raw_data(expect_btf, &expect_btf_size);
6067         if (CHECK(test_btf_size != expect_btf_size,
6068                   "test_btf_size:%u != expect_btf_size:%u",
6069                   test_btf_size, expect_btf_size)) {
6070                 err = -1;
6071                 goto done;
6072         }
6073
6074         test_hdr = test_btf_data;
6075         test_strs = test_btf_data + sizeof(*test_hdr) + test_hdr->str_off;
6076         expect_hdr = expect_btf_data;
6077         expect_strs = expect_btf_data + sizeof(*test_hdr) + expect_hdr->str_off;
6078         if (CHECK(test_hdr->str_len != expect_hdr->str_len,
6079                   "test_hdr->str_len:%u != expect_hdr->str_len:%u",
6080                   test_hdr->str_len, expect_hdr->str_len)) {
6081                 fprintf(stderr, "\ntest strings:\n");
6082                 dump_btf_strings(test_strs, test_hdr->str_len);
6083                 fprintf(stderr, "\nexpected strings:\n");
6084                 dump_btf_strings(expect_strs, expect_hdr->str_len);
6085                 err = -1;
6086                 goto done;
6087         }
6088
6089         test_str_cur = test_strs;
6090         test_str_end = test_strs + test_hdr->str_len;
6091         expect_str_cur = expect_strs;
6092         expect_str_end = expect_strs + expect_hdr->str_len;
6093         while (test_str_cur < test_str_end && expect_str_cur < expect_str_end) {
6094                 size_t test_len, expect_len;
6095
6096                 test_len = strlen(test_str_cur);
6097                 expect_len = strlen(expect_str_cur);
6098                 if (CHECK(test_len != expect_len,
6099                           "test_len:%zu != expect_len:%zu "
6100                           "(test_str:%s, expect_str:%s)",
6101                           test_len, expect_len, test_str_cur, expect_str_cur)) {
6102                         err = -1;
6103                         goto done;
6104                 }
6105                 if (CHECK(strcmp(test_str_cur, expect_str_cur),
6106                           "test_str:%s != expect_str:%s",
6107                           test_str_cur, expect_str_cur)) {
6108                         err = -1;
6109                         goto done;
6110                 }
6111                 test_str_cur += test_len + 1;
6112                 expect_str_cur += expect_len + 1;
6113         }
6114         if (CHECK(test_str_cur != test_str_end,
6115                   "test_str_cur:%p != test_str_end:%p",
6116                   test_str_cur, test_str_end)) {
6117                 err = -1;
6118                 goto done;
6119         }
6120
6121         test_nr_types = btf__get_nr_types(test_btf);
6122         expect_nr_types = btf__get_nr_types(expect_btf);
6123         if (CHECK(test_nr_types != expect_nr_types,
6124                   "test_nr_types:%u != expect_nr_types:%u",
6125                   test_nr_types, expect_nr_types)) {
6126                 err = -1;
6127                 goto done;
6128         }
6129
6130         for (i = 1; i <= test_nr_types; i++) {
6131                 const struct btf_type *test_type, *expect_type;
6132                 int test_size, expect_size;
6133
6134                 test_type = btf__type_by_id(test_btf, i);
6135                 expect_type = btf__type_by_id(expect_btf, i);
6136                 test_size = btf_type_size(test_type);
6137                 expect_size = btf_type_size(expect_type);
6138
6139                 if (CHECK(test_size != expect_size,
6140                           "type #%d: test_size:%d != expect_size:%u",
6141                           i, test_size, expect_size)) {
6142                         err = -1;
6143                         goto done;
6144                 }
6145                 if (CHECK(memcmp((void *)test_type,
6146                                  (void *)expect_type,
6147                                  test_size),
6148                           "type #%d: contents differ", i)) {
6149                         err = -1;
6150                         goto done;
6151                 }
6152         }
6153
6154 done:
6155         if (!err)
6156                 fprintf(stderr, "OK");
6157         if (!IS_ERR(test_btf))
6158                 btf__free(test_btf);
6159         if (!IS_ERR(expect_btf))
6160                 btf__free(expect_btf);
6161
6162         return err;
6163 }
6164
6165 static int test_dedup(void)
6166 {
6167         unsigned int i;
6168         int err = 0;
6169
6170         if (args.dedup_test_num)
6171                 return count_result(do_test_dedup(args.dedup_test_num));
6172
6173         for (i = 1; i <= ARRAY_SIZE(dedup_tests); i++)
6174                 err |= count_result(do_test_dedup(i));
6175
6176         return err;
6177 }
6178
6179 static void usage(const char *cmd)
6180 {
6181         fprintf(stderr, "Usage: %s [-l] [[-r btf_raw_test_num (1 - %zu)] |\n"
6182                         "\t[-g btf_get_info_test_num (1 - %zu)] |\n"
6183                         "\t[-f btf_file_test_num (1 - %zu)] |\n"
6184                         "\t[-k btf_prog_info_raw_test_num (1 - %zu)] |\n"
6185                         "\t[-p (pretty print test)] |\n"
6186                         "\t[-d btf_dedup_test_num (1 - %zu)]]\n",
6187                 cmd, ARRAY_SIZE(raw_tests), ARRAY_SIZE(get_info_tests),
6188                 ARRAY_SIZE(file_tests), ARRAY_SIZE(info_raw_tests),
6189                 ARRAY_SIZE(dedup_tests));
6190 }
6191
6192 static int parse_args(int argc, char **argv)
6193 {
6194         const char *optstr = "hlpk:f:r:g:d:";
6195         int opt;
6196
6197         while ((opt = getopt(argc, argv, optstr)) != -1) {
6198                 switch (opt) {
6199                 case 'l':
6200                         args.always_log = true;
6201                         break;
6202                 case 'f':
6203                         args.file_test_num = atoi(optarg);
6204                         args.file_test = true;
6205                         break;
6206                 case 'r':
6207                         args.raw_test_num = atoi(optarg);
6208                         args.raw_test = true;
6209                         break;
6210                 case 'g':
6211                         args.get_info_test_num = atoi(optarg);
6212                         args.get_info_test = true;
6213                         break;
6214                 case 'p':
6215                         args.pprint_test = true;
6216                         break;
6217                 case 'k':
6218                         args.info_raw_test_num = atoi(optarg);
6219                         args.info_raw_test = true;
6220                         break;
6221                 case 'd':
6222                         args.dedup_test_num = atoi(optarg);
6223                         args.dedup_test = true;
6224                         break;
6225                 case 'h':
6226                         usage(argv[0]);
6227                         exit(0);
6228                 default:
6229                         usage(argv[0]);
6230                         return -1;
6231                 }
6232         }
6233
6234         if (args.raw_test_num &&
6235             (args.raw_test_num < 1 ||
6236              args.raw_test_num > ARRAY_SIZE(raw_tests))) {
6237                 fprintf(stderr, "BTF raw test number must be [1 - %zu]\n",
6238                         ARRAY_SIZE(raw_tests));
6239                 return -1;
6240         }
6241
6242         if (args.file_test_num &&
6243             (args.file_test_num < 1 ||
6244              args.file_test_num > ARRAY_SIZE(file_tests))) {
6245                 fprintf(stderr, "BTF file test number must be [1 - %zu]\n",
6246                         ARRAY_SIZE(file_tests));
6247                 return -1;
6248         }
6249
6250         if (args.get_info_test_num &&
6251             (args.get_info_test_num < 1 ||
6252              args.get_info_test_num > ARRAY_SIZE(get_info_tests))) {
6253                 fprintf(stderr, "BTF get info test number must be [1 - %zu]\n",
6254                         ARRAY_SIZE(get_info_tests));
6255                 return -1;
6256         }
6257
6258         if (args.info_raw_test_num &&
6259             (args.info_raw_test_num < 1 ||
6260              args.info_raw_test_num > ARRAY_SIZE(info_raw_tests))) {
6261                 fprintf(stderr, "BTF prog info raw test number must be [1 - %zu]\n",
6262                         ARRAY_SIZE(info_raw_tests));
6263                 return -1;
6264         }
6265
6266         if (args.dedup_test_num &&
6267             (args.dedup_test_num < 1 ||
6268              args.dedup_test_num > ARRAY_SIZE(dedup_tests))) {
6269                 fprintf(stderr, "BTF dedup test number must be [1 - %zu]\n",
6270                         ARRAY_SIZE(dedup_tests));
6271                 return -1;
6272         }
6273
6274         return 0;
6275 }
6276
6277 static void print_summary(void)
6278 {
6279         fprintf(stderr, "PASS:%u SKIP:%u FAIL:%u\n",
6280                 pass_cnt - skip_cnt, skip_cnt, error_cnt);
6281 }
6282
6283 int main(int argc, char **argv)
6284 {
6285         int err = 0;
6286
6287         err = parse_args(argc, argv);
6288         if (err)
6289                 return err;
6290
6291         if (args.always_log)
6292                 libbpf_set_print(__base_pr);
6293
6294         if (args.raw_test)
6295                 err |= test_raw();
6296
6297         if (args.get_info_test)
6298                 err |= test_get_info();
6299
6300         if (args.file_test)
6301                 err |= test_file();
6302
6303         if (args.pprint_test)
6304                 err |= test_pprint();
6305
6306         if (args.info_raw_test)
6307                 err |= test_info_raw();
6308
6309         if (args.dedup_test)
6310                 err |= test_dedup();
6311
6312         if (args.raw_test || args.get_info_test || args.file_test ||
6313             args.pprint_test || args.info_raw_test || args.dedup_test)
6314                 goto done;
6315
6316         err |= test_raw();
6317         err |= test_get_info();
6318         err |= test_file();
6319         err |= test_info_raw();
6320         err |= test_dedup();
6321
6322 done:
6323         print_summary();
6324         return err;
6325 }