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