]> CyberLeo.Net >> Repos - FreeBSD/releng/10.2.git/blob - contrib/netbsd-tests/lib/libbpfjit/t_bpfjit.c
- Copy stable/10@285827 to releng/10.2 in preparation for 10.2-RC1
[FreeBSD/releng/10.2.git] / contrib / netbsd-tests / lib / libbpfjit / t_bpfjit.c
1 /*      $NetBSD: t_bpfjit.c,v 1.6 2014/07/08 21:07:52 alnsn Exp $ */
2
3 /*-
4  * Copyright (c) 2011-2012, 2014 Alexander Nasonov.
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in
15  *    the documentation and/or other materials provided with the
16  *    distribution.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
21  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
22  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
23  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
24  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
25  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
26  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
27  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
28  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29  * SUCH DAMAGE.
30  */
31
32 #include <sys/cdefs.h>
33 __RCSID("$NetBSD: t_bpfjit.c,v 1.6 2014/07/08 21:07:52 alnsn Exp $");
34
35 #include <atf-c.h>
36 #include <stdint.h>
37 #include <string.h>
38
39 #include <net/bpf.h>
40 #include <net/bpfjit.h>
41
42 static uint8_t deadbeef_at_5[16] = {
43         0, 0xf1, 2, 0xf3, 4, 0xde, 0xad, 0xbe, 0xef, 0xff
44 };
45
46 static inline
47 unsigned int jitcall(bpfjit_func_t fn,
48     const uint8_t *pkt, unsigned int wirelen, unsigned int buflen)
49 {
50         bpf_args_t args;
51
52         args.pkt = pkt;
53         args.wirelen = wirelen;
54         args.buflen = buflen;
55
56         return fn(NULL, &args);
57 }
58
59 ATF_TC(libbpfjit_empty);
60 ATF_TC_HEAD(libbpfjit_empty, tc)
61 {
62         atf_tc_set_md_var(tc, "descr",
63             "Test that JIT compilation of an empty bpf program fails");
64 }
65
66 ATF_TC_BODY(libbpfjit_empty, tc)
67 {
68         struct bpf_insn dummy;
69
70         ATF_CHECK(bpfjit_generate_code(NULL, &dummy, 0) == NULL);
71 }
72
73 ATF_TC(libbpfjit_alu_add_k);
74 ATF_TC_HEAD(libbpfjit_alu_add_k, tc)
75 {
76         atf_tc_set_md_var(tc, "descr",
77             "Test JIT compilation of BPF_ALU+BPF_ADD+BPF_K");
78 }
79
80 ATF_TC_BODY(libbpfjit_alu_add_k, tc)
81 {
82         static struct bpf_insn insns[] = {
83                 BPF_STMT(BPF_LD+BPF_IMM, 3),
84                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 2),
85                 BPF_STMT(BPF_RET+BPF_A, 0)
86         };
87
88         bpfjit_func_t code;
89         uint8_t pkt[1]; /* the program doesn't read any data */
90
91         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
92
93         ATF_CHECK(bpf_validate(insns, insn_count));
94
95         code = bpfjit_generate_code(NULL, insns, insn_count);
96         ATF_REQUIRE(code != NULL);
97
98         ATF_CHECK(jitcall(code, pkt, 1, 1) == 5);
99
100         bpfjit_free_code(code);
101 }
102
103 ATF_TC(libbpfjit_alu_sub_k);
104 ATF_TC_HEAD(libbpfjit_alu_sub_k, tc)
105 {
106         atf_tc_set_md_var(tc, "descr",
107             "Test JIT compilation of BPF_ALU+BPF_SUB+BPF_K");
108 }
109
110 ATF_TC_BODY(libbpfjit_alu_sub_k, tc)
111 {
112         static struct bpf_insn insns[] = {
113                 BPF_STMT(BPF_LD+BPF_IMM, 1),
114                 BPF_STMT(BPF_ALU+BPF_SUB+BPF_K, 2),
115                 BPF_STMT(BPF_RET+BPF_A, 0)
116         };
117
118         bpfjit_func_t code;
119         uint8_t pkt[1]; /* the program doesn't read any data */
120
121         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
122
123         ATF_CHECK(bpf_validate(insns, insn_count));
124
125         code = bpfjit_generate_code(NULL, insns, insn_count);
126         ATF_REQUIRE(code != NULL);
127
128         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
129
130         bpfjit_free_code(code);
131 }
132
133 ATF_TC(libbpfjit_alu_mul_k);
134 ATF_TC_HEAD(libbpfjit_alu_mul_k, tc)
135 {
136         atf_tc_set_md_var(tc, "descr",
137             "Test JIT compilation of BPF_ALU+BPF_MUL+BPF_K");
138 }
139
140 ATF_TC_BODY(libbpfjit_alu_mul_k, tc)
141 {
142         static struct bpf_insn insns[] = {
143                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0xffffffff)),
144                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_K, 3),
145                 BPF_STMT(BPF_RET+BPF_A, 0)
146         };
147
148         bpfjit_func_t code;
149         uint8_t pkt[1]; /* the program doesn't read any data */
150
151         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
152
153         ATF_CHECK(bpf_validate(insns, insn_count));
154
155         code = bpfjit_generate_code(NULL, insns, insn_count);
156         ATF_REQUIRE(code != NULL);
157
158         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0xfffffffd));
159
160         bpfjit_free_code(code);
161 }
162
163 ATF_TC(libbpfjit_alu_div0_k);
164 ATF_TC_HEAD(libbpfjit_alu_div0_k, tc)
165 {
166         atf_tc_set_md_var(tc, "descr",
167             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=0");
168 }
169
170 ATF_TC_BODY(libbpfjit_alu_div0_k, tc)
171 {
172         static struct bpf_insn insns[] = {
173                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 0),
174                 BPF_STMT(BPF_RET+BPF_A, 0)
175         };
176
177         bpfjit_func_t code;
178         uint8_t pkt[1]; /* the program doesn't read any data */
179
180         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
181
182         //ATF_CHECK(bpf_validate(insns, insn_count));
183
184         code = bpfjit_generate_code(NULL, insns, insn_count);
185         ATF_REQUIRE(code != NULL);
186
187         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
188
189         bpfjit_free_code(code);
190 }
191
192 ATF_TC(libbpfjit_alu_div1_k);
193 ATF_TC_HEAD(libbpfjit_alu_div1_k, tc)
194 {
195         atf_tc_set_md_var(tc, "descr",
196             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=1");
197 }
198
199 ATF_TC_BODY(libbpfjit_alu_div1_k, tc)
200 {
201         static struct bpf_insn insns[] = {
202                 BPF_STMT(BPF_LD+BPF_IMM, 7),
203                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 1),
204                 BPF_STMT(BPF_RET+BPF_A, 0)
205         };
206
207         bpfjit_func_t code;
208         uint8_t pkt[1]; /* the program doesn't read any data */
209
210         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
211
212         ATF_CHECK(bpf_validate(insns, insn_count));
213
214         code = bpfjit_generate_code(NULL, insns, insn_count);
215         ATF_REQUIRE(code != NULL);
216
217         ATF_CHECK(jitcall(code, pkt, 1, 1) == 7);
218
219         bpfjit_free_code(code);
220 }
221
222 ATF_TC(libbpfjit_alu_div2_k);
223 ATF_TC_HEAD(libbpfjit_alu_div2_k, tc)
224 {
225         atf_tc_set_md_var(tc, "descr",
226             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=2");
227 }
228
229 ATF_TC_BODY(libbpfjit_alu_div2_k, tc)
230 {
231         static struct bpf_insn insns[] = {
232                 BPF_STMT(BPF_LD+BPF_IMM, 7),
233                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 2),
234                 BPF_STMT(BPF_RET+BPF_A, 0)
235         };
236
237         bpfjit_func_t code;
238         uint8_t pkt[1]; /* the program doesn't read any data */
239
240         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
241
242         ATF_CHECK(bpf_validate(insns, insn_count));
243
244         code = bpfjit_generate_code(NULL, insns, insn_count);
245         ATF_REQUIRE(code != NULL);
246
247         ATF_CHECK(jitcall(code, pkt, 1, 1) == 3);
248
249         bpfjit_free_code(code);
250 }
251
252 ATF_TC(libbpfjit_alu_div4_k);
253 ATF_TC_HEAD(libbpfjit_alu_div4_k, tc)
254 {
255         atf_tc_set_md_var(tc, "descr",
256             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=4");
257 }
258
259 ATF_TC_BODY(libbpfjit_alu_div4_k, tc)
260 {
261         static struct bpf_insn insns[] = {
262                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0xffffffff)),
263                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4),
264                 BPF_STMT(BPF_RET+BPF_A, 0)
265         };
266
267         bpfjit_func_t code;
268         uint8_t pkt[1]; /* the program doesn't read any data */
269
270         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
271
272         ATF_CHECK(bpf_validate(insns, insn_count));
273
274         code = bpfjit_generate_code(NULL, insns, insn_count);
275         ATF_REQUIRE(code != NULL);
276
277         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0x3fffffff));
278
279         bpfjit_free_code(code);
280 }
281
282 ATF_TC(libbpfjit_alu_div10_k);
283 ATF_TC_HEAD(libbpfjit_alu_div10_k, tc)
284 {
285         atf_tc_set_md_var(tc, "descr",
286             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=10");
287 }
288
289 ATF_TC_BODY(libbpfjit_alu_div10_k, tc)
290 {
291         static struct bpf_insn insns[] = {
292                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294843849)),
293                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 10),
294                 BPF_STMT(BPF_RET+BPF_A, 0)
295         };
296
297         bpfjit_func_t code;
298         uint8_t pkt[1]; /* the program doesn't read any data */
299
300         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
301
302         ATF_CHECK(bpf_validate(insns, insn_count));
303
304         code = bpfjit_generate_code(NULL, insns, insn_count);
305         ATF_REQUIRE(code != NULL);
306
307         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(429484384));
308
309         bpfjit_free_code(code);
310 }
311
312 ATF_TC(libbpfjit_alu_div10000_k);
313 ATF_TC_HEAD(libbpfjit_alu_div10000_k, tc)
314 {
315         atf_tc_set_md_var(tc, "descr",
316             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=10000");
317 }
318
319 ATF_TC_BODY(libbpfjit_alu_div10000_k, tc)
320 {
321         static struct bpf_insn insns[] = {
322                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294843849)),
323                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 10000),
324                 BPF_STMT(BPF_RET+BPF_A, 0)
325         };
326
327         bpfjit_func_t code;
328         uint8_t pkt[1]; /* the program doesn't read any data */
329
330         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
331
332         ATF_CHECK(bpf_validate(insns, insn_count));
333
334         code = bpfjit_generate_code(NULL, insns, insn_count);
335         ATF_REQUIRE(code != NULL);
336
337         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(429484));
338
339         bpfjit_free_code(code);
340 }
341
342 ATF_TC(libbpfjit_alu_div7609801_k);
343 ATF_TC_HEAD(libbpfjit_alu_div7609801_k, tc)
344 {
345         atf_tc_set_md_var(tc, "descr",
346             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=7609801");
347 }
348
349 ATF_TC_BODY(libbpfjit_alu_div7609801_k, tc)
350 {
351         static struct bpf_insn insns[] = {
352                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294967295)),
353                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, UINT32_C(7609801)),
354                 BPF_STMT(BPF_RET+BPF_A, 0)
355         };
356
357         bpfjit_func_t code;
358         uint8_t pkt[1]; /* the program doesn't read any data */
359
360         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
361
362         ATF_CHECK(bpf_validate(insns, insn_count));
363
364         code = bpfjit_generate_code(NULL, insns, insn_count);
365         ATF_REQUIRE(code != NULL);
366
367         ATF_CHECK(jitcall(code, pkt, 1, 1) == 564);
368
369         bpfjit_free_code(code);
370 }
371
372 ATF_TC(libbpfjit_alu_div80000000_k);
373 ATF_TC_HEAD(libbpfjit_alu_div80000000_k, tc)
374 {
375         atf_tc_set_md_var(tc, "descr",
376             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_K with k=0x80000000");
377 }
378
379 ATF_TC_BODY(libbpfjit_alu_div80000000_k, tc)
380 {
381         static struct bpf_insn insns[] = {
382                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0xffffffde)),
383                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, UINT32_C(0x80000000)),
384                 BPF_STMT(BPF_RET+BPF_A, 0)
385         };
386
387         bpfjit_func_t code;
388         uint8_t pkt[1]; /* the program doesn't read any data */
389
390         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
391
392         ATF_CHECK(bpf_validate(insns, insn_count));
393
394         code = bpfjit_generate_code(NULL, insns, insn_count);
395         ATF_REQUIRE(code != NULL);
396
397         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
398
399         bpfjit_free_code(code);
400 }
401
402 ATF_TC(libbpfjit_alu_and_k);
403 ATF_TC_HEAD(libbpfjit_alu_and_k, tc)
404 {
405         atf_tc_set_md_var(tc, "descr",
406             "Test JIT compilation of BPF_ALU+BPF_AND+BPF_K");
407 }
408
409 ATF_TC_BODY(libbpfjit_alu_and_k, tc)
410 {
411         static struct bpf_insn insns[] = {
412                 BPF_STMT(BPF_LD+BPF_IMM, 0xdead),
413                 BPF_STMT(BPF_ALU+BPF_AND+BPF_K, 0xbeef),
414                 BPF_STMT(BPF_RET+BPF_A, 0)
415         };
416
417         bpfjit_func_t code;
418         uint8_t pkt[1]; /* the program doesn't read any data */
419
420         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
421
422         ATF_CHECK(bpf_validate(insns, insn_count));
423
424         code = bpfjit_generate_code(NULL, insns, insn_count);
425         ATF_REQUIRE(code != NULL);
426
427         ATF_CHECK(jitcall(code, pkt, 1, 1) == (0xdead&0xbeef));
428
429         bpfjit_free_code(code);
430 }
431
432 ATF_TC(libbpfjit_alu_or_k);
433 ATF_TC_HEAD(libbpfjit_alu_or_k, tc)
434 {
435         atf_tc_set_md_var(tc, "descr",
436             "Test JIT compilation of BPF_ALU+BPF_OR+BPF_K");
437 }
438
439 ATF_TC_BODY(libbpfjit_alu_or_k, tc)
440 {
441         static struct bpf_insn insns[] = {
442                 BPF_STMT(BPF_LD+BPF_IMM, 0xdead0000),
443                 BPF_STMT(BPF_ALU+BPF_OR+BPF_K, 0x0000beef),
444                 BPF_STMT(BPF_RET+BPF_A, 0)
445         };
446
447         bpfjit_func_t code;
448         uint8_t pkt[1]; /* the program doesn't read any data */
449
450         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
451
452         ATF_CHECK(bpf_validate(insns, insn_count));
453
454         code = bpfjit_generate_code(NULL, insns, insn_count);
455         ATF_REQUIRE(code != NULL);
456
457         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
458
459         bpfjit_free_code(code);
460 }
461
462 ATF_TC(libbpfjit_alu_lsh_k);
463 ATF_TC_HEAD(libbpfjit_alu_lsh_k, tc)
464 {
465         atf_tc_set_md_var(tc, "descr",
466             "Test JIT compilation of BPF_ALU+BPF_LSH+BPF_K");
467 }
468
469 ATF_TC_BODY(libbpfjit_alu_lsh_k, tc)
470 {
471         static struct bpf_insn insns[] = {
472                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
473                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_K, 16),
474                 BPF_STMT(BPF_RET+BPF_A, 0)
475         };
476
477         bpfjit_func_t code;
478         uint8_t pkt[1]; /* the program doesn't read any data */
479
480         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
481
482         ATF_CHECK(bpf_validate(insns, insn_count));
483
484         code = bpfjit_generate_code(NULL, insns, insn_count);
485         ATF_REQUIRE(code != NULL);
486
487         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xbeef0000);
488
489         bpfjit_free_code(code);
490 }
491
492 ATF_TC(libbpfjit_alu_lsh0_k);
493 ATF_TC_HEAD(libbpfjit_alu_lsh0_k, tc)
494 {
495         atf_tc_set_md_var(tc, "descr",
496             "Test JIT compilation of BPF_ALU+BPF_LSH+BPF_K with k=0");
497 }
498
499 ATF_TC_BODY(libbpfjit_alu_lsh0_k, tc)
500 {
501         static struct bpf_insn insns[] = {
502                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
503                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_K, 0),
504                 BPF_STMT(BPF_RET+BPF_A, 0)
505         };
506
507         bpfjit_func_t code;
508         uint8_t pkt[1]; /* the program doesn't read any data */
509
510         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
511
512         ATF_CHECK(bpf_validate(insns, insn_count));
513
514         code = bpfjit_generate_code(NULL, insns, insn_count);
515         ATF_REQUIRE(code != NULL);
516
517         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
518
519         bpfjit_free_code(code);
520 }
521
522 ATF_TC(libbpfjit_alu_rsh_k);
523 ATF_TC_HEAD(libbpfjit_alu_rsh_k, tc)
524 {
525         atf_tc_set_md_var(tc, "descr",
526             "Test JIT compilation of BPF_ALU+BPF_RSH+BPF_K");
527 }
528
529 ATF_TC_BODY(libbpfjit_alu_rsh_k, tc)
530 {
531         static struct bpf_insn insns[] = {
532                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
533                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_K, 16),
534                 BPF_STMT(BPF_RET+BPF_A, 0)
535         };
536
537         bpfjit_func_t code;
538         uint8_t pkt[1]; /* the program doesn't read any data */
539
540         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
541
542         ATF_CHECK(bpf_validate(insns, insn_count));
543
544         code = bpfjit_generate_code(NULL, insns, insn_count);
545         ATF_REQUIRE(code != NULL);
546
547         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0x0000dead);
548
549         bpfjit_free_code(code);
550 }
551
552 ATF_TC(libbpfjit_alu_rsh0_k);
553 ATF_TC_HEAD(libbpfjit_alu_rsh0_k, tc)
554 {
555         atf_tc_set_md_var(tc, "descr",
556             "Test JIT compilation of BPF_ALU+BPF_RSH+BPF_K with k=0");
557 }
558
559 ATF_TC_BODY(libbpfjit_alu_rsh0_k, tc)
560 {
561         static struct bpf_insn insns[] = {
562                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
563                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_K, 0),
564                 BPF_STMT(BPF_RET+BPF_A, 0)
565         };
566
567         bpfjit_func_t code;
568         uint8_t pkt[1]; /* the program doesn't read any data */
569
570         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
571
572         ATF_CHECK(bpf_validate(insns, insn_count));
573
574         code = bpfjit_generate_code(NULL, insns, insn_count);
575         ATF_REQUIRE(code != NULL);
576
577         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
578
579         bpfjit_free_code(code);
580 }
581
582 ATF_TC(libbpfjit_alu_modulo_k);
583 ATF_TC_HEAD(libbpfjit_alu_modulo_k, tc)
584 {
585         atf_tc_set_md_var(tc, "descr",
586             "Test JIT compilation of modulo logic of BPF_ALU+BPF_K operations");
587 }
588
589 ATF_TC_BODY(libbpfjit_alu_modulo_k, tc)
590 {
591         static struct bpf_insn insns[] = {
592                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0x7fffff77)),
593
594                 /* (7FFFFF77 * 0FFFFF77) = 07FFFFB2,F0004951 */
595                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_K, UINT32_C(0x0fffff77)),
596
597                 /* 07FFFFB2,F0004951 << 1 = 0FFFFF65,E00092A2 */
598                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_K, 1),
599
600                 /* 0FFFFF65,E00092A2 + DDDDDDDD = 0FFFFF66,BDDE707F */
601                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, UINT32_C(0xdddddddd)),
602
603                 /* 0FFFFF66,BDDE707F - FFFFFFFF = 0FFFFF65,BDDE7080 */
604                 BPF_STMT(BPF_ALU+BPF_SUB+BPF_K, UINT32_C(0xffffffff)),
605
606                 /* 0FFFFF65,BDDE7080 | 0000030C = 0FFFFF65,BDDE738C */
607                 BPF_STMT(BPF_ALU+BPF_OR+BPF_K, UINT32_C(0x0000030c)),
608
609                 /* -0FFFFF65,BDDE738C mod(2^64) = F000009A,42218C74 */
610                 BPF_STMT(BPF_ALU+BPF_NEG, 0),
611
612                 /* F000009A,42218C74 & FFFFFF0F = F000009A,42218C04 */
613                 BPF_STMT(BPF_ALU+BPF_AND+BPF_K, UINT32_C(0xffffff0f)),
614
615                 /* F000009A,42218C74 >> 3 = 1E000013,48443180 */
616                 /* 00000000,42218C74 >> 3 = 00000000,08443180 */
617                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_K, 3),
618
619                 /* 00000000,08443180 * 7FFFFF77 = 042218BB,93818280 */
620                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_K, UINT32_C(0x7fffff77)),
621
622                 /* 042218BB,93818280 / DEAD = 000004C0,71CBBBC3 */
623                 /* 00000000,93818280 / DEAD = 00000000,0000A994 */
624                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, UINT32_C(0xdead)),
625
626                 BPF_STMT(BPF_RET+BPF_A, 0)
627         };
628
629         bpfjit_func_t code;
630         uint8_t pkt[1]; /* the program doesn't read any data */
631
632         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
633
634         ATF_CHECK(bpf_validate(insns, insn_count));
635
636         code = bpfjit_generate_code(NULL, insns, insn_count);
637         ATF_REQUIRE(code != NULL);
638
639         ATF_CHECK(jitcall(code, pkt, 1, 1) != UINT32_C(0x71cbbbc3));
640         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0x0000a994));
641
642
643         bpfjit_free_code(code);
644 }
645
646 ATF_TC(libbpfjit_alu_add_x);
647 ATF_TC_HEAD(libbpfjit_alu_add_x, tc)
648 {
649         atf_tc_set_md_var(tc, "descr",
650             "Test JIT compilation of BPF_ALU+BPF_ADD+BPF_X");
651 }
652
653 ATF_TC_BODY(libbpfjit_alu_add_x, tc)
654 {
655         static struct bpf_insn insns[] = {
656                 BPF_STMT(BPF_LD+BPF_IMM, 3),
657                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
658                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
659                 BPF_STMT(BPF_RET+BPF_A, 0)
660         };
661
662         bpfjit_func_t code;
663         uint8_t pkt[1]; /* the program doesn't read any data */
664
665         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
666
667         ATF_CHECK(bpf_validate(insns, insn_count));
668
669         code = bpfjit_generate_code(NULL, insns, insn_count);
670         ATF_REQUIRE(code != NULL);
671
672         ATF_CHECK(jitcall(code, pkt, 1, 1) == 5);
673
674         bpfjit_free_code(code);
675 }
676
677 ATF_TC(libbpfjit_alu_sub_x);
678 ATF_TC_HEAD(libbpfjit_alu_sub_x, tc)
679 {
680         atf_tc_set_md_var(tc, "descr",
681             "Test JIT compilation of BPF_ALU+BPF_SUB+BPF_X");
682 }
683
684 ATF_TC_BODY(libbpfjit_alu_sub_x, tc)
685 {
686         static struct bpf_insn insns[] = {
687                 BPF_STMT(BPF_LD+BPF_IMM, 1),
688                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
689                 BPF_STMT(BPF_ALU+BPF_SUB+BPF_X, 0),
690                 BPF_STMT(BPF_RET+BPF_A, 0)
691         };
692
693         bpfjit_func_t code;
694         uint8_t pkt[1]; /* the program doesn't read any data */
695
696         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
697
698         ATF_CHECK(bpf_validate(insns, insn_count));
699
700         code = bpfjit_generate_code(NULL, insns, insn_count);
701         ATF_REQUIRE(code != NULL);
702
703         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
704
705         bpfjit_free_code(code);
706 }
707
708 ATF_TC(libbpfjit_alu_mul_x);
709 ATF_TC_HEAD(libbpfjit_alu_mul_x, tc)
710 {
711         atf_tc_set_md_var(tc, "descr",
712             "Test JIT compilation of BPF_ALU+BPF_MUL+BPF_X");
713 }
714
715 ATF_TC_BODY(libbpfjit_alu_mul_x, tc)
716 {
717         static struct bpf_insn insns[] = {
718                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0xffffffff)),
719                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
720                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0),
721                 BPF_STMT(BPF_RET+BPF_A, 0)
722         };
723
724         bpfjit_func_t code;
725         uint8_t pkt[1]; /* the program doesn't read any data */
726
727         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
728
729         ATF_CHECK(bpf_validate(insns, insn_count));
730
731         code = bpfjit_generate_code(NULL, insns, insn_count);
732         ATF_REQUIRE(code != NULL);
733
734         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0xfffffffd));
735
736         bpfjit_free_code(code);
737 }
738
739 ATF_TC(libbpfjit_alu_div0_x);
740 ATF_TC_HEAD(libbpfjit_alu_div0_x, tc)
741 {
742         atf_tc_set_md_var(tc, "descr",
743             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=0");
744 }
745
746 ATF_TC_BODY(libbpfjit_alu_div0_x, tc)
747 {
748         static struct bpf_insn insns[] = {
749                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
750                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
751                 BPF_STMT(BPF_RET+BPF_A, 0)
752         };
753
754         bpfjit_func_t code;
755         uint8_t pkt[1]; /* the program doesn't read any data */
756
757         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
758
759         ATF_CHECK(bpf_validate(insns, insn_count));
760
761         code = bpfjit_generate_code(NULL, insns, insn_count);
762         ATF_REQUIRE(code != NULL);
763
764         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
765
766         bpfjit_free_code(code);
767 }
768
769 ATF_TC(libbpfjit_alu_div1_x);
770 ATF_TC_HEAD(libbpfjit_alu_div1_x, tc)
771 {
772         atf_tc_set_md_var(tc, "descr",
773             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=1");
774 }
775
776 ATF_TC_BODY(libbpfjit_alu_div1_x, tc)
777 {
778         static struct bpf_insn insns[] = {
779                 BPF_STMT(BPF_LD+BPF_IMM, 7),
780                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1),
781                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
782                 BPF_STMT(BPF_RET+BPF_A, 0)
783         };
784
785         bpfjit_func_t code;
786         uint8_t pkt[1]; /* the program doesn't read any data */
787
788         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
789
790         ATF_CHECK(bpf_validate(insns, insn_count));
791
792         code = bpfjit_generate_code(NULL, insns, insn_count);
793         ATF_REQUIRE(code != NULL);
794
795         ATF_CHECK(jitcall(code, pkt, 1, 1) == 7);
796
797         bpfjit_free_code(code);
798 }
799
800 ATF_TC(libbpfjit_alu_div2_x);
801 ATF_TC_HEAD(libbpfjit_alu_div2_x, tc)
802 {
803         atf_tc_set_md_var(tc, "descr",
804             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=2");
805 }
806
807 ATF_TC_BODY(libbpfjit_alu_div2_x, tc)
808 {
809         static struct bpf_insn insns[] = {
810                 BPF_STMT(BPF_LD+BPF_IMM, 7),
811                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
812                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
813                 BPF_STMT(BPF_RET+BPF_A, 0)
814         };
815
816         bpfjit_func_t code;
817         uint8_t pkt[1]; /* the program doesn't read any data */
818
819         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
820
821         ATF_CHECK(bpf_validate(insns, insn_count));
822
823         code = bpfjit_generate_code(NULL, insns, insn_count);
824         ATF_REQUIRE(code != NULL);
825
826         ATF_CHECK(jitcall(code, pkt, 1, 1) == 3);
827
828         bpfjit_free_code(code);
829 }
830
831 ATF_TC(libbpfjit_alu_div4_x);
832 ATF_TC_HEAD(libbpfjit_alu_div4_x, tc)
833 {
834         atf_tc_set_md_var(tc, "descr",
835             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=4");
836 }
837
838 ATF_TC_BODY(libbpfjit_alu_div4_x, tc)
839 {
840         static struct bpf_insn insns[] = {
841                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0xffffffff)),
842                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 4),
843                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
844                 BPF_STMT(BPF_RET+BPF_A, 0)
845         };
846
847         bpfjit_func_t code;
848         uint8_t pkt[1]; /* the program doesn't read any data */
849
850         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
851
852         ATF_CHECK(bpf_validate(insns, insn_count));
853
854         code = bpfjit_generate_code(NULL, insns, insn_count);
855         ATF_REQUIRE(code != NULL);
856
857         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0x3fffffff));
858
859         bpfjit_free_code(code);
860 }
861
862 ATF_TC(libbpfjit_alu_div10_x);
863 ATF_TC_HEAD(libbpfjit_alu_div10_x, tc)
864 {
865         atf_tc_set_md_var(tc, "descr",
866             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=10");
867 }
868
869 ATF_TC_BODY(libbpfjit_alu_div10_x, tc)
870 {
871         static struct bpf_insn insns[] = {
872                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294843849)),
873                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 10),
874                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
875                 BPF_STMT(BPF_RET+BPF_A, 0)
876         };
877
878         bpfjit_func_t code;
879         uint8_t pkt[1]; /* the program doesn't read any data */
880
881         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
882
883         ATF_CHECK(bpf_validate(insns, insn_count));
884
885         code = bpfjit_generate_code(NULL, insns, insn_count);
886         ATF_REQUIRE(code != NULL);
887
888         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(429484384));
889
890         bpfjit_free_code(code);
891 }
892
893 ATF_TC(libbpfjit_alu_div10000_x);
894 ATF_TC_HEAD(libbpfjit_alu_div10000_x, tc)
895 {
896         atf_tc_set_md_var(tc, "descr",
897             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=10000");
898 }
899
900 ATF_TC_BODY(libbpfjit_alu_div10000_x, tc)
901 {
902         static struct bpf_insn insns[] = {
903                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294843849)),
904                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 10000),
905                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
906                 BPF_STMT(BPF_RET+BPF_A, 0)
907         };
908
909         bpfjit_func_t code;
910         uint8_t pkt[1]; /* the program doesn't read any data */
911
912         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
913
914         ATF_CHECK(bpf_validate(insns, insn_count));
915
916         code = bpfjit_generate_code(NULL, insns, insn_count);
917         ATF_REQUIRE(code != NULL);
918
919         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(429484));
920
921         bpfjit_free_code(code);
922 }
923
924 ATF_TC(libbpfjit_alu_div7609801_x);
925 ATF_TC_HEAD(libbpfjit_alu_div7609801_x, tc)
926 {
927         atf_tc_set_md_var(tc, "descr",
928             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=7609801");
929 }
930
931 ATF_TC_BODY(libbpfjit_alu_div7609801_x, tc)
932 {
933         static struct bpf_insn insns[] = {
934                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(4294967295)),
935                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(7609801)),
936                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
937                 BPF_STMT(BPF_RET+BPF_A, 0)
938         };
939
940         bpfjit_func_t code;
941         uint8_t pkt[1]; /* the program doesn't read any data */
942
943         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
944
945         ATF_CHECK(bpf_validate(insns, insn_count));
946
947         code = bpfjit_generate_code(NULL, insns, insn_count);
948         ATF_REQUIRE(code != NULL);
949
950         ATF_CHECK(jitcall(code, pkt, 1, 1) == 564);
951
952         bpfjit_free_code(code);
953 }
954
955 ATF_TC(libbpfjit_alu_div80000000_x);
956 ATF_TC_HEAD(libbpfjit_alu_div80000000_x, tc)
957 {
958         atf_tc_set_md_var(tc, "descr",
959             "Test JIT compilation of BPF_ALU+BPF_DIV+BPF_X with X=0x80000000");
960 }
961
962 ATF_TC_BODY(libbpfjit_alu_div80000000_x, tc)
963 {
964         static struct bpf_insn insns[] = {
965                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_MAX - 33),
966                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0x80000000)),
967                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
968                 BPF_STMT(BPF_RET+BPF_A, 0)
969         };
970
971         bpfjit_func_t code;
972         uint8_t pkt[1]; /* the program doesn't read any data */
973
974         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
975
976         ATF_CHECK(bpf_validate(insns, insn_count));
977
978         code = bpfjit_generate_code(NULL, insns, insn_count);
979         ATF_REQUIRE(code != NULL);
980
981         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
982
983         bpfjit_free_code(code);
984 }
985
986 ATF_TC(libbpfjit_alu_and_x);
987 ATF_TC_HEAD(libbpfjit_alu_and_x, tc)
988 {
989         atf_tc_set_md_var(tc, "descr",
990             "Test JIT compilation of BPF_ALU+BPF_AND+BPF_X");
991 }
992
993 ATF_TC_BODY(libbpfjit_alu_and_x, tc)
994 {
995         static struct bpf_insn insns[] = {
996                 BPF_STMT(BPF_LD+BPF_IMM, 0xdead),
997                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0xbeef),
998                 BPF_STMT(BPF_ALU+BPF_AND+BPF_X, 0),
999                 BPF_STMT(BPF_RET+BPF_A, 0)
1000         };
1001
1002         bpfjit_func_t code;
1003         uint8_t pkt[1]; /* the program doesn't read any data */
1004
1005         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1006
1007         ATF_CHECK(bpf_validate(insns, insn_count));
1008
1009         code = bpfjit_generate_code(NULL, insns, insn_count);
1010         ATF_REQUIRE(code != NULL);
1011
1012         ATF_CHECK(jitcall(code, pkt, 1, 1) == (0xdead&0xbeef));
1013
1014         bpfjit_free_code(code);
1015 }
1016
1017 ATF_TC(libbpfjit_alu_or_x);
1018 ATF_TC_HEAD(libbpfjit_alu_or_x, tc)
1019 {
1020         atf_tc_set_md_var(tc, "descr",
1021             "Test JIT compilation of BPF_ALU+BPF_OR+BPF_X");
1022 }
1023
1024 ATF_TC_BODY(libbpfjit_alu_or_x, tc)
1025 {
1026         static struct bpf_insn insns[] = {
1027                 BPF_STMT(BPF_LD+BPF_IMM, 0xdead0000),
1028                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0x0000beef),
1029                 BPF_STMT(BPF_ALU+BPF_OR+BPF_X, 0),
1030                 BPF_STMT(BPF_RET+BPF_A, 0)
1031         };
1032
1033         bpfjit_func_t code;
1034         uint8_t pkt[1]; /* the program doesn't read any data */
1035
1036         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1037
1038         ATF_CHECK(bpf_validate(insns, insn_count));
1039
1040         code = bpfjit_generate_code(NULL, insns, insn_count);
1041         ATF_REQUIRE(code != NULL);
1042
1043         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
1044
1045         bpfjit_free_code(code);
1046 }
1047
1048 ATF_TC(libbpfjit_alu_lsh_x);
1049 ATF_TC_HEAD(libbpfjit_alu_lsh_x, tc)
1050 {
1051         atf_tc_set_md_var(tc, "descr",
1052             "Test JIT compilation of BPF_ALU+BPF_LSH+BPF_X");
1053 }
1054
1055 ATF_TC_BODY(libbpfjit_alu_lsh_x, tc)
1056 {
1057         static struct bpf_insn insns[] = {
1058                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
1059                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 16),
1060                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_X, 0),
1061                 BPF_STMT(BPF_RET+BPF_A, 0)
1062         };
1063
1064         bpfjit_func_t code;
1065         uint8_t pkt[1]; /* the program doesn't read any data */
1066
1067         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1068
1069         ATF_CHECK(bpf_validate(insns, insn_count));
1070
1071         code = bpfjit_generate_code(NULL, insns, insn_count);
1072         ATF_REQUIRE(code != NULL);
1073
1074         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xbeef0000);
1075
1076         bpfjit_free_code(code);
1077 }
1078
1079 ATF_TC(libbpfjit_alu_lsh0_x);
1080 ATF_TC_HEAD(libbpfjit_alu_lsh0_x, tc)
1081 {
1082         atf_tc_set_md_var(tc, "descr",
1083             "Test JIT compilation of BPF_ALU+BPF_LSH+BPF_X with k=0");
1084 }
1085
1086 ATF_TC_BODY(libbpfjit_alu_lsh0_x, tc)
1087 {
1088         static struct bpf_insn insns[] = {
1089                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
1090                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
1091                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_X, 0),
1092                 BPF_STMT(BPF_RET+BPF_A, 0)
1093         };
1094
1095         bpfjit_func_t code;
1096         uint8_t pkt[1]; /* the program doesn't read any data */
1097
1098         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1099
1100         ATF_CHECK(bpf_validate(insns, insn_count));
1101
1102         code = bpfjit_generate_code(NULL, insns, insn_count);
1103         ATF_REQUIRE(code != NULL);
1104
1105         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
1106
1107         bpfjit_free_code(code);
1108 }
1109
1110 ATF_TC(libbpfjit_alu_rsh_x);
1111 ATF_TC_HEAD(libbpfjit_alu_rsh_x, tc)
1112 {
1113         atf_tc_set_md_var(tc, "descr",
1114             "Test JIT compilation of BPF_ALU+BPF_RSH+BPF_X");
1115 }
1116
1117 ATF_TC_BODY(libbpfjit_alu_rsh_x, tc)
1118 {
1119         static struct bpf_insn insns[] = {
1120                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
1121                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 16),
1122                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_X, 0),
1123                 BPF_STMT(BPF_RET+BPF_A, 0)
1124         };
1125
1126         bpfjit_func_t code;
1127         uint8_t pkt[1]; /* the program doesn't read any data */
1128
1129         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1130
1131         ATF_CHECK(bpf_validate(insns, insn_count));
1132
1133         code = bpfjit_generate_code(NULL, insns, insn_count);
1134         ATF_REQUIRE(code != NULL);
1135
1136         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0x0000dead);
1137
1138         bpfjit_free_code(code);
1139 }
1140
1141 ATF_TC(libbpfjit_alu_rsh0_x);
1142 ATF_TC_HEAD(libbpfjit_alu_rsh0_x, tc)
1143 {
1144         atf_tc_set_md_var(tc, "descr",
1145             "Test JIT compilation of BPF_ALU+BPF_RSH+BPF_X with k=0");
1146 }
1147
1148 ATF_TC_BODY(libbpfjit_alu_rsh0_x, tc)
1149 {
1150         static struct bpf_insn insns[] = {
1151                 BPF_STMT(BPF_LD+BPF_IMM, 0xdeadbeef),
1152                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
1153                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_X, 0),
1154                 BPF_STMT(BPF_RET+BPF_A, 0)
1155         };
1156
1157         bpfjit_func_t code;
1158         uint8_t pkt[1]; /* the program doesn't read any data */
1159
1160         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1161
1162         ATF_CHECK(bpf_validate(insns, insn_count));
1163
1164         code = bpfjit_generate_code(NULL, insns, insn_count);
1165         ATF_REQUIRE(code != NULL);
1166
1167         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0xdeadbeef);
1168
1169         bpfjit_free_code(code);
1170 }
1171
1172 ATF_TC(libbpfjit_alu_modulo_x);
1173 ATF_TC_HEAD(libbpfjit_alu_modulo_x, tc)
1174 {
1175         atf_tc_set_md_var(tc, "descr",
1176             "Test JIT compilation of modulo logic of BPF_ALU+BPF_X operations");
1177 }
1178
1179 ATF_TC_BODY(libbpfjit_alu_modulo_x, tc)
1180 {
1181         static struct bpf_insn insns[] = {
1182                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0x7fffff77)),
1183
1184                 /* (7FFFFF77 * 0FFFFF77) = 07FFFFB2,F0004951 */
1185                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0x0fffff77)),
1186                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0),
1187
1188                 /* 07FFFFB2,F0004951 << 1 = 0FFFFF65,E00092A2 */
1189                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, 1),
1190                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_X, 0),
1191
1192                 /* 0FFFFF65,E00092A2 + DDDDDDDD = 0FFFFF66,BDDE707F */
1193                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0xdddddddd)),
1194                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
1195
1196                 /* 0FFFFF66,BDDE707F - FFFFFFFF = 0FFFFF65,BDDE7080 */
1197                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0xffffffff)),
1198                 BPF_STMT(BPF_ALU+BPF_SUB+BPF_X, 0),
1199
1200                 /* 0FFFFF65,BDDE7080 | 0000030C = 0FFFFF65,BDDE738C */
1201                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0x0000030c)),
1202                 BPF_STMT(BPF_ALU+BPF_OR+BPF_X, 0),
1203
1204                 /* -0FFFFF65,BDDE738C mod(2^64) = F000009A,42218C74 */
1205                 BPF_STMT(BPF_ALU+BPF_NEG, 0),
1206
1207                 /* F000009A,42218C74 & FFFFFF0F = F000009A,42218C04 */
1208                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0xffffff0f)),
1209                 BPF_STMT(BPF_ALU+BPF_AND+BPF_X, 0),
1210
1211                 /* F000009A,42218C74 >> 3 = 1E000013,48443180 */
1212                 /* 00000000,42218C74 >> 3 = 00000000,08443180 */
1213                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, 3),
1214                 BPF_STMT(BPF_ALU+BPF_RSH+BPF_X, 0),
1215
1216                 /* 00000000,08443180 * 7FFFFF77 = 042218BB,93818280 */
1217                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0x7fffff77)),
1218                 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0),
1219
1220                 /* 042218BB,93818280 / DEAD = 000004C0,71CBBBC3 */
1221                 /* 00000000,93818280 / DEAD = 00000000,0000A994 */
1222                 BPF_STMT(BPF_LDX+BPF_W+BPF_K, UINT32_C(0xdead)),
1223                 BPF_STMT(BPF_ALU+BPF_DIV+BPF_X, 0),
1224
1225                 BPF_STMT(BPF_RET+BPF_A, 0)
1226         };
1227
1228         bpfjit_func_t code;
1229         uint8_t pkt[1]; /* the program doesn't read any data */
1230
1231         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1232
1233         ATF_CHECK(bpf_validate(insns, insn_count));
1234
1235         code = bpfjit_generate_code(NULL, insns, insn_count);
1236         ATF_REQUIRE(code != NULL);
1237
1238         ATF_CHECK(jitcall(code, pkt, 1, 1) != UINT32_C(0x71cbbbc3));
1239         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_C(0x0000a994));
1240
1241
1242         bpfjit_free_code(code);
1243 }
1244
1245 ATF_TC(libbpfjit_alu_neg);
1246 ATF_TC_HEAD(libbpfjit_alu_neg, tc)
1247 {
1248         atf_tc_set_md_var(tc, "descr",
1249             "Test JIT compilation of BPF_ALU+BPF_NEG");
1250 }
1251
1252 ATF_TC_BODY(libbpfjit_alu_neg, tc)
1253 {
1254         static struct bpf_insn insns[] = {
1255                 BPF_STMT(BPF_LD+BPF_IMM, 777),
1256                 BPF_STMT(BPF_ALU+BPF_NEG, 0),
1257                 BPF_STMT(BPF_RET+BPF_A, 0)
1258         };
1259
1260         bpfjit_func_t code;
1261         uint8_t pkt[1]; /* the program doesn't read any data */
1262
1263         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1264
1265         ATF_CHECK(bpf_validate(insns, insn_count));
1266
1267         code = bpfjit_generate_code(NULL, insns, insn_count);
1268         ATF_REQUIRE(code != NULL);
1269
1270         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0u-777u);
1271
1272         bpfjit_free_code(code);
1273 }
1274
1275 ATF_TC(libbpfjit_jmp_ja);
1276 ATF_TC_HEAD(libbpfjit_jmp_ja, tc)
1277 {
1278         atf_tc_set_md_var(tc, "descr",
1279             "Test JIT compilation of BPF_JMP+BPF_JA");
1280 }
1281
1282 ATF_TC_BODY(libbpfjit_jmp_ja, tc)
1283 {
1284         static struct bpf_insn insns[] = {
1285                 BPF_STMT(BPF_JMP+BPF_JA, 1),
1286                 BPF_STMT(BPF_RET+BPF_K, 0),
1287                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
1288                 BPF_STMT(BPF_RET+BPF_K, 1),
1289                 BPF_STMT(BPF_RET+BPF_K, 2),
1290                 BPF_STMT(BPF_RET+BPF_K, 3),
1291         };
1292
1293         bpfjit_func_t code;
1294         uint8_t pkt[1]; /* the program doesn't read any data */
1295
1296         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1297
1298         ATF_CHECK(bpf_validate(insns, insn_count));
1299
1300         code = bpfjit_generate_code(NULL, insns, insn_count);
1301         ATF_REQUIRE(code != NULL);
1302
1303         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
1304
1305         bpfjit_free_code(code);
1306 }
1307
1308 ATF_TC(libbpfjit_jmp_jgt_k);
1309 ATF_TC_HEAD(libbpfjit_jmp_jgt_k, tc)
1310 {
1311         atf_tc_set_md_var(tc, "descr",
1312             "Test JIT compilation of BPF_JMP+BPF_JGT+BPF_K");
1313 }
1314
1315 ATF_TC_BODY(libbpfjit_jmp_jgt_k, tc)
1316 {
1317         static struct bpf_insn insns[] = {
1318                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1319                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 7, 0, 1),
1320                 BPF_STMT(BPF_RET+BPF_K, 0),
1321                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 2, 2, 0),
1322                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 9, 0, 0),
1323                 BPF_STMT(BPF_RET+BPF_K, 1),
1324                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 4, 1, 1),
1325                 BPF_STMT(BPF_RET+BPF_K, 2),
1326                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 6, 2, 3),
1327                 BPF_STMT(BPF_RET+BPF_K, 3),
1328                 BPF_STMT(BPF_RET+BPF_K, 4),
1329                 BPF_STMT(BPF_RET+BPF_K, 5),
1330                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 5, 3, 1),
1331                 BPF_STMT(BPF_RET+BPF_K, 6),
1332                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 0, 0, 0),
1333                 BPF_STMT(BPF_RET+BPF_K, 7),
1334                 BPF_STMT(BPF_RET+BPF_K, 8)
1335         };
1336
1337         bpfjit_func_t code;
1338         uint8_t pkt[8]; /* the program doesn't read any data */
1339
1340         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1341
1342         ATF_CHECK(bpf_validate(insns, insn_count));
1343
1344         code = bpfjit_generate_code(NULL, insns, insn_count);
1345         ATF_REQUIRE(code != NULL);
1346
1347         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1348         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1349         ATF_CHECK(jitcall(code, pkt, 3, 3) == 7);
1350         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1351         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1352         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1353         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1354         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1355
1356         bpfjit_free_code(code);
1357 }
1358
1359 ATF_TC(libbpfjit_jmp_jge_k);
1360 ATF_TC_HEAD(libbpfjit_jmp_jge_k, tc)
1361 {
1362         atf_tc_set_md_var(tc, "descr",
1363             "Test JIT compilation of BPF_JMP+BPF_JGE+BPF_K");
1364 }
1365
1366 ATF_TC_BODY(libbpfjit_jmp_jge_k, tc)
1367 {
1368         static struct bpf_insn insns[] = {
1369                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1370                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 8, 0, 1),
1371                 BPF_STMT(BPF_RET+BPF_K, 0),
1372                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 3, 2, 0),
1373                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 9, 0, 0),
1374                 BPF_STMT(BPF_RET+BPF_K, 1),
1375                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 5, 1, 1),
1376                 BPF_STMT(BPF_RET+BPF_K, 2),
1377                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 7, 2, 3),
1378                 BPF_STMT(BPF_RET+BPF_K, 3),
1379                 BPF_STMT(BPF_RET+BPF_K, 4),
1380                 BPF_STMT(BPF_RET+BPF_K, 5),
1381                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 6, 3, 1),
1382                 BPF_STMT(BPF_RET+BPF_K, 6),
1383                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 1, 0, 0),
1384                 BPF_STMT(BPF_RET+BPF_K, 7),
1385                 BPF_STMT(BPF_RET+BPF_K, 8)
1386         };
1387
1388         bpfjit_func_t code;
1389         uint8_t pkt[8]; /* the program doesn't read any data */
1390
1391         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1392
1393         ATF_CHECK(bpf_validate(insns, insn_count));
1394
1395         code = bpfjit_generate_code(NULL, insns, insn_count);
1396         ATF_REQUIRE(code != NULL);
1397
1398         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1399         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1400         ATF_CHECK(jitcall(code, pkt, 3, 3) == 7);
1401         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1402         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1403         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1404         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1405         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1406
1407         bpfjit_free_code(code);
1408 }
1409
1410 ATF_TC(libbpfjit_jmp_jeq_k);
1411 ATF_TC_HEAD(libbpfjit_jmp_jeq_k, tc)
1412 {
1413         atf_tc_set_md_var(tc, "descr",
1414             "Test JIT compilation of BPF_JMP+BPF_JEQ+BPF_K");
1415 }
1416
1417 ATF_TC_BODY(libbpfjit_jmp_jeq_k, tc)
1418 {
1419         static struct bpf_insn insns[] = {
1420                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1421                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 8, 0, 1),
1422                 BPF_STMT(BPF_RET+BPF_K, 0),
1423                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 3, 1, 0),
1424                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 9, 1, 1),
1425                 BPF_STMT(BPF_RET+BPF_K, 1),
1426                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 5, 1, 1),
1427                 BPF_STMT(BPF_RET+BPF_K, 2),
1428                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 7, 2, 3),
1429                 BPF_STMT(BPF_RET+BPF_K, 3),
1430                 BPF_STMT(BPF_RET+BPF_K, 4),
1431                 BPF_STMT(BPF_RET+BPF_K, 5),
1432                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 6, 3, 1),
1433                 BPF_STMT(BPF_RET+BPF_K, 6),
1434                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 1, 0, 0),
1435                 BPF_STMT(BPF_RET+BPF_K, 7),
1436                 BPF_STMT(BPF_RET+BPF_K, 8)
1437         };
1438
1439         bpfjit_func_t code;
1440         uint8_t pkt[8]; /* the program doesn't read any data */
1441
1442         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1443
1444         ATF_CHECK(bpf_validate(insns, insn_count));
1445
1446         code = bpfjit_generate_code(NULL, insns, insn_count);
1447         ATF_REQUIRE(code != NULL);
1448
1449         ATF_CHECK(jitcall(code, pkt, 1, 1) == 7);
1450         ATF_CHECK(jitcall(code, pkt, 2, 2) == 7);
1451         ATF_CHECK(jitcall(code, pkt, 3, 3) == 1);
1452         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1453         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1454         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1455         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1456         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1457
1458         bpfjit_free_code(code);
1459 }
1460
1461 ATF_TC(libbpfjit_jmp_jset_k);
1462 ATF_TC_HEAD(libbpfjit_jmp_jset_k, tc)
1463 {
1464         atf_tc_set_md_var(tc, "descr",
1465             "Test JIT compilation of BPF_JMP+BPF_JSET+BPF_K");
1466 }
1467
1468 ATF_TC_BODY(libbpfjit_jmp_jset_k, tc)
1469 {
1470         static struct bpf_insn insns[] = {
1471                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1472                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 8, 0, 1),
1473                 BPF_STMT(BPF_RET+BPF_K, 0),
1474                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 4, 2, 0),
1475                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 3, 0, 0),
1476                 BPF_STMT(BPF_RET+BPF_K, 1),
1477                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 2, 1, 1),
1478                 BPF_STMT(BPF_RET+BPF_K, 2),
1479                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 1, 2, 3),
1480                 BPF_STMT(BPF_RET+BPF_K, 3),
1481                 BPF_STMT(BPF_RET+BPF_K, 4),
1482                 BPF_STMT(BPF_RET+BPF_K, 5),
1483                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 2, 3, 1),
1484                 BPF_STMT(BPF_RET+BPF_K, 6),
1485                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 7, 0, 0),
1486                 BPF_STMT(BPF_RET+BPF_K, 7),
1487                 BPF_STMT(BPF_RET+BPF_K, 8)
1488         };
1489
1490         bpfjit_func_t code;
1491         uint8_t pkt[8]; /* the program doesn't read any data */
1492
1493         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1494
1495         ATF_CHECK(bpf_validate(insns, insn_count));
1496
1497         code = bpfjit_generate_code(NULL, insns, insn_count);
1498         ATF_REQUIRE(code != NULL);
1499
1500         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1501         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1502         ATF_CHECK(jitcall(code, pkt, 3, 3) == 1);
1503         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1504         ATF_CHECK(jitcall(code, pkt, 5, 5) == 5);
1505         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1506         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1507         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1508
1509         bpfjit_free_code(code);
1510 }
1511
1512 ATF_TC(libbpfjit_jmp_modulo_k);
1513 ATF_TC_HEAD(libbpfjit_jmp_modulo_k, tc)
1514 {
1515         atf_tc_set_md_var(tc, "descr",
1516             "Test JIT compilation of modulo logic of BPF_JMP+BPF_K operations");
1517 }
1518
1519 ATF_TC_BODY(libbpfjit_jmp_modulo_k, tc)
1520 {
1521         static struct bpf_insn insns[] = {
1522                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0x7fffff77)),
1523                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_K, 4),
1524                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, UINT32_C(0xfffff770), 1, 0),
1525                 BPF_STMT(BPF_RET+BPF_K, 0),
1526                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, UINT32_C(0xfffff770), 0, 1),
1527                 BPF_STMT(BPF_RET+BPF_K, 1),
1528                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, UINT32_C(0xfffff771), 0, 1),
1529                 BPF_STMT(BPF_RET+BPF_K, 2),
1530                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, UINT32_C(0xfffff770), 0, 3),
1531                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, UINT32_C(0xfffff770), 2, 0),
1532                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, UINT32_C(0xfffff771), 1, 0),
1533                 BPF_STMT(BPF_JMP+BPF_JA, 1),
1534                 BPF_STMT(BPF_RET+BPF_K, 3),
1535
1536                 /* FFFFF770+FFFFF770 = 00000001,FFFFEEE0 */
1537                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, UINT32_C(0xfffff770)),
1538
1539                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, UINT32_C(0xffffeee0), 1, 0),
1540                 BPF_STMT(BPF_RET+BPF_K, 4),
1541                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, UINT32_C(0xffffeee0), 0, 1),
1542                 BPF_STMT(BPF_RET+BPF_K, 5),
1543                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, UINT32_C(0xffffeee1), 0, 1),
1544                 BPF_STMT(BPF_RET+BPF_K, 6),
1545                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, UINT32_C(0xffffeee0), 0, 3),
1546                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, UINT32_C(0xffffeee0), 2, 0),
1547                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, UINT32_C(0xffffeee1), 1, 0),
1548                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
1549                 BPF_STMT(BPF_RET+BPF_K, 7)
1550         };
1551
1552         bpfjit_func_t code;
1553         uint8_t pkt[1]; /* the program doesn't read any data */
1554
1555         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1556
1557         ATF_CHECK(bpf_validate(insns, insn_count));
1558
1559         code = bpfjit_generate_code(NULL, insns, insn_count);
1560         ATF_REQUIRE(code != NULL);
1561
1562         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
1563
1564         bpfjit_free_code(code);
1565 }
1566
1567 ATF_TC(libbpfjit_jmp_jgt_x);
1568 ATF_TC_HEAD(libbpfjit_jmp_jgt_x, tc)
1569 {
1570         atf_tc_set_md_var(tc, "descr",
1571             "Test JIT compilation of BPF_JMP+BPF_JGT+BPF_X");
1572 }
1573
1574 ATF_TC_BODY(libbpfjit_jmp_jgt_x, tc)
1575 {
1576         static struct bpf_insn insns[] = {
1577                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1578                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 7),
1579                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 0, 1),
1580                 BPF_STMT(BPF_RET+BPF_K, 0),
1581                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
1582                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 3, 0),
1583                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 9),
1584                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 0, 0),
1585                 BPF_STMT(BPF_RET+BPF_K, 1),
1586                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 4),
1587                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 1, 1),
1588                 BPF_STMT(BPF_RET+BPF_K, 2),
1589                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 6),
1590                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 2, 3),
1591                 BPF_STMT(BPF_RET+BPF_K, 3),
1592                 BPF_STMT(BPF_RET+BPF_K, 4),
1593                 BPF_STMT(BPF_RET+BPF_K, 5),
1594                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
1595                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 4, 1),
1596                 BPF_STMT(BPF_RET+BPF_K, 6),
1597                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
1598                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 0, 0),
1599                 BPF_STMT(BPF_RET+BPF_K, 7),
1600                 BPF_STMT(BPF_RET+BPF_K, 8)
1601         };
1602
1603         bpfjit_func_t code;
1604         uint8_t pkt[8]; /* the program doesn't read any data */
1605
1606         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1607
1608         ATF_CHECK(bpf_validate(insns, insn_count));
1609
1610         code = bpfjit_generate_code(NULL, insns, insn_count);
1611         ATF_REQUIRE(code != NULL);
1612
1613         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1614         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1615         ATF_CHECK(jitcall(code, pkt, 3, 3) == 7);
1616         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1617         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1618         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1619         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1620         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1621
1622         bpfjit_free_code(code);
1623 }
1624
1625 ATF_TC(libbpfjit_jmp_jge_x);
1626 ATF_TC_HEAD(libbpfjit_jmp_jge_x, tc)
1627 {
1628         atf_tc_set_md_var(tc, "descr",
1629             "Test JIT compilation of BPF_JMP+BPF_JGE+BPF_X");
1630 }
1631
1632 ATF_TC_BODY(libbpfjit_jmp_jge_x, tc)
1633 {
1634         static struct bpf_insn insns[] = {
1635                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1636                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 8),
1637                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 0, 1),
1638                 BPF_STMT(BPF_RET+BPF_K, 0),
1639                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
1640                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 3, 0),
1641                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 9),
1642                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 0, 0),
1643                 BPF_STMT(BPF_RET+BPF_K, 1),
1644                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
1645                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 1, 1),
1646                 BPF_STMT(BPF_RET+BPF_K, 2),
1647                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 7),
1648                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 2, 3),
1649                 BPF_STMT(BPF_RET+BPF_K, 3),
1650                 BPF_STMT(BPF_RET+BPF_K, 4),
1651                 BPF_STMT(BPF_RET+BPF_K, 5),
1652                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 6),
1653                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 4, 1),
1654                 BPF_STMT(BPF_RET+BPF_K, 6),
1655                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1),
1656                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 0, 0),
1657                 BPF_STMT(BPF_RET+BPF_K, 7),
1658                 BPF_STMT(BPF_RET+BPF_K, 8)
1659         };
1660
1661         bpfjit_func_t code;
1662         uint8_t pkt[8]; /* the program doesn't read any data */
1663
1664         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1665
1666         ATF_CHECK(bpf_validate(insns, insn_count));
1667
1668         code = bpfjit_generate_code(NULL, insns, insn_count);
1669         ATF_REQUIRE(code != NULL);
1670
1671         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1672         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1673         ATF_CHECK(jitcall(code, pkt, 3, 3) == 7);
1674         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1675         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1676         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1677         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1678         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1679
1680         bpfjit_free_code(code);
1681 }
1682
1683 ATF_TC(libbpfjit_jmp_jeq_x);
1684 ATF_TC_HEAD(libbpfjit_jmp_jeq_x, tc)
1685 {
1686         atf_tc_set_md_var(tc, "descr",
1687             "Test JIT compilation of BPF_JMP+BPF_JEQ+BPF_X");
1688 }
1689
1690 ATF_TC_BODY(libbpfjit_jmp_jeq_x, tc)
1691 {
1692         static struct bpf_insn insns[] = {
1693                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1694                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 8),
1695                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 0, 1),
1696                 BPF_STMT(BPF_RET+BPF_K, 0),
1697                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
1698                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 2, 0),
1699                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 9),
1700                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 1),
1701                 BPF_STMT(BPF_RET+BPF_K, 1),
1702                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
1703                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 1),
1704                 BPF_STMT(BPF_RET+BPF_K, 2),
1705                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 7),
1706                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 2, 3),
1707                 BPF_STMT(BPF_RET+BPF_K, 3),
1708                 BPF_STMT(BPF_RET+BPF_K, 4),
1709                 BPF_STMT(BPF_RET+BPF_K, 5),
1710                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 6),
1711                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 3, 1),
1712                 BPF_STMT(BPF_RET+BPF_K, 6),
1713                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 1, 0, 0),
1714                 BPF_STMT(BPF_RET+BPF_K, 7),
1715                 BPF_STMT(BPF_RET+BPF_K, 8)
1716         };
1717
1718         bpfjit_func_t code;
1719         uint8_t pkt[8]; /* the program doesn't read any data */
1720
1721         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1722
1723         ATF_CHECK(bpf_validate(insns, insn_count));
1724
1725         code = bpfjit_generate_code(NULL, insns, insn_count);
1726         ATF_REQUIRE(code != NULL);
1727
1728         ATF_CHECK(jitcall(code, pkt, 1, 1) == 7);
1729         ATF_CHECK(jitcall(code, pkt, 2, 2) == 7);
1730         ATF_CHECK(jitcall(code, pkt, 3, 3) == 1);
1731         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1732         ATF_CHECK(jitcall(code, pkt, 5, 5) == 7);
1733         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1734         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1735         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1736
1737         bpfjit_free_code(code);
1738 }
1739
1740 ATF_TC(libbpfjit_jmp_jset_x);
1741 ATF_TC_HEAD(libbpfjit_jmp_jset_x, tc)
1742 {
1743         atf_tc_set_md_var(tc, "descr",
1744             "Test JIT compilation of BPF_JMP+BPF_JSET+BPF_X");
1745 }
1746
1747 ATF_TC_BODY(libbpfjit_jmp_jset_x, tc)
1748 {
1749         static struct bpf_insn insns[] = {
1750                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
1751                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 8),
1752                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 0, 1),
1753                 BPF_STMT(BPF_RET+BPF_K, 0),
1754                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 4),
1755                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 2, 0),
1756                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 3, 0, 0),
1757                 BPF_STMT(BPF_RET+BPF_K, 1),
1758                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
1759                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 1, 1),
1760                 BPF_STMT(BPF_RET+BPF_K, 2),
1761                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1),
1762                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 2, 3),
1763                 BPF_STMT(BPF_RET+BPF_K, 3),
1764                 BPF_STMT(BPF_RET+BPF_K, 4),
1765                 BPF_STMT(BPF_RET+BPF_K, 5),
1766                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 2),
1767                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 4, 1),
1768                 BPF_STMT(BPF_RET+BPF_K, 6),
1769                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 7),
1770                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_X, 0, 0, 0),
1771                 BPF_STMT(BPF_RET+BPF_K, 7),
1772                 BPF_STMT(BPF_RET+BPF_K, 8)
1773         };
1774
1775         bpfjit_func_t code;
1776         uint8_t pkt[8]; /* the program doesn't read any data */
1777
1778         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1779
1780         ATF_CHECK(bpf_validate(insns, insn_count));
1781
1782         code = bpfjit_generate_code(NULL, insns, insn_count);
1783         ATF_REQUIRE(code != NULL);
1784
1785         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
1786         ATF_CHECK(jitcall(code, pkt, 2, 2) == 1);
1787         ATF_CHECK(jitcall(code, pkt, 3, 3) == 1);
1788         ATF_CHECK(jitcall(code, pkt, 4, 4) == 7);
1789         ATF_CHECK(jitcall(code, pkt, 5, 5) == 5);
1790         ATF_CHECK(jitcall(code, pkt, 6, 6) == 8);
1791         ATF_CHECK(jitcall(code, pkt, 7, 7) == 5);
1792         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
1793
1794         bpfjit_free_code(code);
1795 }
1796
1797 ATF_TC(libbpfjit_jmp_modulo_x);
1798 ATF_TC_HEAD(libbpfjit_jmp_modulo_x, tc)
1799 {
1800         atf_tc_set_md_var(tc, "descr",
1801             "Test JIT compilation of modulo logic of BPF_JMP+BPF_X operations");
1802 }
1803
1804 ATF_TC_BODY(libbpfjit_jmp_modulo_x, tc)
1805 {
1806         static struct bpf_insn insns[] = {
1807                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_C(0x7fffff77)),
1808                 /* FFFFF770 << 4 = FFFFF770 */
1809                 BPF_STMT(BPF_ALU+BPF_LSH+BPF_K, 4),
1810
1811                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xfffff770)),
1812                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 0),
1813                 BPF_STMT(BPF_RET+BPF_K, 0),
1814                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 0, 1),
1815                 BPF_STMT(BPF_RET+BPF_K, 1),
1816                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xfffff771)),
1817                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 0, 1),
1818                 BPF_STMT(BPF_RET+BPF_K, 2),
1819                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xfffff770)),
1820                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 0, 4),
1821                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 3, 0),
1822                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xfffff771)),
1823                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 1, 0),
1824                 BPF_STMT(BPF_JMP+BPF_JA, 1),
1825                 BPF_STMT(BPF_RET+BPF_K, 3),
1826
1827                 /* FFFFF770+FFFFF770 = 00000001,FFFFEEE0 */
1828                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, UINT32_C(0xfffff770)),
1829
1830                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xffffeee0)),
1831                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 0),
1832                 BPF_STMT(BPF_RET+BPF_K, 4),
1833                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 0, 1),
1834                 BPF_STMT(BPF_RET+BPF_K, 5),
1835                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xffffeee1)),
1836                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 0, 1),
1837                 BPF_STMT(BPF_RET+BPF_K, 6),
1838                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xffffeee0)),
1839                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 0, 4),
1840                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_X, 0, 3, 0),
1841                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_C(0xffffeee1)),
1842                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_X, 0, 1, 0),
1843                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
1844                 BPF_STMT(BPF_RET+BPF_K, 7)
1845         };
1846
1847         bpfjit_func_t code;
1848         uint8_t pkt[1]; /* the program doesn't read any data */
1849
1850         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
1851
1852         ATF_CHECK(bpf_validate(insns, insn_count));
1853
1854         code = bpfjit_generate_code(NULL, insns, insn_count);
1855         ATF_REQUIRE(code != NULL);
1856
1857         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
1858
1859         bpfjit_free_code(code);
1860 }
1861
1862 ATF_TC(libbpfjit_ld_abs);
1863 ATF_TC_HEAD(libbpfjit_ld_abs, tc)
1864 {
1865         atf_tc_set_md_var(tc, "descr",
1866             "Test JIT compilation of BPF_LD+BPF_ABS");
1867 }
1868
1869 ATF_TC_BODY(libbpfjit_ld_abs, tc)
1870 {
1871         static struct bpf_insn insns[3][2] = {
1872                 {
1873                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 5),
1874                         BPF_STMT(BPF_RET+BPF_A, 0)
1875                 },
1876                 {
1877                         BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 5),
1878                         BPF_STMT(BPF_RET+BPF_A, 0)
1879                 },
1880                 {
1881                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 5),
1882                         BPF_STMT(BPF_RET+BPF_A, 0)
1883                 }
1884         };
1885
1886         static size_t lengths[3] = { 1, 2, 4 };
1887         static unsigned int expected[3] = { 0xde, 0xdead, 0xdeadbeef };
1888
1889         size_t i, l;
1890         uint8_t *pkt = deadbeef_at_5;
1891         size_t pktsize = sizeof(deadbeef_at_5);
1892
1893         size_t insn_count = sizeof(insns[0]) / sizeof(insns[0][0]);
1894
1895         for (i = 0; i < 3; i++) {
1896                 bpfjit_func_t code;
1897
1898                 ATF_CHECK(bpf_validate(insns[i], insn_count));
1899
1900                 code = bpfjit_generate_code(NULL, insns[i], insn_count);
1901                 ATF_REQUIRE(code != NULL);
1902
1903                 for (l = 1; l < 5 + lengths[i]; l++) {
1904                         ATF_CHECK(jitcall(code, pkt, l, l) == 0);
1905                         ATF_CHECK(jitcall(code, pkt, pktsize, l) == 0);
1906                 }
1907
1908                 l = 5 + lengths[i];
1909                 ATF_CHECK(jitcall(code, pkt, l, l) == expected[i]);
1910                 ATF_CHECK(jitcall(code, pkt, pktsize, l) == expected[i]);
1911
1912                 l = pktsize;
1913                 ATF_CHECK(jitcall(code, pkt, l, l) == expected[i]);
1914
1915                 bpfjit_free_code(code);
1916         }
1917 }
1918
1919 ATF_TC(libbpfjit_ld_abs_k_overflow);
1920 ATF_TC_HEAD(libbpfjit_ld_abs_k_overflow, tc)
1921 {
1922         atf_tc_set_md_var(tc, "descr",
1923             "Test JIT compilation of BPF_LD+BPF_ABS with overflow in k+4");
1924 }
1925
1926 ATF_TC_BODY(libbpfjit_ld_abs_k_overflow, tc)
1927 {
1928         static struct bpf_insn insns[12][3] = {
1929                 {
1930                         BPF_STMT(BPF_LD+BPF_H+BPF_ABS, UINT32_MAX),
1931                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1932                         BPF_STMT(BPF_RET+BPF_K, 1)
1933                 },
1934                 {
1935                         BPF_STMT(BPF_LD+BPF_H+BPF_ABS, UINT32_MAX - 1),
1936                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1937                         BPF_STMT(BPF_RET+BPF_K, 1)
1938                 },
1939                 {
1940                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX),
1941                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1942                         BPF_STMT(BPF_RET+BPF_K, 1)
1943                 },
1944                 {
1945                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 1),
1946                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1947                         BPF_STMT(BPF_RET+BPF_K, 1)
1948                 },
1949                 {
1950                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 2),
1951                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1952                         BPF_STMT(BPF_RET+BPF_K, 1)
1953                 },
1954                 {
1955                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 3),
1956                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1957                         BPF_STMT(BPF_RET+BPF_K, 1)
1958                 },
1959                 {
1960                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1961                         BPF_STMT(BPF_LD+BPF_H+BPF_ABS, UINT32_MAX),
1962                         BPF_STMT(BPF_RET+BPF_K, 1)
1963                 },
1964                 {
1965                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1966                         BPF_STMT(BPF_LD+BPF_H+BPF_ABS, UINT32_MAX - 1),
1967                         BPF_STMT(BPF_RET+BPF_K, 1)
1968                 },
1969                 {
1970                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1971                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX),
1972                         BPF_STMT(BPF_RET+BPF_K, 1)
1973                 },
1974                 {
1975                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1976                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 1),
1977                         BPF_STMT(BPF_RET+BPF_K, 1)
1978                 },
1979                 {
1980                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1981                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 2),
1982                         BPF_STMT(BPF_RET+BPF_K, 1)
1983                 },
1984                 {
1985                         BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
1986                         BPF_STMT(BPF_LD+BPF_W+BPF_ABS, UINT32_MAX - 3),
1987                         BPF_STMT(BPF_RET+BPF_K, 1)
1988                 }
1989         };
1990
1991         int i;
1992         uint8_t pkt[8] = { 0 };
1993
1994         size_t insn_count = sizeof(insns[0]) / sizeof(insns[0][0]);
1995
1996         for (i = 0; i < 3; i++) {
1997                 bpfjit_func_t code;
1998
1999                 ATF_CHECK(bpf_validate(insns[i], insn_count));
2000
2001                 code = bpfjit_generate_code(NULL, insns[i], insn_count);
2002                 ATF_REQUIRE(code != NULL);
2003
2004                 ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
2005
2006                 bpfjit_free_code(code);
2007         }
2008 }
2009
2010 ATF_TC(libbpfjit_ld_ind);
2011 ATF_TC_HEAD(libbpfjit_ld_ind, tc)
2012 {
2013         atf_tc_set_md_var(tc, "descr",
2014             "Test JIT compilation of BPF_LD+BPF_IND");
2015 }
2016
2017 ATF_TC_BODY(libbpfjit_ld_ind, tc)
2018 {
2019         static struct bpf_insn insns[6][3] = {
2020                 {
2021                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
2022                         BPF_STMT(BPF_LD+BPF_B+BPF_IND, 2),
2023                         BPF_STMT(BPF_RET+BPF_A, 0)
2024                 },
2025                 {
2026                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
2027                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 2),
2028                         BPF_STMT(BPF_RET+BPF_A, 0)
2029                 },
2030                 {
2031                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 3),
2032                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, 2),
2033                         BPF_STMT(BPF_RET+BPF_A, 0)
2034                 },
2035                 {
2036                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
2037                         BPF_STMT(BPF_LD+BPF_B+BPF_IND, 0),
2038                         BPF_STMT(BPF_RET+BPF_A, 0)
2039                 },
2040                 {
2041                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
2042                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 0),
2043                         BPF_STMT(BPF_RET+BPF_A, 0)
2044                 },
2045                 {
2046                         BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
2047                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, 0),
2048                         BPF_STMT(BPF_RET+BPF_A, 0)
2049                 }
2050         };
2051
2052         static size_t lengths[6] = { 1, 2, 4, 1, 2, 4 };
2053
2054         static unsigned int expected[6] = {
2055                 0xde, 0xdead, 0xdeadbeef,
2056                 0xde, 0xdead, 0xdeadbeef
2057         };
2058
2059         size_t i, l;
2060         uint8_t *pkt = deadbeef_at_5;
2061         size_t pktsize = sizeof(deadbeef_at_5);
2062
2063         size_t insn_count = sizeof(insns[0]) / sizeof(insns[0][0]);
2064
2065         for (i = 0; i < 3; i++) {
2066                 bpfjit_func_t code;
2067
2068                 ATF_CHECK(bpf_validate(insns[i], insn_count));
2069
2070                 code = bpfjit_generate_code(NULL, insns[i], insn_count);
2071                 ATF_REQUIRE(code != NULL);
2072
2073                 for (l = 1; l < 5 + lengths[i]; l++) {
2074                         ATF_CHECK(jitcall(code, pkt, l, l) == 0);
2075                         ATF_CHECK(jitcall(code, pkt, pktsize, l) == 0);
2076                 }
2077
2078                 l = 5 + lengths[i];
2079                 ATF_CHECK(jitcall(code, pkt, l, l) == expected[i]);
2080                 ATF_CHECK(jitcall(code, pkt, pktsize, l) == expected[i]);
2081
2082                 l = pktsize;
2083                 ATF_CHECK(jitcall(code, pkt, l, l) == expected[i]);
2084
2085                 bpfjit_free_code(code);
2086         }
2087 }
2088
2089 ATF_TC(libbpfjit_ld_ind_k_overflow);
2090 ATF_TC_HEAD(libbpfjit_ld_ind_k_overflow, tc)
2091 {
2092         atf_tc_set_md_var(tc, "descr",
2093             "Test JIT compilation of BPF_LD+BPF_IND with overflow in k+4");
2094 }
2095
2096 ATF_TC_BODY(libbpfjit_ld_ind_k_overflow, tc)
2097 {
2098         static struct bpf_insn insns[12][3] = {
2099                 {
2100                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, UINT32_MAX),
2101                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2102                         BPF_STMT(BPF_RET+BPF_K, 1)
2103                 },
2104                 {
2105                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, UINT32_MAX - 1),
2106                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2107                         BPF_STMT(BPF_RET+BPF_K, 1)
2108                 },
2109                 {
2110                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX),
2111                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2112                         BPF_STMT(BPF_RET+BPF_K, 1)
2113                 },
2114                 {
2115                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 1),
2116                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2117                         BPF_STMT(BPF_RET+BPF_K, 1)
2118                 },
2119                 {
2120                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 2),
2121                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2122                         BPF_STMT(BPF_RET+BPF_K, 1)
2123                 },
2124                 {
2125                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 3),
2126                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2127                         BPF_STMT(BPF_RET+BPF_K, 1)
2128                 },
2129                 {
2130                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2131                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, UINT32_MAX),
2132                         BPF_STMT(BPF_RET+BPF_K, 1)
2133                 },
2134                 {
2135                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2136                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, UINT32_MAX - 1),
2137                         BPF_STMT(BPF_RET+BPF_K, 1)
2138                 },
2139                 {
2140                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2141                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX),
2142                         BPF_STMT(BPF_RET+BPF_K, 1)
2143                 },
2144                 {
2145                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2146                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 1),
2147                         BPF_STMT(BPF_RET+BPF_K, 1)
2148                 },
2149                 {
2150                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2151                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 2),
2152                         BPF_STMT(BPF_RET+BPF_K, 1)
2153                 },
2154                 {
2155                         BPF_STMT(BPF_LD+BPF_H+BPF_IND, 7),
2156                         BPF_STMT(BPF_LD+BPF_W+BPF_IND, UINT32_MAX - 3),
2157                         BPF_STMT(BPF_RET+BPF_K, 1)
2158                 }
2159         };
2160
2161         int i;
2162         uint8_t pkt[8] = { 0 };
2163
2164         size_t insn_count = sizeof(insns[0]) / sizeof(insns[0][0]);
2165
2166         for (i = 0; i < 3; i++) {
2167                 bpfjit_func_t code;
2168
2169                 ATF_CHECK(bpf_validate(insns[i], insn_count));
2170
2171                 code = bpfjit_generate_code(NULL, insns[i], insn_count);
2172                 ATF_REQUIRE(code != NULL);
2173
2174                 ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
2175
2176                 bpfjit_free_code(code);
2177         }
2178 }
2179
2180 ATF_TC(libbpfjit_ld_ind_x_overflow1);
2181 ATF_TC_HEAD(libbpfjit_ld_ind_x_overflow1, tc)
2182 {
2183         atf_tc_set_md_var(tc, "descr",
2184             "Test JIT compilation of BPF_LD+BPF_IND with overflow in X+4");
2185 }
2186
2187 ATF_TC_BODY(libbpfjit_ld_ind_x_overflow1, tc)
2188 {
2189         static struct bpf_insn insns[] = {
2190                 BPF_STMT(BPF_LD+BPF_LEN, 0),
2191                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, UINT32_C(0xffffffff)),
2192                 BPF_STMT(BPF_MISC+BPF_TAX, 0),
2193                 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 0),
2194                 BPF_STMT(BPF_RET+BPF_A, 0)
2195         };
2196
2197         size_t i;
2198         bpfjit_func_t code;
2199         uint8_t pkt[8] = { 10, 20, 30, 40, 50, 60, 70, 80 };
2200
2201         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2202
2203         ATF_CHECK(bpf_validate(insns, insn_count));
2204
2205         code = bpfjit_generate_code(NULL, insns, insn_count);
2206         ATF_REQUIRE(code != NULL);
2207
2208         for (i = 1; i <= sizeof(pkt); i++) {
2209                 ATF_CHECK(bpf_filter(insns, pkt, i, i) == 10 * i);
2210                 ATF_CHECK(jitcall(code, pkt, i, i) == 10 * i);
2211         }
2212
2213         bpfjit_free_code(code);
2214 }
2215
2216 ATF_TC(libbpfjit_ld_ind_x_overflow2);
2217 ATF_TC_HEAD(libbpfjit_ld_ind_x_overflow2, tc)
2218 {
2219         atf_tc_set_md_var(tc, "descr",
2220             "Test JIT compilation of BPF_LD+BPF_IND with overflow in X+4");
2221 }
2222
2223 ATF_TC_BODY(libbpfjit_ld_ind_x_overflow2, tc)
2224 {
2225         static struct bpf_insn insns[] = {
2226                 BPF_STMT(BPF_LD+BPF_LEN, 0),
2227                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, UINT32_C(0xffffffff)),
2228                 BPF_STMT(BPF_ST, 3),
2229                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 3),
2230                 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 0),
2231                 BPF_STMT(BPF_RET+BPF_A, 0)
2232         };
2233
2234         size_t i;
2235         bpfjit_func_t code;
2236         uint8_t pkt[8] = { 10, 20, 30, 40, 50, 60, 70, 80 };
2237
2238         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2239
2240         ATF_CHECK(bpf_validate(insns, insn_count));
2241
2242         code = bpfjit_generate_code(NULL, insns, insn_count);
2243         ATF_REQUIRE(code != NULL);
2244
2245         for (i = 1; i <= sizeof(pkt); i++) {
2246                 ATF_CHECK(bpf_filter(insns, pkt, i, i) == 10 * i);
2247                 ATF_CHECK(jitcall(code, pkt, i, i) == 10 * i);
2248         }
2249
2250         bpfjit_free_code(code);
2251 }
2252
2253 ATF_TC(libbpfjit_ld_len);
2254 ATF_TC_HEAD(libbpfjit_ld_len, tc)
2255 {
2256         atf_tc_set_md_var(tc, "descr",
2257             "Test JIT compilation of BPF_LD+BPF_W+BPF_LEN");
2258 }
2259
2260 ATF_TC_BODY(libbpfjit_ld_len, tc)
2261 {
2262         static struct bpf_insn insns[] = {
2263                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
2264                 BPF_STMT(BPF_RET+BPF_A, 0)
2265         };
2266
2267         size_t i;
2268         bpfjit_func_t code;
2269         uint8_t pkt[32]; /* the program doesn't read any data */
2270
2271         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2272
2273         ATF_CHECK(bpf_validate(insns, insn_count));
2274
2275         code = bpfjit_generate_code(NULL, insns, insn_count);
2276         ATF_REQUIRE(code != NULL);
2277
2278         for (i = 0; i < sizeof(pkt); i++)
2279                 ATF_CHECK(jitcall(code, pkt, i, 1) == i);
2280
2281         bpfjit_free_code(code);
2282 }
2283
2284 ATF_TC(libbpfjit_ld_imm);
2285 ATF_TC_HEAD(libbpfjit_ld_imm, tc)
2286 {
2287         atf_tc_set_md_var(tc, "descr",
2288             "Test JIT compilation of BPF_LD+BPF_IMM");
2289 }
2290
2291 ATF_TC_BODY(libbpfjit_ld_imm, tc)
2292 {
2293         static struct bpf_insn insns[] = {
2294                 BPF_STMT(BPF_LD+BPF_IMM, UINT32_MAX),
2295                 BPF_STMT(BPF_RET+BPF_A, 0)
2296         };
2297
2298         bpfjit_func_t code;
2299         uint8_t pkt[1]; /* the program doesn't read any data */
2300
2301         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2302
2303         ATF_CHECK(bpf_validate(insns, insn_count));
2304
2305         code = bpfjit_generate_code(NULL, insns, insn_count);
2306         ATF_REQUIRE(code != NULL);
2307
2308         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
2309
2310         bpfjit_free_code(code);
2311 }
2312
2313 ATF_TC(libbpfjit_ldx_imm1);
2314 ATF_TC_HEAD(libbpfjit_ldx_imm1, tc)
2315 {
2316         atf_tc_set_md_var(tc, "descr",
2317             "Test JIT compilation of BPF_LDX+BPF_IMM");
2318 }
2319
2320 ATF_TC_BODY(libbpfjit_ldx_imm1, tc)
2321 {
2322         static struct bpf_insn insns[] = {
2323                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, UINT32_MAX - 5),
2324                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2325                 BPF_STMT(BPF_RET+BPF_A, 0)
2326         };
2327
2328         bpfjit_func_t code;
2329         uint8_t pkt[1]; /* the program doesn't read any data */
2330
2331         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2332
2333         ATF_CHECK(bpf_validate(insns, insn_count));
2334
2335         code = bpfjit_generate_code(NULL, insns, insn_count);
2336         ATF_REQUIRE(code != NULL);
2337
2338         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX - 5);
2339
2340         bpfjit_free_code(code);
2341 }
2342
2343 ATF_TC(libbpfjit_ldx_imm2);
2344 ATF_TC_HEAD(libbpfjit_ldx_imm2, tc)
2345 {
2346         atf_tc_set_md_var(tc, "descr",
2347             "Test JIT compilation of BPF_LDX+BPF_IMM");
2348 }
2349
2350 ATF_TC_BODY(libbpfjit_ldx_imm2, tc)
2351 {
2352         static struct bpf_insn insns[] = {
2353                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 5),
2354                 BPF_STMT(BPF_LD+BPF_IMM, 5),
2355                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 0),
2356                 BPF_STMT(BPF_RET+BPF_K, 7),
2357                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX)
2358         };
2359
2360         bpfjit_func_t code;
2361         uint8_t pkt[1]; /* the program doesn't read any data */
2362
2363         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2364
2365         ATF_CHECK(bpf_validate(insns, insn_count));
2366
2367         code = bpfjit_generate_code(NULL, insns, insn_count);
2368         ATF_REQUIRE(code != NULL);
2369
2370         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
2371
2372         bpfjit_free_code(code);
2373 }
2374
2375 ATF_TC(libbpfjit_ldx_len1);
2376 ATF_TC_HEAD(libbpfjit_ldx_len1, tc)
2377 {
2378         atf_tc_set_md_var(tc, "descr",
2379             "Test JIT compilation of BPF_LDX+BPF_LEN");
2380 }
2381
2382 ATF_TC_BODY(libbpfjit_ldx_len1, tc)
2383 {
2384         static struct bpf_insn insns[] = {
2385                 BPF_STMT(BPF_LDX+BPF_W+BPF_LEN, 0),
2386                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2387                 BPF_STMT(BPF_RET+BPF_A, 0)
2388         };
2389
2390         size_t i;
2391         bpfjit_func_t code;
2392         uint8_t pkt[5]; /* the program doesn't read any data */
2393
2394         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2395
2396         ATF_CHECK(bpf_validate(insns, insn_count));
2397
2398         code = bpfjit_generate_code(NULL, insns, insn_count);
2399         ATF_REQUIRE(code != NULL);
2400
2401         for (i = 1; i < sizeof(pkt); i++) {
2402                 ATF_CHECK(jitcall(code, pkt, i, 1) == i);
2403                 ATF_CHECK(jitcall(code, pkt, i + 1, i) == i + 1);
2404         }
2405
2406         bpfjit_free_code(code);
2407 }
2408
2409 ATF_TC(libbpfjit_ldx_len2);
2410 ATF_TC_HEAD(libbpfjit_ldx_len2, tc)
2411 {
2412         atf_tc_set_md_var(tc, "descr",
2413             "Test JIT compilation of BPF_LDX+BPF_LEN");
2414 }
2415
2416 ATF_TC_BODY(libbpfjit_ldx_len2, tc)
2417 {
2418         static struct bpf_insn insns[] = {
2419                 BPF_STMT(BPF_LDX+BPF_W+BPF_LEN, 0),
2420                 BPF_STMT(BPF_LD+BPF_IMM, 5),
2421                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_X, 0, 1, 0),
2422                 BPF_STMT(BPF_RET+BPF_K, 7),
2423                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX)
2424         };
2425
2426         bpfjit_func_t code;
2427         uint8_t pkt[5]; /* the program doesn't read any data */
2428
2429         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2430
2431         ATF_CHECK(bpf_validate(insns, insn_count));
2432
2433         code = bpfjit_generate_code(NULL, insns, insn_count);
2434         ATF_REQUIRE(code != NULL);
2435
2436         ATF_CHECK(jitcall(code, pkt, 5, 1) == UINT32_MAX);
2437         ATF_CHECK(jitcall(code, pkt, 6, 5) == 7);
2438
2439         bpfjit_free_code(code);
2440 }
2441
2442 ATF_TC(libbpfjit_ldx_msh);
2443 ATF_TC_HEAD(libbpfjit_ldx_msh, tc)
2444 {
2445         atf_tc_set_md_var(tc, "descr",
2446             "Test JIT compilation of BPF_LDX+BPF_MSH");
2447 }
2448
2449 ATF_TC_BODY(libbpfjit_ldx_msh, tc)
2450 {
2451         static struct bpf_insn insns[] = {
2452                 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 1),
2453                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2454                 BPF_STMT(BPF_RET+BPF_A, 0)
2455         };
2456
2457         bpfjit_func_t code;
2458         uint8_t pkt[2] = { 0, 0x7a };
2459
2460         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2461
2462         ATF_CHECK(bpf_validate(insns, insn_count));
2463
2464         code = bpfjit_generate_code(NULL, insns, insn_count);
2465         ATF_REQUIRE(code != NULL);
2466
2467         ATF_CHECK(jitcall(code, pkt, 2, 2) == 40);
2468
2469         bpfjit_free_code(code);
2470 }
2471
2472 ATF_TC(libbpfjit_misc_tax);
2473 ATF_TC_HEAD(libbpfjit_misc_tax, tc)
2474 {
2475         atf_tc_set_md_var(tc, "descr",
2476             "Test JIT compilation of BPF_MISC+BPF_TAX");
2477 }
2478
2479 ATF_TC_BODY(libbpfjit_misc_tax, tc)
2480 {
2481         static struct bpf_insn insns[] = {
2482                 BPF_STMT(BPF_LD+BPF_IMM, 3),
2483                 BPF_STMT(BPF_MISC+BPF_TAX, 0),
2484                 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 2),
2485                 BPF_STMT(BPF_RET+BPF_A, 0)
2486         };
2487
2488         bpfjit_func_t code;
2489         uint8_t pkt[] = { 0, 11, 22, 33, 44, 55 };
2490
2491         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2492
2493         ATF_CHECK(bpf_validate(insns, insn_count));
2494
2495         code = bpfjit_generate_code(NULL, insns, insn_count);
2496         ATF_REQUIRE(code != NULL);
2497
2498         ATF_CHECK(jitcall(code, pkt, sizeof(pkt), sizeof(pkt)) == 55);
2499
2500         bpfjit_free_code(code);
2501 }
2502
2503 ATF_TC(libbpfjit_misc_txa);
2504 ATF_TC_HEAD(libbpfjit_misc_txa, tc)
2505 {
2506         atf_tc_set_md_var(tc, "descr",
2507             "Test JIT compilation of BPF_MISC+BPF_TXA");
2508 }
2509
2510 ATF_TC_BODY(libbpfjit_misc_txa, tc)
2511 {
2512         static struct bpf_insn insns[] = {
2513                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 391),
2514                 BPF_STMT(BPF_MISC+BPF_TXA, 0),
2515                 BPF_STMT(BPF_RET+BPF_A, 0)
2516         };
2517
2518         bpfjit_func_t code;
2519         uint8_t pkt[1]; /* the program doesn't read any data */
2520
2521         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2522
2523         ATF_CHECK(bpf_validate(insns, insn_count));
2524
2525         code = bpfjit_generate_code(NULL, insns, insn_count);
2526         ATF_REQUIRE(code != NULL);
2527
2528         ATF_CHECK(jitcall(code, pkt, 1, 1) == 391);
2529
2530         bpfjit_free_code(code);
2531 }
2532
2533 ATF_TC(libbpfjit_st1);
2534 ATF_TC_HEAD(libbpfjit_st1, tc)
2535 {
2536         atf_tc_set_md_var(tc, "descr",
2537             "Test JIT compilation of BPF_ST");
2538 }
2539
2540 ATF_TC_BODY(libbpfjit_st1, tc)
2541 {
2542         static struct bpf_insn insns[] = {
2543                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
2544                 BPF_STMT(BPF_ST, 0),
2545                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 1),
2546                 BPF_STMT(BPF_LD+BPF_MEM, 0),
2547                 BPF_STMT(BPF_RET+BPF_A, 0)
2548         };
2549
2550         size_t i;
2551         bpfjit_func_t code;
2552         uint8_t pkt[16]; /* the program doesn't read any data */
2553
2554         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2555
2556         ATF_CHECK(bpf_validate(insns, insn_count));
2557
2558         code = bpfjit_generate_code(NULL, insns, insn_count);
2559         ATF_REQUIRE(code != NULL);
2560
2561         for (i = 1; i <= sizeof(pkt); i++)
2562                 ATF_CHECK(jitcall(code, pkt, i, sizeof(pkt)) == i);
2563
2564         bpfjit_free_code(code);
2565 }
2566
2567 ATF_TC(libbpfjit_st2);
2568 ATF_TC_HEAD(libbpfjit_st2, tc)
2569 {
2570         atf_tc_set_md_var(tc, "descr",
2571             "Test JIT compilation of BPF_ST");
2572 }
2573
2574 ATF_TC_BODY(libbpfjit_st2, tc)
2575 {
2576         static struct bpf_insn insns[] = {
2577                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
2578                 BPF_STMT(BPF_ST, BPF_MEMWORDS-1),
2579                 BPF_STMT(BPF_LD+BPF_MEM, 0),
2580                 BPF_STMT(BPF_RET+BPF_A, 0)
2581         };
2582
2583         bpfjit_func_t code;
2584         uint8_t pkt[1]; /* the program doesn't read any data */
2585
2586         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2587
2588         ATF_CHECK(bpf_validate(insns, insn_count));
2589
2590         code = bpfjit_generate_code(NULL, insns, insn_count);
2591         ATF_REQUIRE(code != NULL);
2592
2593         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
2594
2595         bpfjit_free_code(code);
2596 }
2597
2598 ATF_TC(libbpfjit_st3);
2599 ATF_TC_HEAD(libbpfjit_st3, tc)
2600 {
2601         atf_tc_set_md_var(tc, "descr",
2602             "Test JIT compilation of BPF_ST");
2603 }
2604
2605 ATF_TC_BODY(libbpfjit_st3, tc)
2606 {
2607         static struct bpf_insn insns[] = {
2608                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
2609                 BPF_STMT(BPF_ST, 0),
2610                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 100),
2611                 BPF_STMT(BPF_ST, BPF_MEMWORDS-1),
2612                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 200),
2613                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 301, 2, 0),
2614                 BPF_STMT(BPF_LD+BPF_MEM, BPF_MEMWORDS-1),
2615                 BPF_STMT(BPF_RET+BPF_A, 0),
2616                 BPF_STMT(BPF_LD+BPF_MEM, 0),
2617                 BPF_STMT(BPF_RET+BPF_A, 0)
2618         };
2619
2620         bpfjit_func_t code;
2621         uint8_t pkt[2]; /* the program doesn't read any data */
2622
2623         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2624
2625         ATF_REQUIRE(BPF_MEMWORDS > 1);
2626
2627         ATF_CHECK(bpf_validate(insns, insn_count));
2628
2629         code = bpfjit_generate_code(NULL, insns, insn_count);
2630         ATF_REQUIRE(code != NULL);
2631
2632         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
2633         ATF_CHECK(jitcall(code, pkt, 2, 2) == 102);
2634
2635         bpfjit_free_code(code);
2636 }
2637
2638 ATF_TC(libbpfjit_st4);
2639 ATF_TC_HEAD(libbpfjit_st4, tc)
2640 {
2641         atf_tc_set_md_var(tc, "descr",
2642             "Test JIT compilation of BPF_ST");
2643 }
2644
2645 ATF_TC_BODY(libbpfjit_st4, tc)
2646 {
2647         static struct bpf_insn insns[] = {
2648                 BPF_STMT(BPF_LD+BPF_W+BPF_LEN, 0),
2649                 BPF_STMT(BPF_ST, 5),
2650                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 100),
2651                 BPF_STMT(BPF_ST, BPF_MEMWORDS-1),
2652                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_K, 200),
2653                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 301, 2, 0),
2654                 BPF_STMT(BPF_LD+BPF_MEM, BPF_MEMWORDS-1),
2655                 BPF_STMT(BPF_RET+BPF_A, 0),
2656                 BPF_STMT(BPF_LD+BPF_MEM, 5),
2657                 BPF_STMT(BPF_RET+BPF_A, 0)
2658         };
2659
2660         bpfjit_func_t code;
2661         uint8_t pkt[2]; /* the program doesn't read any data */
2662
2663         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2664
2665         ATF_REQUIRE(BPF_MEMWORDS > 6);
2666
2667         ATF_CHECK(bpf_validate(insns, insn_count));
2668
2669         code = bpfjit_generate_code(NULL, insns, insn_count);
2670         ATF_REQUIRE(code != NULL);
2671
2672         ATF_CHECK(jitcall(code, pkt, 1, 1) == 1);
2673         ATF_CHECK(jitcall(code, pkt, 2, 2) == 102);
2674
2675         bpfjit_free_code(code);
2676 }
2677
2678 ATF_TC(libbpfjit_st5);
2679 ATF_TC_HEAD(libbpfjit_st5, tc)
2680 {
2681         atf_tc_set_md_var(tc, "descr",
2682             "Test JIT compilation of BPF_ST");
2683 }
2684
2685 ATF_TC_BODY(libbpfjit_st5, tc)
2686 {
2687         struct bpf_insn insns[5*BPF_MEMWORDS+2];
2688         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2689
2690         size_t k;
2691         bpfjit_func_t code;
2692         uint8_t pkt[BPF_MEMWORDS]; /* the program doesn't read any data */
2693
2694         memset(insns, 0, sizeof(insns));
2695
2696         /* for each k do M[k] = k */
2697         for (k = 0; k < BPF_MEMWORDS; k++) {
2698                 insns[2*k].code   = BPF_LD+BPF_IMM;
2699                 insns[2*k].k      = 3*k;
2700                 insns[2*k+1].code = BPF_ST;
2701                 insns[2*k+1].k    = k;
2702         }
2703
2704         /* load wirelen into A */
2705         insns[2*BPF_MEMWORDS].code = BPF_LD+BPF_W+BPF_LEN;
2706
2707         /* for each k, if (A == k + 1) return M[k] */
2708         for (k = 0; k < BPF_MEMWORDS; k++) {
2709                 insns[2*BPF_MEMWORDS+3*k+1].code = BPF_JMP+BPF_JEQ+BPF_K;
2710                 insns[2*BPF_MEMWORDS+3*k+1].k    = k+1;
2711                 insns[2*BPF_MEMWORDS+3*k+1].jt   = 0;
2712                 insns[2*BPF_MEMWORDS+3*k+1].jf   = 2;
2713                 insns[2*BPF_MEMWORDS+3*k+2].code = BPF_LD+BPF_MEM;
2714                 insns[2*BPF_MEMWORDS+3*k+2].k    = k;
2715                 insns[2*BPF_MEMWORDS+3*k+3].code = BPF_RET+BPF_A;
2716                 insns[2*BPF_MEMWORDS+3*k+3].k    = 0;
2717         }
2718
2719         insns[5*BPF_MEMWORDS+1].code = BPF_RET+BPF_K;
2720         insns[5*BPF_MEMWORDS+1].k    = UINT32_MAX;
2721
2722         ATF_CHECK(bpf_validate(insns, insn_count));
2723
2724         code = bpfjit_generate_code(NULL, insns, insn_count);
2725         ATF_REQUIRE(code != NULL);
2726
2727         for (k = 1; k <= sizeof(pkt); k++)
2728                 ATF_CHECK(jitcall(code, pkt, k, k) == 3*(k-1));
2729
2730         bpfjit_free_code(code);
2731 }
2732
2733 ATF_TC(libbpfjit_stx1);
2734 ATF_TC_HEAD(libbpfjit_stx1, tc)
2735 {
2736         atf_tc_set_md_var(tc, "descr",
2737             "Test JIT compilation of BPF_STX");
2738 }
2739
2740 ATF_TC_BODY(libbpfjit_stx1, tc)
2741 {
2742         static struct bpf_insn insns[] = {
2743                 BPF_STMT(BPF_LDX+BPF_W+BPF_LEN, 0),
2744                 BPF_STMT(BPF_STX, 0),
2745                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0),
2746                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2747                 BPF_STMT(BPF_RET+BPF_A, 0)
2748         };
2749
2750         size_t i;
2751         bpfjit_func_t code;
2752         uint8_t pkt[16]; /* the program doesn't read any data */
2753
2754         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2755
2756         ATF_CHECK(bpf_validate(insns, insn_count));
2757
2758         code = bpfjit_generate_code(NULL, insns, insn_count);
2759         ATF_REQUIRE(code != NULL);
2760
2761         for (i = 1; i <= sizeof(pkt); i++)
2762                 ATF_CHECK(jitcall(code, pkt, i, sizeof(pkt)) == i);
2763
2764         bpfjit_free_code(code);
2765 }
2766
2767 ATF_TC(libbpfjit_stx2);
2768 ATF_TC_HEAD(libbpfjit_stx2, tc)
2769 {
2770         atf_tc_set_md_var(tc, "descr",
2771             "Test JIT compilation of BPF_STX");
2772 }
2773
2774 ATF_TC_BODY(libbpfjit_stx2, tc)
2775 {
2776         static struct bpf_insn insns[] = {
2777                 BPF_STMT(BPF_LDX+BPF_W+BPF_LEN, 0),
2778                 BPF_STMT(BPF_STX, BPF_MEMWORDS-1),
2779                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0),
2780                 BPF_STMT(BPF_MISC+BPF_TXA, 0),
2781                 BPF_STMT(BPF_RET+BPF_A, 0)
2782         };
2783
2784         bpfjit_func_t code;
2785         uint8_t pkt[1]; /* the program doesn't read any data */
2786
2787         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2788
2789         ATF_CHECK(bpf_validate(insns, insn_count));
2790
2791         code = bpfjit_generate_code(NULL, insns, insn_count);
2792         ATF_REQUIRE(code != NULL);
2793
2794         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
2795
2796         bpfjit_free_code(code);
2797 }
2798
2799 ATF_TC(libbpfjit_stx3);
2800 ATF_TC_HEAD(libbpfjit_stx3, tc)
2801 {
2802         atf_tc_set_md_var(tc, "descr",
2803             "Test JIT compilation of BPF_STX");
2804 }
2805
2806 ATF_TC_BODY(libbpfjit_stx3, tc)
2807 {
2808         static struct bpf_insn insns[] = {
2809                 BPF_STMT(BPF_LDX+BPF_W+BPF_LEN, 0),
2810                 BPF_STMT(BPF_STX, 5),
2811                 BPF_STMT(BPF_STX, 2),
2812                 BPF_STMT(BPF_STX, 3),
2813                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 1),
2814                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2815                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 2),
2816                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2817                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 3),
2818                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2819                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 5),
2820                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2821                 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 6),
2822                 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0),
2823                 BPF_STMT(BPF_RET+BPF_A, 0)
2824         };
2825
2826         size_t i;
2827         bpfjit_func_t code;
2828         uint8_t pkt[16]; /* the program doesn't read any data */
2829
2830         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2831
2832         ATF_CHECK(bpf_validate(insns, insn_count));
2833
2834         code = bpfjit_generate_code(NULL, insns, insn_count);
2835         ATF_REQUIRE(code != NULL);
2836
2837         for (i = 1; i <= sizeof(pkt); i++)
2838                 ATF_CHECK(jitcall(code, pkt, i, sizeof(pkt)) == 3 * i);
2839
2840         bpfjit_free_code(code);
2841 }
2842
2843 ATF_TC(libbpfjit_stx4);
2844 ATF_TC_HEAD(libbpfjit_stx4, tc)
2845 {
2846         atf_tc_set_md_var(tc, "descr",
2847             "Test JIT compilation of BPF_STX");
2848 }
2849
2850 ATF_TC_BODY(libbpfjit_stx4, tc)
2851 {
2852         struct bpf_insn insns[5*BPF_MEMWORDS+2];
2853         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2854
2855         size_t k;
2856         bpfjit_func_t code;
2857         uint8_t pkt[BPF_MEMWORDS]; /* the program doesn't read any data */
2858
2859         memset(insns, 0, sizeof(insns));
2860
2861         /* for each k do M[k] = k */
2862         for (k = 0; k < BPF_MEMWORDS; k++) {
2863                 insns[2*k].code   = BPF_LDX+BPF_W+BPF_IMM;
2864                 insns[2*k].k      = 3*k;
2865                 insns[2*k+1].code = BPF_STX;
2866                 insns[2*k+1].k    = k;
2867         }
2868
2869         /* load wirelen into A */
2870         insns[2*BPF_MEMWORDS].code = BPF_LD+BPF_W+BPF_LEN;
2871
2872         /* for each k, if (A == k + 1) return M[k] */
2873         for (k = 0; k < BPF_MEMWORDS; k++) {
2874                 insns[2*BPF_MEMWORDS+3*k+1].code = BPF_JMP+BPF_JEQ+BPF_K;
2875                 insns[2*BPF_MEMWORDS+3*k+1].k    = k+1;
2876                 insns[2*BPF_MEMWORDS+3*k+1].jt   = 0;
2877                 insns[2*BPF_MEMWORDS+3*k+1].jf   = 2;
2878                 insns[2*BPF_MEMWORDS+3*k+2].code = BPF_LD+BPF_MEM;
2879                 insns[2*BPF_MEMWORDS+3*k+2].k    = k;
2880                 insns[2*BPF_MEMWORDS+3*k+3].code = BPF_RET+BPF_A;
2881                 insns[2*BPF_MEMWORDS+3*k+3].k    = 0;
2882         }
2883
2884         insns[5*BPF_MEMWORDS+1].code = BPF_RET+BPF_K;
2885         insns[5*BPF_MEMWORDS+1].k    = UINT32_MAX;
2886
2887         ATF_CHECK(bpf_validate(insns, insn_count));
2888
2889         code = bpfjit_generate_code(NULL, insns, insn_count);
2890         ATF_REQUIRE(code != NULL);
2891
2892         for (k = 1; k <= sizeof(pkt); k++)
2893                 ATF_CHECK(jitcall(code, pkt, k, k) == 3*(k-1));
2894
2895         bpfjit_free_code(code);
2896 }
2897
2898 ATF_TC(libbpfjit_opt_ld_abs_1);
2899 ATF_TC_HEAD(libbpfjit_opt_ld_abs_1, tc)
2900 {
2901         atf_tc_set_md_var(tc, "descr",
2902             "Test JIT compilation with length optimization "
2903             "applied to BPF_LD+BPF_ABS");
2904 }
2905
2906 ATF_TC_BODY(libbpfjit_opt_ld_abs_1, tc)
2907 {
2908         static struct bpf_insn insns[] = {
2909                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
2910                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 8),
2911                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 26),
2912                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 2),
2913                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
2914                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 3, 4),
2915                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 3),
2916                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
2917                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 1),
2918                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
2919                 BPF_STMT(BPF_RET+BPF_K, 0),
2920         };
2921
2922         size_t i, j;
2923         bpfjit_func_t code;
2924         uint8_t pkt[2][34] = {
2925                 {
2926                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
2927                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
2928                         0x80, 0x03, 0x70, 0x0f,
2929                         0x80, 0x03, 0x70, 0x23
2930                 },
2931                 {
2932                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
2933                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
2934                         0x80, 0x03, 0x70, 0x23,
2935                         0x80, 0x03, 0x70, 0x0f
2936                 }
2937         };
2938
2939         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2940
2941         ATF_CHECK(bpf_validate(insns, insn_count));
2942
2943         code = bpfjit_generate_code(NULL, insns, insn_count);
2944         ATF_REQUIRE(code != NULL);
2945
2946         for (i = 0; i < 2; i++) {
2947                 for (j = 1; j < sizeof(pkt[i]); j++)
2948                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
2949                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
2950         }
2951
2952         bpfjit_free_code(code);
2953 }
2954
2955 ATF_TC(libbpfjit_opt_ld_abs_2);
2956 ATF_TC_HEAD(libbpfjit_opt_ld_abs_2, tc)
2957 {
2958         atf_tc_set_md_var(tc, "descr",
2959             "Test JIT compilation with length optimization "
2960             "applied to BPF_LD+BPF_ABS");
2961 }
2962
2963 ATF_TC_BODY(libbpfjit_opt_ld_abs_2, tc)
2964 {
2965         static struct bpf_insn insns[] = {
2966                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 26),
2967                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 2),
2968                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
2969                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 3, 6),
2970                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 5),
2971                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
2972                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 3),
2973                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
2974                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 1),
2975                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
2976                 BPF_STMT(BPF_RET+BPF_K, 0),
2977         };
2978
2979         size_t i, j;
2980         bpfjit_func_t code;
2981         uint8_t pkt[2][34] = {
2982                 {
2983                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
2984                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
2985                         0x80, 0x03, 0x70, 0x0f,
2986                         0x80, 0x03, 0x70, 0x23
2987                 },
2988                 {
2989                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
2990                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
2991                         0x80, 0x03, 0x70, 0x23,
2992                         0x80, 0x03, 0x70, 0x0f
2993                 }
2994         };
2995
2996         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
2997
2998         ATF_CHECK(bpf_validate(insns, insn_count));
2999
3000         code = bpfjit_generate_code(NULL, insns, insn_count);
3001         ATF_REQUIRE(code != NULL);
3002
3003         for (i = 0; i < 2; i++) {
3004                 for (j = 1; j < sizeof(pkt[i]); j++)
3005                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3006                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3007         }
3008
3009         bpfjit_free_code(code);
3010 }
3011
3012 ATF_TC(libbpfjit_opt_ld_abs_3);
3013 ATF_TC_HEAD(libbpfjit_opt_ld_abs_3, tc)
3014 {
3015         atf_tc_set_md_var(tc, "descr",
3016             "Test JIT compilation with length optimization "
3017             "applied to BPF_LD+BPF_ABS");
3018 }
3019
3020 ATF_TC_BODY(libbpfjit_opt_ld_abs_3, tc)
3021 {
3022         static struct bpf_insn insns[] = {
3023                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
3024                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 2),
3025                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 26),
3026                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 3, 6),
3027                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 5),
3028                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 26),
3029                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 3),
3030                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
3031                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 1),
3032                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3033                 BPF_STMT(BPF_RET+BPF_K, 0),
3034         };
3035
3036         size_t i, j;
3037         bpfjit_func_t code;
3038         uint8_t pkt[2][34] = {
3039                 {
3040                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3041                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3042                         0x80, 0x03, 0x70, 0x0f,
3043                         0x80, 0x03, 0x70, 0x23
3044                 },
3045                 {
3046                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3047                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3048                         0x80, 0x03, 0x70, 0x23,
3049                         0x80, 0x03, 0x70, 0x0f
3050                 }
3051         };
3052
3053         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3054
3055         ATF_CHECK(bpf_validate(insns, insn_count));
3056
3057         code = bpfjit_generate_code(NULL, insns, insn_count);
3058         ATF_REQUIRE(code != NULL);
3059
3060         for (i = 0; i < 2; i++) {
3061                 for (j = 1; j < sizeof(pkt[i]); j++)
3062                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3063                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3064         }
3065
3066         bpfjit_free_code(code);
3067 }
3068
3069 ATF_TC(libbpfjit_opt_ld_ind_1);
3070 ATF_TC_HEAD(libbpfjit_opt_ld_ind_1, tc)
3071 {
3072         atf_tc_set_md_var(tc, "descr",
3073             "Test JIT compilation with length optimization "
3074             "applied to BPF_LD+BPF_IND");
3075 }
3076
3077 ATF_TC_BODY(libbpfjit_opt_ld_ind_1, tc)
3078 {
3079         static struct bpf_insn insns[] = {
3080                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 12),
3081                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 0),
3082                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 8),
3083                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 14),
3084                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 2),
3085                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 18),
3086                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 3, 4),
3087                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 3),
3088                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 18),
3089                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 1),
3090                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3091                 BPF_STMT(BPF_RET+BPF_K, 0),
3092         };
3093
3094         size_t i, j;
3095         bpfjit_func_t code;
3096         uint8_t pkt[2][34] = {
3097                 {
3098                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3099                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3100                         0x80, 0x03, 0x70, 0x0f,
3101                         0x80, 0x03, 0x70, 0x23
3102                 },
3103                 {
3104                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3105                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3106                         0x80, 0x03, 0x70, 0x23,
3107                         0x80, 0x03, 0x70, 0x0f
3108                 }
3109         };
3110
3111         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3112
3113         ATF_CHECK(bpf_validate(insns, insn_count));
3114
3115         code = bpfjit_generate_code(NULL, insns, insn_count);
3116         ATF_REQUIRE(code != NULL);
3117
3118         for (i = 0; i < 2; i++) {
3119                 for (j = 1; j < sizeof(pkt[i]); j++)
3120                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3121                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3122         }
3123
3124         bpfjit_free_code(code);
3125 }
3126
3127 ATF_TC(libbpfjit_opt_ld_ind_2);
3128 ATF_TC_HEAD(libbpfjit_opt_ld_ind_2, tc)
3129 {
3130         atf_tc_set_md_var(tc, "descr",
3131             "Test JIT compilation with length optimization "
3132             "applied to BPF_LD+BPF_IND");
3133 }
3134
3135 ATF_TC_BODY(libbpfjit_opt_ld_ind_2, tc)
3136 {
3137         static struct bpf_insn insns[] = {
3138                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
3139                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 26),
3140                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 2),
3141                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 30),
3142                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 3, 6),
3143                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 5),
3144                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 30),
3145                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 3),
3146                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 12),
3147                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 1),
3148                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3149                 BPF_STMT(BPF_RET+BPF_K, 0),
3150         };
3151
3152         size_t i, j;
3153         bpfjit_func_t code;
3154         uint8_t pkt[2][34] = {
3155                 {
3156                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3157                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3158                         0x80, 0x03, 0x70, 0x0f,
3159                         0x80, 0x03, 0x70, 0x23
3160                 },
3161                 {
3162                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3163                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3164                         0x80, 0x03, 0x70, 0x23,
3165                         0x80, 0x03, 0x70, 0x0f
3166                 }
3167         };
3168
3169         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3170
3171         ATF_CHECK(bpf_validate(insns, insn_count));
3172
3173         code = bpfjit_generate_code(NULL, insns, insn_count);
3174         ATF_REQUIRE(code != NULL);
3175
3176         for (i = 0; i < 2; i++) {
3177                 for (j = 1; j < sizeof(pkt[i]); j++)
3178                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3179                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3180         }
3181
3182         bpfjit_free_code(code);
3183 }
3184
3185 ATF_TC(libbpfjit_opt_ld_ind_3);
3186 ATF_TC_HEAD(libbpfjit_opt_ld_ind_3, tc)
3187 {
3188         atf_tc_set_md_var(tc, "descr",
3189             "Test JIT compilation with length optimization "
3190             "applied to BPF_LD+BPF_IND");
3191 }
3192
3193 ATF_TC_BODY(libbpfjit_opt_ld_ind_3, tc)
3194 {
3195         static struct bpf_insn insns[] = {
3196                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 15),
3197                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 15),
3198                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 2),
3199                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 11),
3200                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 3, 7),
3201                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 6),
3202                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 11),
3203                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 4),
3204                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
3205                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 12),
3206                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 1),
3207                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3208                 BPF_STMT(BPF_RET+BPF_K, 0),
3209         };
3210
3211         size_t i, j;
3212         bpfjit_func_t code;
3213         uint8_t pkt[2][34] = {
3214                 {
3215                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3216                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3217                         0x80, 0x03, 0x70, 0x0f,
3218                         0x80, 0x03, 0x70, 0x23
3219                 },
3220                 {
3221                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3222                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3223                         0x80, 0x03, 0x70, 0x23,
3224                         0x80, 0x03, 0x70, 0x0f
3225                 }
3226         };
3227
3228         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3229
3230         ATF_CHECK(bpf_validate(insns, insn_count));
3231
3232         code = bpfjit_generate_code(NULL, insns, insn_count);
3233         ATF_REQUIRE(code != NULL);
3234
3235         for (i = 0; i < 2; i++) {
3236                 for (j = 1; j < sizeof(pkt[i]); j++)
3237                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3238                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3239         }
3240
3241         bpfjit_free_code(code);
3242 }
3243
3244 ATF_TC(libbpfjit_opt_ld_ind_4);
3245 ATF_TC_HEAD(libbpfjit_opt_ld_ind_4, tc)
3246 {
3247         atf_tc_set_md_var(tc, "descr",
3248             "Test JIT compilation with length optimization "
3249             "applied to BPF_LD+BPF_IND");
3250 }
3251
3252 ATF_TC_BODY(libbpfjit_opt_ld_ind_4, tc)
3253 {
3254         static struct bpf_insn insns[] = {
3255                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 11),
3256                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 19),
3257                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 2),
3258                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 15),
3259                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 3, 7),
3260                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 6),
3261                 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 15),
3262                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 4),
3263                 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0),
3264                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 12),
3265                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x800, 0, 1),
3266                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3267                 BPF_STMT(BPF_RET+BPF_K, 0),
3268         };
3269
3270         size_t i, j;
3271         bpfjit_func_t code;
3272         uint8_t pkt[2][34] = {
3273                 {
3274                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3275                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3276                         0x80, 0x03, 0x70, 0x0f,
3277                         0x80, 0x03, 0x70, 0x23
3278                 },
3279                 {
3280                         0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0x08, 0x00,
3281                         14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
3282                         0x80, 0x03, 0x70, 0x23,
3283                         0x80, 0x03, 0x70, 0x0f
3284                 }
3285         };
3286
3287         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3288
3289         ATF_CHECK(bpf_validate(insns, insn_count));
3290
3291         code = bpfjit_generate_code(NULL, insns, insn_count);
3292         ATF_REQUIRE(code != NULL);
3293
3294         for (i = 0; i < 2; i++) {
3295                 for (j = 1; j < sizeof(pkt[i]); j++)
3296                         ATF_CHECK(jitcall(code, pkt[i], j, j) == 0);
3297                 ATF_CHECK(jitcall(code, pkt[i], j, j) == UINT32_MAX);
3298         }
3299
3300         bpfjit_free_code(code);
3301 }
3302
3303 ATF_TC(libbpfjit_abc_ja);
3304 ATF_TC_HEAD(libbpfjit_abc_ja, tc)
3305 {
3306         atf_tc_set_md_var(tc, "descr",
3307             "Test ABC optimization with a single BPF_JMP+BPF_JA");
3308 }
3309
3310 ATF_TC_BODY(libbpfjit_abc_ja, tc)
3311 {
3312         static struct bpf_insn insns[] = {
3313                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 3), /* min. length 4 */
3314                 BPF_STMT(BPF_JMP+BPF_JA, 2),
3315                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, UINT32_MAX - 1),
3316                 BPF_STMT(BPF_RET+BPF_K, 0),
3317                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 2), /* min. length 6 */
3318                 BPF_STMT(BPF_RET+BPF_A, 0),
3319                 BPF_STMT(BPF_RET+BPF_K, 1),
3320                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 6),
3321                 BPF_STMT(BPF_RET+BPF_K, 2),
3322                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 7),
3323                 BPF_STMT(BPF_RET+BPF_K, 3),
3324         };
3325
3326         bpfjit_func_t code;
3327         uint8_t pkt[6] = {0, 0, /* UINT32_MAX: */ 255, 255, 255, 255};
3328
3329         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3330
3331         ATF_CHECK(bpf_validate(insns, insn_count));
3332
3333         code = bpfjit_generate_code(NULL, insns, insn_count);
3334         ATF_REQUIRE(code != NULL);
3335
3336         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3337         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3338         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3339         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3340         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3341         ATF_CHECK(jitcall(code, pkt, 6, 6) == UINT32_MAX);
3342
3343         bpfjit_free_code(code);
3344 }
3345
3346 ATF_TC(libbpfjit_abc_ja_over);
3347 ATF_TC_HEAD(libbpfjit_abc_ja_over, tc)
3348 {
3349         atf_tc_set_md_var(tc, "descr",
3350             "Test ABC optimization when BPF_JMP+BPF_JA jumps over all loads");
3351 }
3352
3353 ATF_TC_BODY(libbpfjit_abc_ja_over, tc)
3354 {
3355         static struct bpf_insn insns[] = {
3356                 BPF_STMT(BPF_JMP+BPF_JA, 2),
3357                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 3),
3358                 BPF_STMT(BPF_RET+BPF_K, 0),
3359                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3360                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 4),
3361                 BPF_STMT(BPF_RET+BPF_K, 1),
3362                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 5),
3363                 BPF_STMT(BPF_RET+BPF_K, 2),
3364                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 6),
3365                 BPF_STMT(BPF_RET+BPF_K, 3),
3366         };
3367
3368         bpfjit_func_t code;
3369         uint8_t pkt[1]; /* the program doesn't read any data */
3370
3371         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3372
3373         ATF_CHECK(bpf_validate(insns, insn_count));
3374
3375         code = bpfjit_generate_code(NULL, insns, insn_count);
3376         ATF_REQUIRE(code != NULL);
3377
3378         ATF_CHECK(jitcall(code, pkt, 1, 1) == UINT32_MAX);
3379
3380         bpfjit_free_code(code);
3381 }
3382
3383 ATF_TC(libbpfjit_abc_ld_chain);
3384 ATF_TC_HEAD(libbpfjit_abc_ld_chain, tc)
3385 {
3386         atf_tc_set_md_var(tc, "descr",
3387             "Test ABC optimization of a chain of BPF_LD instructions "
3388             "with exits leading to a single BPF_RET");
3389 }
3390
3391 ATF_TC_BODY(libbpfjit_abc_ld_chain, tc)
3392 {
3393         static struct bpf_insn insns[] = {
3394                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 3), /* min. length 4 */
3395                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 8, 0, 4),
3396                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 4), /* min. length 6 */
3397                 BPF_JUMP(BPF_JMP+BPF_JGE+BPF_K, 7, 0, 2),
3398                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 6), /* min. length 10 */
3399                 BPF_JUMP(BPF_JMP+BPF_JGT+BPF_K, 6, 0, 1),
3400                 BPF_STMT(BPF_RET+BPF_K, 123456789),
3401                 BPF_STMT(BPF_RET+BPF_K, 987654321),
3402         };
3403
3404         bpfjit_func_t code;
3405         uint8_t pkt[10] = {};
3406
3407         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3408
3409         ATF_CHECK(bpf_validate(insns, insn_count));
3410
3411         code = bpfjit_generate_code(NULL, insns, insn_count);
3412         ATF_REQUIRE(code != NULL);
3413
3414         /* Packet is too short. */
3415         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3416         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3417         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3418
3419         /* !(pkt[3] == 8) => return 123456789 */
3420         ATF_CHECK(jitcall(code, pkt, 4, 4) == 123456789);
3421         ATF_CHECK(jitcall(code, pkt, 5, 5) == 123456789);
3422         ATF_CHECK(jitcall(code, pkt, 6, 6) == 123456789);
3423         ATF_CHECK(jitcall(code, pkt, 7, 7) == 123456789);
3424         ATF_CHECK(jitcall(code, pkt, 8, 8) == 123456789);
3425         ATF_CHECK(jitcall(code, pkt, 9, 9) == 123456789);
3426
3427         /* !(pkt[4:2] >= 7) => too short or return 123456789 */
3428         pkt[3] = 8;
3429         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3430         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3431         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3432         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3433         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3434         ATF_CHECK(jitcall(code, pkt, 6, 6) == 123456789);
3435         ATF_CHECK(jitcall(code, pkt, 9, 9) == 123456789);
3436
3437         /* !(pkt[6:4] > 6) => too short or return 987654321 */
3438         pkt[4] = pkt[5] = 1;
3439         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3440         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3441         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3442         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3443         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3444         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3445         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3446         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3447         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3448         ATF_CHECK(jitcall(code, pkt, 10, 10) == 987654321);
3449
3450         /* (pkt[6:4] > 6) => too short or return 123456789 */
3451         pkt[6] = pkt[7] = pkt[8] = pkt[9] = 1;
3452         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3453         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3454         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3455         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3456         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3457         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3458         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3459         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3460         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3461         ATF_CHECK(jitcall(code, pkt, 10, 10) == 123456789);
3462
3463         bpfjit_free_code(code);
3464 }
3465
3466 ATF_TC(libbpfjit_examples_1);
3467 ATF_TC_HEAD(libbpfjit_examples_1, tc)
3468 {
3469         atf_tc_set_md_var(tc, "descr",
3470             "Test the first example from bpf(4) - "
3471             "accept Reverse ARP requests");
3472 }
3473
3474 ATF_TC_BODY(libbpfjit_examples_1, tc)
3475 {
3476         /*
3477          * The following filter is taken from the Reverse ARP
3478          * Daemon. It accepts only Reverse ARP requests.
3479          */
3480         struct bpf_insn insns[] = {
3481                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
3482                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8035, 0, 3),
3483                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 20),
3484                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 3, 0, 1),
3485                 BPF_STMT(BPF_RET+BPF_K, 42),
3486                 BPF_STMT(BPF_RET+BPF_K, 0),
3487         };
3488
3489         bpfjit_func_t code;
3490         uint8_t pkt[22] = {};
3491
3492         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3493
3494         ATF_CHECK(bpf_validate(insns, insn_count));
3495
3496         code = bpfjit_generate_code(NULL, insns, insn_count);
3497         ATF_REQUIRE(code != NULL);
3498
3499         /* Packet is too short. */
3500         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3501         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3502         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3503         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3504         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3505         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3506         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3507         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3508         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3509         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3510         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3511         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3512         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3513         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3514         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3515         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3516         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3517         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3518         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3519         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3520         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3521
3522         /* The packet doesn't match. */
3523         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3524
3525         /* Still no match after setting the protocol field. */
3526         pkt[12] = 0x80; pkt[13] = 0x35;
3527         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3528
3529         /* Set RARP message type. */
3530         pkt[21] = 3;
3531         ATF_CHECK(jitcall(code, pkt, 22, 22) == 42);
3532
3533         /* Packet is too short. */
3534         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3535         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3536         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3537         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3538         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3539         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3540         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3541         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3542         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3543         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3544         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3545         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3546         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3547         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3548         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3549         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3550         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3551         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3552         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3553         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3554         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3555
3556         /* Change RARP message type. */
3557         pkt[20] = 3;
3558         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3559
3560         bpfjit_free_code(code);
3561 }
3562
3563 ATF_TC(libbpfjit_examples_2);
3564 ATF_TC_HEAD(libbpfjit_examples_2, tc)
3565 {
3566         atf_tc_set_md_var(tc, "descr",
3567             "Test the second example from bpf(4) - "
3568             "accept IP packets between two specified hosts");
3569 }
3570
3571 ATF_TC_BODY(libbpfjit_examples_2, tc)
3572 {
3573         /*
3574          * This filter accepts only IP packets between host 128.3.112.15
3575          * and 128.3.112.35.
3576          */
3577         static struct bpf_insn insns[] = {
3578                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
3579                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x0800, 0, 8),
3580                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 26),
3581                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 2),
3582                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
3583                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 3, 4),
3584                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x80037023, 0, 3),
3585                 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 30),
3586                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x8003700f, 0, 1),
3587                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3588                 BPF_STMT(BPF_RET+BPF_K, 0),
3589         };
3590
3591         bpfjit_func_t code;
3592         uint8_t pkt[34] = {};
3593
3594         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3595
3596         ATF_CHECK(bpf_validate(insns, insn_count));
3597
3598         code = bpfjit_generate_code(NULL, insns, insn_count);
3599         ATF_REQUIRE(code != NULL);
3600
3601         /* Packet is too short. */
3602         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3603         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3604         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3605         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3606         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3607         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3608         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3609         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3610         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3611         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3612         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3613         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3614         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3615         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3616         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3617         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3618         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3619         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3620         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3621         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3622         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3623         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3624         ATF_CHECK(jitcall(code, pkt, 23, 23) == 0);
3625         ATF_CHECK(jitcall(code, pkt, 24, 24) == 0);
3626         ATF_CHECK(jitcall(code, pkt, 25, 25) == 0);
3627         ATF_CHECK(jitcall(code, pkt, 26, 26) == 0);
3628         ATF_CHECK(jitcall(code, pkt, 27, 27) == 0);
3629         ATF_CHECK(jitcall(code, pkt, 28, 28) == 0);
3630         ATF_CHECK(jitcall(code, pkt, 29, 29) == 0);
3631         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3632         ATF_CHECK(jitcall(code, pkt, 31, 31) == 0);
3633         ATF_CHECK(jitcall(code, pkt, 32, 32) == 0);
3634         ATF_CHECK(jitcall(code, pkt, 33, 33) == 0);
3635
3636         /* The packet doesn't match. */
3637         ATF_CHECK(jitcall(code, pkt, 34, 34) == 0);
3638
3639         /* Still no match after setting the protocol field. */
3640         pkt[12] = 8;
3641         ATF_CHECK(jitcall(code, pkt, 34, 34) == 0);
3642
3643         pkt[26] = 128; pkt[27] = 3; pkt[28] = 112; pkt[29] = 15;
3644         ATF_CHECK(jitcall(code, pkt, 34, 34) == 0);
3645
3646         pkt[30] = 128; pkt[31] = 3; pkt[32] = 112; pkt[33] = 35;
3647         ATF_CHECK(jitcall(code, pkt, 34, 34) == UINT32_MAX);
3648
3649         /* Swap the ip addresses. */
3650         pkt[26] = 128; pkt[27] = 3; pkt[28] = 112; pkt[29] = 35;
3651         ATF_CHECK(jitcall(code, pkt, 34, 34) == 0);
3652
3653         pkt[30] = 128; pkt[31] = 3; pkt[32] = 112; pkt[33] = 15;
3654         ATF_CHECK(jitcall(code, pkt, 34, 34) == UINT32_MAX);
3655
3656         /* Packet is too short. */
3657         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3658         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3659         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3660         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3661         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3662         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3663         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3664         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3665         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3666         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3667         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3668         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3669         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3670         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3671         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3672         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3673         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3674         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3675         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3676         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3677         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3678         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3679         ATF_CHECK(jitcall(code, pkt, 23, 23) == 0);
3680         ATF_CHECK(jitcall(code, pkt, 24, 24) == 0);
3681         ATF_CHECK(jitcall(code, pkt, 25, 25) == 0);
3682         ATF_CHECK(jitcall(code, pkt, 26, 26) == 0);
3683         ATF_CHECK(jitcall(code, pkt, 27, 27) == 0);
3684         ATF_CHECK(jitcall(code, pkt, 28, 28) == 0);
3685         ATF_CHECK(jitcall(code, pkt, 29, 29) == 0);
3686         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3687         ATF_CHECK(jitcall(code, pkt, 31, 31) == 0);
3688         ATF_CHECK(jitcall(code, pkt, 32, 32) == 0);
3689         ATF_CHECK(jitcall(code, pkt, 33, 33) == 0);
3690
3691         /* Change the protocol field. */
3692         pkt[13] = 8;
3693         ATF_CHECK(jitcall(code, pkt, 34, 34) == 0);
3694
3695         bpfjit_free_code(code);
3696 }
3697
3698 ATF_TC(libbpfjit_examples_3);
3699 ATF_TC_HEAD(libbpfjit_examples_3, tc)
3700 {
3701         atf_tc_set_md_var(tc, "descr",
3702             "Test the third example from bpf(4) - "
3703             "accept TCP finger packets");
3704 }
3705
3706 ATF_TC_BODY(libbpfjit_examples_3, tc)
3707 {
3708         /*
3709          * This filter returns only TCP finger packets.
3710          */
3711         struct bpf_insn insns[] = {
3712                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 12),
3713                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 0x0800, 0, 10),
3714                 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 23),
3715                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 6, 0, 8),
3716                 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 20),
3717                 BPF_JUMP(BPF_JMP+BPF_JSET+BPF_K, 0x1fff, 6, 0),
3718                 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 14),
3719                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 14),
3720                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 79, 2, 0),
3721                 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 16),
3722                 BPF_JUMP(BPF_JMP+BPF_JEQ+BPF_K, 79, 0, 1),
3723                 BPF_STMT(BPF_RET+BPF_K, UINT32_MAX),
3724                 BPF_STMT(BPF_RET+BPF_K, 0),
3725         };
3726
3727         bpfjit_func_t code;
3728         uint8_t pkt[30] = {};
3729
3730         /* Set IP fragment offset to non-zero. */
3731         pkt[20] = 1; pkt[21] = 1;
3732
3733         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3734
3735         ATF_CHECK(bpf_validate(insns, insn_count));
3736
3737         code = bpfjit_generate_code(NULL, insns, insn_count);
3738         ATF_REQUIRE(code != NULL);
3739
3740         /* Packet is too short. */
3741         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3742         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3743         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3744         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3745         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3746         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3747         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3748         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3749         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3750         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3751         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3752         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3753         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3754         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3755         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3756         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3757         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3758         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3759         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3760         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3761         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3762         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3763         ATF_CHECK(jitcall(code, pkt, 23, 23) == 0);
3764         ATF_CHECK(jitcall(code, pkt, 24, 24) == 0);
3765         ATF_CHECK(jitcall(code, pkt, 25, 25) == 0);
3766         ATF_CHECK(jitcall(code, pkt, 26, 26) == 0);
3767         ATF_CHECK(jitcall(code, pkt, 27, 27) == 0);
3768         ATF_CHECK(jitcall(code, pkt, 28, 28) == 0);
3769         ATF_CHECK(jitcall(code, pkt, 29, 29) == 0);
3770
3771         /* The packet doesn't match. */
3772         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3773
3774         /* Still no match after setting the protocol field. */
3775         pkt[12] = 8;
3776         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3777
3778         /* Get one step closer to the match. */
3779         pkt[23] = 6;
3780         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3781
3782         /* Set IP fragment offset to zero. */
3783         pkt[20] = 0x20; pkt[21] = 0;
3784         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3785
3786         /* Set IP header length to 12. */
3787         pkt[14] = 0xd3;
3788         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3789
3790         /* Match one branch of the program. */
3791         pkt[27] = 79;
3792         ATF_CHECK(jitcall(code, pkt, 30, 30) == UINT32_MAX);
3793
3794         /* Match the other branch of the program. */
3795         pkt[29] = 79; pkt[27] = 0;
3796         ATF_CHECK(jitcall(code, pkt, 30, 30) == UINT32_MAX);
3797
3798         /* Packet is too short. */
3799         ATF_CHECK(jitcall(code, pkt, 1, 1) == 0);
3800         ATF_CHECK(jitcall(code, pkt, 2, 2) == 0);
3801         ATF_CHECK(jitcall(code, pkt, 3, 3) == 0);
3802         ATF_CHECK(jitcall(code, pkt, 4, 4) == 0);
3803         ATF_CHECK(jitcall(code, pkt, 5, 5) == 0);
3804         ATF_CHECK(jitcall(code, pkt, 6, 6) == 0);
3805         ATF_CHECK(jitcall(code, pkt, 7, 7) == 0);
3806         ATF_CHECK(jitcall(code, pkt, 8, 8) == 0);
3807         ATF_CHECK(jitcall(code, pkt, 9, 9) == 0);
3808         ATF_CHECK(jitcall(code, pkt, 10, 10) == 0);
3809         ATF_CHECK(jitcall(code, pkt, 11, 11) == 0);
3810         ATF_CHECK(jitcall(code, pkt, 12, 12) == 0);
3811         ATF_CHECK(jitcall(code, pkt, 13, 13) == 0);
3812         ATF_CHECK(jitcall(code, pkt, 14, 14) == 0);
3813         ATF_CHECK(jitcall(code, pkt, 15, 15) == 0);
3814         ATF_CHECK(jitcall(code, pkt, 16, 16) == 0);
3815         ATF_CHECK(jitcall(code, pkt, 17, 17) == 0);
3816         ATF_CHECK(jitcall(code, pkt, 18, 18) == 0);
3817         ATF_CHECK(jitcall(code, pkt, 19, 19) == 0);
3818         ATF_CHECK(jitcall(code, pkt, 20, 20) == 0);
3819         ATF_CHECK(jitcall(code, pkt, 21, 21) == 0);
3820         ATF_CHECK(jitcall(code, pkt, 22, 22) == 0);
3821         ATF_CHECK(jitcall(code, pkt, 23, 23) == 0);
3822         ATF_CHECK(jitcall(code, pkt, 24, 24) == 0);
3823         ATF_CHECK(jitcall(code, pkt, 25, 25) == 0);
3824         ATF_CHECK(jitcall(code, pkt, 26, 26) == 0);
3825         ATF_CHECK(jitcall(code, pkt, 27, 27) == 0);
3826         ATF_CHECK(jitcall(code, pkt, 28, 28) == 0);
3827         ATF_CHECK(jitcall(code, pkt, 29, 29) == 0);
3828
3829         /* Set IP header length to 16. Packet is too short. */
3830         pkt[14] = 4;
3831         ATF_CHECK(jitcall(code, pkt, 30, 30) == 0);
3832
3833         bpfjit_free_code(code);
3834 }
3835
3836 ATF_TC(libbpfjit_cop_no_ctx);
3837 ATF_TC_HEAD(libbpfjit_cop_no_ctx, tc)
3838 {
3839         atf_tc_set_md_var(tc, "descr", "Test that BPF_MISC|BPF_COP "
3840             "instruction can't be accepted without a context");
3841 }
3842
3843 ATF_TC_BODY(libbpfjit_cop_no_ctx, tc)
3844 {
3845         static struct bpf_insn insns[] = {
3846                 BPF_STMT(BPF_MISC+BPF_COP, 0),
3847                 BPF_STMT(BPF_RET+BPF_K, 7)
3848         };
3849
3850         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3851
3852         ATF_CHECK(!bpf_validate(insns, insn_count));
3853
3854         ATF_CHECK(bpfjit_generate_code(NULL, insns, insn_count) == NULL);
3855 }
3856
3857 ATF_TC(libbpfjit_copx_no_ctx);
3858 ATF_TC_HEAD(libbpfjit_copx_no_ctx, tc)
3859 {
3860         atf_tc_set_md_var(tc, "descr", "Test that BPF_MISC|BPF_COPX "
3861             "instruction can't be accepted without a context");
3862 }
3863
3864 ATF_TC_BODY(libbpfjit_copx_no_ctx, tc)
3865 {
3866         static struct bpf_insn insns[] = {
3867                 BPF_STMT(BPF_MISC+BPF_COPX, 0),
3868                 BPF_STMT(BPF_RET+BPF_K, 7)
3869         };
3870
3871         size_t insn_count = sizeof(insns) / sizeof(insns[0]);
3872
3873         ATF_CHECK(!bpf_validate(insns, insn_count));
3874
3875         ATF_CHECK(bpfjit_generate_code(NULL, insns, insn_count) == NULL);
3876 }
3877
3878 ATF_TP_ADD_TCS(tp)
3879 {
3880
3881         /*
3882          * For every new test please also add a similar test
3883          * to ../../net/bpfjit/t_bpfjit.c
3884          */
3885         ATF_TP_ADD_TC(tp, libbpfjit_empty);
3886         ATF_TP_ADD_TC(tp, libbpfjit_alu_add_k);
3887         ATF_TP_ADD_TC(tp, libbpfjit_alu_sub_k);
3888         ATF_TP_ADD_TC(tp, libbpfjit_alu_mul_k);
3889         ATF_TP_ADD_TC(tp, libbpfjit_alu_div0_k);
3890         ATF_TP_ADD_TC(tp, libbpfjit_alu_div1_k);
3891         ATF_TP_ADD_TC(tp, libbpfjit_alu_div2_k);
3892         ATF_TP_ADD_TC(tp, libbpfjit_alu_div4_k);
3893         ATF_TP_ADD_TC(tp, libbpfjit_alu_div10_k);
3894         ATF_TP_ADD_TC(tp, libbpfjit_alu_div10000_k);
3895         ATF_TP_ADD_TC(tp, libbpfjit_alu_div7609801_k);
3896         ATF_TP_ADD_TC(tp, libbpfjit_alu_div80000000_k);
3897         ATF_TP_ADD_TC(tp, libbpfjit_alu_and_k);
3898         ATF_TP_ADD_TC(tp, libbpfjit_alu_or_k);
3899         ATF_TP_ADD_TC(tp, libbpfjit_alu_lsh_k);
3900         ATF_TP_ADD_TC(tp, libbpfjit_alu_lsh0_k);
3901         ATF_TP_ADD_TC(tp, libbpfjit_alu_rsh_k);
3902         ATF_TP_ADD_TC(tp, libbpfjit_alu_rsh0_k);
3903         ATF_TP_ADD_TC(tp, libbpfjit_alu_modulo_k);
3904         ATF_TP_ADD_TC(tp, libbpfjit_alu_add_x);
3905         ATF_TP_ADD_TC(tp, libbpfjit_alu_sub_x);
3906         ATF_TP_ADD_TC(tp, libbpfjit_alu_mul_x);
3907         ATF_TP_ADD_TC(tp, libbpfjit_alu_div0_x);
3908         ATF_TP_ADD_TC(tp, libbpfjit_alu_div1_x);
3909         ATF_TP_ADD_TC(tp, libbpfjit_alu_div2_x);
3910         ATF_TP_ADD_TC(tp, libbpfjit_alu_div4_x);
3911         ATF_TP_ADD_TC(tp, libbpfjit_alu_div10_x);
3912         ATF_TP_ADD_TC(tp, libbpfjit_alu_div10000_x);
3913         ATF_TP_ADD_TC(tp, libbpfjit_alu_div7609801_x);
3914         ATF_TP_ADD_TC(tp, libbpfjit_alu_div80000000_x);
3915         ATF_TP_ADD_TC(tp, libbpfjit_alu_and_x);
3916         ATF_TP_ADD_TC(tp, libbpfjit_alu_or_x);
3917         ATF_TP_ADD_TC(tp, libbpfjit_alu_lsh_x);
3918         ATF_TP_ADD_TC(tp, libbpfjit_alu_lsh0_x);
3919         ATF_TP_ADD_TC(tp, libbpfjit_alu_rsh_x);
3920         ATF_TP_ADD_TC(tp, libbpfjit_alu_rsh0_x);
3921         ATF_TP_ADD_TC(tp, libbpfjit_alu_modulo_x);
3922         ATF_TP_ADD_TC(tp, libbpfjit_alu_neg);
3923         ATF_TP_ADD_TC(tp, libbpfjit_jmp_ja);
3924         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jgt_k);
3925         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jge_k);
3926         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jeq_k);
3927         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jset_k);
3928         ATF_TP_ADD_TC(tp, libbpfjit_jmp_modulo_k);
3929         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jgt_x);
3930         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jge_x);
3931         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jeq_x);
3932         ATF_TP_ADD_TC(tp, libbpfjit_jmp_jset_x);
3933         ATF_TP_ADD_TC(tp, libbpfjit_jmp_modulo_x);
3934         ATF_TP_ADD_TC(tp, libbpfjit_ld_abs);
3935         ATF_TP_ADD_TC(tp, libbpfjit_ld_abs_k_overflow);
3936         ATF_TP_ADD_TC(tp, libbpfjit_ld_ind);
3937         ATF_TP_ADD_TC(tp, libbpfjit_ld_ind_k_overflow);
3938         ATF_TP_ADD_TC(tp, libbpfjit_ld_ind_x_overflow1);
3939         ATF_TP_ADD_TC(tp, libbpfjit_ld_ind_x_overflow2);
3940         ATF_TP_ADD_TC(tp, libbpfjit_ld_len);
3941         ATF_TP_ADD_TC(tp, libbpfjit_ld_imm);
3942         ATF_TP_ADD_TC(tp, libbpfjit_ldx_imm1);
3943         ATF_TP_ADD_TC(tp, libbpfjit_ldx_imm2);
3944         ATF_TP_ADD_TC(tp, libbpfjit_ldx_len1);
3945         ATF_TP_ADD_TC(tp, libbpfjit_ldx_len2);
3946         ATF_TP_ADD_TC(tp, libbpfjit_ldx_msh);
3947         ATF_TP_ADD_TC(tp, libbpfjit_misc_tax);
3948         ATF_TP_ADD_TC(tp, libbpfjit_misc_txa);
3949         ATF_TP_ADD_TC(tp, libbpfjit_st1);
3950         ATF_TP_ADD_TC(tp, libbpfjit_st2);
3951         ATF_TP_ADD_TC(tp, libbpfjit_st3);
3952         ATF_TP_ADD_TC(tp, libbpfjit_st4);
3953         ATF_TP_ADD_TC(tp, libbpfjit_st5);
3954         ATF_TP_ADD_TC(tp, libbpfjit_stx1);
3955         ATF_TP_ADD_TC(tp, libbpfjit_stx2);
3956         ATF_TP_ADD_TC(tp, libbpfjit_stx3);
3957         ATF_TP_ADD_TC(tp, libbpfjit_stx4);
3958         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_abs_1);
3959         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_abs_2);
3960         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_abs_3);
3961         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_ind_1);
3962         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_ind_2);
3963         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_ind_3);
3964         ATF_TP_ADD_TC(tp, libbpfjit_opt_ld_ind_4);
3965         ATF_TP_ADD_TC(tp, libbpfjit_abc_ja);
3966         ATF_TP_ADD_TC(tp, libbpfjit_abc_ja_over);
3967         ATF_TP_ADD_TC(tp, libbpfjit_abc_ld_chain);
3968         ATF_TP_ADD_TC(tp, libbpfjit_examples_1);
3969         ATF_TP_ADD_TC(tp, libbpfjit_examples_2);
3970         ATF_TP_ADD_TC(tp, libbpfjit_examples_3);
3971         ATF_TP_ADD_TC(tp, libbpfjit_cop_no_ctx);
3972         ATF_TP_ADD_TC(tp, libbpfjit_copx_no_ctx);
3973
3974         return atf_no_error();
3975 }