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