]> git.proxmox.com Git - mirror_ubuntu-bionic-kernel.git/blob - tools/testing/selftests/bpf/test_verifier.c
UBUNTU: SAUCE: Fix "bpf: relax verifier restriction on BPF_MOV | BPF_ALU"
[mirror_ubuntu-bionic-kernel.git] / tools / testing / selftests / bpf / test_verifier.c
1 /*
2 * Testsuite for eBPF verifier
3 *
4 * Copyright (c) 2014 PLUMgrid, http://plumgrid.com
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of version 2 of the GNU General Public
8 * License as published by the Free Software Foundation.
9 */
10
11 #include <endian.h>
12 #include <asm/types.h>
13 #include <linux/types.h>
14 #include <stdint.h>
15 #include <stdio.h>
16 #include <stdlib.h>
17 #include <unistd.h>
18 #include <errno.h>
19 #include <string.h>
20 #include <stddef.h>
21 #include <stdbool.h>
22 #include <sched.h>
23 #include <limits.h>
24 #include <assert.h>
25
26 #include <sys/capability.h>
27 #include <sys/resource.h>
28
29 #include <linux/unistd.h>
30 #include <linux/filter.h>
31 #include <linux/bpf_perf_event.h>
32 #include <linux/bpf.h>
33
34 #include <bpf/bpf.h>
35
36 #ifdef HAVE_GENHDR
37 # include "autoconf.h"
38 #else
39 # if defined(__i386) || defined(__x86_64) || defined(__s390x__) || defined(__aarch64__)
40 # define CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS 1
41 # endif
42 #endif
43
44 #include "../../../include/linux/filter.h"
45
46 #ifndef ARRAY_SIZE
47 # define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
48 #endif
49
50 #define MAX_INSNS 512
51 #define MAX_FIXUPS 8
52 #define MAX_NR_MAPS 4
53
54 #define F_NEEDS_EFFICIENT_UNALIGNED_ACCESS (1 << 0)
55 #define F_LOAD_WITH_STRICT_ALIGNMENT (1 << 1)
56
57 struct bpf_test {
58 const char *descr;
59 struct bpf_insn insns[MAX_INSNS];
60 int fixup_map1[MAX_FIXUPS];
61 int fixup_map2[MAX_FIXUPS];
62 int fixup_prog[MAX_FIXUPS];
63 int fixup_map_in_map[MAX_FIXUPS];
64 const char *errstr;
65 const char *errstr_unpriv;
66 enum {
67 UNDEF,
68 ACCEPT,
69 REJECT
70 } result, result_unpriv;
71 enum bpf_prog_type prog_type;
72 uint8_t flags;
73 };
74
75 /* Note we want this to be 64 bit aligned so that the end of our array is
76 * actually the end of the structure.
77 */
78 #define MAX_ENTRIES 11
79
80 struct test_val {
81 unsigned int index;
82 int foo[MAX_ENTRIES];
83 };
84
85 static struct bpf_test tests[] = {
86 {
87 "add+sub+mul",
88 .insns = {
89 BPF_MOV64_IMM(BPF_REG_1, 1),
90 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 2),
91 BPF_MOV64_IMM(BPF_REG_2, 3),
92 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_2),
93 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -1),
94 BPF_ALU64_IMM(BPF_MUL, BPF_REG_1, 3),
95 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
96 BPF_EXIT_INSN(),
97 },
98 .result = ACCEPT,
99 },
100 {
101 "unreachable",
102 .insns = {
103 BPF_EXIT_INSN(),
104 BPF_EXIT_INSN(),
105 },
106 .errstr = "unreachable",
107 .result = REJECT,
108 },
109 {
110 "unreachable2",
111 .insns = {
112 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
113 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
114 BPF_EXIT_INSN(),
115 },
116 .errstr = "unreachable",
117 .result = REJECT,
118 },
119 {
120 "out of range jump",
121 .insns = {
122 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
123 BPF_EXIT_INSN(),
124 },
125 .errstr = "jump out of range",
126 .result = REJECT,
127 },
128 {
129 "out of range jump2",
130 .insns = {
131 BPF_JMP_IMM(BPF_JA, 0, 0, -2),
132 BPF_EXIT_INSN(),
133 },
134 .errstr = "jump out of range",
135 .result = REJECT,
136 },
137 {
138 "test1 ld_imm64",
139 .insns = {
140 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 1),
141 BPF_LD_IMM64(BPF_REG_0, 0),
142 BPF_LD_IMM64(BPF_REG_0, 0),
143 BPF_LD_IMM64(BPF_REG_0, 1),
144 BPF_LD_IMM64(BPF_REG_0, 1),
145 BPF_MOV64_IMM(BPF_REG_0, 2),
146 BPF_EXIT_INSN(),
147 },
148 .errstr = "invalid BPF_LD_IMM insn",
149 .errstr_unpriv = "R1 pointer comparison",
150 .result = REJECT,
151 },
152 {
153 "test2 ld_imm64",
154 .insns = {
155 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 1),
156 BPF_LD_IMM64(BPF_REG_0, 0),
157 BPF_LD_IMM64(BPF_REG_0, 0),
158 BPF_LD_IMM64(BPF_REG_0, 1),
159 BPF_LD_IMM64(BPF_REG_0, 1),
160 BPF_EXIT_INSN(),
161 },
162 .errstr = "invalid BPF_LD_IMM insn",
163 .errstr_unpriv = "R1 pointer comparison",
164 .result = REJECT,
165 },
166 {
167 "test3 ld_imm64",
168 .insns = {
169 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 1),
170 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 0),
171 BPF_LD_IMM64(BPF_REG_0, 0),
172 BPF_LD_IMM64(BPF_REG_0, 0),
173 BPF_LD_IMM64(BPF_REG_0, 1),
174 BPF_LD_IMM64(BPF_REG_0, 1),
175 BPF_EXIT_INSN(),
176 },
177 .errstr = "invalid bpf_ld_imm64 insn",
178 .result = REJECT,
179 },
180 {
181 "test4 ld_imm64",
182 .insns = {
183 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 0),
184 BPF_EXIT_INSN(),
185 },
186 .errstr = "invalid bpf_ld_imm64 insn",
187 .result = REJECT,
188 },
189 {
190 "test5 ld_imm64",
191 .insns = {
192 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 0),
193 },
194 .errstr = "invalid bpf_ld_imm64 insn",
195 .result = REJECT,
196 },
197 {
198 "test6 ld_imm64",
199 .insns = {
200 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 0),
201 BPF_RAW_INSN(0, 0, 0, 0, 0),
202 BPF_EXIT_INSN(),
203 },
204 .result = ACCEPT,
205 },
206 {
207 "test7 ld_imm64",
208 .insns = {
209 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 1),
210 BPF_RAW_INSN(0, 0, 0, 0, 1),
211 BPF_EXIT_INSN(),
212 },
213 .result = ACCEPT,
214 },
215 {
216 "test8 ld_imm64",
217 .insns = {
218 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 1, 1),
219 BPF_RAW_INSN(0, 0, 0, 0, 1),
220 BPF_EXIT_INSN(),
221 },
222 .errstr = "uses reserved fields",
223 .result = REJECT,
224 },
225 {
226 "test9 ld_imm64",
227 .insns = {
228 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 1),
229 BPF_RAW_INSN(0, 0, 0, 1, 1),
230 BPF_EXIT_INSN(),
231 },
232 .errstr = "invalid bpf_ld_imm64 insn",
233 .result = REJECT,
234 },
235 {
236 "test10 ld_imm64",
237 .insns = {
238 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 1),
239 BPF_RAW_INSN(0, BPF_REG_1, 0, 0, 1),
240 BPF_EXIT_INSN(),
241 },
242 .errstr = "invalid bpf_ld_imm64 insn",
243 .result = REJECT,
244 },
245 {
246 "test11 ld_imm64",
247 .insns = {
248 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, 0, 0, 1),
249 BPF_RAW_INSN(0, 0, BPF_REG_1, 0, 1),
250 BPF_EXIT_INSN(),
251 },
252 .errstr = "invalid bpf_ld_imm64 insn",
253 .result = REJECT,
254 },
255 {
256 "test12 ld_imm64",
257 .insns = {
258 BPF_MOV64_IMM(BPF_REG_1, 0),
259 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, BPF_REG_1, 0, 1),
260 BPF_RAW_INSN(0, 0, 0, 0, 1),
261 BPF_EXIT_INSN(),
262 },
263 .errstr = "not pointing to valid bpf_map",
264 .result = REJECT,
265 },
266 {
267 "test13 ld_imm64",
268 .insns = {
269 BPF_MOV64_IMM(BPF_REG_1, 0),
270 BPF_RAW_INSN(BPF_LD | BPF_IMM | BPF_DW, 0, BPF_REG_1, 0, 1),
271 BPF_RAW_INSN(0, 0, BPF_REG_1, 0, 1),
272 BPF_EXIT_INSN(),
273 },
274 .errstr = "invalid bpf_ld_imm64 insn",
275 .result = REJECT,
276 },
277 {
278 "arsh32 on imm",
279 .insns = {
280 BPF_MOV64_IMM(BPF_REG_0, 1),
281 BPF_ALU32_IMM(BPF_ARSH, BPF_REG_0, 5),
282 BPF_EXIT_INSN(),
283 },
284 .result = REJECT,
285 .errstr = "BPF_ARSH not supported for 32 bit ALU",
286 },
287 {
288 "arsh32 on reg",
289 .insns = {
290 BPF_MOV64_IMM(BPF_REG_0, 1),
291 BPF_MOV64_IMM(BPF_REG_1, 5),
292 BPF_ALU32_REG(BPF_ARSH, BPF_REG_0, BPF_REG_1),
293 BPF_EXIT_INSN(),
294 },
295 .result = REJECT,
296 .errstr = "BPF_ARSH not supported for 32 bit ALU",
297 },
298 {
299 "arsh64 on imm",
300 .insns = {
301 BPF_MOV64_IMM(BPF_REG_0, 1),
302 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_0, 5),
303 BPF_EXIT_INSN(),
304 },
305 .result = ACCEPT,
306 },
307 {
308 "arsh64 on reg",
309 .insns = {
310 BPF_MOV64_IMM(BPF_REG_0, 1),
311 BPF_MOV64_IMM(BPF_REG_1, 5),
312 BPF_ALU64_REG(BPF_ARSH, BPF_REG_0, BPF_REG_1),
313 BPF_EXIT_INSN(),
314 },
315 .result = ACCEPT,
316 },
317 {
318 "no bpf_exit",
319 .insns = {
320 BPF_ALU64_REG(BPF_MOV, BPF_REG_0, BPF_REG_2),
321 },
322 .errstr = "jump out of range",
323 .result = REJECT,
324 },
325 {
326 "loop (back-edge)",
327 .insns = {
328 BPF_JMP_IMM(BPF_JA, 0, 0, -1),
329 BPF_EXIT_INSN(),
330 },
331 .errstr = "back-edge",
332 .result = REJECT,
333 },
334 {
335 "loop2 (back-edge)",
336 .insns = {
337 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
338 BPF_MOV64_REG(BPF_REG_2, BPF_REG_0),
339 BPF_MOV64_REG(BPF_REG_3, BPF_REG_0),
340 BPF_JMP_IMM(BPF_JA, 0, 0, -4),
341 BPF_EXIT_INSN(),
342 },
343 .errstr = "back-edge",
344 .result = REJECT,
345 },
346 {
347 "conditional loop",
348 .insns = {
349 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
350 BPF_MOV64_REG(BPF_REG_2, BPF_REG_0),
351 BPF_MOV64_REG(BPF_REG_3, BPF_REG_0),
352 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, -3),
353 BPF_EXIT_INSN(),
354 },
355 .errstr = "back-edge",
356 .result = REJECT,
357 },
358 {
359 "read uninitialized register",
360 .insns = {
361 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
362 BPF_EXIT_INSN(),
363 },
364 .errstr = "R2 !read_ok",
365 .result = REJECT,
366 },
367 {
368 "read invalid register",
369 .insns = {
370 BPF_MOV64_REG(BPF_REG_0, -1),
371 BPF_EXIT_INSN(),
372 },
373 .errstr = "R15 is invalid",
374 .result = REJECT,
375 },
376 {
377 "program doesn't init R0 before exit",
378 .insns = {
379 BPF_ALU64_REG(BPF_MOV, BPF_REG_2, BPF_REG_1),
380 BPF_EXIT_INSN(),
381 },
382 .errstr = "R0 !read_ok",
383 .result = REJECT,
384 },
385 {
386 "program doesn't init R0 before exit in all branches",
387 .insns = {
388 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
389 BPF_MOV64_IMM(BPF_REG_0, 1),
390 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 2),
391 BPF_EXIT_INSN(),
392 },
393 .errstr = "R0 !read_ok",
394 .errstr_unpriv = "R1 pointer comparison",
395 .result = REJECT,
396 },
397 {
398 "stack out of bounds",
399 .insns = {
400 BPF_ST_MEM(BPF_DW, BPF_REG_10, 8, 0),
401 BPF_EXIT_INSN(),
402 },
403 .errstr = "invalid stack",
404 .result = REJECT,
405 },
406 {
407 "invalid call insn1",
408 .insns = {
409 BPF_RAW_INSN(BPF_JMP | BPF_CALL | BPF_X, 0, 0, 0, 0),
410 BPF_EXIT_INSN(),
411 },
412 .errstr = "BPF_CALL uses reserved",
413 .result = REJECT,
414 },
415 {
416 "invalid call insn2",
417 .insns = {
418 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 1, 0),
419 BPF_EXIT_INSN(),
420 },
421 .errstr = "BPF_CALL uses reserved",
422 .result = REJECT,
423 },
424 {
425 "invalid function call",
426 .insns = {
427 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, 1234567),
428 BPF_EXIT_INSN(),
429 },
430 .errstr = "invalid func unknown#1234567",
431 .result = REJECT,
432 },
433 {
434 "uninitialized stack1",
435 .insns = {
436 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
437 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
438 BPF_LD_MAP_FD(BPF_REG_1, 0),
439 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
440 BPF_FUNC_map_lookup_elem),
441 BPF_EXIT_INSN(),
442 },
443 .fixup_map1 = { 2 },
444 .errstr = "invalid indirect read from stack",
445 .result = REJECT,
446 },
447 {
448 "uninitialized stack2",
449 .insns = {
450 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
451 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_2, -8),
452 BPF_EXIT_INSN(),
453 },
454 .errstr = "invalid read from stack",
455 .result = REJECT,
456 },
457 {
458 "invalid fp arithmetic",
459 /* If this gets ever changed, make sure JITs can deal with it. */
460 .insns = {
461 BPF_MOV64_IMM(BPF_REG_0, 0),
462 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
463 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 8),
464 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
465 BPF_EXIT_INSN(),
466 },
467 .errstr = "R1 subtraction from stack pointer",
468 .result = REJECT,
469 },
470 {
471 "non-invalid fp arithmetic",
472 .insns = {
473 BPF_MOV64_IMM(BPF_REG_0, 0),
474 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
475 BPF_EXIT_INSN(),
476 },
477 .result = ACCEPT,
478 },
479 {
480 "invalid argument register",
481 .insns = {
482 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
483 BPF_FUNC_get_cgroup_classid),
484 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
485 BPF_FUNC_get_cgroup_classid),
486 BPF_EXIT_INSN(),
487 },
488 .errstr = "R1 !read_ok",
489 .result = REJECT,
490 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
491 },
492 {
493 "non-invalid argument register",
494 .insns = {
495 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_1),
496 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
497 BPF_FUNC_get_cgroup_classid),
498 BPF_ALU64_REG(BPF_MOV, BPF_REG_1, BPF_REG_6),
499 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
500 BPF_FUNC_get_cgroup_classid),
501 BPF_EXIT_INSN(),
502 },
503 .result = ACCEPT,
504 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
505 },
506 {
507 "check valid spill/fill",
508 .insns = {
509 /* spill R1(ctx) into stack */
510 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
511 /* fill it back into R2 */
512 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -8),
513 /* should be able to access R0 = *(R2 + 8) */
514 /* BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_2, 8), */
515 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
516 BPF_EXIT_INSN(),
517 },
518 .errstr_unpriv = "R0 leaks addr",
519 .result = ACCEPT,
520 .result_unpriv = REJECT,
521 },
522 {
523 "check valid spill/fill, skb mark",
524 .insns = {
525 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_1),
526 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_6, -8),
527 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
528 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
529 offsetof(struct __sk_buff, mark)),
530 BPF_EXIT_INSN(),
531 },
532 .result = ACCEPT,
533 .result_unpriv = ACCEPT,
534 },
535 {
536 "check corrupted spill/fill",
537 .insns = {
538 /* spill R1(ctx) into stack */
539 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
540 /* mess up with R1 pointer on stack */
541 BPF_ST_MEM(BPF_B, BPF_REG_10, -7, 0x23),
542 /* fill back into R0 should fail */
543 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
544 BPF_EXIT_INSN(),
545 },
546 .errstr_unpriv = "attempt to corrupt spilled",
547 .errstr = "corrupted spill",
548 .result = REJECT,
549 },
550 {
551 "invalid src register in STX",
552 .insns = {
553 BPF_STX_MEM(BPF_B, BPF_REG_10, -1, -1),
554 BPF_EXIT_INSN(),
555 },
556 .errstr = "R15 is invalid",
557 .result = REJECT,
558 },
559 {
560 "invalid dst register in STX",
561 .insns = {
562 BPF_STX_MEM(BPF_B, 14, BPF_REG_10, -1),
563 BPF_EXIT_INSN(),
564 },
565 .errstr = "R14 is invalid",
566 .result = REJECT,
567 },
568 {
569 "invalid dst register in ST",
570 .insns = {
571 BPF_ST_MEM(BPF_B, 14, -1, -1),
572 BPF_EXIT_INSN(),
573 },
574 .errstr = "R14 is invalid",
575 .result = REJECT,
576 },
577 {
578 "invalid src register in LDX",
579 .insns = {
580 BPF_LDX_MEM(BPF_B, BPF_REG_0, 12, 0),
581 BPF_EXIT_INSN(),
582 },
583 .errstr = "R12 is invalid",
584 .result = REJECT,
585 },
586 {
587 "invalid dst register in LDX",
588 .insns = {
589 BPF_LDX_MEM(BPF_B, 11, BPF_REG_1, 0),
590 BPF_EXIT_INSN(),
591 },
592 .errstr = "R11 is invalid",
593 .result = REJECT,
594 },
595 {
596 "junk insn",
597 .insns = {
598 BPF_RAW_INSN(0, 0, 0, 0, 0),
599 BPF_EXIT_INSN(),
600 },
601 .errstr = "invalid BPF_LD_IMM",
602 .result = REJECT,
603 },
604 {
605 "junk insn2",
606 .insns = {
607 BPF_RAW_INSN(1, 0, 0, 0, 0),
608 BPF_EXIT_INSN(),
609 },
610 .errstr = "BPF_LDX uses reserved fields",
611 .result = REJECT,
612 },
613 {
614 "junk insn3",
615 .insns = {
616 BPF_RAW_INSN(-1, 0, 0, 0, 0),
617 BPF_EXIT_INSN(),
618 },
619 .errstr = "invalid BPF_ALU opcode f0",
620 .result = REJECT,
621 },
622 {
623 "junk insn4",
624 .insns = {
625 BPF_RAW_INSN(-1, -1, -1, -1, -1),
626 BPF_EXIT_INSN(),
627 },
628 .errstr = "invalid BPF_ALU opcode f0",
629 .result = REJECT,
630 },
631 {
632 "junk insn5",
633 .insns = {
634 BPF_RAW_INSN(0x7f, -1, -1, -1, -1),
635 BPF_EXIT_INSN(),
636 },
637 .errstr = "BPF_ALU uses reserved fields",
638 .result = REJECT,
639 },
640 {
641 "misaligned read from stack",
642 .insns = {
643 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
644 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_2, -4),
645 BPF_EXIT_INSN(),
646 },
647 .errstr = "misaligned stack access",
648 .result = REJECT,
649 },
650 {
651 "invalid map_fd for function call",
652 .insns = {
653 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
654 BPF_ALU64_REG(BPF_MOV, BPF_REG_2, BPF_REG_10),
655 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
656 BPF_LD_MAP_FD(BPF_REG_1, 0),
657 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
658 BPF_FUNC_map_delete_elem),
659 BPF_EXIT_INSN(),
660 },
661 .errstr = "fd 0 is not pointing to valid bpf_map",
662 .result = REJECT,
663 },
664 {
665 "don't check return value before access",
666 .insns = {
667 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
668 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
669 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
670 BPF_LD_MAP_FD(BPF_REG_1, 0),
671 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
672 BPF_FUNC_map_lookup_elem),
673 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 0),
674 BPF_EXIT_INSN(),
675 },
676 .fixup_map1 = { 3 },
677 .errstr = "R0 invalid mem access 'map_value_or_null'",
678 .result = REJECT,
679 },
680 {
681 "access memory with incorrect alignment",
682 .insns = {
683 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
684 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
685 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
686 BPF_LD_MAP_FD(BPF_REG_1, 0),
687 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
688 BPF_FUNC_map_lookup_elem),
689 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
690 BPF_ST_MEM(BPF_DW, BPF_REG_0, 4, 0),
691 BPF_EXIT_INSN(),
692 },
693 .fixup_map1 = { 3 },
694 .errstr = "misaligned value access",
695 .result = REJECT,
696 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
697 },
698 {
699 "sometimes access memory with incorrect alignment",
700 .insns = {
701 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
702 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
703 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
704 BPF_LD_MAP_FD(BPF_REG_1, 0),
705 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
706 BPF_FUNC_map_lookup_elem),
707 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
708 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 0),
709 BPF_EXIT_INSN(),
710 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 1),
711 BPF_EXIT_INSN(),
712 },
713 .fixup_map1 = { 3 },
714 .errstr = "R0 invalid mem access",
715 .errstr_unpriv = "R0 leaks addr",
716 .result = REJECT,
717 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
718 },
719 {
720 "jump test 1",
721 .insns = {
722 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
723 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -8),
724 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 1),
725 BPF_ST_MEM(BPF_DW, BPF_REG_2, -8, 0),
726 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 1, 1),
727 BPF_ST_MEM(BPF_DW, BPF_REG_2, -16, 1),
728 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 2, 1),
729 BPF_ST_MEM(BPF_DW, BPF_REG_2, -8, 2),
730 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 3, 1),
731 BPF_ST_MEM(BPF_DW, BPF_REG_2, -16, 3),
732 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 4, 1),
733 BPF_ST_MEM(BPF_DW, BPF_REG_2, -8, 4),
734 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 5, 1),
735 BPF_ST_MEM(BPF_DW, BPF_REG_2, -32, 5),
736 BPF_MOV64_IMM(BPF_REG_0, 0),
737 BPF_EXIT_INSN(),
738 },
739 .errstr_unpriv = "R1 pointer comparison",
740 .result_unpriv = REJECT,
741 .result = ACCEPT,
742 },
743 {
744 "jump test 2",
745 .insns = {
746 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
747 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 2),
748 BPF_ST_MEM(BPF_DW, BPF_REG_2, -8, 0),
749 BPF_JMP_IMM(BPF_JA, 0, 0, 14),
750 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 1, 2),
751 BPF_ST_MEM(BPF_DW, BPF_REG_2, -16, 0),
752 BPF_JMP_IMM(BPF_JA, 0, 0, 11),
753 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 2, 2),
754 BPF_ST_MEM(BPF_DW, BPF_REG_2, -32, 0),
755 BPF_JMP_IMM(BPF_JA, 0, 0, 8),
756 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 3, 2),
757 BPF_ST_MEM(BPF_DW, BPF_REG_2, -40, 0),
758 BPF_JMP_IMM(BPF_JA, 0, 0, 5),
759 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 4, 2),
760 BPF_ST_MEM(BPF_DW, BPF_REG_2, -48, 0),
761 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
762 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 5, 1),
763 BPF_ST_MEM(BPF_DW, BPF_REG_2, -56, 0),
764 BPF_MOV64_IMM(BPF_REG_0, 0),
765 BPF_EXIT_INSN(),
766 },
767 .errstr_unpriv = "R1 pointer comparison",
768 .result_unpriv = REJECT,
769 .result = ACCEPT,
770 },
771 {
772 "jump test 3",
773 .insns = {
774 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
775 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 3),
776 BPF_ST_MEM(BPF_DW, BPF_REG_2, -8, 0),
777 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
778 BPF_JMP_IMM(BPF_JA, 0, 0, 19),
779 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 1, 3),
780 BPF_ST_MEM(BPF_DW, BPF_REG_2, -16, 0),
781 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -16),
782 BPF_JMP_IMM(BPF_JA, 0, 0, 15),
783 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 2, 3),
784 BPF_ST_MEM(BPF_DW, BPF_REG_2, -32, 0),
785 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -32),
786 BPF_JMP_IMM(BPF_JA, 0, 0, 11),
787 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 3, 3),
788 BPF_ST_MEM(BPF_DW, BPF_REG_2, -40, 0),
789 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -40),
790 BPF_JMP_IMM(BPF_JA, 0, 0, 7),
791 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 4, 3),
792 BPF_ST_MEM(BPF_DW, BPF_REG_2, -48, 0),
793 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -48),
794 BPF_JMP_IMM(BPF_JA, 0, 0, 3),
795 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 5, 0),
796 BPF_ST_MEM(BPF_DW, BPF_REG_2, -56, 0),
797 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -56),
798 BPF_LD_MAP_FD(BPF_REG_1, 0),
799 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
800 BPF_FUNC_map_delete_elem),
801 BPF_EXIT_INSN(),
802 },
803 .fixup_map1 = { 24 },
804 .errstr_unpriv = "R1 pointer comparison",
805 .result_unpriv = REJECT,
806 .result = ACCEPT,
807 },
808 {
809 "jump test 4",
810 .insns = {
811 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
812 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
813 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
814 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
815 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
816 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
817 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
818 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
819 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
820 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
821 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
822 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
823 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
824 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
825 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
826 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
827 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
828 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
829 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
830 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
831 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
832 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
833 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
834 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
835 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
836 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
837 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
838 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
839 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
840 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
841 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
842 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
843 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 1),
844 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 2),
845 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 3),
846 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 4),
847 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 0),
848 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 0),
849 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 0),
850 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, BPF_REG_10, 0),
851 BPF_MOV64_IMM(BPF_REG_0, 0),
852 BPF_EXIT_INSN(),
853 },
854 .errstr_unpriv = "R1 pointer comparison",
855 .result_unpriv = REJECT,
856 .result = ACCEPT,
857 },
858 {
859 "jump test 5",
860 .insns = {
861 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
862 BPF_MOV64_REG(BPF_REG_3, BPF_REG_2),
863 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
864 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_3, -8),
865 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
866 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_2, -8),
867 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
868 BPF_MOV64_IMM(BPF_REG_0, 0),
869 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
870 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_3, -8),
871 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
872 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_2, -8),
873 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
874 BPF_MOV64_IMM(BPF_REG_0, 0),
875 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
876 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_3, -8),
877 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
878 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_2, -8),
879 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
880 BPF_MOV64_IMM(BPF_REG_0, 0),
881 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
882 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_3, -8),
883 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
884 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_2, -8),
885 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
886 BPF_MOV64_IMM(BPF_REG_0, 0),
887 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
888 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_3, -8),
889 BPF_JMP_IMM(BPF_JA, 0, 0, 2),
890 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_2, -8),
891 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
892 BPF_MOV64_IMM(BPF_REG_0, 0),
893 BPF_EXIT_INSN(),
894 },
895 .errstr_unpriv = "R1 pointer comparison",
896 .result_unpriv = REJECT,
897 .result = ACCEPT,
898 },
899 {
900 "access skb fields ok",
901 .insns = {
902 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
903 offsetof(struct __sk_buff, len)),
904 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 1),
905 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
906 offsetof(struct __sk_buff, mark)),
907 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 1),
908 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
909 offsetof(struct __sk_buff, pkt_type)),
910 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 1),
911 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
912 offsetof(struct __sk_buff, queue_mapping)),
913 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 0),
914 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
915 offsetof(struct __sk_buff, protocol)),
916 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 0),
917 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
918 offsetof(struct __sk_buff, vlan_present)),
919 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 0),
920 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
921 offsetof(struct __sk_buff, vlan_tci)),
922 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 0),
923 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
924 offsetof(struct __sk_buff, napi_id)),
925 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 0),
926 BPF_EXIT_INSN(),
927 },
928 .result = ACCEPT,
929 },
930 {
931 "access skb fields bad1",
932 .insns = {
933 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -4),
934 BPF_EXIT_INSN(),
935 },
936 .errstr = "invalid bpf_context access",
937 .result = REJECT,
938 },
939 {
940 "access skb fields bad2",
941 .insns = {
942 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 9),
943 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
944 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
945 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
946 BPF_LD_MAP_FD(BPF_REG_1, 0),
947 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
948 BPF_FUNC_map_lookup_elem),
949 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
950 BPF_EXIT_INSN(),
951 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
952 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
953 offsetof(struct __sk_buff, pkt_type)),
954 BPF_EXIT_INSN(),
955 },
956 .fixup_map1 = { 4 },
957 .errstr = "different pointers",
958 .errstr_unpriv = "R1 pointer comparison",
959 .result = REJECT,
960 },
961 {
962 "access skb fields bad3",
963 .insns = {
964 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 2),
965 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
966 offsetof(struct __sk_buff, pkt_type)),
967 BPF_EXIT_INSN(),
968 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
969 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
970 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
971 BPF_LD_MAP_FD(BPF_REG_1, 0),
972 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
973 BPF_FUNC_map_lookup_elem),
974 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
975 BPF_EXIT_INSN(),
976 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
977 BPF_JMP_IMM(BPF_JA, 0, 0, -12),
978 },
979 .fixup_map1 = { 6 },
980 .errstr = "different pointers",
981 .errstr_unpriv = "R1 pointer comparison",
982 .result = REJECT,
983 },
984 {
985 "access skb fields bad4",
986 .insns = {
987 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, 0, 3),
988 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
989 offsetof(struct __sk_buff, len)),
990 BPF_MOV64_IMM(BPF_REG_0, 0),
991 BPF_EXIT_INSN(),
992 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
993 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
994 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
995 BPF_LD_MAP_FD(BPF_REG_1, 0),
996 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
997 BPF_FUNC_map_lookup_elem),
998 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
999 BPF_EXIT_INSN(),
1000 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
1001 BPF_JMP_IMM(BPF_JA, 0, 0, -13),
1002 },
1003 .fixup_map1 = { 7 },
1004 .errstr = "different pointers",
1005 .errstr_unpriv = "R1 pointer comparison",
1006 .result = REJECT,
1007 },
1008 {
1009 "invalid access __sk_buff family",
1010 .insns = {
1011 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1012 offsetof(struct __sk_buff, family)),
1013 BPF_EXIT_INSN(),
1014 },
1015 .errstr = "invalid bpf_context access",
1016 .result = REJECT,
1017 },
1018 {
1019 "invalid access __sk_buff remote_ip4",
1020 .insns = {
1021 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1022 offsetof(struct __sk_buff, remote_ip4)),
1023 BPF_EXIT_INSN(),
1024 },
1025 .errstr = "invalid bpf_context access",
1026 .result = REJECT,
1027 },
1028 {
1029 "invalid access __sk_buff local_ip4",
1030 .insns = {
1031 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1032 offsetof(struct __sk_buff, local_ip4)),
1033 BPF_EXIT_INSN(),
1034 },
1035 .errstr = "invalid bpf_context access",
1036 .result = REJECT,
1037 },
1038 {
1039 "invalid access __sk_buff remote_ip6",
1040 .insns = {
1041 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1042 offsetof(struct __sk_buff, remote_ip6)),
1043 BPF_EXIT_INSN(),
1044 },
1045 .errstr = "invalid bpf_context access",
1046 .result = REJECT,
1047 },
1048 {
1049 "invalid access __sk_buff local_ip6",
1050 .insns = {
1051 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1052 offsetof(struct __sk_buff, local_ip6)),
1053 BPF_EXIT_INSN(),
1054 },
1055 .errstr = "invalid bpf_context access",
1056 .result = REJECT,
1057 },
1058 {
1059 "invalid access __sk_buff remote_port",
1060 .insns = {
1061 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1062 offsetof(struct __sk_buff, remote_port)),
1063 BPF_EXIT_INSN(),
1064 },
1065 .errstr = "invalid bpf_context access",
1066 .result = REJECT,
1067 },
1068 {
1069 "invalid access __sk_buff remote_port",
1070 .insns = {
1071 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1072 offsetof(struct __sk_buff, local_port)),
1073 BPF_EXIT_INSN(),
1074 },
1075 .errstr = "invalid bpf_context access",
1076 .result = REJECT,
1077 },
1078 {
1079 "valid access __sk_buff family",
1080 .insns = {
1081 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1082 offsetof(struct __sk_buff, family)),
1083 BPF_EXIT_INSN(),
1084 },
1085 .result = ACCEPT,
1086 .prog_type = BPF_PROG_TYPE_SK_SKB,
1087 },
1088 {
1089 "valid access __sk_buff remote_ip4",
1090 .insns = {
1091 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1092 offsetof(struct __sk_buff, remote_ip4)),
1093 BPF_EXIT_INSN(),
1094 },
1095 .result = ACCEPT,
1096 .prog_type = BPF_PROG_TYPE_SK_SKB,
1097 },
1098 {
1099 "valid access __sk_buff local_ip4",
1100 .insns = {
1101 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1102 offsetof(struct __sk_buff, local_ip4)),
1103 BPF_EXIT_INSN(),
1104 },
1105 .result = ACCEPT,
1106 .prog_type = BPF_PROG_TYPE_SK_SKB,
1107 },
1108 {
1109 "valid access __sk_buff remote_ip6",
1110 .insns = {
1111 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1112 offsetof(struct __sk_buff, remote_ip6[0])),
1113 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1114 offsetof(struct __sk_buff, remote_ip6[1])),
1115 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1116 offsetof(struct __sk_buff, remote_ip6[2])),
1117 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1118 offsetof(struct __sk_buff, remote_ip6[3])),
1119 BPF_EXIT_INSN(),
1120 },
1121 .result = ACCEPT,
1122 .prog_type = BPF_PROG_TYPE_SK_SKB,
1123 },
1124 {
1125 "valid access __sk_buff local_ip6",
1126 .insns = {
1127 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1128 offsetof(struct __sk_buff, local_ip6[0])),
1129 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1130 offsetof(struct __sk_buff, local_ip6[1])),
1131 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1132 offsetof(struct __sk_buff, local_ip6[2])),
1133 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1134 offsetof(struct __sk_buff, local_ip6[3])),
1135 BPF_EXIT_INSN(),
1136 },
1137 .result = ACCEPT,
1138 .prog_type = BPF_PROG_TYPE_SK_SKB,
1139 },
1140 {
1141 "valid access __sk_buff remote_port",
1142 .insns = {
1143 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1144 offsetof(struct __sk_buff, remote_port)),
1145 BPF_EXIT_INSN(),
1146 },
1147 .result = ACCEPT,
1148 .prog_type = BPF_PROG_TYPE_SK_SKB,
1149 },
1150 {
1151 "valid access __sk_buff remote_port",
1152 .insns = {
1153 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1154 offsetof(struct __sk_buff, local_port)),
1155 BPF_EXIT_INSN(),
1156 },
1157 .result = ACCEPT,
1158 .prog_type = BPF_PROG_TYPE_SK_SKB,
1159 },
1160 {
1161 "invalid access of tc_classid for SK_SKB",
1162 .insns = {
1163 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1164 offsetof(struct __sk_buff, tc_classid)),
1165 BPF_EXIT_INSN(),
1166 },
1167 .result = REJECT,
1168 .prog_type = BPF_PROG_TYPE_SK_SKB,
1169 .errstr = "invalid bpf_context access",
1170 },
1171 {
1172 "invalid access of skb->mark for SK_SKB",
1173 .insns = {
1174 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1175 offsetof(struct __sk_buff, mark)),
1176 BPF_EXIT_INSN(),
1177 },
1178 .result = REJECT,
1179 .prog_type = BPF_PROG_TYPE_SK_SKB,
1180 .errstr = "invalid bpf_context access",
1181 },
1182 {
1183 "check skb->mark is not writeable by SK_SKB",
1184 .insns = {
1185 BPF_MOV64_IMM(BPF_REG_0, 0),
1186 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1187 offsetof(struct __sk_buff, mark)),
1188 BPF_EXIT_INSN(),
1189 },
1190 .result = REJECT,
1191 .prog_type = BPF_PROG_TYPE_SK_SKB,
1192 .errstr = "invalid bpf_context access",
1193 },
1194 {
1195 "check skb->tc_index is writeable by SK_SKB",
1196 .insns = {
1197 BPF_MOV64_IMM(BPF_REG_0, 0),
1198 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1199 offsetof(struct __sk_buff, tc_index)),
1200 BPF_EXIT_INSN(),
1201 },
1202 .result = ACCEPT,
1203 .prog_type = BPF_PROG_TYPE_SK_SKB,
1204 },
1205 {
1206 "check skb->priority is writeable by SK_SKB",
1207 .insns = {
1208 BPF_MOV64_IMM(BPF_REG_0, 0),
1209 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1210 offsetof(struct __sk_buff, priority)),
1211 BPF_EXIT_INSN(),
1212 },
1213 .result = ACCEPT,
1214 .prog_type = BPF_PROG_TYPE_SK_SKB,
1215 },
1216 {
1217 "direct packet read for SK_SKB",
1218 .insns = {
1219 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
1220 offsetof(struct __sk_buff, data)),
1221 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
1222 offsetof(struct __sk_buff, data_end)),
1223 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
1224 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
1225 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
1226 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
1227 BPF_MOV64_IMM(BPF_REG_0, 0),
1228 BPF_EXIT_INSN(),
1229 },
1230 .result = ACCEPT,
1231 .prog_type = BPF_PROG_TYPE_SK_SKB,
1232 },
1233 {
1234 "direct packet write for SK_SKB",
1235 .insns = {
1236 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
1237 offsetof(struct __sk_buff, data)),
1238 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
1239 offsetof(struct __sk_buff, data_end)),
1240 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
1241 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
1242 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
1243 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
1244 BPF_MOV64_IMM(BPF_REG_0, 0),
1245 BPF_EXIT_INSN(),
1246 },
1247 .result = ACCEPT,
1248 .prog_type = BPF_PROG_TYPE_SK_SKB,
1249 },
1250 {
1251 "overlapping checks for direct packet access SK_SKB",
1252 .insns = {
1253 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
1254 offsetof(struct __sk_buff, data)),
1255 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
1256 offsetof(struct __sk_buff, data_end)),
1257 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
1258 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
1259 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 4),
1260 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
1261 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 6),
1262 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
1263 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_2, 6),
1264 BPF_MOV64_IMM(BPF_REG_0, 0),
1265 BPF_EXIT_INSN(),
1266 },
1267 .result = ACCEPT,
1268 .prog_type = BPF_PROG_TYPE_SK_SKB,
1269 },
1270 {
1271 "check skb->mark is not writeable by sockets",
1272 .insns = {
1273 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
1274 offsetof(struct __sk_buff, mark)),
1275 BPF_EXIT_INSN(),
1276 },
1277 .errstr = "invalid bpf_context access",
1278 .errstr_unpriv = "R1 leaks addr",
1279 .result = REJECT,
1280 },
1281 {
1282 "check skb->tc_index is not writeable by sockets",
1283 .insns = {
1284 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
1285 offsetof(struct __sk_buff, tc_index)),
1286 BPF_EXIT_INSN(),
1287 },
1288 .errstr = "invalid bpf_context access",
1289 .errstr_unpriv = "R1 leaks addr",
1290 .result = REJECT,
1291 },
1292 {
1293 "check cb access: byte",
1294 .insns = {
1295 BPF_MOV64_IMM(BPF_REG_0, 0),
1296 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1297 offsetof(struct __sk_buff, cb[0])),
1298 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1299 offsetof(struct __sk_buff, cb[0]) + 1),
1300 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1301 offsetof(struct __sk_buff, cb[0]) + 2),
1302 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1303 offsetof(struct __sk_buff, cb[0]) + 3),
1304 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1305 offsetof(struct __sk_buff, cb[1])),
1306 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1307 offsetof(struct __sk_buff, cb[1]) + 1),
1308 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1309 offsetof(struct __sk_buff, cb[1]) + 2),
1310 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1311 offsetof(struct __sk_buff, cb[1]) + 3),
1312 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1313 offsetof(struct __sk_buff, cb[2])),
1314 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1315 offsetof(struct __sk_buff, cb[2]) + 1),
1316 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1317 offsetof(struct __sk_buff, cb[2]) + 2),
1318 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1319 offsetof(struct __sk_buff, cb[2]) + 3),
1320 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1321 offsetof(struct __sk_buff, cb[3])),
1322 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1323 offsetof(struct __sk_buff, cb[3]) + 1),
1324 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1325 offsetof(struct __sk_buff, cb[3]) + 2),
1326 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1327 offsetof(struct __sk_buff, cb[3]) + 3),
1328 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1329 offsetof(struct __sk_buff, cb[4])),
1330 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1331 offsetof(struct __sk_buff, cb[4]) + 1),
1332 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1333 offsetof(struct __sk_buff, cb[4]) + 2),
1334 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1335 offsetof(struct __sk_buff, cb[4]) + 3),
1336 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1337 offsetof(struct __sk_buff, cb[0])),
1338 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1339 offsetof(struct __sk_buff, cb[0]) + 1),
1340 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1341 offsetof(struct __sk_buff, cb[0]) + 2),
1342 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1343 offsetof(struct __sk_buff, cb[0]) + 3),
1344 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1345 offsetof(struct __sk_buff, cb[1])),
1346 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1347 offsetof(struct __sk_buff, cb[1]) + 1),
1348 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1349 offsetof(struct __sk_buff, cb[1]) + 2),
1350 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1351 offsetof(struct __sk_buff, cb[1]) + 3),
1352 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1353 offsetof(struct __sk_buff, cb[2])),
1354 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1355 offsetof(struct __sk_buff, cb[2]) + 1),
1356 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1357 offsetof(struct __sk_buff, cb[2]) + 2),
1358 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1359 offsetof(struct __sk_buff, cb[2]) + 3),
1360 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1361 offsetof(struct __sk_buff, cb[3])),
1362 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1363 offsetof(struct __sk_buff, cb[3]) + 1),
1364 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1365 offsetof(struct __sk_buff, cb[3]) + 2),
1366 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1367 offsetof(struct __sk_buff, cb[3]) + 3),
1368 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1369 offsetof(struct __sk_buff, cb[4])),
1370 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1371 offsetof(struct __sk_buff, cb[4]) + 1),
1372 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1373 offsetof(struct __sk_buff, cb[4]) + 2),
1374 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1375 offsetof(struct __sk_buff, cb[4]) + 3),
1376 BPF_EXIT_INSN(),
1377 },
1378 .result = ACCEPT,
1379 },
1380 {
1381 "__sk_buff->hash, offset 0, byte store not permitted",
1382 .insns = {
1383 BPF_MOV64_IMM(BPF_REG_0, 0),
1384 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1385 offsetof(struct __sk_buff, hash)),
1386 BPF_EXIT_INSN(),
1387 },
1388 .errstr = "invalid bpf_context access",
1389 .result = REJECT,
1390 },
1391 {
1392 "__sk_buff->tc_index, offset 3, byte store not permitted",
1393 .insns = {
1394 BPF_MOV64_IMM(BPF_REG_0, 0),
1395 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1396 offsetof(struct __sk_buff, tc_index) + 3),
1397 BPF_EXIT_INSN(),
1398 },
1399 .errstr = "invalid bpf_context access",
1400 .result = REJECT,
1401 },
1402 {
1403 "check skb->hash byte load permitted",
1404 .insns = {
1405 BPF_MOV64_IMM(BPF_REG_0, 0),
1406 #if __BYTE_ORDER == __LITTLE_ENDIAN
1407 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1408 offsetof(struct __sk_buff, hash)),
1409 #else
1410 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1411 offsetof(struct __sk_buff, hash) + 3),
1412 #endif
1413 BPF_EXIT_INSN(),
1414 },
1415 .result = ACCEPT,
1416 },
1417 {
1418 "check skb->hash byte load not permitted 1",
1419 .insns = {
1420 BPF_MOV64_IMM(BPF_REG_0, 0),
1421 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1422 offsetof(struct __sk_buff, hash) + 1),
1423 BPF_EXIT_INSN(),
1424 },
1425 .errstr = "invalid bpf_context access",
1426 .result = REJECT,
1427 },
1428 {
1429 "check skb->hash byte load not permitted 2",
1430 .insns = {
1431 BPF_MOV64_IMM(BPF_REG_0, 0),
1432 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1433 offsetof(struct __sk_buff, hash) + 2),
1434 BPF_EXIT_INSN(),
1435 },
1436 .errstr = "invalid bpf_context access",
1437 .result = REJECT,
1438 },
1439 {
1440 "check skb->hash byte load not permitted 3",
1441 .insns = {
1442 BPF_MOV64_IMM(BPF_REG_0, 0),
1443 #if __BYTE_ORDER == __LITTLE_ENDIAN
1444 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1445 offsetof(struct __sk_buff, hash) + 3),
1446 #else
1447 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
1448 offsetof(struct __sk_buff, hash)),
1449 #endif
1450 BPF_EXIT_INSN(),
1451 },
1452 .errstr = "invalid bpf_context access",
1453 .result = REJECT,
1454 },
1455 {
1456 "check cb access: byte, wrong type",
1457 .insns = {
1458 BPF_MOV64_IMM(BPF_REG_0, 0),
1459 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0,
1460 offsetof(struct __sk_buff, cb[0])),
1461 BPF_EXIT_INSN(),
1462 },
1463 .errstr = "invalid bpf_context access",
1464 .result = REJECT,
1465 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
1466 },
1467 {
1468 "check cb access: half",
1469 .insns = {
1470 BPF_MOV64_IMM(BPF_REG_0, 0),
1471 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1472 offsetof(struct __sk_buff, cb[0])),
1473 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1474 offsetof(struct __sk_buff, cb[0]) + 2),
1475 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1476 offsetof(struct __sk_buff, cb[1])),
1477 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1478 offsetof(struct __sk_buff, cb[1]) + 2),
1479 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1480 offsetof(struct __sk_buff, cb[2])),
1481 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1482 offsetof(struct __sk_buff, cb[2]) + 2),
1483 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1484 offsetof(struct __sk_buff, cb[3])),
1485 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1486 offsetof(struct __sk_buff, cb[3]) + 2),
1487 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1488 offsetof(struct __sk_buff, cb[4])),
1489 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1490 offsetof(struct __sk_buff, cb[4]) + 2),
1491 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1492 offsetof(struct __sk_buff, cb[0])),
1493 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1494 offsetof(struct __sk_buff, cb[0]) + 2),
1495 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1496 offsetof(struct __sk_buff, cb[1])),
1497 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1498 offsetof(struct __sk_buff, cb[1]) + 2),
1499 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1500 offsetof(struct __sk_buff, cb[2])),
1501 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1502 offsetof(struct __sk_buff, cb[2]) + 2),
1503 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1504 offsetof(struct __sk_buff, cb[3])),
1505 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1506 offsetof(struct __sk_buff, cb[3]) + 2),
1507 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1508 offsetof(struct __sk_buff, cb[4])),
1509 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1510 offsetof(struct __sk_buff, cb[4]) + 2),
1511 BPF_EXIT_INSN(),
1512 },
1513 .result = ACCEPT,
1514 },
1515 {
1516 "check cb access: half, unaligned",
1517 .insns = {
1518 BPF_MOV64_IMM(BPF_REG_0, 0),
1519 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1520 offsetof(struct __sk_buff, cb[0]) + 1),
1521 BPF_EXIT_INSN(),
1522 },
1523 .errstr = "misaligned context access",
1524 .result = REJECT,
1525 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1526 },
1527 {
1528 "check __sk_buff->hash, offset 0, half store not permitted",
1529 .insns = {
1530 BPF_MOV64_IMM(BPF_REG_0, 0),
1531 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1532 offsetof(struct __sk_buff, hash)),
1533 BPF_EXIT_INSN(),
1534 },
1535 .errstr = "invalid bpf_context access",
1536 .result = REJECT,
1537 },
1538 {
1539 "check __sk_buff->tc_index, offset 2, half store not permitted",
1540 .insns = {
1541 BPF_MOV64_IMM(BPF_REG_0, 0),
1542 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1543 offsetof(struct __sk_buff, tc_index) + 2),
1544 BPF_EXIT_INSN(),
1545 },
1546 .errstr = "invalid bpf_context access",
1547 .result = REJECT,
1548 },
1549 {
1550 "check skb->hash half load permitted",
1551 .insns = {
1552 BPF_MOV64_IMM(BPF_REG_0, 0),
1553 #if __BYTE_ORDER == __LITTLE_ENDIAN
1554 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1555 offsetof(struct __sk_buff, hash)),
1556 #else
1557 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1558 offsetof(struct __sk_buff, hash) + 2),
1559 #endif
1560 BPF_EXIT_INSN(),
1561 },
1562 .result = ACCEPT,
1563 },
1564 {
1565 "check skb->hash half load not permitted",
1566 .insns = {
1567 BPF_MOV64_IMM(BPF_REG_0, 0),
1568 #if __BYTE_ORDER == __LITTLE_ENDIAN
1569 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1570 offsetof(struct __sk_buff, hash) + 2),
1571 #else
1572 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
1573 offsetof(struct __sk_buff, hash)),
1574 #endif
1575 BPF_EXIT_INSN(),
1576 },
1577 .errstr = "invalid bpf_context access",
1578 .result = REJECT,
1579 },
1580 {
1581 "check cb access: half, wrong type",
1582 .insns = {
1583 BPF_MOV64_IMM(BPF_REG_0, 0),
1584 BPF_STX_MEM(BPF_H, BPF_REG_1, BPF_REG_0,
1585 offsetof(struct __sk_buff, cb[0])),
1586 BPF_EXIT_INSN(),
1587 },
1588 .errstr = "invalid bpf_context access",
1589 .result = REJECT,
1590 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
1591 },
1592 {
1593 "check cb access: word",
1594 .insns = {
1595 BPF_MOV64_IMM(BPF_REG_0, 0),
1596 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1597 offsetof(struct __sk_buff, cb[0])),
1598 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1599 offsetof(struct __sk_buff, cb[1])),
1600 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1601 offsetof(struct __sk_buff, cb[2])),
1602 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1603 offsetof(struct __sk_buff, cb[3])),
1604 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1605 offsetof(struct __sk_buff, cb[4])),
1606 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1607 offsetof(struct __sk_buff, cb[0])),
1608 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1609 offsetof(struct __sk_buff, cb[1])),
1610 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1611 offsetof(struct __sk_buff, cb[2])),
1612 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1613 offsetof(struct __sk_buff, cb[3])),
1614 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1615 offsetof(struct __sk_buff, cb[4])),
1616 BPF_EXIT_INSN(),
1617 },
1618 .result = ACCEPT,
1619 },
1620 {
1621 "check cb access: word, unaligned 1",
1622 .insns = {
1623 BPF_MOV64_IMM(BPF_REG_0, 0),
1624 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1625 offsetof(struct __sk_buff, cb[0]) + 2),
1626 BPF_EXIT_INSN(),
1627 },
1628 .errstr = "misaligned context access",
1629 .result = REJECT,
1630 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1631 },
1632 {
1633 "check cb access: word, unaligned 2",
1634 .insns = {
1635 BPF_MOV64_IMM(BPF_REG_0, 0),
1636 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1637 offsetof(struct __sk_buff, cb[4]) + 1),
1638 BPF_EXIT_INSN(),
1639 },
1640 .errstr = "misaligned context access",
1641 .result = REJECT,
1642 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1643 },
1644 {
1645 "check cb access: word, unaligned 3",
1646 .insns = {
1647 BPF_MOV64_IMM(BPF_REG_0, 0),
1648 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1649 offsetof(struct __sk_buff, cb[4]) + 2),
1650 BPF_EXIT_INSN(),
1651 },
1652 .errstr = "misaligned context access",
1653 .result = REJECT,
1654 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1655 },
1656 {
1657 "check cb access: word, unaligned 4",
1658 .insns = {
1659 BPF_MOV64_IMM(BPF_REG_0, 0),
1660 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1661 offsetof(struct __sk_buff, cb[4]) + 3),
1662 BPF_EXIT_INSN(),
1663 },
1664 .errstr = "misaligned context access",
1665 .result = REJECT,
1666 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1667 },
1668 {
1669 "check cb access: double",
1670 .insns = {
1671 BPF_MOV64_IMM(BPF_REG_0, 0),
1672 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1673 offsetof(struct __sk_buff, cb[0])),
1674 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1675 offsetof(struct __sk_buff, cb[2])),
1676 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1,
1677 offsetof(struct __sk_buff, cb[0])),
1678 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1,
1679 offsetof(struct __sk_buff, cb[2])),
1680 BPF_EXIT_INSN(),
1681 },
1682 .result = ACCEPT,
1683 },
1684 {
1685 "check cb access: double, unaligned 1",
1686 .insns = {
1687 BPF_MOV64_IMM(BPF_REG_0, 0),
1688 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1689 offsetof(struct __sk_buff, cb[1])),
1690 BPF_EXIT_INSN(),
1691 },
1692 .errstr = "misaligned context access",
1693 .result = REJECT,
1694 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1695 },
1696 {
1697 "check cb access: double, unaligned 2",
1698 .insns = {
1699 BPF_MOV64_IMM(BPF_REG_0, 0),
1700 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1701 offsetof(struct __sk_buff, cb[3])),
1702 BPF_EXIT_INSN(),
1703 },
1704 .errstr = "misaligned context access",
1705 .result = REJECT,
1706 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
1707 },
1708 {
1709 "check cb access: double, oob 1",
1710 .insns = {
1711 BPF_MOV64_IMM(BPF_REG_0, 0),
1712 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1713 offsetof(struct __sk_buff, cb[4])),
1714 BPF_EXIT_INSN(),
1715 },
1716 .errstr = "invalid bpf_context access",
1717 .result = REJECT,
1718 },
1719 {
1720 "check cb access: double, oob 2",
1721 .insns = {
1722 BPF_MOV64_IMM(BPF_REG_0, 0),
1723 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1,
1724 offsetof(struct __sk_buff, cb[4])),
1725 BPF_EXIT_INSN(),
1726 },
1727 .errstr = "invalid bpf_context access",
1728 .result = REJECT,
1729 },
1730 {
1731 "check __sk_buff->ifindex dw store not permitted",
1732 .insns = {
1733 BPF_MOV64_IMM(BPF_REG_0, 0),
1734 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1735 offsetof(struct __sk_buff, ifindex)),
1736 BPF_EXIT_INSN(),
1737 },
1738 .errstr = "invalid bpf_context access",
1739 .result = REJECT,
1740 },
1741 {
1742 "check __sk_buff->ifindex dw load not permitted",
1743 .insns = {
1744 BPF_MOV64_IMM(BPF_REG_0, 0),
1745 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1,
1746 offsetof(struct __sk_buff, ifindex)),
1747 BPF_EXIT_INSN(),
1748 },
1749 .errstr = "invalid bpf_context access",
1750 .result = REJECT,
1751 },
1752 {
1753 "check cb access: double, wrong type",
1754 .insns = {
1755 BPF_MOV64_IMM(BPF_REG_0, 0),
1756 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
1757 offsetof(struct __sk_buff, cb[0])),
1758 BPF_EXIT_INSN(),
1759 },
1760 .errstr = "invalid bpf_context access",
1761 .result = REJECT,
1762 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
1763 },
1764 {
1765 "check out of range skb->cb access",
1766 .insns = {
1767 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1768 offsetof(struct __sk_buff, cb[0]) + 256),
1769 BPF_EXIT_INSN(),
1770 },
1771 .errstr = "invalid bpf_context access",
1772 .errstr_unpriv = "",
1773 .result = REJECT,
1774 .prog_type = BPF_PROG_TYPE_SCHED_ACT,
1775 },
1776 {
1777 "write skb fields from socket prog",
1778 .insns = {
1779 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1780 offsetof(struct __sk_buff, cb[4])),
1781 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 1),
1782 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1783 offsetof(struct __sk_buff, mark)),
1784 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1785 offsetof(struct __sk_buff, tc_index)),
1786 BPF_JMP_IMM(BPF_JGE, BPF_REG_0, 0, 1),
1787 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
1788 offsetof(struct __sk_buff, cb[0])),
1789 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
1790 offsetof(struct __sk_buff, cb[2])),
1791 BPF_EXIT_INSN(),
1792 },
1793 .result = ACCEPT,
1794 .errstr_unpriv = "R1 leaks addr",
1795 .result_unpriv = REJECT,
1796 },
1797 {
1798 "write skb fields from tc_cls_act prog",
1799 .insns = {
1800 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1801 offsetof(struct __sk_buff, cb[0])),
1802 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1803 offsetof(struct __sk_buff, mark)),
1804 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
1805 offsetof(struct __sk_buff, tc_index)),
1806 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1807 offsetof(struct __sk_buff, tc_index)),
1808 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_0,
1809 offsetof(struct __sk_buff, cb[3])),
1810 BPF_EXIT_INSN(),
1811 },
1812 .errstr_unpriv = "",
1813 .result_unpriv = REJECT,
1814 .result = ACCEPT,
1815 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
1816 },
1817 {
1818 "PTR_TO_STACK store/load",
1819 .insns = {
1820 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1821 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -10),
1822 BPF_ST_MEM(BPF_DW, BPF_REG_1, 2, 0xfaceb00c),
1823 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 2),
1824 BPF_EXIT_INSN(),
1825 },
1826 .result = ACCEPT,
1827 },
1828 {
1829 "PTR_TO_STACK store/load - bad alignment on off",
1830 .insns = {
1831 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1832 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
1833 BPF_ST_MEM(BPF_DW, BPF_REG_1, 2, 0xfaceb00c),
1834 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 2),
1835 BPF_EXIT_INSN(),
1836 },
1837 .result = REJECT,
1838 .errstr = "misaligned stack access off (0x0; 0x0)+-8+2 size 8",
1839 },
1840 {
1841 "PTR_TO_STACK store/load - bad alignment on reg",
1842 .insns = {
1843 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1844 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -10),
1845 BPF_ST_MEM(BPF_DW, BPF_REG_1, 8, 0xfaceb00c),
1846 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 8),
1847 BPF_EXIT_INSN(),
1848 },
1849 .result = REJECT,
1850 .errstr = "misaligned stack access off (0x0; 0x0)+-10+8 size 8",
1851 },
1852 {
1853 "PTR_TO_STACK store/load - out of bounds low",
1854 .insns = {
1855 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1856 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -80000),
1857 BPF_ST_MEM(BPF_DW, BPF_REG_1, 8, 0xfaceb00c),
1858 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 8),
1859 BPF_EXIT_INSN(),
1860 },
1861 .result = REJECT,
1862 .errstr = "invalid stack off=-79992 size=8",
1863 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
1864 },
1865 {
1866 "PTR_TO_STACK store/load - out of bounds high",
1867 .insns = {
1868 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1869 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
1870 BPF_ST_MEM(BPF_DW, BPF_REG_1, 8, 0xfaceb00c),
1871 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 8),
1872 BPF_EXIT_INSN(),
1873 },
1874 .result = REJECT,
1875 .errstr = "invalid stack off=0 size=8",
1876 },
1877 {
1878 "unpriv: return pointer",
1879 .insns = {
1880 BPF_MOV64_REG(BPF_REG_0, BPF_REG_10),
1881 BPF_EXIT_INSN(),
1882 },
1883 .result = ACCEPT,
1884 .result_unpriv = REJECT,
1885 .errstr_unpriv = "R0 leaks addr",
1886 },
1887 {
1888 "unpriv: add const to pointer",
1889 .insns = {
1890 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
1891 BPF_MOV64_IMM(BPF_REG_0, 0),
1892 BPF_EXIT_INSN(),
1893 },
1894 .result = ACCEPT,
1895 },
1896 {
1897 "unpriv: add pointer to pointer",
1898 .insns = {
1899 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_10),
1900 BPF_MOV64_IMM(BPF_REG_0, 0),
1901 BPF_EXIT_INSN(),
1902 },
1903 .result = REJECT,
1904 .errstr = "R1 pointer += pointer",
1905 },
1906 {
1907 "unpriv: neg pointer",
1908 .insns = {
1909 BPF_ALU64_IMM(BPF_NEG, BPF_REG_1, 0),
1910 BPF_MOV64_IMM(BPF_REG_0, 0),
1911 BPF_EXIT_INSN(),
1912 },
1913 .result = ACCEPT,
1914 .result_unpriv = REJECT,
1915 .errstr_unpriv = "R1 pointer arithmetic",
1916 },
1917 {
1918 "unpriv: cmp pointer with const",
1919 .insns = {
1920 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 0),
1921 BPF_MOV64_IMM(BPF_REG_0, 0),
1922 BPF_EXIT_INSN(),
1923 },
1924 .result = ACCEPT,
1925 .result_unpriv = REJECT,
1926 .errstr_unpriv = "R1 pointer comparison",
1927 },
1928 {
1929 "unpriv: cmp pointer with pointer",
1930 .insns = {
1931 BPF_JMP_REG(BPF_JEQ, BPF_REG_1, BPF_REG_10, 0),
1932 BPF_MOV64_IMM(BPF_REG_0, 0),
1933 BPF_EXIT_INSN(),
1934 },
1935 .result = ACCEPT,
1936 .result_unpriv = REJECT,
1937 .errstr_unpriv = "R10 pointer comparison",
1938 },
1939 {
1940 "unpriv: check that printk is disallowed",
1941 .insns = {
1942 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
1943 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
1944 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
1945 BPF_MOV64_IMM(BPF_REG_2, 8),
1946 BPF_MOV64_REG(BPF_REG_3, BPF_REG_1),
1947 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
1948 BPF_FUNC_trace_printk),
1949 BPF_MOV64_IMM(BPF_REG_0, 0),
1950 BPF_EXIT_INSN(),
1951 },
1952 .errstr_unpriv = "unknown func bpf_trace_printk#6",
1953 .result_unpriv = REJECT,
1954 .result = ACCEPT,
1955 },
1956 {
1957 "unpriv: pass pointer to helper function",
1958 .insns = {
1959 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
1960 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
1961 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
1962 BPF_LD_MAP_FD(BPF_REG_1, 0),
1963 BPF_MOV64_REG(BPF_REG_3, BPF_REG_2),
1964 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
1965 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
1966 BPF_FUNC_map_update_elem),
1967 BPF_MOV64_IMM(BPF_REG_0, 0),
1968 BPF_EXIT_INSN(),
1969 },
1970 .fixup_map1 = { 3 },
1971 .errstr_unpriv = "R4 leaks addr",
1972 .result_unpriv = REJECT,
1973 .result = ACCEPT,
1974 },
1975 {
1976 "unpriv: indirectly pass pointer on stack to helper function",
1977 .insns = {
1978 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_10, -8),
1979 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
1980 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
1981 BPF_LD_MAP_FD(BPF_REG_1, 0),
1982 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
1983 BPF_FUNC_map_lookup_elem),
1984 BPF_MOV64_IMM(BPF_REG_0, 0),
1985 BPF_EXIT_INSN(),
1986 },
1987 .fixup_map1 = { 3 },
1988 .errstr = "invalid indirect read from stack off -8+0 size 8",
1989 .result = REJECT,
1990 },
1991 {
1992 "unpriv: mangle pointer on stack 1",
1993 .insns = {
1994 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_10, -8),
1995 BPF_ST_MEM(BPF_W, BPF_REG_10, -8, 0),
1996 BPF_MOV64_IMM(BPF_REG_0, 0),
1997 BPF_EXIT_INSN(),
1998 },
1999 .errstr_unpriv = "attempt to corrupt spilled",
2000 .result_unpriv = REJECT,
2001 .result = ACCEPT,
2002 },
2003 {
2004 "unpriv: mangle pointer on stack 2",
2005 .insns = {
2006 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_10, -8),
2007 BPF_ST_MEM(BPF_B, BPF_REG_10, -1, 0),
2008 BPF_MOV64_IMM(BPF_REG_0, 0),
2009 BPF_EXIT_INSN(),
2010 },
2011 .errstr_unpriv = "attempt to corrupt spilled",
2012 .result_unpriv = REJECT,
2013 .result = ACCEPT,
2014 },
2015 {
2016 "unpriv: read pointer from stack in small chunks",
2017 .insns = {
2018 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_10, -8),
2019 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_10, -8),
2020 BPF_MOV64_IMM(BPF_REG_0, 0),
2021 BPF_EXIT_INSN(),
2022 },
2023 .errstr = "invalid size",
2024 .result = REJECT,
2025 },
2026 {
2027 "unpriv: write pointer into ctx",
2028 .insns = {
2029 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_1, 0),
2030 BPF_MOV64_IMM(BPF_REG_0, 0),
2031 BPF_EXIT_INSN(),
2032 },
2033 .errstr_unpriv = "R1 leaks addr",
2034 .result_unpriv = REJECT,
2035 .errstr = "invalid bpf_context access",
2036 .result = REJECT,
2037 },
2038 {
2039 "unpriv: spill/fill of ctx",
2040 .insns = {
2041 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2042 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2043 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2044 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2045 BPF_MOV64_IMM(BPF_REG_0, 0),
2046 BPF_EXIT_INSN(),
2047 },
2048 .result = ACCEPT,
2049 },
2050 {
2051 "unpriv: spill/fill of ctx 2",
2052 .insns = {
2053 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2054 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2055 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2056 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2057 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2058 BPF_FUNC_get_hash_recalc),
2059 BPF_EXIT_INSN(),
2060 },
2061 .result = ACCEPT,
2062 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2063 },
2064 {
2065 "unpriv: spill/fill of ctx 3",
2066 .insns = {
2067 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2068 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2069 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2070 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_10, 0),
2071 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2072 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2073 BPF_FUNC_get_hash_recalc),
2074 BPF_EXIT_INSN(),
2075 },
2076 .result = REJECT,
2077 .errstr = "R1 type=fp expected=ctx",
2078 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2079 },
2080 {
2081 "unpriv: spill/fill of ctx 4",
2082 .insns = {
2083 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2084 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2085 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2086 BPF_MOV64_IMM(BPF_REG_0, 1),
2087 BPF_RAW_INSN(BPF_STX | BPF_XADD | BPF_DW, BPF_REG_10,
2088 BPF_REG_0, -8, 0),
2089 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2090 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2091 BPF_FUNC_get_hash_recalc),
2092 BPF_EXIT_INSN(),
2093 },
2094 .result = REJECT,
2095 .errstr = "R1 type=inv expected=ctx",
2096 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2097 },
2098 {
2099 "unpriv: spill/fill of different pointers stx",
2100 .insns = {
2101 BPF_MOV64_IMM(BPF_REG_3, 42),
2102 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2103 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2104 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 3),
2105 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
2106 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -16),
2107 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_2, 0),
2108 BPF_JMP_IMM(BPF_JNE, BPF_REG_1, 0, 1),
2109 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2110 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2111 BPF_STX_MEM(BPF_W, BPF_REG_1, BPF_REG_3,
2112 offsetof(struct __sk_buff, mark)),
2113 BPF_MOV64_IMM(BPF_REG_0, 0),
2114 BPF_EXIT_INSN(),
2115 },
2116 .result = REJECT,
2117 .errstr = "same insn cannot be used with different pointers",
2118 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2119 },
2120 {
2121 "unpriv: spill/fill of different pointers ldx",
2122 .insns = {
2123 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2124 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2125 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 3),
2126 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
2127 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2,
2128 -(__s32)offsetof(struct bpf_perf_event_data,
2129 sample_period) - 8),
2130 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_2, 0),
2131 BPF_JMP_IMM(BPF_JNE, BPF_REG_1, 0, 1),
2132 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2133 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_6, 0),
2134 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_1,
2135 offsetof(struct bpf_perf_event_data,
2136 sample_period)),
2137 BPF_MOV64_IMM(BPF_REG_0, 0),
2138 BPF_EXIT_INSN(),
2139 },
2140 .result = REJECT,
2141 .errstr = "same insn cannot be used with different pointers",
2142 .prog_type = BPF_PROG_TYPE_PERF_EVENT,
2143 },
2144 {
2145 "unpriv: write pointer into map elem value",
2146 .insns = {
2147 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
2148 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
2149 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
2150 BPF_LD_MAP_FD(BPF_REG_1, 0),
2151 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2152 BPF_FUNC_map_lookup_elem),
2153 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
2154 BPF_STX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 0),
2155 BPF_EXIT_INSN(),
2156 },
2157 .fixup_map1 = { 3 },
2158 .errstr_unpriv = "R0 leaks addr",
2159 .result_unpriv = REJECT,
2160 .result = ACCEPT,
2161 },
2162 {
2163 "alu32: mov u32 const",
2164 .insns = {
2165 BPF_MOV32_IMM(BPF_REG_7, 0),
2166 BPF_ALU32_IMM(BPF_AND, BPF_REG_7, 1),
2167 BPF_MOV32_REG(BPF_REG_0, BPF_REG_7),
2168 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
2169 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_7, 0),
2170 BPF_EXIT_INSN(),
2171 },
2172 .result = ACCEPT,
2173 },
2174 {
2175 "unpriv: partial copy of pointer",
2176 .insns = {
2177 BPF_MOV32_REG(BPF_REG_1, BPF_REG_10),
2178 BPF_MOV64_IMM(BPF_REG_0, 0),
2179 BPF_EXIT_INSN(),
2180 },
2181 .errstr_unpriv = "R10 partial copy",
2182 .result_unpriv = REJECT,
2183 .result = ACCEPT,
2184 },
2185 {
2186 "unpriv: pass pointer to tail_call",
2187 .insns = {
2188 BPF_MOV64_REG(BPF_REG_3, BPF_REG_1),
2189 BPF_LD_MAP_FD(BPF_REG_2, 0),
2190 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2191 BPF_FUNC_tail_call),
2192 BPF_MOV64_IMM(BPF_REG_0, 0),
2193 BPF_EXIT_INSN(),
2194 },
2195 .fixup_prog = { 1 },
2196 .errstr_unpriv = "R3 leaks addr into helper",
2197 .result_unpriv = REJECT,
2198 .result = ACCEPT,
2199 },
2200 {
2201 "unpriv: cmp map pointer with zero",
2202 .insns = {
2203 BPF_MOV64_IMM(BPF_REG_1, 0),
2204 BPF_LD_MAP_FD(BPF_REG_1, 0),
2205 BPF_JMP_IMM(BPF_JEQ, BPF_REG_1, 0, 0),
2206 BPF_MOV64_IMM(BPF_REG_0, 0),
2207 BPF_EXIT_INSN(),
2208 },
2209 .fixup_map1 = { 1 },
2210 .errstr_unpriv = "R1 pointer comparison",
2211 .result_unpriv = REJECT,
2212 .result = ACCEPT,
2213 },
2214 {
2215 "unpriv: write into frame pointer",
2216 .insns = {
2217 BPF_MOV64_REG(BPF_REG_10, BPF_REG_1),
2218 BPF_MOV64_IMM(BPF_REG_0, 0),
2219 BPF_EXIT_INSN(),
2220 },
2221 .errstr = "frame pointer is read only",
2222 .result = REJECT,
2223 },
2224 {
2225 "unpriv: spill/fill frame pointer",
2226 .insns = {
2227 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2228 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2229 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_10, 0),
2230 BPF_LDX_MEM(BPF_DW, BPF_REG_10, BPF_REG_6, 0),
2231 BPF_MOV64_IMM(BPF_REG_0, 0),
2232 BPF_EXIT_INSN(),
2233 },
2234 .errstr = "frame pointer is read only",
2235 .result = REJECT,
2236 },
2237 {
2238 "unpriv: cmp of frame pointer",
2239 .insns = {
2240 BPF_JMP_IMM(BPF_JEQ, BPF_REG_10, 0, 0),
2241 BPF_MOV64_IMM(BPF_REG_0, 0),
2242 BPF_EXIT_INSN(),
2243 },
2244 .errstr_unpriv = "R10 pointer comparison",
2245 .result_unpriv = REJECT,
2246 .result = ACCEPT,
2247 },
2248 {
2249 "unpriv: adding of fp",
2250 .insns = {
2251 BPF_MOV64_IMM(BPF_REG_0, 0),
2252 BPF_MOV64_IMM(BPF_REG_1, 0),
2253 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_10),
2254 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, -8),
2255 BPF_EXIT_INSN(),
2256 },
2257 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2258 .result_unpriv = REJECT,
2259 .result = ACCEPT,
2260 },
2261 {
2262 "unpriv: cmp of stack pointer",
2263 .insns = {
2264 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
2265 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
2266 BPF_JMP_IMM(BPF_JEQ, BPF_REG_2, 0, 0),
2267 BPF_MOV64_IMM(BPF_REG_0, 0),
2268 BPF_EXIT_INSN(),
2269 },
2270 .errstr_unpriv = "R2 pointer comparison",
2271 .result_unpriv = REJECT,
2272 .result = ACCEPT,
2273 },
2274 {
2275 "runtime/jit: pass negative index to tail_call",
2276 .insns = {
2277 BPF_MOV64_IMM(BPF_REG_3, -1),
2278 BPF_LD_MAP_FD(BPF_REG_2, 0),
2279 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2280 BPF_FUNC_tail_call),
2281 BPF_MOV64_IMM(BPF_REG_0, 0),
2282 BPF_EXIT_INSN(),
2283 },
2284 .fixup_prog = { 1 },
2285 .result = ACCEPT,
2286 },
2287 {
2288 "runtime/jit: pass > 32bit index to tail_call",
2289 .insns = {
2290 BPF_LD_IMM64(BPF_REG_3, 0x100000000ULL),
2291 BPF_LD_MAP_FD(BPF_REG_2, 0),
2292 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2293 BPF_FUNC_tail_call),
2294 BPF_MOV64_IMM(BPF_REG_0, 0),
2295 BPF_EXIT_INSN(),
2296 },
2297 .fixup_prog = { 2 },
2298 .result = ACCEPT,
2299 },
2300 {
2301 "PTR_TO_STACK check high 1",
2302 .insns = {
2303 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2304 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -1),
2305 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2306 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2307 BPF_EXIT_INSN(),
2308 },
2309 .result = ACCEPT,
2310 },
2311 {
2312 "PTR_TO_STACK check high 2",
2313 .insns = {
2314 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2315 BPF_ST_MEM(BPF_B, BPF_REG_1, -1, 42),
2316 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, -1),
2317 BPF_EXIT_INSN(),
2318 },
2319 .result = ACCEPT,
2320 },
2321 {
2322 "PTR_TO_STACK check high 3",
2323 .insns = {
2324 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2325 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0),
2326 BPF_ST_MEM(BPF_B, BPF_REG_1, -1, 42),
2327 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, -1),
2328 BPF_EXIT_INSN(),
2329 },
2330 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2331 .result_unpriv = REJECT,
2332 .result = ACCEPT,
2333 },
2334 {
2335 "PTR_TO_STACK check high 4",
2336 .insns = {
2337 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2338 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0),
2339 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2340 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2341 BPF_EXIT_INSN(),
2342 },
2343 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2344 .errstr = "invalid stack off=0 size=1",
2345 .result = REJECT,
2346 },
2347 {
2348 "PTR_TO_STACK check high 5",
2349 .insns = {
2350 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2351 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1),
2352 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2353 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2354 BPF_EXIT_INSN(),
2355 },
2356 .result = REJECT,
2357 .errstr = "invalid stack off",
2358 },
2359 {
2360 "PTR_TO_STACK check high 6",
2361 .insns = {
2362 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2363 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1),
2364 BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MAX, 42),
2365 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MAX),
2366 BPF_EXIT_INSN(),
2367 },
2368 .result = REJECT,
2369 .errstr = "invalid stack off",
2370 },
2371 {
2372 "PTR_TO_STACK check high 7",
2373 .insns = {
2374 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2375 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1),
2376 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1),
2377 BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MAX, 42),
2378 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MAX),
2379 BPF_EXIT_INSN(),
2380 },
2381 .result = REJECT,
2382 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2383 .errstr = "fp pointer offset",
2384 },
2385 {
2386 "PTR_TO_STACK check low 1",
2387 .insns = {
2388 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2389 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -512),
2390 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2391 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2392 BPF_EXIT_INSN(),
2393 },
2394 .result = ACCEPT,
2395 },
2396 {
2397 "PTR_TO_STACK check low 2",
2398 .insns = {
2399 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2400 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -513),
2401 BPF_ST_MEM(BPF_B, BPF_REG_1, 1, 42),
2402 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 1),
2403 BPF_EXIT_INSN(),
2404 },
2405 .result_unpriv = REJECT,
2406 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2407 .result = ACCEPT,
2408 },
2409 {
2410 "PTR_TO_STACK check low 3",
2411 .insns = {
2412 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2413 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -513),
2414 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2415 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2416 BPF_EXIT_INSN(),
2417 },
2418 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2419 .errstr = "invalid stack off=-513 size=1",
2420 .result = REJECT,
2421 },
2422 {
2423 "PTR_TO_STACK check low 4",
2424 .insns = {
2425 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2426 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, INT_MIN),
2427 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2428 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2429 BPF_EXIT_INSN(),
2430 },
2431 .result = REJECT,
2432 .errstr = "math between fp pointer",
2433 },
2434 {
2435 "PTR_TO_STACK check low 5",
2436 .insns = {
2437 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2438 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)),
2439 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2440 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2441 BPF_EXIT_INSN(),
2442 },
2443 .result = REJECT,
2444 .errstr = "invalid stack off",
2445 },
2446 {
2447 "PTR_TO_STACK check low 6",
2448 .insns = {
2449 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2450 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)),
2451 BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MIN, 42),
2452 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MIN),
2453 BPF_EXIT_INSN(),
2454 },
2455 .result = REJECT,
2456 .errstr = "invalid stack off",
2457 },
2458 {
2459 "PTR_TO_STACK check low 7",
2460 .insns = {
2461 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2462 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)),
2463 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)),
2464 BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MIN, 42),
2465 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MIN),
2466 BPF_EXIT_INSN(),
2467 },
2468 .result = REJECT,
2469 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
2470 .errstr = "fp pointer offset",
2471 },
2472 {
2473 "PTR_TO_STACK mixed reg/k, 1",
2474 .insns = {
2475 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2476 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3),
2477 BPF_MOV64_IMM(BPF_REG_2, -3),
2478 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
2479 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2480 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2481 BPF_EXIT_INSN(),
2482 },
2483 .result = ACCEPT,
2484 },
2485 {
2486 "PTR_TO_STACK mixed reg/k, 2",
2487 .insns = {
2488 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
2489 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, 0),
2490 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2491 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3),
2492 BPF_MOV64_IMM(BPF_REG_2, -3),
2493 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
2494 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2495 BPF_MOV64_REG(BPF_REG_5, BPF_REG_10),
2496 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_5, -6),
2497 BPF_EXIT_INSN(),
2498 },
2499 .result = ACCEPT,
2500 },
2501 {
2502 "PTR_TO_STACK mixed reg/k, 3",
2503 .insns = {
2504 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2505 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3),
2506 BPF_MOV64_IMM(BPF_REG_2, -3),
2507 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
2508 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2509 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
2510 BPF_EXIT_INSN(),
2511 },
2512 .result = ACCEPT,
2513 },
2514 {
2515 "PTR_TO_STACK reg",
2516 .insns = {
2517 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
2518 BPF_MOV64_IMM(BPF_REG_2, -3),
2519 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
2520 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42),
2521 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0),
2522 BPF_EXIT_INSN(),
2523 },
2524 .result_unpriv = REJECT,
2525 .errstr_unpriv = "invalid stack off=0 size=1",
2526 .result = ACCEPT,
2527 },
2528 {
2529 "stack pointer arithmetic",
2530 .insns = {
2531 BPF_MOV64_IMM(BPF_REG_1, 4),
2532 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
2533 BPF_MOV64_REG(BPF_REG_7, BPF_REG_10),
2534 BPF_ALU64_IMM(BPF_ADD, BPF_REG_7, -10),
2535 BPF_ALU64_IMM(BPF_ADD, BPF_REG_7, -10),
2536 BPF_MOV64_REG(BPF_REG_2, BPF_REG_7),
2537 BPF_ALU64_REG(BPF_ADD, BPF_REG_2, BPF_REG_1),
2538 BPF_ST_MEM(0, BPF_REG_2, 4, 0),
2539 BPF_MOV64_REG(BPF_REG_2, BPF_REG_7),
2540 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 8),
2541 BPF_ST_MEM(0, BPF_REG_2, 4, 0),
2542 BPF_MOV64_IMM(BPF_REG_0, 0),
2543 BPF_EXIT_INSN(),
2544 },
2545 .result = ACCEPT,
2546 },
2547 {
2548 "raw_stack: no skb_load_bytes",
2549 .insns = {
2550 BPF_MOV64_IMM(BPF_REG_2, 4),
2551 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2552 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2553 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2554 BPF_MOV64_IMM(BPF_REG_4, 8),
2555 /* Call to skb_load_bytes() omitted. */
2556 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2557 BPF_EXIT_INSN(),
2558 },
2559 .result = REJECT,
2560 .errstr = "invalid read from stack off -8+0 size 8",
2561 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2562 },
2563 {
2564 "raw_stack: skb_load_bytes, negative len",
2565 .insns = {
2566 BPF_MOV64_IMM(BPF_REG_2, 4),
2567 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2568 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2569 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2570 BPF_MOV64_IMM(BPF_REG_4, -8),
2571 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2572 BPF_FUNC_skb_load_bytes),
2573 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2574 BPF_EXIT_INSN(),
2575 },
2576 .result = REJECT,
2577 .errstr = "R4 min value is negative",
2578 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2579 },
2580 {
2581 "raw_stack: skb_load_bytes, negative len 2",
2582 .insns = {
2583 BPF_MOV64_IMM(BPF_REG_2, 4),
2584 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2585 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2586 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2587 BPF_MOV64_IMM(BPF_REG_4, ~0),
2588 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2589 BPF_FUNC_skb_load_bytes),
2590 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2591 BPF_EXIT_INSN(),
2592 },
2593 .result = REJECT,
2594 .errstr = "R4 min value is negative",
2595 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2596 },
2597 {
2598 "raw_stack: skb_load_bytes, zero len",
2599 .insns = {
2600 BPF_MOV64_IMM(BPF_REG_2, 4),
2601 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2602 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2603 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2604 BPF_MOV64_IMM(BPF_REG_4, 0),
2605 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2606 BPF_FUNC_skb_load_bytes),
2607 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2608 BPF_EXIT_INSN(),
2609 },
2610 .result = REJECT,
2611 .errstr = "invalid stack type R3",
2612 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2613 },
2614 {
2615 "raw_stack: skb_load_bytes, no init",
2616 .insns = {
2617 BPF_MOV64_IMM(BPF_REG_2, 4),
2618 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2619 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2620 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2621 BPF_MOV64_IMM(BPF_REG_4, 8),
2622 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2623 BPF_FUNC_skb_load_bytes),
2624 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2625 BPF_EXIT_INSN(),
2626 },
2627 .result = ACCEPT,
2628 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2629 },
2630 {
2631 "raw_stack: skb_load_bytes, init",
2632 .insns = {
2633 BPF_MOV64_IMM(BPF_REG_2, 4),
2634 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2635 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2636 BPF_ST_MEM(BPF_DW, BPF_REG_6, 0, 0xcafe),
2637 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2638 BPF_MOV64_IMM(BPF_REG_4, 8),
2639 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2640 BPF_FUNC_skb_load_bytes),
2641 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2642 BPF_EXIT_INSN(),
2643 },
2644 .result = ACCEPT,
2645 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2646 },
2647 {
2648 "raw_stack: skb_load_bytes, spilled regs around bounds",
2649 .insns = {
2650 BPF_MOV64_IMM(BPF_REG_2, 4),
2651 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2652 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -16),
2653 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, -8),
2654 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 8),
2655 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2656 BPF_MOV64_IMM(BPF_REG_4, 8),
2657 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2658 BPF_FUNC_skb_load_bytes),
2659 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, -8),
2660 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_6, 8),
2661 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
2662 offsetof(struct __sk_buff, mark)),
2663 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_2,
2664 offsetof(struct __sk_buff, priority)),
2665 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
2666 BPF_EXIT_INSN(),
2667 },
2668 .result = ACCEPT,
2669 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2670 },
2671 {
2672 "raw_stack: skb_load_bytes, spilled regs corruption",
2673 .insns = {
2674 BPF_MOV64_IMM(BPF_REG_2, 4),
2675 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2676 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -8),
2677 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2678 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2679 BPF_MOV64_IMM(BPF_REG_4, 8),
2680 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2681 BPF_FUNC_skb_load_bytes),
2682 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2683 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
2684 offsetof(struct __sk_buff, mark)),
2685 BPF_EXIT_INSN(),
2686 },
2687 .result = REJECT,
2688 .errstr = "R0 invalid mem access 'inv'",
2689 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2690 },
2691 {
2692 "raw_stack: skb_load_bytes, spilled regs corruption 2",
2693 .insns = {
2694 BPF_MOV64_IMM(BPF_REG_2, 4),
2695 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2696 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -16),
2697 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, -8),
2698 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2699 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 8),
2700 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2701 BPF_MOV64_IMM(BPF_REG_4, 8),
2702 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2703 BPF_FUNC_skb_load_bytes),
2704 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, -8),
2705 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_6, 8),
2706 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_6, 0),
2707 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
2708 offsetof(struct __sk_buff, mark)),
2709 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_2,
2710 offsetof(struct __sk_buff, priority)),
2711 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
2712 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_3,
2713 offsetof(struct __sk_buff, pkt_type)),
2714 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_3),
2715 BPF_EXIT_INSN(),
2716 },
2717 .result = REJECT,
2718 .errstr = "R3 invalid mem access 'inv'",
2719 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2720 },
2721 {
2722 "raw_stack: skb_load_bytes, spilled regs + data",
2723 .insns = {
2724 BPF_MOV64_IMM(BPF_REG_2, 4),
2725 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2726 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -16),
2727 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, -8),
2728 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 0),
2729 BPF_STX_MEM(BPF_DW, BPF_REG_6, BPF_REG_1, 8),
2730 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2731 BPF_MOV64_IMM(BPF_REG_4, 8),
2732 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2733 BPF_FUNC_skb_load_bytes),
2734 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, -8),
2735 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_6, 8),
2736 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_6, 0),
2737 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
2738 offsetof(struct __sk_buff, mark)),
2739 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_2,
2740 offsetof(struct __sk_buff, priority)),
2741 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
2742 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_3),
2743 BPF_EXIT_INSN(),
2744 },
2745 .result = ACCEPT,
2746 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2747 },
2748 {
2749 "raw_stack: skb_load_bytes, invalid access 1",
2750 .insns = {
2751 BPF_MOV64_IMM(BPF_REG_2, 4),
2752 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2753 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -513),
2754 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2755 BPF_MOV64_IMM(BPF_REG_4, 8),
2756 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2757 BPF_FUNC_skb_load_bytes),
2758 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2759 BPF_EXIT_INSN(),
2760 },
2761 .result = REJECT,
2762 .errstr = "invalid stack type R3 off=-513 access_size=8",
2763 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2764 },
2765 {
2766 "raw_stack: skb_load_bytes, invalid access 2",
2767 .insns = {
2768 BPF_MOV64_IMM(BPF_REG_2, 4),
2769 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2770 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -1),
2771 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2772 BPF_MOV64_IMM(BPF_REG_4, 8),
2773 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2774 BPF_FUNC_skb_load_bytes),
2775 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2776 BPF_EXIT_INSN(),
2777 },
2778 .result = REJECT,
2779 .errstr = "invalid stack type R3 off=-1 access_size=8",
2780 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2781 },
2782 {
2783 "raw_stack: skb_load_bytes, invalid access 3",
2784 .insns = {
2785 BPF_MOV64_IMM(BPF_REG_2, 4),
2786 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2787 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 0xffffffff),
2788 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2789 BPF_MOV64_IMM(BPF_REG_4, 0xffffffff),
2790 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2791 BPF_FUNC_skb_load_bytes),
2792 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2793 BPF_EXIT_INSN(),
2794 },
2795 .result = REJECT,
2796 .errstr = "R4 min value is negative",
2797 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2798 },
2799 {
2800 "raw_stack: skb_load_bytes, invalid access 4",
2801 .insns = {
2802 BPF_MOV64_IMM(BPF_REG_2, 4),
2803 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2804 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -1),
2805 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2806 BPF_MOV64_IMM(BPF_REG_4, 0x7fffffff),
2807 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2808 BPF_FUNC_skb_load_bytes),
2809 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2810 BPF_EXIT_INSN(),
2811 },
2812 .result = REJECT,
2813 .errstr = "R4 unbounded memory access, use 'var &= const' or 'if (var < const)'",
2814 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2815 },
2816 {
2817 "raw_stack: skb_load_bytes, invalid access 5",
2818 .insns = {
2819 BPF_MOV64_IMM(BPF_REG_2, 4),
2820 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2821 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -512),
2822 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2823 BPF_MOV64_IMM(BPF_REG_4, 0x7fffffff),
2824 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2825 BPF_FUNC_skb_load_bytes),
2826 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2827 BPF_EXIT_INSN(),
2828 },
2829 .result = REJECT,
2830 .errstr = "R4 unbounded memory access, use 'var &= const' or 'if (var < const)'",
2831 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2832 },
2833 {
2834 "raw_stack: skb_load_bytes, invalid access 6",
2835 .insns = {
2836 BPF_MOV64_IMM(BPF_REG_2, 4),
2837 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2838 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -512),
2839 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2840 BPF_MOV64_IMM(BPF_REG_4, 0),
2841 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2842 BPF_FUNC_skb_load_bytes),
2843 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2844 BPF_EXIT_INSN(),
2845 },
2846 .result = REJECT,
2847 .errstr = "invalid stack type R3 off=-512 access_size=0",
2848 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2849 },
2850 {
2851 "raw_stack: skb_load_bytes, large access",
2852 .insns = {
2853 BPF_MOV64_IMM(BPF_REG_2, 4),
2854 BPF_ALU64_REG(BPF_MOV, BPF_REG_6, BPF_REG_10),
2855 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, -512),
2856 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
2857 BPF_MOV64_IMM(BPF_REG_4, 512),
2858 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
2859 BPF_FUNC_skb_load_bytes),
2860 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
2861 BPF_EXIT_INSN(),
2862 },
2863 .result = ACCEPT,
2864 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2865 },
2866 {
2867 "context stores via ST",
2868 .insns = {
2869 BPF_MOV64_IMM(BPF_REG_0, 0),
2870 BPF_ST_MEM(BPF_DW, BPF_REG_1, offsetof(struct __sk_buff, mark), 0),
2871 BPF_EXIT_INSN(),
2872 },
2873 .errstr = "BPF_ST stores into R1 context is not allowed",
2874 .result = REJECT,
2875 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2876 },
2877 {
2878 "context stores via XADD",
2879 .insns = {
2880 BPF_MOV64_IMM(BPF_REG_0, 0),
2881 BPF_RAW_INSN(BPF_STX | BPF_XADD | BPF_W, BPF_REG_1,
2882 BPF_REG_0, offsetof(struct __sk_buff, mark), 0),
2883 BPF_EXIT_INSN(),
2884 },
2885 .errstr = "BPF_XADD stores into R1 context is not allowed",
2886 .result = REJECT,
2887 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2888 },
2889 {
2890 "direct packet access: test1",
2891 .insns = {
2892 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2893 offsetof(struct __sk_buff, data)),
2894 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2895 offsetof(struct __sk_buff, data_end)),
2896 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
2897 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
2898 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
2899 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
2900 BPF_MOV64_IMM(BPF_REG_0, 0),
2901 BPF_EXIT_INSN(),
2902 },
2903 .result = ACCEPT,
2904 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2905 },
2906 {
2907 "direct packet access: test2",
2908 .insns = {
2909 BPF_MOV64_IMM(BPF_REG_0, 1),
2910 BPF_LDX_MEM(BPF_W, BPF_REG_4, BPF_REG_1,
2911 offsetof(struct __sk_buff, data_end)),
2912 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2913 offsetof(struct __sk_buff, data)),
2914 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
2915 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 14),
2916 BPF_JMP_REG(BPF_JGT, BPF_REG_5, BPF_REG_4, 15),
2917 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_3, 7),
2918 BPF_LDX_MEM(BPF_B, BPF_REG_4, BPF_REG_3, 12),
2919 BPF_ALU64_IMM(BPF_MUL, BPF_REG_4, 14),
2920 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2921 offsetof(struct __sk_buff, data)),
2922 BPF_ALU64_REG(BPF_ADD, BPF_REG_3, BPF_REG_4),
2923 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2924 offsetof(struct __sk_buff, len)),
2925 BPF_ALU64_IMM(BPF_LSH, BPF_REG_2, 49),
2926 BPF_ALU64_IMM(BPF_RSH, BPF_REG_2, 49),
2927 BPF_ALU64_REG(BPF_ADD, BPF_REG_3, BPF_REG_2),
2928 BPF_MOV64_REG(BPF_REG_2, BPF_REG_3),
2929 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 8),
2930 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_1,
2931 offsetof(struct __sk_buff, data_end)),
2932 BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_1, 1),
2933 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_3, 4),
2934 BPF_MOV64_IMM(BPF_REG_0, 0),
2935 BPF_EXIT_INSN(),
2936 },
2937 .result = ACCEPT,
2938 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2939 },
2940 {
2941 "direct packet access: test3",
2942 .insns = {
2943 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2944 offsetof(struct __sk_buff, data)),
2945 BPF_MOV64_IMM(BPF_REG_0, 0),
2946 BPF_EXIT_INSN(),
2947 },
2948 .errstr = "invalid bpf_context access off=76",
2949 .result = REJECT,
2950 .prog_type = BPF_PROG_TYPE_SOCKET_FILTER,
2951 },
2952 {
2953 "direct packet access: test4 (write)",
2954 .insns = {
2955 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2956 offsetof(struct __sk_buff, data)),
2957 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2958 offsetof(struct __sk_buff, data_end)),
2959 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
2960 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
2961 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
2962 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
2963 BPF_MOV64_IMM(BPF_REG_0, 0),
2964 BPF_EXIT_INSN(),
2965 },
2966 .result = ACCEPT,
2967 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2968 },
2969 {
2970 "direct packet access: test5 (pkt_end >= reg, good access)",
2971 .insns = {
2972 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2973 offsetof(struct __sk_buff, data)),
2974 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2975 offsetof(struct __sk_buff, data_end)),
2976 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
2977 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
2978 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_0, 2),
2979 BPF_MOV64_IMM(BPF_REG_0, 1),
2980 BPF_EXIT_INSN(),
2981 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
2982 BPF_MOV64_IMM(BPF_REG_0, 0),
2983 BPF_EXIT_INSN(),
2984 },
2985 .result = ACCEPT,
2986 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
2987 },
2988 {
2989 "direct packet access: test6 (pkt_end >= reg, bad access)",
2990 .insns = {
2991 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
2992 offsetof(struct __sk_buff, data)),
2993 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
2994 offsetof(struct __sk_buff, data_end)),
2995 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
2996 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
2997 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_0, 3),
2998 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
2999 BPF_MOV64_IMM(BPF_REG_0, 1),
3000 BPF_EXIT_INSN(),
3001 BPF_MOV64_IMM(BPF_REG_0, 0),
3002 BPF_EXIT_INSN(),
3003 },
3004 .errstr = "invalid access to packet",
3005 .result = REJECT,
3006 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3007 },
3008 {
3009 "direct packet access: test7 (pkt_end >= reg, both accesses)",
3010 .insns = {
3011 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3012 offsetof(struct __sk_buff, data)),
3013 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3014 offsetof(struct __sk_buff, data_end)),
3015 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3016 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3017 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_0, 3),
3018 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3019 BPF_MOV64_IMM(BPF_REG_0, 1),
3020 BPF_EXIT_INSN(),
3021 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3022 BPF_MOV64_IMM(BPF_REG_0, 0),
3023 BPF_EXIT_INSN(),
3024 },
3025 .errstr = "invalid access to packet",
3026 .result = REJECT,
3027 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3028 },
3029 {
3030 "direct packet access: test8 (double test, variant 1)",
3031 .insns = {
3032 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3033 offsetof(struct __sk_buff, data)),
3034 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3035 offsetof(struct __sk_buff, data_end)),
3036 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3037 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3038 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_0, 4),
3039 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3040 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3041 BPF_MOV64_IMM(BPF_REG_0, 1),
3042 BPF_EXIT_INSN(),
3043 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3044 BPF_MOV64_IMM(BPF_REG_0, 0),
3045 BPF_EXIT_INSN(),
3046 },
3047 .result = ACCEPT,
3048 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3049 },
3050 {
3051 "direct packet access: test9 (double test, variant 2)",
3052 .insns = {
3053 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3054 offsetof(struct __sk_buff, data)),
3055 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3056 offsetof(struct __sk_buff, data_end)),
3057 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3058 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3059 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_0, 2),
3060 BPF_MOV64_IMM(BPF_REG_0, 1),
3061 BPF_EXIT_INSN(),
3062 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3063 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3064 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3065 BPF_MOV64_IMM(BPF_REG_0, 0),
3066 BPF_EXIT_INSN(),
3067 },
3068 .result = ACCEPT,
3069 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3070 },
3071 {
3072 "direct packet access: test10 (write invalid)",
3073 .insns = {
3074 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3075 offsetof(struct __sk_buff, data)),
3076 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3077 offsetof(struct __sk_buff, data_end)),
3078 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3079 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3080 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 2),
3081 BPF_MOV64_IMM(BPF_REG_0, 0),
3082 BPF_EXIT_INSN(),
3083 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
3084 BPF_MOV64_IMM(BPF_REG_0, 0),
3085 BPF_EXIT_INSN(),
3086 },
3087 .errstr = "invalid access to packet",
3088 .result = REJECT,
3089 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3090 },
3091 {
3092 "direct packet access: test11 (shift, good access)",
3093 .insns = {
3094 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3095 offsetof(struct __sk_buff, data)),
3096 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3097 offsetof(struct __sk_buff, data_end)),
3098 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3099 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 22),
3100 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 8),
3101 BPF_MOV64_IMM(BPF_REG_3, 144),
3102 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
3103 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 23),
3104 BPF_ALU64_IMM(BPF_RSH, BPF_REG_5, 3),
3105 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
3106 BPF_ALU64_REG(BPF_ADD, BPF_REG_6, BPF_REG_5),
3107 BPF_MOV64_IMM(BPF_REG_0, 1),
3108 BPF_EXIT_INSN(),
3109 BPF_MOV64_IMM(BPF_REG_0, 0),
3110 BPF_EXIT_INSN(),
3111 },
3112 .result = ACCEPT,
3113 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3114 },
3115 {
3116 "direct packet access: test12 (and, good access)",
3117 .insns = {
3118 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3119 offsetof(struct __sk_buff, data)),
3120 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3121 offsetof(struct __sk_buff, data_end)),
3122 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3123 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 22),
3124 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 8),
3125 BPF_MOV64_IMM(BPF_REG_3, 144),
3126 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
3127 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 23),
3128 BPF_ALU64_IMM(BPF_AND, BPF_REG_5, 15),
3129 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
3130 BPF_ALU64_REG(BPF_ADD, BPF_REG_6, BPF_REG_5),
3131 BPF_MOV64_IMM(BPF_REG_0, 1),
3132 BPF_EXIT_INSN(),
3133 BPF_MOV64_IMM(BPF_REG_0, 0),
3134 BPF_EXIT_INSN(),
3135 },
3136 .result = ACCEPT,
3137 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3138 },
3139 {
3140 "direct packet access: test13 (branches, good access)",
3141 .insns = {
3142 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3143 offsetof(struct __sk_buff, data)),
3144 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3145 offsetof(struct __sk_buff, data_end)),
3146 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3147 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 22),
3148 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 13),
3149 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3150 offsetof(struct __sk_buff, mark)),
3151 BPF_MOV64_IMM(BPF_REG_4, 1),
3152 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_4, 2),
3153 BPF_MOV64_IMM(BPF_REG_3, 14),
3154 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
3155 BPF_MOV64_IMM(BPF_REG_3, 24),
3156 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
3157 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 23),
3158 BPF_ALU64_IMM(BPF_AND, BPF_REG_5, 15),
3159 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
3160 BPF_ALU64_REG(BPF_ADD, BPF_REG_6, BPF_REG_5),
3161 BPF_MOV64_IMM(BPF_REG_0, 1),
3162 BPF_EXIT_INSN(),
3163 BPF_MOV64_IMM(BPF_REG_0, 0),
3164 BPF_EXIT_INSN(),
3165 },
3166 .result = ACCEPT,
3167 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3168 },
3169 {
3170 "direct packet access: test14 (pkt_ptr += 0, CONST_IMM, good access)",
3171 .insns = {
3172 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3173 offsetof(struct __sk_buff, data)),
3174 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3175 offsetof(struct __sk_buff, data_end)),
3176 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3177 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 22),
3178 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 7),
3179 BPF_MOV64_IMM(BPF_REG_5, 12),
3180 BPF_ALU64_IMM(BPF_RSH, BPF_REG_5, 4),
3181 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
3182 BPF_ALU64_REG(BPF_ADD, BPF_REG_6, BPF_REG_5),
3183 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_6, 0),
3184 BPF_MOV64_IMM(BPF_REG_0, 1),
3185 BPF_EXIT_INSN(),
3186 BPF_MOV64_IMM(BPF_REG_0, 0),
3187 BPF_EXIT_INSN(),
3188 },
3189 .result = ACCEPT,
3190 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3191 },
3192 {
3193 "direct packet access: test15 (spill with xadd)",
3194 .insns = {
3195 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3196 offsetof(struct __sk_buff, data)),
3197 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3198 offsetof(struct __sk_buff, data_end)),
3199 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3200 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3201 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 8),
3202 BPF_MOV64_IMM(BPF_REG_5, 4096),
3203 BPF_MOV64_REG(BPF_REG_4, BPF_REG_10),
3204 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, -8),
3205 BPF_STX_MEM(BPF_DW, BPF_REG_4, BPF_REG_2, 0),
3206 BPF_STX_XADD(BPF_DW, BPF_REG_4, BPF_REG_5, 0),
3207 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_4, 0),
3208 BPF_STX_MEM(BPF_W, BPF_REG_2, BPF_REG_5, 0),
3209 BPF_MOV64_IMM(BPF_REG_0, 0),
3210 BPF_EXIT_INSN(),
3211 },
3212 .errstr = "R2 invalid mem access 'inv'",
3213 .result = REJECT,
3214 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3215 },
3216 {
3217 "direct packet access: test16 (arith on data_end)",
3218 .insns = {
3219 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3220 offsetof(struct __sk_buff, data)),
3221 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3222 offsetof(struct __sk_buff, data_end)),
3223 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3224 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3225 BPF_ALU64_IMM(BPF_ADD, BPF_REG_3, 16),
3226 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3227 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
3228 BPF_MOV64_IMM(BPF_REG_0, 0),
3229 BPF_EXIT_INSN(),
3230 },
3231 .errstr = "R3 pointer arithmetic on PTR_TO_PACKET_END",
3232 .result = REJECT,
3233 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3234 },
3235 {
3236 "direct packet access: test17 (pruning, alignment)",
3237 .insns = {
3238 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3239 offsetof(struct __sk_buff, data)),
3240 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3241 offsetof(struct __sk_buff, data_end)),
3242 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3243 offsetof(struct __sk_buff, mark)),
3244 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3245 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 14),
3246 BPF_JMP_IMM(BPF_JGT, BPF_REG_7, 1, 4),
3247 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3248 BPF_STX_MEM(BPF_W, BPF_REG_0, BPF_REG_0, -4),
3249 BPF_MOV64_IMM(BPF_REG_0, 0),
3250 BPF_EXIT_INSN(),
3251 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 1),
3252 BPF_JMP_A(-6),
3253 },
3254 .errstr = "misaligned packet access off 2+(0x0; 0x0)+15+-4 size 4",
3255 .result = REJECT,
3256 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3257 .flags = F_LOAD_WITH_STRICT_ALIGNMENT,
3258 },
3259 {
3260 "direct packet access: test18 (imm += pkt_ptr, 1)",
3261 .insns = {
3262 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3263 offsetof(struct __sk_buff, data)),
3264 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3265 offsetof(struct __sk_buff, data_end)),
3266 BPF_MOV64_IMM(BPF_REG_0, 8),
3267 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
3268 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3269 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
3270 BPF_MOV64_IMM(BPF_REG_0, 0),
3271 BPF_EXIT_INSN(),
3272 },
3273 .result = ACCEPT,
3274 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3275 },
3276 {
3277 "direct packet access: test19 (imm += pkt_ptr, 2)",
3278 .insns = {
3279 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3280 offsetof(struct __sk_buff, data)),
3281 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3282 offsetof(struct __sk_buff, data_end)),
3283 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3284 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3285 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 3),
3286 BPF_MOV64_IMM(BPF_REG_4, 4),
3287 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_2),
3288 BPF_STX_MEM(BPF_B, BPF_REG_4, BPF_REG_4, 0),
3289 BPF_MOV64_IMM(BPF_REG_0, 0),
3290 BPF_EXIT_INSN(),
3291 },
3292 .result = ACCEPT,
3293 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3294 },
3295 {
3296 "direct packet access: test20 (x += pkt_ptr, 1)",
3297 .insns = {
3298 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3299 offsetof(struct __sk_buff, data)),
3300 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3301 offsetof(struct __sk_buff, data_end)),
3302 BPF_MOV64_IMM(BPF_REG_0, 0xffffffff),
3303 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
3304 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
3305 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 0x7fff),
3306 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
3307 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_2),
3308 BPF_MOV64_REG(BPF_REG_5, BPF_REG_4),
3309 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 0x7fff - 1),
3310 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
3311 BPF_STX_MEM(BPF_DW, BPF_REG_5, BPF_REG_4, 0),
3312 BPF_MOV64_IMM(BPF_REG_0, 0),
3313 BPF_EXIT_INSN(),
3314 },
3315 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3316 .result = ACCEPT,
3317 },
3318 {
3319 "direct packet access: test21 (x += pkt_ptr, 2)",
3320 .insns = {
3321 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3322 offsetof(struct __sk_buff, data)),
3323 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3324 offsetof(struct __sk_buff, data_end)),
3325 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3326 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3327 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 9),
3328 BPF_MOV64_IMM(BPF_REG_4, 0xffffffff),
3329 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_4, -8),
3330 BPF_LDX_MEM(BPF_DW, BPF_REG_4, BPF_REG_10, -8),
3331 BPF_ALU64_IMM(BPF_AND, BPF_REG_4, 0x7fff),
3332 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_2),
3333 BPF_MOV64_REG(BPF_REG_5, BPF_REG_4),
3334 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 0x7fff - 1),
3335 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
3336 BPF_STX_MEM(BPF_DW, BPF_REG_5, BPF_REG_4, 0),
3337 BPF_MOV64_IMM(BPF_REG_0, 0),
3338 BPF_EXIT_INSN(),
3339 },
3340 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3341 .result = ACCEPT,
3342 },
3343 {
3344 "direct packet access: test22 (x += pkt_ptr, 3)",
3345 .insns = {
3346 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3347 offsetof(struct __sk_buff, data)),
3348 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3349 offsetof(struct __sk_buff, data_end)),
3350 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3351 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3352 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -8),
3353 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_3, -16),
3354 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_10, -16),
3355 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 11),
3356 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -8),
3357 BPF_MOV64_IMM(BPF_REG_4, 0xffffffff),
3358 BPF_STX_XADD(BPF_DW, BPF_REG_10, BPF_REG_4, -8),
3359 BPF_LDX_MEM(BPF_DW, BPF_REG_4, BPF_REG_10, -8),
3360 BPF_ALU64_IMM(BPF_RSH, BPF_REG_4, 49),
3361 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_2),
3362 BPF_MOV64_REG(BPF_REG_0, BPF_REG_4),
3363 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 2),
3364 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 2),
3365 BPF_MOV64_IMM(BPF_REG_2, 1),
3366 BPF_STX_MEM(BPF_H, BPF_REG_4, BPF_REG_2, 0),
3367 BPF_MOV64_IMM(BPF_REG_0, 0),
3368 BPF_EXIT_INSN(),
3369 },
3370 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3371 .result = ACCEPT,
3372 },
3373 {
3374 "direct packet access: test23 (x += pkt_ptr, 4)",
3375 .insns = {
3376 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3377 offsetof(struct __sk_buff, data)),
3378 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3379 offsetof(struct __sk_buff, data_end)),
3380 BPF_MOV64_IMM(BPF_REG_0, 0xffffffff),
3381 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
3382 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
3383 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 0xffff),
3384 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
3385 BPF_MOV64_IMM(BPF_REG_0, 31),
3386 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_4),
3387 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
3388 BPF_MOV64_REG(BPF_REG_5, BPF_REG_0),
3389 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0xffff - 1),
3390 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3391 BPF_STX_MEM(BPF_DW, BPF_REG_5, BPF_REG_0, 0),
3392 BPF_MOV64_IMM(BPF_REG_0, 0),
3393 BPF_EXIT_INSN(),
3394 },
3395 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3396 .result = REJECT,
3397 .errstr = "invalid access to packet, off=0 size=8, R5(id=1,off=0,r=0)",
3398 },
3399 {
3400 "direct packet access: test24 (x += pkt_ptr, 5)",
3401 .insns = {
3402 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3403 offsetof(struct __sk_buff, data)),
3404 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3405 offsetof(struct __sk_buff, data_end)),
3406 BPF_MOV64_IMM(BPF_REG_0, 0xffffffff),
3407 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
3408 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
3409 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 0xff),
3410 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
3411 BPF_MOV64_IMM(BPF_REG_0, 64),
3412 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_4),
3413 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
3414 BPF_MOV64_REG(BPF_REG_5, BPF_REG_0),
3415 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0x7fff - 1),
3416 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
3417 BPF_STX_MEM(BPF_DW, BPF_REG_5, BPF_REG_0, 0),
3418 BPF_MOV64_IMM(BPF_REG_0, 0),
3419 BPF_EXIT_INSN(),
3420 },
3421 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3422 .result = ACCEPT,
3423 },
3424 {
3425 "direct packet access: test25 (marking on <, good access)",
3426 .insns = {
3427 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3428 offsetof(struct __sk_buff, data)),
3429 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3430 offsetof(struct __sk_buff, data_end)),
3431 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3432 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3433 BPF_JMP_REG(BPF_JLT, BPF_REG_0, BPF_REG_3, 2),
3434 BPF_MOV64_IMM(BPF_REG_0, 0),
3435 BPF_EXIT_INSN(),
3436 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3437 BPF_JMP_IMM(BPF_JA, 0, 0, -4),
3438 },
3439 .result = ACCEPT,
3440 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3441 },
3442 {
3443 "direct packet access: test26 (marking on <, bad access)",
3444 .insns = {
3445 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3446 offsetof(struct __sk_buff, data)),
3447 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3448 offsetof(struct __sk_buff, data_end)),
3449 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3450 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3451 BPF_JMP_REG(BPF_JLT, BPF_REG_0, BPF_REG_3, 3),
3452 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3453 BPF_MOV64_IMM(BPF_REG_0, 0),
3454 BPF_EXIT_INSN(),
3455 BPF_JMP_IMM(BPF_JA, 0, 0, -3),
3456 },
3457 .result = REJECT,
3458 .errstr = "invalid access to packet",
3459 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3460 },
3461 {
3462 "direct packet access: test27 (marking on <=, good access)",
3463 .insns = {
3464 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3465 offsetof(struct __sk_buff, data)),
3466 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3467 offsetof(struct __sk_buff, data_end)),
3468 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3469 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3470 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_0, 1),
3471 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3472 BPF_MOV64_IMM(BPF_REG_0, 1),
3473 BPF_EXIT_INSN(),
3474 },
3475 .result = ACCEPT,
3476 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3477 },
3478 {
3479 "direct packet access: test28 (marking on <=, bad access)",
3480 .insns = {
3481 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3482 offsetof(struct __sk_buff, data)),
3483 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3484 offsetof(struct __sk_buff, data_end)),
3485 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
3486 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
3487 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_0, 2),
3488 BPF_MOV64_IMM(BPF_REG_0, 1),
3489 BPF_EXIT_INSN(),
3490 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
3491 BPF_JMP_IMM(BPF_JA, 0, 0, -4),
3492 },
3493 .result = REJECT,
3494 .errstr = "invalid access to packet",
3495 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3496 },
3497 {
3498 "helper access to packet: test1, valid packet_ptr range",
3499 .insns = {
3500 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3501 offsetof(struct xdp_md, data)),
3502 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3503 offsetof(struct xdp_md, data_end)),
3504 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
3505 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
3506 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 5),
3507 BPF_LD_MAP_FD(BPF_REG_1, 0),
3508 BPF_MOV64_REG(BPF_REG_3, BPF_REG_2),
3509 BPF_MOV64_IMM(BPF_REG_4, 0),
3510 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3511 BPF_FUNC_map_update_elem),
3512 BPF_MOV64_IMM(BPF_REG_0, 0),
3513 BPF_EXIT_INSN(),
3514 },
3515 .fixup_map1 = { 5 },
3516 .result_unpriv = ACCEPT,
3517 .result = ACCEPT,
3518 .prog_type = BPF_PROG_TYPE_XDP,
3519 },
3520 {
3521 "helper access to packet: test2, unchecked packet_ptr",
3522 .insns = {
3523 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3524 offsetof(struct xdp_md, data)),
3525 BPF_LD_MAP_FD(BPF_REG_1, 0),
3526 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3527 BPF_FUNC_map_lookup_elem),
3528 BPF_MOV64_IMM(BPF_REG_0, 0),
3529 BPF_EXIT_INSN(),
3530 },
3531 .fixup_map1 = { 1 },
3532 .result = REJECT,
3533 .errstr = "invalid access to packet",
3534 .prog_type = BPF_PROG_TYPE_XDP,
3535 },
3536 {
3537 "helper access to packet: test3, variable add",
3538 .insns = {
3539 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3540 offsetof(struct xdp_md, data)),
3541 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3542 offsetof(struct xdp_md, data_end)),
3543 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3544 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 8),
3545 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 10),
3546 BPF_LDX_MEM(BPF_B, BPF_REG_5, BPF_REG_2, 0),
3547 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3548 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_5),
3549 BPF_MOV64_REG(BPF_REG_5, BPF_REG_4),
3550 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 8),
3551 BPF_JMP_REG(BPF_JGT, BPF_REG_5, BPF_REG_3, 4),
3552 BPF_LD_MAP_FD(BPF_REG_1, 0),
3553 BPF_MOV64_REG(BPF_REG_2, BPF_REG_4),
3554 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3555 BPF_FUNC_map_lookup_elem),
3556 BPF_MOV64_IMM(BPF_REG_0, 0),
3557 BPF_EXIT_INSN(),
3558 },
3559 .fixup_map1 = { 11 },
3560 .result = ACCEPT,
3561 .prog_type = BPF_PROG_TYPE_XDP,
3562 },
3563 {
3564 "helper access to packet: test4, packet_ptr with bad range",
3565 .insns = {
3566 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3567 offsetof(struct xdp_md, data)),
3568 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3569 offsetof(struct xdp_md, data_end)),
3570 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3571 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 4),
3572 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 2),
3573 BPF_MOV64_IMM(BPF_REG_0, 0),
3574 BPF_EXIT_INSN(),
3575 BPF_LD_MAP_FD(BPF_REG_1, 0),
3576 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3577 BPF_FUNC_map_lookup_elem),
3578 BPF_MOV64_IMM(BPF_REG_0, 0),
3579 BPF_EXIT_INSN(),
3580 },
3581 .fixup_map1 = { 7 },
3582 .result = REJECT,
3583 .errstr = "invalid access to packet",
3584 .prog_type = BPF_PROG_TYPE_XDP,
3585 },
3586 {
3587 "helper access to packet: test5, packet_ptr with too short range",
3588 .insns = {
3589 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3590 offsetof(struct xdp_md, data)),
3591 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3592 offsetof(struct xdp_md, data_end)),
3593 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
3594 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3595 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 7),
3596 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 3),
3597 BPF_LD_MAP_FD(BPF_REG_1, 0),
3598 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3599 BPF_FUNC_map_lookup_elem),
3600 BPF_MOV64_IMM(BPF_REG_0, 0),
3601 BPF_EXIT_INSN(),
3602 },
3603 .fixup_map1 = { 6 },
3604 .result = REJECT,
3605 .errstr = "invalid access to packet",
3606 .prog_type = BPF_PROG_TYPE_XDP,
3607 },
3608 {
3609 "helper access to packet: test6, cls valid packet_ptr range",
3610 .insns = {
3611 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3612 offsetof(struct __sk_buff, data)),
3613 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3614 offsetof(struct __sk_buff, data_end)),
3615 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
3616 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
3617 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 5),
3618 BPF_LD_MAP_FD(BPF_REG_1, 0),
3619 BPF_MOV64_REG(BPF_REG_3, BPF_REG_2),
3620 BPF_MOV64_IMM(BPF_REG_4, 0),
3621 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3622 BPF_FUNC_map_update_elem),
3623 BPF_MOV64_IMM(BPF_REG_0, 0),
3624 BPF_EXIT_INSN(),
3625 },
3626 .fixup_map1 = { 5 },
3627 .result = ACCEPT,
3628 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3629 },
3630 {
3631 "helper access to packet: test7, cls unchecked packet_ptr",
3632 .insns = {
3633 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3634 offsetof(struct __sk_buff, data)),
3635 BPF_LD_MAP_FD(BPF_REG_1, 0),
3636 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3637 BPF_FUNC_map_lookup_elem),
3638 BPF_MOV64_IMM(BPF_REG_0, 0),
3639 BPF_EXIT_INSN(),
3640 },
3641 .fixup_map1 = { 1 },
3642 .result = REJECT,
3643 .errstr = "invalid access to packet",
3644 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3645 },
3646 {
3647 "helper access to packet: test8, cls variable add",
3648 .insns = {
3649 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3650 offsetof(struct __sk_buff, data)),
3651 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3652 offsetof(struct __sk_buff, data_end)),
3653 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3654 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 8),
3655 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 10),
3656 BPF_LDX_MEM(BPF_B, BPF_REG_5, BPF_REG_2, 0),
3657 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3658 BPF_ALU64_REG(BPF_ADD, BPF_REG_4, BPF_REG_5),
3659 BPF_MOV64_REG(BPF_REG_5, BPF_REG_4),
3660 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 8),
3661 BPF_JMP_REG(BPF_JGT, BPF_REG_5, BPF_REG_3, 4),
3662 BPF_LD_MAP_FD(BPF_REG_1, 0),
3663 BPF_MOV64_REG(BPF_REG_2, BPF_REG_4),
3664 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3665 BPF_FUNC_map_lookup_elem),
3666 BPF_MOV64_IMM(BPF_REG_0, 0),
3667 BPF_EXIT_INSN(),
3668 },
3669 .fixup_map1 = { 11 },
3670 .result = ACCEPT,
3671 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3672 },
3673 {
3674 "helper access to packet: test9, cls packet_ptr with bad range",
3675 .insns = {
3676 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3677 offsetof(struct __sk_buff, data)),
3678 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3679 offsetof(struct __sk_buff, data_end)),
3680 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3681 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 4),
3682 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 2),
3683 BPF_MOV64_IMM(BPF_REG_0, 0),
3684 BPF_EXIT_INSN(),
3685 BPF_LD_MAP_FD(BPF_REG_1, 0),
3686 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3687 BPF_FUNC_map_lookup_elem),
3688 BPF_MOV64_IMM(BPF_REG_0, 0),
3689 BPF_EXIT_INSN(),
3690 },
3691 .fixup_map1 = { 7 },
3692 .result = REJECT,
3693 .errstr = "invalid access to packet",
3694 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3695 },
3696 {
3697 "helper access to packet: test10, cls packet_ptr with too short range",
3698 .insns = {
3699 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
3700 offsetof(struct __sk_buff, data)),
3701 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
3702 offsetof(struct __sk_buff, data_end)),
3703 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
3704 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
3705 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 7),
3706 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 3),
3707 BPF_LD_MAP_FD(BPF_REG_1, 0),
3708 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3709 BPF_FUNC_map_lookup_elem),
3710 BPF_MOV64_IMM(BPF_REG_0, 0),
3711 BPF_EXIT_INSN(),
3712 },
3713 .fixup_map1 = { 6 },
3714 .result = REJECT,
3715 .errstr = "invalid access to packet",
3716 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3717 },
3718 {
3719 "helper access to packet: test11, cls unsuitable helper 1",
3720 .insns = {
3721 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3722 offsetof(struct __sk_buff, data)),
3723 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3724 offsetof(struct __sk_buff, data_end)),
3725 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3726 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
3727 BPF_ALU64_IMM(BPF_ADD, BPF_REG_3, 7),
3728 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_7, 4),
3729 BPF_MOV64_IMM(BPF_REG_2, 0),
3730 BPF_MOV64_IMM(BPF_REG_4, 42),
3731 BPF_MOV64_IMM(BPF_REG_5, 0),
3732 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3733 BPF_FUNC_skb_store_bytes),
3734 BPF_MOV64_IMM(BPF_REG_0, 0),
3735 BPF_EXIT_INSN(),
3736 },
3737 .result = REJECT,
3738 .errstr = "helper access to the packet",
3739 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3740 },
3741 {
3742 "helper access to packet: test12, cls unsuitable helper 2",
3743 .insns = {
3744 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3745 offsetof(struct __sk_buff, data)),
3746 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3747 offsetof(struct __sk_buff, data_end)),
3748 BPF_MOV64_REG(BPF_REG_3, BPF_REG_6),
3749 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 8),
3750 BPF_JMP_REG(BPF_JGT, BPF_REG_6, BPF_REG_7, 3),
3751 BPF_MOV64_IMM(BPF_REG_2, 0),
3752 BPF_MOV64_IMM(BPF_REG_4, 4),
3753 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3754 BPF_FUNC_skb_load_bytes),
3755 BPF_MOV64_IMM(BPF_REG_0, 0),
3756 BPF_EXIT_INSN(),
3757 },
3758 .result = REJECT,
3759 .errstr = "helper access to the packet",
3760 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3761 },
3762 {
3763 "helper access to packet: test13, cls helper ok",
3764 .insns = {
3765 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3766 offsetof(struct __sk_buff, data)),
3767 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3768 offsetof(struct __sk_buff, data_end)),
3769 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3770 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3771 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3772 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3773 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3774 BPF_MOV64_IMM(BPF_REG_2, 4),
3775 BPF_MOV64_IMM(BPF_REG_3, 0),
3776 BPF_MOV64_IMM(BPF_REG_4, 0),
3777 BPF_MOV64_IMM(BPF_REG_5, 0),
3778 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3779 BPF_FUNC_csum_diff),
3780 BPF_MOV64_IMM(BPF_REG_0, 0),
3781 BPF_EXIT_INSN(),
3782 },
3783 .result = ACCEPT,
3784 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3785 },
3786 {
3787 "helper access to packet: test14, cls helper ok sub",
3788 .insns = {
3789 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3790 offsetof(struct __sk_buff, data)),
3791 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3792 offsetof(struct __sk_buff, data_end)),
3793 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3794 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3795 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3796 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3797 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 4),
3798 BPF_MOV64_IMM(BPF_REG_2, 4),
3799 BPF_MOV64_IMM(BPF_REG_3, 0),
3800 BPF_MOV64_IMM(BPF_REG_4, 0),
3801 BPF_MOV64_IMM(BPF_REG_5, 0),
3802 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3803 BPF_FUNC_csum_diff),
3804 BPF_MOV64_IMM(BPF_REG_0, 0),
3805 BPF_EXIT_INSN(),
3806 },
3807 .result = ACCEPT,
3808 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3809 },
3810 {
3811 "helper access to packet: test15, cls helper fail sub",
3812 .insns = {
3813 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3814 offsetof(struct __sk_buff, data)),
3815 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3816 offsetof(struct __sk_buff, data_end)),
3817 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3818 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3819 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3820 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3821 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 12),
3822 BPF_MOV64_IMM(BPF_REG_2, 4),
3823 BPF_MOV64_IMM(BPF_REG_3, 0),
3824 BPF_MOV64_IMM(BPF_REG_4, 0),
3825 BPF_MOV64_IMM(BPF_REG_5, 0),
3826 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3827 BPF_FUNC_csum_diff),
3828 BPF_MOV64_IMM(BPF_REG_0, 0),
3829 BPF_EXIT_INSN(),
3830 },
3831 .result = REJECT,
3832 .errstr = "invalid access to packet",
3833 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3834 },
3835 {
3836 "helper access to packet: test16, cls helper fail range 1",
3837 .insns = {
3838 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3839 offsetof(struct __sk_buff, data)),
3840 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3841 offsetof(struct __sk_buff, data_end)),
3842 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3843 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3844 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3845 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3846 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3847 BPF_MOV64_IMM(BPF_REG_2, 8),
3848 BPF_MOV64_IMM(BPF_REG_3, 0),
3849 BPF_MOV64_IMM(BPF_REG_4, 0),
3850 BPF_MOV64_IMM(BPF_REG_5, 0),
3851 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3852 BPF_FUNC_csum_diff),
3853 BPF_MOV64_IMM(BPF_REG_0, 0),
3854 BPF_EXIT_INSN(),
3855 },
3856 .result = REJECT,
3857 .errstr = "invalid access to packet",
3858 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3859 },
3860 {
3861 "helper access to packet: test17, cls helper fail range 2",
3862 .insns = {
3863 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3864 offsetof(struct __sk_buff, data)),
3865 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3866 offsetof(struct __sk_buff, data_end)),
3867 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3868 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3869 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3870 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3871 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3872 BPF_MOV64_IMM(BPF_REG_2, -9),
3873 BPF_MOV64_IMM(BPF_REG_3, 0),
3874 BPF_MOV64_IMM(BPF_REG_4, 0),
3875 BPF_MOV64_IMM(BPF_REG_5, 0),
3876 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3877 BPF_FUNC_csum_diff),
3878 BPF_MOV64_IMM(BPF_REG_0, 0),
3879 BPF_EXIT_INSN(),
3880 },
3881 .result = REJECT,
3882 .errstr = "R2 min value is negative",
3883 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3884 },
3885 {
3886 "helper access to packet: test18, cls helper fail range 3",
3887 .insns = {
3888 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3889 offsetof(struct __sk_buff, data)),
3890 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3891 offsetof(struct __sk_buff, data_end)),
3892 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3893 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3894 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3895 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3896 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3897 BPF_MOV64_IMM(BPF_REG_2, ~0),
3898 BPF_MOV64_IMM(BPF_REG_3, 0),
3899 BPF_MOV64_IMM(BPF_REG_4, 0),
3900 BPF_MOV64_IMM(BPF_REG_5, 0),
3901 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3902 BPF_FUNC_csum_diff),
3903 BPF_MOV64_IMM(BPF_REG_0, 0),
3904 BPF_EXIT_INSN(),
3905 },
3906 .result = REJECT,
3907 .errstr = "R2 min value is negative",
3908 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3909 },
3910 {
3911 "helper access to packet: test19, cls helper range zero",
3912 .insns = {
3913 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3914 offsetof(struct __sk_buff, data)),
3915 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3916 offsetof(struct __sk_buff, data_end)),
3917 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3918 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3919 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3920 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3921 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3922 BPF_MOV64_IMM(BPF_REG_2, 0),
3923 BPF_MOV64_IMM(BPF_REG_3, 0),
3924 BPF_MOV64_IMM(BPF_REG_4, 0),
3925 BPF_MOV64_IMM(BPF_REG_5, 0),
3926 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3927 BPF_FUNC_csum_diff),
3928 BPF_MOV64_IMM(BPF_REG_0, 0),
3929 BPF_EXIT_INSN(),
3930 },
3931 .result = ACCEPT,
3932 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3933 },
3934 {
3935 "helper access to packet: test20, pkt end as input",
3936 .insns = {
3937 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3938 offsetof(struct __sk_buff, data)),
3939 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3940 offsetof(struct __sk_buff, data_end)),
3941 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3942 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3943 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3944 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3945 BPF_MOV64_REG(BPF_REG_1, BPF_REG_7),
3946 BPF_MOV64_IMM(BPF_REG_2, 4),
3947 BPF_MOV64_IMM(BPF_REG_3, 0),
3948 BPF_MOV64_IMM(BPF_REG_4, 0),
3949 BPF_MOV64_IMM(BPF_REG_5, 0),
3950 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3951 BPF_FUNC_csum_diff),
3952 BPF_MOV64_IMM(BPF_REG_0, 0),
3953 BPF_EXIT_INSN(),
3954 },
3955 .result = REJECT,
3956 .errstr = "R1 type=pkt_end expected=fp",
3957 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3958 },
3959 {
3960 "helper access to packet: test21, wrong reg",
3961 .insns = {
3962 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
3963 offsetof(struct __sk_buff, data)),
3964 BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_1,
3965 offsetof(struct __sk_buff, data_end)),
3966 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 1),
3967 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
3968 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 7),
3969 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_7, 6),
3970 BPF_MOV64_IMM(BPF_REG_2, 4),
3971 BPF_MOV64_IMM(BPF_REG_3, 0),
3972 BPF_MOV64_IMM(BPF_REG_4, 0),
3973 BPF_MOV64_IMM(BPF_REG_5, 0),
3974 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3975 BPF_FUNC_csum_diff),
3976 BPF_MOV64_IMM(BPF_REG_0, 0),
3977 BPF_EXIT_INSN(),
3978 },
3979 .result = REJECT,
3980 .errstr = "invalid access to packet",
3981 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
3982 },
3983 {
3984 "valid map access into an array with a constant",
3985 .insns = {
3986 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
3987 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
3988 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
3989 BPF_LD_MAP_FD(BPF_REG_1, 0),
3990 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
3991 BPF_FUNC_map_lookup_elem),
3992 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
3993 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
3994 offsetof(struct test_val, foo)),
3995 BPF_EXIT_INSN(),
3996 },
3997 .fixup_map2 = { 3 },
3998 .errstr_unpriv = "R0 leaks addr",
3999 .result_unpriv = REJECT,
4000 .result = ACCEPT,
4001 },
4002 {
4003 "valid map access into an array with a register",
4004 .insns = {
4005 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4006 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4007 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4008 BPF_LD_MAP_FD(BPF_REG_1, 0),
4009 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4010 BPF_FUNC_map_lookup_elem),
4011 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4012 BPF_MOV64_IMM(BPF_REG_1, 4),
4013 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
4014 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4015 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4016 offsetof(struct test_val, foo)),
4017 BPF_EXIT_INSN(),
4018 },
4019 .fixup_map2 = { 3 },
4020 .errstr_unpriv = "R0 leaks addr",
4021 .result_unpriv = REJECT,
4022 .result = ACCEPT,
4023 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4024 },
4025 {
4026 "valid map access into an array with a variable",
4027 .insns = {
4028 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4029 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4030 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4031 BPF_LD_MAP_FD(BPF_REG_1, 0),
4032 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4033 BPF_FUNC_map_lookup_elem),
4034 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4035 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
4036 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, MAX_ENTRIES, 3),
4037 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
4038 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4039 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4040 offsetof(struct test_val, foo)),
4041 BPF_EXIT_INSN(),
4042 },
4043 .fixup_map2 = { 3 },
4044 .errstr_unpriv = "R0 leaks addr",
4045 .result_unpriv = REJECT,
4046 .result = ACCEPT,
4047 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4048 },
4049 {
4050 "valid map access into an array with a signed variable",
4051 .insns = {
4052 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4053 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4054 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4055 BPF_LD_MAP_FD(BPF_REG_1, 0),
4056 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4057 BPF_FUNC_map_lookup_elem),
4058 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
4059 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
4060 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 0xffffffff, 1),
4061 BPF_MOV32_IMM(BPF_REG_1, 0),
4062 BPF_MOV32_IMM(BPF_REG_2, MAX_ENTRIES),
4063 BPF_JMP_REG(BPF_JSGT, BPF_REG_2, BPF_REG_1, 1),
4064 BPF_MOV32_IMM(BPF_REG_1, 0),
4065 BPF_ALU32_IMM(BPF_LSH, BPF_REG_1, 2),
4066 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4067 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4068 offsetof(struct test_val, foo)),
4069 BPF_EXIT_INSN(),
4070 },
4071 .fixup_map2 = { 3 },
4072 .errstr_unpriv = "R0 leaks addr",
4073 .result_unpriv = REJECT,
4074 .result = ACCEPT,
4075 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4076 },
4077 {
4078 "invalid map access into an array with a constant",
4079 .insns = {
4080 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4081 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4082 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4083 BPF_LD_MAP_FD(BPF_REG_1, 0),
4084 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4085 BPF_FUNC_map_lookup_elem),
4086 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4087 BPF_ST_MEM(BPF_DW, BPF_REG_0, (MAX_ENTRIES + 1) << 2,
4088 offsetof(struct test_val, foo)),
4089 BPF_EXIT_INSN(),
4090 },
4091 .fixup_map2 = { 3 },
4092 .errstr = "invalid access to map value, value_size=48 off=48 size=8",
4093 .result = REJECT,
4094 },
4095 {
4096 "invalid map access into an array with a register",
4097 .insns = {
4098 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4099 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4100 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4101 BPF_LD_MAP_FD(BPF_REG_1, 0),
4102 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4103 BPF_FUNC_map_lookup_elem),
4104 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4105 BPF_MOV64_IMM(BPF_REG_1, MAX_ENTRIES + 1),
4106 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
4107 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4108 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4109 offsetof(struct test_val, foo)),
4110 BPF_EXIT_INSN(),
4111 },
4112 .fixup_map2 = { 3 },
4113 .errstr = "R0 min value is outside of the array range",
4114 .result = REJECT,
4115 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4116 },
4117 {
4118 "invalid map access into an array with a variable",
4119 .insns = {
4120 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4121 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4122 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4123 BPF_LD_MAP_FD(BPF_REG_1, 0),
4124 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4125 BPF_FUNC_map_lookup_elem),
4126 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4127 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
4128 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
4129 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4130 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4131 offsetof(struct test_val, foo)),
4132 BPF_EXIT_INSN(),
4133 },
4134 .fixup_map2 = { 3 },
4135 .errstr = "R0 unbounded memory access, make sure to bounds check any array access into a map",
4136 .result = REJECT,
4137 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4138 },
4139 {
4140 "invalid map access into an array with no floor check",
4141 .insns = {
4142 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4143 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4144 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4145 BPF_LD_MAP_FD(BPF_REG_1, 0),
4146 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4147 BPF_FUNC_map_lookup_elem),
4148 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
4149 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
4150 BPF_MOV32_IMM(BPF_REG_2, MAX_ENTRIES),
4151 BPF_JMP_REG(BPF_JSGT, BPF_REG_2, BPF_REG_1, 1),
4152 BPF_MOV32_IMM(BPF_REG_1, 0),
4153 BPF_ALU32_IMM(BPF_LSH, BPF_REG_1, 2),
4154 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4155 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4156 offsetof(struct test_val, foo)),
4157 BPF_EXIT_INSN(),
4158 },
4159 .fixup_map2 = { 3 },
4160 .errstr_unpriv = "R0 leaks addr",
4161 .errstr = "R0 unbounded memory access",
4162 .result_unpriv = REJECT,
4163 .result = REJECT,
4164 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4165 },
4166 {
4167 "invalid map access into an array with a invalid max check",
4168 .insns = {
4169 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4170 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4171 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4172 BPF_LD_MAP_FD(BPF_REG_1, 0),
4173 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4174 BPF_FUNC_map_lookup_elem),
4175 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
4176 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
4177 BPF_MOV32_IMM(BPF_REG_2, MAX_ENTRIES + 1),
4178 BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_1, 1),
4179 BPF_MOV32_IMM(BPF_REG_1, 0),
4180 BPF_ALU32_IMM(BPF_LSH, BPF_REG_1, 2),
4181 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4182 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
4183 offsetof(struct test_val, foo)),
4184 BPF_EXIT_INSN(),
4185 },
4186 .fixup_map2 = { 3 },
4187 .errstr_unpriv = "R0 leaks addr",
4188 .errstr = "invalid access to map value, value_size=48 off=44 size=8",
4189 .result_unpriv = REJECT,
4190 .result = REJECT,
4191 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4192 },
4193 {
4194 "invalid map access into an array with a invalid max check",
4195 .insns = {
4196 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4197 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4198 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4199 BPF_LD_MAP_FD(BPF_REG_1, 0),
4200 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4201 BPF_FUNC_map_lookup_elem),
4202 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 10),
4203 BPF_MOV64_REG(BPF_REG_8, BPF_REG_0),
4204 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4205 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4206 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4207 BPF_LD_MAP_FD(BPF_REG_1, 0),
4208 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4209 BPF_FUNC_map_lookup_elem),
4210 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
4211 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_8),
4212 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0,
4213 offsetof(struct test_val, foo)),
4214 BPF_EXIT_INSN(),
4215 },
4216 .fixup_map2 = { 3, 11 },
4217 .errstr = "R0 pointer += pointer",
4218 .result = REJECT,
4219 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4220 },
4221 {
4222 "multiple registers share map_lookup_elem result",
4223 .insns = {
4224 BPF_MOV64_IMM(BPF_REG_1, 10),
4225 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4226 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4227 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4228 BPF_LD_MAP_FD(BPF_REG_1, 0),
4229 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4230 BPF_FUNC_map_lookup_elem),
4231 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4232 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4233 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4234 BPF_EXIT_INSN(),
4235 },
4236 .fixup_map1 = { 4 },
4237 .result = ACCEPT,
4238 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4239 },
4240 {
4241 "alu ops on ptr_to_map_value_or_null, 1",
4242 .insns = {
4243 BPF_MOV64_IMM(BPF_REG_1, 10),
4244 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4245 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4246 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4247 BPF_LD_MAP_FD(BPF_REG_1, 0),
4248 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4249 BPF_FUNC_map_lookup_elem),
4250 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4251 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, -2),
4252 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 2),
4253 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4254 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4255 BPF_EXIT_INSN(),
4256 },
4257 .fixup_map1 = { 4 },
4258 .errstr = "R4 pointer arithmetic on PTR_TO_MAP_VALUE_OR_NULL",
4259 .result = REJECT,
4260 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4261 },
4262 {
4263 "alu ops on ptr_to_map_value_or_null, 2",
4264 .insns = {
4265 BPF_MOV64_IMM(BPF_REG_1, 10),
4266 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4267 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4268 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4269 BPF_LD_MAP_FD(BPF_REG_1, 0),
4270 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4271 BPF_FUNC_map_lookup_elem),
4272 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4273 BPF_ALU64_IMM(BPF_AND, BPF_REG_4, -1),
4274 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4275 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4276 BPF_EXIT_INSN(),
4277 },
4278 .fixup_map1 = { 4 },
4279 .errstr = "R4 pointer arithmetic on PTR_TO_MAP_VALUE_OR_NULL",
4280 .result = REJECT,
4281 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4282 },
4283 {
4284 "alu ops on ptr_to_map_value_or_null, 3",
4285 .insns = {
4286 BPF_MOV64_IMM(BPF_REG_1, 10),
4287 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4288 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4289 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4290 BPF_LD_MAP_FD(BPF_REG_1, 0),
4291 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4292 BPF_FUNC_map_lookup_elem),
4293 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4294 BPF_ALU64_IMM(BPF_LSH, BPF_REG_4, 1),
4295 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4296 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4297 BPF_EXIT_INSN(),
4298 },
4299 .fixup_map1 = { 4 },
4300 .errstr = "R4 pointer arithmetic on PTR_TO_MAP_VALUE_OR_NULL",
4301 .result = REJECT,
4302 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4303 },
4304 {
4305 "invalid memory access with multiple map_lookup_elem calls",
4306 .insns = {
4307 BPF_MOV64_IMM(BPF_REG_1, 10),
4308 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4309 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4310 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4311 BPF_LD_MAP_FD(BPF_REG_1, 0),
4312 BPF_MOV64_REG(BPF_REG_8, BPF_REG_1),
4313 BPF_MOV64_REG(BPF_REG_7, BPF_REG_2),
4314 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4315 BPF_FUNC_map_lookup_elem),
4316 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4317 BPF_MOV64_REG(BPF_REG_1, BPF_REG_8),
4318 BPF_MOV64_REG(BPF_REG_2, BPF_REG_7),
4319 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4320 BPF_FUNC_map_lookup_elem),
4321 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4322 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4323 BPF_EXIT_INSN(),
4324 },
4325 .fixup_map1 = { 4 },
4326 .result = REJECT,
4327 .errstr = "R4 !read_ok",
4328 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4329 },
4330 {
4331 "valid indirect map_lookup_elem access with 2nd lookup in branch",
4332 .insns = {
4333 BPF_MOV64_IMM(BPF_REG_1, 10),
4334 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_1, -8),
4335 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4336 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4337 BPF_LD_MAP_FD(BPF_REG_1, 0),
4338 BPF_MOV64_REG(BPF_REG_8, BPF_REG_1),
4339 BPF_MOV64_REG(BPF_REG_7, BPF_REG_2),
4340 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4341 BPF_FUNC_map_lookup_elem),
4342 BPF_MOV64_IMM(BPF_REG_2, 10),
4343 BPF_JMP_IMM(BPF_JNE, BPF_REG_2, 0, 3),
4344 BPF_MOV64_REG(BPF_REG_1, BPF_REG_8),
4345 BPF_MOV64_REG(BPF_REG_2, BPF_REG_7),
4346 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4347 BPF_FUNC_map_lookup_elem),
4348 BPF_MOV64_REG(BPF_REG_4, BPF_REG_0),
4349 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
4350 BPF_ST_MEM(BPF_DW, BPF_REG_4, 0, 0),
4351 BPF_EXIT_INSN(),
4352 },
4353 .fixup_map1 = { 4 },
4354 .result = ACCEPT,
4355 .prog_type = BPF_PROG_TYPE_SCHED_CLS
4356 },
4357 {
4358 "invalid map access from else condition",
4359 .insns = {
4360 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4361 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4362 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4363 BPF_LD_MAP_FD(BPF_REG_1, 0),
4364 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, BPF_FUNC_map_lookup_elem),
4365 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
4366 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
4367 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, MAX_ENTRIES-1, 1),
4368 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 1),
4369 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
4370 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
4371 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, offsetof(struct test_val, foo)),
4372 BPF_EXIT_INSN(),
4373 },
4374 .fixup_map2 = { 3 },
4375 .errstr = "R0 unbounded memory access",
4376 .result = REJECT,
4377 .errstr_unpriv = "R0 leaks addr",
4378 .result_unpriv = REJECT,
4379 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
4380 },
4381 {
4382 "constant register |= constant should keep constant type",
4383 .insns = {
4384 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
4385 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -48),
4386 BPF_MOV64_IMM(BPF_REG_2, 34),
4387 BPF_ALU64_IMM(BPF_OR, BPF_REG_2, 13),
4388 BPF_MOV64_IMM(BPF_REG_3, 0),
4389 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4390 BPF_EXIT_INSN(),
4391 },
4392 .result = ACCEPT,
4393 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4394 },
4395 {
4396 "constant register |= constant should not bypass stack boundary checks",
4397 .insns = {
4398 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
4399 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -48),
4400 BPF_MOV64_IMM(BPF_REG_2, 34),
4401 BPF_ALU64_IMM(BPF_OR, BPF_REG_2, 24),
4402 BPF_MOV64_IMM(BPF_REG_3, 0),
4403 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4404 BPF_EXIT_INSN(),
4405 },
4406 .errstr = "invalid stack type R1 off=-48 access_size=58",
4407 .result = REJECT,
4408 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4409 },
4410 {
4411 "constant register |= constant register should keep constant type",
4412 .insns = {
4413 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
4414 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -48),
4415 BPF_MOV64_IMM(BPF_REG_2, 34),
4416 BPF_MOV64_IMM(BPF_REG_4, 13),
4417 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_4),
4418 BPF_MOV64_IMM(BPF_REG_3, 0),
4419 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4420 BPF_EXIT_INSN(),
4421 },
4422 .result = ACCEPT,
4423 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4424 },
4425 {
4426 "constant register |= constant register should not bypass stack boundary checks",
4427 .insns = {
4428 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
4429 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -48),
4430 BPF_MOV64_IMM(BPF_REG_2, 34),
4431 BPF_MOV64_IMM(BPF_REG_4, 24),
4432 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_4),
4433 BPF_MOV64_IMM(BPF_REG_3, 0),
4434 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4435 BPF_EXIT_INSN(),
4436 },
4437 .errstr = "invalid stack type R1 off=-48 access_size=58",
4438 .result = REJECT,
4439 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4440 },
4441 {
4442 "invalid direct packet write for LWT_IN",
4443 .insns = {
4444 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4445 offsetof(struct __sk_buff, data)),
4446 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4447 offsetof(struct __sk_buff, data_end)),
4448 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4449 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4450 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4451 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
4452 BPF_MOV64_IMM(BPF_REG_0, 0),
4453 BPF_EXIT_INSN(),
4454 },
4455 .errstr = "cannot write into packet",
4456 .result = REJECT,
4457 .prog_type = BPF_PROG_TYPE_LWT_IN,
4458 },
4459 {
4460 "invalid direct packet write for LWT_OUT",
4461 .insns = {
4462 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4463 offsetof(struct __sk_buff, data)),
4464 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4465 offsetof(struct __sk_buff, data_end)),
4466 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4467 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4468 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4469 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
4470 BPF_MOV64_IMM(BPF_REG_0, 0),
4471 BPF_EXIT_INSN(),
4472 },
4473 .errstr = "cannot write into packet",
4474 .result = REJECT,
4475 .prog_type = BPF_PROG_TYPE_LWT_OUT,
4476 },
4477 {
4478 "direct packet write for LWT_XMIT",
4479 .insns = {
4480 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4481 offsetof(struct __sk_buff, data)),
4482 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4483 offsetof(struct __sk_buff, data_end)),
4484 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4485 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4486 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4487 BPF_STX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
4488 BPF_MOV64_IMM(BPF_REG_0, 0),
4489 BPF_EXIT_INSN(),
4490 },
4491 .result = ACCEPT,
4492 .prog_type = BPF_PROG_TYPE_LWT_XMIT,
4493 },
4494 {
4495 "direct packet read for LWT_IN",
4496 .insns = {
4497 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4498 offsetof(struct __sk_buff, data)),
4499 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4500 offsetof(struct __sk_buff, data_end)),
4501 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4502 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4503 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4504 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
4505 BPF_MOV64_IMM(BPF_REG_0, 0),
4506 BPF_EXIT_INSN(),
4507 },
4508 .result = ACCEPT,
4509 .prog_type = BPF_PROG_TYPE_LWT_IN,
4510 },
4511 {
4512 "direct packet read for LWT_OUT",
4513 .insns = {
4514 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4515 offsetof(struct __sk_buff, data)),
4516 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4517 offsetof(struct __sk_buff, data_end)),
4518 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4519 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4520 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4521 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
4522 BPF_MOV64_IMM(BPF_REG_0, 0),
4523 BPF_EXIT_INSN(),
4524 },
4525 .result = ACCEPT,
4526 .prog_type = BPF_PROG_TYPE_LWT_OUT,
4527 },
4528 {
4529 "direct packet read for LWT_XMIT",
4530 .insns = {
4531 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4532 offsetof(struct __sk_buff, data)),
4533 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4534 offsetof(struct __sk_buff, data_end)),
4535 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4536 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4537 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
4538 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
4539 BPF_MOV64_IMM(BPF_REG_0, 0),
4540 BPF_EXIT_INSN(),
4541 },
4542 .result = ACCEPT,
4543 .prog_type = BPF_PROG_TYPE_LWT_XMIT,
4544 },
4545 {
4546 "overlapping checks for direct packet access",
4547 .insns = {
4548 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
4549 offsetof(struct __sk_buff, data)),
4550 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
4551 offsetof(struct __sk_buff, data_end)),
4552 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
4553 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
4554 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 4),
4555 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
4556 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 6),
4557 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
4558 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_2, 6),
4559 BPF_MOV64_IMM(BPF_REG_0, 0),
4560 BPF_EXIT_INSN(),
4561 },
4562 .result = ACCEPT,
4563 .prog_type = BPF_PROG_TYPE_LWT_XMIT,
4564 },
4565 {
4566 "invalid access of tc_classid for LWT_IN",
4567 .insns = {
4568 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
4569 offsetof(struct __sk_buff, tc_classid)),
4570 BPF_EXIT_INSN(),
4571 },
4572 .result = REJECT,
4573 .errstr = "invalid bpf_context access",
4574 },
4575 {
4576 "invalid access of tc_classid for LWT_OUT",
4577 .insns = {
4578 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
4579 offsetof(struct __sk_buff, tc_classid)),
4580 BPF_EXIT_INSN(),
4581 },
4582 .result = REJECT,
4583 .errstr = "invalid bpf_context access",
4584 },
4585 {
4586 "invalid access of tc_classid for LWT_XMIT",
4587 .insns = {
4588 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
4589 offsetof(struct __sk_buff, tc_classid)),
4590 BPF_EXIT_INSN(),
4591 },
4592 .result = REJECT,
4593 .errstr = "invalid bpf_context access",
4594 },
4595 {
4596 "leak pointer into ctx 1",
4597 .insns = {
4598 BPF_MOV64_IMM(BPF_REG_0, 0),
4599 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
4600 offsetof(struct __sk_buff, cb[0])),
4601 BPF_LD_MAP_FD(BPF_REG_2, 0),
4602 BPF_STX_XADD(BPF_DW, BPF_REG_1, BPF_REG_2,
4603 offsetof(struct __sk_buff, cb[0])),
4604 BPF_EXIT_INSN(),
4605 },
4606 .fixup_map1 = { 2 },
4607 .errstr_unpriv = "R2 leaks addr into mem",
4608 .result_unpriv = REJECT,
4609 .result = REJECT,
4610 .errstr = "BPF_XADD stores into R1 context is not allowed",
4611 },
4612 {
4613 "leak pointer into ctx 2",
4614 .insns = {
4615 BPF_MOV64_IMM(BPF_REG_0, 0),
4616 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0,
4617 offsetof(struct __sk_buff, cb[0])),
4618 BPF_STX_XADD(BPF_DW, BPF_REG_1, BPF_REG_10,
4619 offsetof(struct __sk_buff, cb[0])),
4620 BPF_EXIT_INSN(),
4621 },
4622 .errstr_unpriv = "R10 leaks addr into mem",
4623 .result_unpriv = REJECT,
4624 .result = REJECT,
4625 .errstr = "BPF_XADD stores into R1 context is not allowed",
4626 },
4627 {
4628 "leak pointer into ctx 3",
4629 .insns = {
4630 BPF_MOV64_IMM(BPF_REG_0, 0),
4631 BPF_LD_MAP_FD(BPF_REG_2, 0),
4632 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2,
4633 offsetof(struct __sk_buff, cb[0])),
4634 BPF_EXIT_INSN(),
4635 },
4636 .fixup_map1 = { 1 },
4637 .errstr_unpriv = "R2 leaks addr into ctx",
4638 .result_unpriv = REJECT,
4639 .result = ACCEPT,
4640 },
4641 {
4642 "leak pointer into map val",
4643 .insns = {
4644 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
4645 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
4646 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4647 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4648 BPF_LD_MAP_FD(BPF_REG_1, 0),
4649 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
4650 BPF_FUNC_map_lookup_elem),
4651 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3),
4652 BPF_MOV64_IMM(BPF_REG_3, 0),
4653 BPF_STX_MEM(BPF_DW, BPF_REG_0, BPF_REG_3, 0),
4654 BPF_STX_XADD(BPF_DW, BPF_REG_0, BPF_REG_6, 0),
4655 BPF_MOV64_IMM(BPF_REG_0, 0),
4656 BPF_EXIT_INSN(),
4657 },
4658 .fixup_map1 = { 4 },
4659 .errstr_unpriv = "R6 leaks addr into mem",
4660 .result_unpriv = REJECT,
4661 .result = ACCEPT,
4662 },
4663 {
4664 "helper access to map: full range",
4665 .insns = {
4666 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4667 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4668 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4669 BPF_LD_MAP_FD(BPF_REG_1, 0),
4670 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4671 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4672 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4673 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val)),
4674 BPF_MOV64_IMM(BPF_REG_3, 0),
4675 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4676 BPF_EXIT_INSN(),
4677 },
4678 .fixup_map2 = { 3 },
4679 .result = ACCEPT,
4680 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4681 },
4682 {
4683 "helper access to map: partial range",
4684 .insns = {
4685 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4686 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4687 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4688 BPF_LD_MAP_FD(BPF_REG_1, 0),
4689 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4690 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4691 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4692 BPF_MOV64_IMM(BPF_REG_2, 8),
4693 BPF_MOV64_IMM(BPF_REG_3, 0),
4694 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4695 BPF_EXIT_INSN(),
4696 },
4697 .fixup_map2 = { 3 },
4698 .result = ACCEPT,
4699 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4700 },
4701 {
4702 "helper access to map: empty range",
4703 .insns = {
4704 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4705 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4706 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4707 BPF_LD_MAP_FD(BPF_REG_1, 0),
4708 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4709 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3),
4710 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4711 BPF_MOV64_IMM(BPF_REG_2, 0),
4712 BPF_EMIT_CALL(BPF_FUNC_trace_printk),
4713 BPF_EXIT_INSN(),
4714 },
4715 .fixup_map2 = { 3 },
4716 .errstr = "invalid access to map value, value_size=48 off=0 size=0",
4717 .result = REJECT,
4718 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4719 },
4720 {
4721 "helper access to map: out-of-bound range",
4722 .insns = {
4723 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4724 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4725 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4726 BPF_LD_MAP_FD(BPF_REG_1, 0),
4727 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4728 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4729 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4730 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val) + 8),
4731 BPF_MOV64_IMM(BPF_REG_3, 0),
4732 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4733 BPF_EXIT_INSN(),
4734 },
4735 .fixup_map2 = { 3 },
4736 .errstr = "invalid access to map value, value_size=48 off=0 size=56",
4737 .result = REJECT,
4738 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4739 },
4740 {
4741 "helper access to map: negative range",
4742 .insns = {
4743 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4744 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4745 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4746 BPF_LD_MAP_FD(BPF_REG_1, 0),
4747 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4748 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4749 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4750 BPF_MOV64_IMM(BPF_REG_2, -8),
4751 BPF_MOV64_IMM(BPF_REG_3, 0),
4752 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4753 BPF_EXIT_INSN(),
4754 },
4755 .fixup_map2 = { 3 },
4756 .errstr = "R2 min value is negative",
4757 .result = REJECT,
4758 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4759 },
4760 {
4761 "helper access to adjusted map (via const imm): full range",
4762 .insns = {
4763 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4764 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4765 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4766 BPF_LD_MAP_FD(BPF_REG_1, 0),
4767 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4768 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4769 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4770 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4771 offsetof(struct test_val, foo)),
4772 BPF_MOV64_IMM(BPF_REG_2,
4773 sizeof(struct test_val) -
4774 offsetof(struct test_val, foo)),
4775 BPF_MOV64_IMM(BPF_REG_3, 0),
4776 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4777 BPF_EXIT_INSN(),
4778 },
4779 .fixup_map2 = { 3 },
4780 .result = ACCEPT,
4781 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4782 },
4783 {
4784 "helper access to adjusted map (via const imm): partial range",
4785 .insns = {
4786 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4787 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4788 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4789 BPF_LD_MAP_FD(BPF_REG_1, 0),
4790 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4791 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4792 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4793 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4794 offsetof(struct test_val, foo)),
4795 BPF_MOV64_IMM(BPF_REG_2, 8),
4796 BPF_MOV64_IMM(BPF_REG_3, 0),
4797 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4798 BPF_EXIT_INSN(),
4799 },
4800 .fixup_map2 = { 3 },
4801 .result = ACCEPT,
4802 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4803 },
4804 {
4805 "helper access to adjusted map (via const imm): empty range",
4806 .insns = {
4807 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4808 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4809 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4810 BPF_LD_MAP_FD(BPF_REG_1, 0),
4811 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4812 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
4813 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4814 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4815 offsetof(struct test_val, foo)),
4816 BPF_MOV64_IMM(BPF_REG_2, 0),
4817 BPF_EMIT_CALL(BPF_FUNC_trace_printk),
4818 BPF_EXIT_INSN(),
4819 },
4820 .fixup_map2 = { 3 },
4821 .errstr = "invalid access to map value, value_size=48 off=4 size=0",
4822 .result = REJECT,
4823 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4824 },
4825 {
4826 "helper access to adjusted map (via const imm): out-of-bound range",
4827 .insns = {
4828 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4829 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4830 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4831 BPF_LD_MAP_FD(BPF_REG_1, 0),
4832 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4833 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4834 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4835 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4836 offsetof(struct test_val, foo)),
4837 BPF_MOV64_IMM(BPF_REG_2,
4838 sizeof(struct test_val) -
4839 offsetof(struct test_val, foo) + 8),
4840 BPF_MOV64_IMM(BPF_REG_3, 0),
4841 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4842 BPF_EXIT_INSN(),
4843 },
4844 .fixup_map2 = { 3 },
4845 .errstr = "invalid access to map value, value_size=48 off=4 size=52",
4846 .result = REJECT,
4847 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4848 },
4849 {
4850 "helper access to adjusted map (via const imm): negative range (> adjustment)",
4851 .insns = {
4852 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4853 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4854 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4855 BPF_LD_MAP_FD(BPF_REG_1, 0),
4856 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4857 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4858 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4859 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4860 offsetof(struct test_val, foo)),
4861 BPF_MOV64_IMM(BPF_REG_2, -8),
4862 BPF_MOV64_IMM(BPF_REG_3, 0),
4863 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4864 BPF_EXIT_INSN(),
4865 },
4866 .fixup_map2 = { 3 },
4867 .errstr = "R2 min value is negative",
4868 .result = REJECT,
4869 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4870 },
4871 {
4872 "helper access to adjusted map (via const imm): negative range (< adjustment)",
4873 .insns = {
4874 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4875 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4876 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4877 BPF_LD_MAP_FD(BPF_REG_1, 0),
4878 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4879 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4880 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4881 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
4882 offsetof(struct test_val, foo)),
4883 BPF_MOV64_IMM(BPF_REG_2, -1),
4884 BPF_MOV64_IMM(BPF_REG_3, 0),
4885 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4886 BPF_EXIT_INSN(),
4887 },
4888 .fixup_map2 = { 3 },
4889 .errstr = "R2 min value is negative",
4890 .result = REJECT,
4891 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4892 },
4893 {
4894 "helper access to adjusted map (via const reg): full range",
4895 .insns = {
4896 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4897 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4898 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4899 BPF_LD_MAP_FD(BPF_REG_1, 0),
4900 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4901 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
4902 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4903 BPF_MOV64_IMM(BPF_REG_3,
4904 offsetof(struct test_val, foo)),
4905 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
4906 BPF_MOV64_IMM(BPF_REG_2,
4907 sizeof(struct test_val) -
4908 offsetof(struct test_val, foo)),
4909 BPF_MOV64_IMM(BPF_REG_3, 0),
4910 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4911 BPF_EXIT_INSN(),
4912 },
4913 .fixup_map2 = { 3 },
4914 .result = ACCEPT,
4915 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4916 },
4917 {
4918 "helper access to adjusted map (via const reg): partial range",
4919 .insns = {
4920 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4921 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4922 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4923 BPF_LD_MAP_FD(BPF_REG_1, 0),
4924 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4925 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
4926 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4927 BPF_MOV64_IMM(BPF_REG_3,
4928 offsetof(struct test_val, foo)),
4929 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
4930 BPF_MOV64_IMM(BPF_REG_2, 8),
4931 BPF_MOV64_IMM(BPF_REG_3, 0),
4932 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4933 BPF_EXIT_INSN(),
4934 },
4935 .fixup_map2 = { 3 },
4936 .result = ACCEPT,
4937 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4938 },
4939 {
4940 "helper access to adjusted map (via const reg): empty range",
4941 .insns = {
4942 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4943 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4944 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4945 BPF_LD_MAP_FD(BPF_REG_1, 0),
4946 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4947 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
4948 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4949 BPF_MOV64_IMM(BPF_REG_3, 0),
4950 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
4951 BPF_MOV64_IMM(BPF_REG_2, 0),
4952 BPF_EMIT_CALL(BPF_FUNC_trace_printk),
4953 BPF_EXIT_INSN(),
4954 },
4955 .fixup_map2 = { 3 },
4956 .errstr = "R1 min value is outside of the array range",
4957 .result = REJECT,
4958 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4959 },
4960 {
4961 "helper access to adjusted map (via const reg): out-of-bound range",
4962 .insns = {
4963 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4964 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4965 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4966 BPF_LD_MAP_FD(BPF_REG_1, 0),
4967 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4968 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
4969 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4970 BPF_MOV64_IMM(BPF_REG_3,
4971 offsetof(struct test_val, foo)),
4972 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
4973 BPF_MOV64_IMM(BPF_REG_2,
4974 sizeof(struct test_val) -
4975 offsetof(struct test_val, foo) + 8),
4976 BPF_MOV64_IMM(BPF_REG_3, 0),
4977 BPF_EMIT_CALL(BPF_FUNC_probe_read),
4978 BPF_EXIT_INSN(),
4979 },
4980 .fixup_map2 = { 3 },
4981 .errstr = "invalid access to map value, value_size=48 off=4 size=52",
4982 .result = REJECT,
4983 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
4984 },
4985 {
4986 "helper access to adjusted map (via const reg): negative range (> adjustment)",
4987 .insns = {
4988 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
4989 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
4990 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
4991 BPF_LD_MAP_FD(BPF_REG_1, 0),
4992 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
4993 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
4994 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
4995 BPF_MOV64_IMM(BPF_REG_3,
4996 offsetof(struct test_val, foo)),
4997 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
4998 BPF_MOV64_IMM(BPF_REG_2, -8),
4999 BPF_MOV64_IMM(BPF_REG_3, 0),
5000 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5001 BPF_EXIT_INSN(),
5002 },
5003 .fixup_map2 = { 3 },
5004 .errstr = "R2 min value is negative",
5005 .result = REJECT,
5006 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5007 },
5008 {
5009 "helper access to adjusted map (via const reg): negative range (< adjustment)",
5010 .insns = {
5011 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5012 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5013 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5014 BPF_LD_MAP_FD(BPF_REG_1, 0),
5015 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5016 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
5017 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5018 BPF_MOV64_IMM(BPF_REG_3,
5019 offsetof(struct test_val, foo)),
5020 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5021 BPF_MOV64_IMM(BPF_REG_2, -1),
5022 BPF_MOV64_IMM(BPF_REG_3, 0),
5023 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5024 BPF_EXIT_INSN(),
5025 },
5026 .fixup_map2 = { 3 },
5027 .errstr = "R2 min value is negative",
5028 .result = REJECT,
5029 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5030 },
5031 {
5032 "helper access to adjusted map (via variable): full range",
5033 .insns = {
5034 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5035 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5036 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5037 BPF_LD_MAP_FD(BPF_REG_1, 0),
5038 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5039 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
5040 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5041 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5042 BPF_JMP_IMM(BPF_JGT, BPF_REG_3,
5043 offsetof(struct test_val, foo), 4),
5044 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5045 BPF_MOV64_IMM(BPF_REG_2,
5046 sizeof(struct test_val) -
5047 offsetof(struct test_val, foo)),
5048 BPF_MOV64_IMM(BPF_REG_3, 0),
5049 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5050 BPF_EXIT_INSN(),
5051 },
5052 .fixup_map2 = { 3 },
5053 .result = ACCEPT,
5054 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5055 },
5056 {
5057 "helper access to adjusted map (via variable): partial range",
5058 .insns = {
5059 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5060 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5061 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5062 BPF_LD_MAP_FD(BPF_REG_1, 0),
5063 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5064 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
5065 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5066 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5067 BPF_JMP_IMM(BPF_JGT, BPF_REG_3,
5068 offsetof(struct test_val, foo), 4),
5069 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5070 BPF_MOV64_IMM(BPF_REG_2, 8),
5071 BPF_MOV64_IMM(BPF_REG_3, 0),
5072 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5073 BPF_EXIT_INSN(),
5074 },
5075 .fixup_map2 = { 3 },
5076 .result = ACCEPT,
5077 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5078 },
5079 {
5080 "helper access to adjusted map (via variable): empty range",
5081 .insns = {
5082 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5083 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5084 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5085 BPF_LD_MAP_FD(BPF_REG_1, 0),
5086 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5087 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
5088 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5089 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5090 BPF_JMP_IMM(BPF_JGT, BPF_REG_3,
5091 offsetof(struct test_val, foo), 3),
5092 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5093 BPF_MOV64_IMM(BPF_REG_2, 0),
5094 BPF_EMIT_CALL(BPF_FUNC_trace_printk),
5095 BPF_EXIT_INSN(),
5096 },
5097 .fixup_map2 = { 3 },
5098 .errstr = "R1 min value is outside of the array range",
5099 .result = REJECT,
5100 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5101 },
5102 {
5103 "helper access to adjusted map (via variable): no max check",
5104 .insns = {
5105 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5106 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5107 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5108 BPF_LD_MAP_FD(BPF_REG_1, 0),
5109 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5110 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
5111 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5112 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5113 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5114 BPF_MOV64_IMM(BPF_REG_2, 1),
5115 BPF_MOV64_IMM(BPF_REG_3, 0),
5116 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5117 BPF_EXIT_INSN(),
5118 },
5119 .fixup_map2 = { 3 },
5120 .errstr = "R1 unbounded memory access",
5121 .result = REJECT,
5122 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5123 },
5124 {
5125 "helper access to adjusted map (via variable): wrong max check",
5126 .insns = {
5127 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5128 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5129 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5130 BPF_LD_MAP_FD(BPF_REG_1, 0),
5131 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5132 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
5133 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5134 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5135 BPF_JMP_IMM(BPF_JGT, BPF_REG_3,
5136 offsetof(struct test_val, foo), 4),
5137 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5138 BPF_MOV64_IMM(BPF_REG_2,
5139 sizeof(struct test_val) -
5140 offsetof(struct test_val, foo) + 1),
5141 BPF_MOV64_IMM(BPF_REG_3, 0),
5142 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5143 BPF_EXIT_INSN(),
5144 },
5145 .fixup_map2 = { 3 },
5146 .errstr = "invalid access to map value, value_size=48 off=4 size=45",
5147 .result = REJECT,
5148 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5149 },
5150 {
5151 "helper access to map: bounds check using <, good access",
5152 .insns = {
5153 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5154 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5155 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5156 BPF_LD_MAP_FD(BPF_REG_1, 0),
5157 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5158 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5159 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5160 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5161 BPF_JMP_IMM(BPF_JLT, BPF_REG_3, 32, 2),
5162 BPF_MOV64_IMM(BPF_REG_0, 0),
5163 BPF_EXIT_INSN(),
5164 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5165 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5166 BPF_MOV64_IMM(BPF_REG_0, 0),
5167 BPF_EXIT_INSN(),
5168 },
5169 .fixup_map2 = { 3 },
5170 .result = ACCEPT,
5171 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5172 },
5173 {
5174 "helper access to map: bounds check using <, bad access",
5175 .insns = {
5176 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5177 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5178 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5179 BPF_LD_MAP_FD(BPF_REG_1, 0),
5180 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5181 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5182 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5183 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5184 BPF_JMP_IMM(BPF_JLT, BPF_REG_3, 32, 4),
5185 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5186 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5187 BPF_MOV64_IMM(BPF_REG_0, 0),
5188 BPF_EXIT_INSN(),
5189 BPF_MOV64_IMM(BPF_REG_0, 0),
5190 BPF_EXIT_INSN(),
5191 },
5192 .fixup_map2 = { 3 },
5193 .result = REJECT,
5194 .errstr = "R1 unbounded memory access",
5195 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5196 },
5197 {
5198 "helper access to map: bounds check using <=, good access",
5199 .insns = {
5200 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5201 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5202 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5203 BPF_LD_MAP_FD(BPF_REG_1, 0),
5204 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5205 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5206 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5207 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5208 BPF_JMP_IMM(BPF_JLE, BPF_REG_3, 32, 2),
5209 BPF_MOV64_IMM(BPF_REG_0, 0),
5210 BPF_EXIT_INSN(),
5211 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5212 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5213 BPF_MOV64_IMM(BPF_REG_0, 0),
5214 BPF_EXIT_INSN(),
5215 },
5216 .fixup_map2 = { 3 },
5217 .result = ACCEPT,
5218 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5219 },
5220 {
5221 "helper access to map: bounds check using <=, bad access",
5222 .insns = {
5223 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5224 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5225 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5226 BPF_LD_MAP_FD(BPF_REG_1, 0),
5227 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5228 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5229 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5230 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5231 BPF_JMP_IMM(BPF_JLE, BPF_REG_3, 32, 4),
5232 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5233 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5234 BPF_MOV64_IMM(BPF_REG_0, 0),
5235 BPF_EXIT_INSN(),
5236 BPF_MOV64_IMM(BPF_REG_0, 0),
5237 BPF_EXIT_INSN(),
5238 },
5239 .fixup_map2 = { 3 },
5240 .result = REJECT,
5241 .errstr = "R1 unbounded memory access",
5242 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5243 },
5244 {
5245 "helper access to map: bounds check using s<, good access",
5246 .insns = {
5247 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5248 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5249 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5250 BPF_LD_MAP_FD(BPF_REG_1, 0),
5251 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5252 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5253 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5254 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5255 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, 32, 2),
5256 BPF_MOV64_IMM(BPF_REG_0, 0),
5257 BPF_EXIT_INSN(),
5258 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, 0, -3),
5259 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5260 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5261 BPF_MOV64_IMM(BPF_REG_0, 0),
5262 BPF_EXIT_INSN(),
5263 },
5264 .fixup_map2 = { 3 },
5265 .result = ACCEPT,
5266 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5267 },
5268 {
5269 "helper access to map: bounds check using s<, good access 2",
5270 .insns = {
5271 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5272 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5273 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5274 BPF_LD_MAP_FD(BPF_REG_1, 0),
5275 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5276 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5277 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5278 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5279 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, 32, 2),
5280 BPF_MOV64_IMM(BPF_REG_0, 0),
5281 BPF_EXIT_INSN(),
5282 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, -3, -3),
5283 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5284 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5285 BPF_MOV64_IMM(BPF_REG_0, 0),
5286 BPF_EXIT_INSN(),
5287 },
5288 .fixup_map2 = { 3 },
5289 .result = ACCEPT,
5290 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5291 },
5292 {
5293 "helper access to map: bounds check using s<, bad access",
5294 .insns = {
5295 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5296 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5297 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5298 BPF_LD_MAP_FD(BPF_REG_1, 0),
5299 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5300 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5301 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5302 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_0, 0),
5303 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, 32, 2),
5304 BPF_MOV64_IMM(BPF_REG_0, 0),
5305 BPF_EXIT_INSN(),
5306 BPF_JMP_IMM(BPF_JSLT, BPF_REG_3, -3, -3),
5307 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5308 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5309 BPF_MOV64_IMM(BPF_REG_0, 0),
5310 BPF_EXIT_INSN(),
5311 },
5312 .fixup_map2 = { 3 },
5313 .result = REJECT,
5314 .errstr = "R1 min value is negative",
5315 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5316 },
5317 {
5318 "helper access to map: bounds check using s<=, good access",
5319 .insns = {
5320 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5321 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5322 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5323 BPF_LD_MAP_FD(BPF_REG_1, 0),
5324 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5325 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5326 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5327 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5328 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, 32, 2),
5329 BPF_MOV64_IMM(BPF_REG_0, 0),
5330 BPF_EXIT_INSN(),
5331 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, 0, -3),
5332 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5333 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5334 BPF_MOV64_IMM(BPF_REG_0, 0),
5335 BPF_EXIT_INSN(),
5336 },
5337 .fixup_map2 = { 3 },
5338 .result = ACCEPT,
5339 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5340 },
5341 {
5342 "helper access to map: bounds check using s<=, good access 2",
5343 .insns = {
5344 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5345 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5346 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5347 BPF_LD_MAP_FD(BPF_REG_1, 0),
5348 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5349 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5350 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5351 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_0, 0),
5352 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, 32, 2),
5353 BPF_MOV64_IMM(BPF_REG_0, 0),
5354 BPF_EXIT_INSN(),
5355 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, -3, -3),
5356 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5357 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5358 BPF_MOV64_IMM(BPF_REG_0, 0),
5359 BPF_EXIT_INSN(),
5360 },
5361 .fixup_map2 = { 3 },
5362 .result = ACCEPT,
5363 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5364 },
5365 {
5366 "helper access to map: bounds check using s<=, bad access",
5367 .insns = {
5368 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5369 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5370 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5371 BPF_LD_MAP_FD(BPF_REG_1, 0),
5372 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5373 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
5374 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5375 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_0, 0),
5376 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, 32, 2),
5377 BPF_MOV64_IMM(BPF_REG_0, 0),
5378 BPF_EXIT_INSN(),
5379 BPF_JMP_IMM(BPF_JSLE, BPF_REG_3, -3, -3),
5380 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
5381 BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 0),
5382 BPF_MOV64_IMM(BPF_REG_0, 0),
5383 BPF_EXIT_INSN(),
5384 },
5385 .fixup_map2 = { 3 },
5386 .result = REJECT,
5387 .errstr = "R1 min value is negative",
5388 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5389 },
5390 {
5391 "map element value is preserved across register spilling",
5392 .insns = {
5393 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5394 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5395 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5396 BPF_LD_MAP_FD(BPF_REG_1, 0),
5397 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5398 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
5399 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 42),
5400 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5401 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -184),
5402 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
5403 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_1, 0),
5404 BPF_ST_MEM(BPF_DW, BPF_REG_3, 0, 42),
5405 BPF_EXIT_INSN(),
5406 },
5407 .fixup_map2 = { 3 },
5408 .errstr_unpriv = "R0 leaks addr",
5409 .result = ACCEPT,
5410 .result_unpriv = REJECT,
5411 },
5412 {
5413 "map element value or null is marked on register spilling",
5414 .insns = {
5415 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5416 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5417 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5418 BPF_LD_MAP_FD(BPF_REG_1, 0),
5419 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5420 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5421 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -152),
5422 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
5423 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
5424 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_1, 0),
5425 BPF_ST_MEM(BPF_DW, BPF_REG_3, 0, 42),
5426 BPF_EXIT_INSN(),
5427 },
5428 .fixup_map2 = { 3 },
5429 .errstr_unpriv = "R0 leaks addr",
5430 .result = ACCEPT,
5431 .result_unpriv = REJECT,
5432 },
5433 {
5434 "map element value store of cleared call register",
5435 .insns = {
5436 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5437 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5438 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5439 BPF_LD_MAP_FD(BPF_REG_1, 0),
5440 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5441 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 1),
5442 BPF_STX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, 0),
5443 BPF_EXIT_INSN(),
5444 },
5445 .fixup_map2 = { 3 },
5446 .errstr_unpriv = "R1 !read_ok",
5447 .errstr = "R1 !read_ok",
5448 .result = REJECT,
5449 .result_unpriv = REJECT,
5450 },
5451 {
5452 "map element value with unaligned store",
5453 .insns = {
5454 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5455 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5456 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5457 BPF_LD_MAP_FD(BPF_REG_1, 0),
5458 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5459 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 17),
5460 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 3),
5461 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 42),
5462 BPF_ST_MEM(BPF_DW, BPF_REG_0, 2, 43),
5463 BPF_ST_MEM(BPF_DW, BPF_REG_0, -2, 44),
5464 BPF_MOV64_REG(BPF_REG_8, BPF_REG_0),
5465 BPF_ST_MEM(BPF_DW, BPF_REG_8, 0, 32),
5466 BPF_ST_MEM(BPF_DW, BPF_REG_8, 2, 33),
5467 BPF_ST_MEM(BPF_DW, BPF_REG_8, -2, 34),
5468 BPF_ALU64_IMM(BPF_ADD, BPF_REG_8, 5),
5469 BPF_ST_MEM(BPF_DW, BPF_REG_8, 0, 22),
5470 BPF_ST_MEM(BPF_DW, BPF_REG_8, 4, 23),
5471 BPF_ST_MEM(BPF_DW, BPF_REG_8, -7, 24),
5472 BPF_MOV64_REG(BPF_REG_7, BPF_REG_8),
5473 BPF_ALU64_IMM(BPF_ADD, BPF_REG_7, 3),
5474 BPF_ST_MEM(BPF_DW, BPF_REG_7, 0, 22),
5475 BPF_ST_MEM(BPF_DW, BPF_REG_7, 4, 23),
5476 BPF_ST_MEM(BPF_DW, BPF_REG_7, -4, 24),
5477 BPF_EXIT_INSN(),
5478 },
5479 .fixup_map2 = { 3 },
5480 .errstr_unpriv = "R0 leaks addr",
5481 .result = ACCEPT,
5482 .result_unpriv = REJECT,
5483 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
5484 },
5485 {
5486 "map element value with unaligned load",
5487 .insns = {
5488 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5489 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5490 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5491 BPF_LD_MAP_FD(BPF_REG_1, 0),
5492 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5493 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 11),
5494 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
5495 BPF_JMP_IMM(BPF_JGE, BPF_REG_1, MAX_ENTRIES, 9),
5496 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 3),
5497 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_0, 0),
5498 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_0, 2),
5499 BPF_MOV64_REG(BPF_REG_8, BPF_REG_0),
5500 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_8, 0),
5501 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_8, 2),
5502 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 5),
5503 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_0, 0),
5504 BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_0, 4),
5505 BPF_EXIT_INSN(),
5506 },
5507 .fixup_map2 = { 3 },
5508 .errstr_unpriv = "R0 leaks addr",
5509 .result = ACCEPT,
5510 .result_unpriv = REJECT,
5511 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
5512 },
5513 {
5514 "map element value illegal alu op, 1",
5515 .insns = {
5516 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5517 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5518 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5519 BPF_LD_MAP_FD(BPF_REG_1, 0),
5520 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5521 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
5522 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 8),
5523 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 22),
5524 BPF_EXIT_INSN(),
5525 },
5526 .fixup_map2 = { 3 },
5527 .errstr = "R0 bitwise operator &= on pointer",
5528 .result = REJECT,
5529 },
5530 {
5531 "map element value illegal alu op, 2",
5532 .insns = {
5533 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5534 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5535 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5536 BPF_LD_MAP_FD(BPF_REG_1, 0),
5537 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5538 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
5539 BPF_ALU32_IMM(BPF_ADD, BPF_REG_0, 0),
5540 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 22),
5541 BPF_EXIT_INSN(),
5542 },
5543 .fixup_map2 = { 3 },
5544 .errstr = "R0 32-bit pointer arithmetic prohibited",
5545 .result = REJECT,
5546 },
5547 {
5548 "map element value illegal alu op, 3",
5549 .insns = {
5550 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5551 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5552 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5553 BPF_LD_MAP_FD(BPF_REG_1, 0),
5554 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5555 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
5556 BPF_ALU64_IMM(BPF_DIV, BPF_REG_0, 42),
5557 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 22),
5558 BPF_EXIT_INSN(),
5559 },
5560 .fixup_map2 = { 3 },
5561 .errstr = "R0 pointer arithmetic with /= operator",
5562 .result = REJECT,
5563 },
5564 {
5565 "map element value illegal alu op, 4",
5566 .insns = {
5567 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5568 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5569 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5570 BPF_LD_MAP_FD(BPF_REG_1, 0),
5571 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5572 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
5573 BPF_ENDIAN(BPF_FROM_BE, BPF_REG_0, 64),
5574 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 22),
5575 BPF_EXIT_INSN(),
5576 },
5577 .fixup_map2 = { 3 },
5578 .errstr_unpriv = "R0 pointer arithmetic prohibited",
5579 .errstr = "invalid mem access 'inv'",
5580 .result = REJECT,
5581 .result_unpriv = REJECT,
5582 },
5583 {
5584 "map element value illegal alu op, 5",
5585 .insns = {
5586 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5587 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5588 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5589 BPF_LD_MAP_FD(BPF_REG_1, 0),
5590 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5591 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
5592 BPF_MOV64_IMM(BPF_REG_3, 4096),
5593 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5594 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5595 BPF_STX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 0),
5596 BPF_STX_XADD(BPF_DW, BPF_REG_2, BPF_REG_3, 0),
5597 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_2, 0),
5598 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 22),
5599 BPF_EXIT_INSN(),
5600 },
5601 .fixup_map2 = { 3 },
5602 .errstr = "R0 invalid mem access 'inv'",
5603 .result = REJECT,
5604 },
5605 {
5606 "map element value is preserved across register spilling",
5607 .insns = {
5608 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5609 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5610 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5611 BPF_LD_MAP_FD(BPF_REG_1, 0),
5612 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5613 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
5614 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0,
5615 offsetof(struct test_val, foo)),
5616 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0, 42),
5617 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5618 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -184),
5619 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
5620 BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_1, 0),
5621 BPF_ST_MEM(BPF_DW, BPF_REG_3, 0, 42),
5622 BPF_EXIT_INSN(),
5623 },
5624 .fixup_map2 = { 3 },
5625 .errstr_unpriv = "R0 leaks addr",
5626 .result = ACCEPT,
5627 .result_unpriv = REJECT,
5628 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
5629 },
5630 {
5631 "helper access to variable memory: stack, bitwise AND + JMP, correct bounds",
5632 .insns = {
5633 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5634 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5635 BPF_MOV64_IMM(BPF_REG_0, 0),
5636 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -64),
5637 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -56),
5638 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -48),
5639 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -40),
5640 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -32),
5641 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -24),
5642 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -16),
5643 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
5644 BPF_MOV64_IMM(BPF_REG_2, 16),
5645 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5646 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5647 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 64),
5648 BPF_MOV64_IMM(BPF_REG_4, 0),
5649 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 2),
5650 BPF_MOV64_IMM(BPF_REG_3, 0),
5651 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5652 BPF_MOV64_IMM(BPF_REG_0, 0),
5653 BPF_EXIT_INSN(),
5654 },
5655 .result = ACCEPT,
5656 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5657 },
5658 {
5659 "helper access to variable memory: stack, bitwise AND, zero included",
5660 .insns = {
5661 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5662 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5663 BPF_MOV64_IMM(BPF_REG_2, 16),
5664 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5665 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5666 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 64),
5667 BPF_MOV64_IMM(BPF_REG_3, 0),
5668 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5669 BPF_EXIT_INSN(),
5670 },
5671 .errstr = "invalid indirect read from stack off -64+0 size 64",
5672 .result = REJECT,
5673 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5674 },
5675 {
5676 "helper access to variable memory: stack, bitwise AND + JMP, wrong max",
5677 .insns = {
5678 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5679 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5680 BPF_MOV64_IMM(BPF_REG_2, 16),
5681 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5682 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5683 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 65),
5684 BPF_MOV64_IMM(BPF_REG_4, 0),
5685 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 2),
5686 BPF_MOV64_IMM(BPF_REG_3, 0),
5687 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5688 BPF_MOV64_IMM(BPF_REG_0, 0),
5689 BPF_EXIT_INSN(),
5690 },
5691 .errstr = "invalid stack type R1 off=-64 access_size=65",
5692 .result = REJECT,
5693 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5694 },
5695 {
5696 "helper access to variable memory: stack, JMP, correct bounds",
5697 .insns = {
5698 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5699 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5700 BPF_MOV64_IMM(BPF_REG_0, 0),
5701 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -64),
5702 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -56),
5703 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -48),
5704 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -40),
5705 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -32),
5706 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -24),
5707 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -16),
5708 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
5709 BPF_MOV64_IMM(BPF_REG_2, 16),
5710 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5711 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5712 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 64, 4),
5713 BPF_MOV64_IMM(BPF_REG_4, 0),
5714 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 2),
5715 BPF_MOV64_IMM(BPF_REG_3, 0),
5716 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5717 BPF_MOV64_IMM(BPF_REG_0, 0),
5718 BPF_EXIT_INSN(),
5719 },
5720 .result = ACCEPT,
5721 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5722 },
5723 {
5724 "helper access to variable memory: stack, JMP (signed), correct bounds",
5725 .insns = {
5726 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5727 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5728 BPF_MOV64_IMM(BPF_REG_0, 0),
5729 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -64),
5730 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -56),
5731 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -48),
5732 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -40),
5733 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -32),
5734 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -24),
5735 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -16),
5736 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
5737 BPF_MOV64_IMM(BPF_REG_2, 16),
5738 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5739 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5740 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2, 64, 4),
5741 BPF_MOV64_IMM(BPF_REG_4, 0),
5742 BPF_JMP_REG(BPF_JSGE, BPF_REG_4, BPF_REG_2, 2),
5743 BPF_MOV64_IMM(BPF_REG_3, 0),
5744 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5745 BPF_MOV64_IMM(BPF_REG_0, 0),
5746 BPF_EXIT_INSN(),
5747 },
5748 .result = ACCEPT,
5749 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5750 },
5751 {
5752 "helper access to variable memory: stack, JMP, bounds + offset",
5753 .insns = {
5754 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5755 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5756 BPF_MOV64_IMM(BPF_REG_2, 16),
5757 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5758 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5759 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 64, 5),
5760 BPF_MOV64_IMM(BPF_REG_4, 0),
5761 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 3),
5762 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
5763 BPF_MOV64_IMM(BPF_REG_3, 0),
5764 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5765 BPF_MOV64_IMM(BPF_REG_0, 0),
5766 BPF_EXIT_INSN(),
5767 },
5768 .errstr = "invalid stack type R1 off=-64 access_size=65",
5769 .result = REJECT,
5770 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5771 },
5772 {
5773 "helper access to variable memory: stack, JMP, wrong max",
5774 .insns = {
5775 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5776 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5777 BPF_MOV64_IMM(BPF_REG_2, 16),
5778 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5779 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5780 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 65, 4),
5781 BPF_MOV64_IMM(BPF_REG_4, 0),
5782 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 2),
5783 BPF_MOV64_IMM(BPF_REG_3, 0),
5784 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5785 BPF_MOV64_IMM(BPF_REG_0, 0),
5786 BPF_EXIT_INSN(),
5787 },
5788 .errstr = "invalid stack type R1 off=-64 access_size=65",
5789 .result = REJECT,
5790 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5791 },
5792 {
5793 "helper access to variable memory: stack, JMP, no max check",
5794 .insns = {
5795 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5796 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5797 BPF_MOV64_IMM(BPF_REG_2, 16),
5798 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5799 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5800 BPF_MOV64_IMM(BPF_REG_4, 0),
5801 BPF_JMP_REG(BPF_JGE, BPF_REG_4, BPF_REG_2, 2),
5802 BPF_MOV64_IMM(BPF_REG_3, 0),
5803 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5804 BPF_MOV64_IMM(BPF_REG_0, 0),
5805 BPF_EXIT_INSN(),
5806 },
5807 /* because max wasn't checked, signed min is negative */
5808 .errstr = "R2 min value is negative, either use unsigned or 'var &= const'",
5809 .result = REJECT,
5810 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5811 },
5812 {
5813 "helper access to variable memory: stack, JMP, no min check",
5814 .insns = {
5815 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5816 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5817 BPF_MOV64_IMM(BPF_REG_2, 16),
5818 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5819 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5820 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 64, 3),
5821 BPF_MOV64_IMM(BPF_REG_3, 0),
5822 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5823 BPF_MOV64_IMM(BPF_REG_0, 0),
5824 BPF_EXIT_INSN(),
5825 },
5826 .errstr = "invalid indirect read from stack off -64+0 size 64",
5827 .result = REJECT,
5828 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5829 },
5830 {
5831 "helper access to variable memory: stack, JMP (signed), no min check",
5832 .insns = {
5833 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5834 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
5835 BPF_MOV64_IMM(BPF_REG_2, 16),
5836 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, -128),
5837 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_1, -128),
5838 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2, 64, 3),
5839 BPF_MOV64_IMM(BPF_REG_3, 0),
5840 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5841 BPF_MOV64_IMM(BPF_REG_0, 0),
5842 BPF_EXIT_INSN(),
5843 },
5844 .errstr = "R2 min value is negative",
5845 .result = REJECT,
5846 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5847 },
5848 {
5849 "helper access to variable memory: map, JMP, correct bounds",
5850 .insns = {
5851 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5852 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5853 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5854 BPF_LD_MAP_FD(BPF_REG_1, 0),
5855 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5856 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 10),
5857 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5858 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val)),
5859 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
5860 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
5861 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2,
5862 sizeof(struct test_val), 4),
5863 BPF_MOV64_IMM(BPF_REG_4, 0),
5864 BPF_JMP_REG(BPF_JSGE, BPF_REG_4, BPF_REG_2, 2),
5865 BPF_MOV64_IMM(BPF_REG_3, 0),
5866 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5867 BPF_MOV64_IMM(BPF_REG_0, 0),
5868 BPF_EXIT_INSN(),
5869 },
5870 .fixup_map2 = { 3 },
5871 .result = ACCEPT,
5872 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5873 },
5874 {
5875 "helper access to variable memory: map, JMP, wrong max",
5876 .insns = {
5877 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5878 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5879 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5880 BPF_LD_MAP_FD(BPF_REG_1, 0),
5881 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5882 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 10),
5883 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5884 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val)),
5885 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
5886 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
5887 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2,
5888 sizeof(struct test_val) + 1, 4),
5889 BPF_MOV64_IMM(BPF_REG_4, 0),
5890 BPF_JMP_REG(BPF_JSGE, BPF_REG_4, BPF_REG_2, 2),
5891 BPF_MOV64_IMM(BPF_REG_3, 0),
5892 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5893 BPF_MOV64_IMM(BPF_REG_0, 0),
5894 BPF_EXIT_INSN(),
5895 },
5896 .fixup_map2 = { 3 },
5897 .errstr = "invalid access to map value, value_size=48 off=0 size=49",
5898 .result = REJECT,
5899 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5900 },
5901 {
5902 "helper access to variable memory: map adjusted, JMP, correct bounds",
5903 .insns = {
5904 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5905 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5906 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5907 BPF_LD_MAP_FD(BPF_REG_1, 0),
5908 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5909 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 11),
5910 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5911 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 20),
5912 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val)),
5913 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
5914 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
5915 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2,
5916 sizeof(struct test_val) - 20, 4),
5917 BPF_MOV64_IMM(BPF_REG_4, 0),
5918 BPF_JMP_REG(BPF_JSGE, BPF_REG_4, BPF_REG_2, 2),
5919 BPF_MOV64_IMM(BPF_REG_3, 0),
5920 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5921 BPF_MOV64_IMM(BPF_REG_0, 0),
5922 BPF_EXIT_INSN(),
5923 },
5924 .fixup_map2 = { 3 },
5925 .result = ACCEPT,
5926 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5927 },
5928 {
5929 "helper access to variable memory: map adjusted, JMP, wrong max",
5930 .insns = {
5931 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
5932 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
5933 BPF_ST_MEM(BPF_DW, BPF_REG_2, 0, 0),
5934 BPF_LD_MAP_FD(BPF_REG_1, 0),
5935 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
5936 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 11),
5937 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
5938 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 20),
5939 BPF_MOV64_IMM(BPF_REG_2, sizeof(struct test_val)),
5940 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
5941 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
5942 BPF_JMP_IMM(BPF_JSGT, BPF_REG_2,
5943 sizeof(struct test_val) - 19, 4),
5944 BPF_MOV64_IMM(BPF_REG_4, 0),
5945 BPF_JMP_REG(BPF_JSGE, BPF_REG_4, BPF_REG_2, 2),
5946 BPF_MOV64_IMM(BPF_REG_3, 0),
5947 BPF_EMIT_CALL(BPF_FUNC_probe_read),
5948 BPF_MOV64_IMM(BPF_REG_0, 0),
5949 BPF_EXIT_INSN(),
5950 },
5951 .fixup_map2 = { 3 },
5952 .errstr = "R1 min value is outside of the array range",
5953 .result = REJECT,
5954 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
5955 },
5956 {
5957 "helper access to variable memory: size = 0 allowed on NULL (ARG_PTR_TO_MEM_OR_NULL)",
5958 .insns = {
5959 BPF_MOV64_IMM(BPF_REG_1, 0),
5960 BPF_MOV64_IMM(BPF_REG_2, 0),
5961 BPF_MOV64_IMM(BPF_REG_3, 0),
5962 BPF_MOV64_IMM(BPF_REG_4, 0),
5963 BPF_MOV64_IMM(BPF_REG_5, 0),
5964 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
5965 BPF_EXIT_INSN(),
5966 },
5967 .result = ACCEPT,
5968 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
5969 },
5970 {
5971 "helper access to variable memory: size > 0 not allowed on NULL (ARG_PTR_TO_MEM_OR_NULL)",
5972 .insns = {
5973 BPF_MOV64_IMM(BPF_REG_1, 0),
5974 BPF_MOV64_IMM(BPF_REG_2, 0),
5975 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
5976 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
5977 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 64),
5978 BPF_MOV64_IMM(BPF_REG_3, 0),
5979 BPF_MOV64_IMM(BPF_REG_4, 0),
5980 BPF_MOV64_IMM(BPF_REG_5, 0),
5981 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
5982 BPF_EXIT_INSN(),
5983 },
5984 .errstr = "R1 type=inv expected=fp",
5985 .result = REJECT,
5986 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
5987 },
5988 {
5989 "helper access to variable memory: size = 0 allowed on != NULL stack pointer (ARG_PTR_TO_MEM_OR_NULL)",
5990 .insns = {
5991 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
5992 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
5993 BPF_MOV64_IMM(BPF_REG_2, 0),
5994 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, 0),
5995 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 8),
5996 BPF_MOV64_IMM(BPF_REG_3, 0),
5997 BPF_MOV64_IMM(BPF_REG_4, 0),
5998 BPF_MOV64_IMM(BPF_REG_5, 0),
5999 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
6000 BPF_EXIT_INSN(),
6001 },
6002 .result = ACCEPT,
6003 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6004 },
6005 {
6006 "helper access to variable memory: size = 0 allowed on != NULL map pointer (ARG_PTR_TO_MEM_OR_NULL)",
6007 .insns = {
6008 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6009 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6010 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6011 BPF_LD_MAP_FD(BPF_REG_1, 0),
6012 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6013 BPF_FUNC_map_lookup_elem),
6014 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
6015 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6016 BPF_MOV64_IMM(BPF_REG_2, 0),
6017 BPF_MOV64_IMM(BPF_REG_3, 0),
6018 BPF_MOV64_IMM(BPF_REG_4, 0),
6019 BPF_MOV64_IMM(BPF_REG_5, 0),
6020 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
6021 BPF_EXIT_INSN(),
6022 },
6023 .fixup_map1 = { 3 },
6024 .result = ACCEPT,
6025 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6026 },
6027 {
6028 "helper access to variable memory: size possible = 0 allowed on != NULL stack pointer (ARG_PTR_TO_MEM_OR_NULL)",
6029 .insns = {
6030 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6031 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6032 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6033 BPF_LD_MAP_FD(BPF_REG_1, 0),
6034 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6035 BPF_FUNC_map_lookup_elem),
6036 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6037 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 0),
6038 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 8, 7),
6039 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
6040 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
6041 BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_2, 0),
6042 BPF_MOV64_IMM(BPF_REG_3, 0),
6043 BPF_MOV64_IMM(BPF_REG_4, 0),
6044 BPF_MOV64_IMM(BPF_REG_5, 0),
6045 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
6046 BPF_EXIT_INSN(),
6047 },
6048 .fixup_map1 = { 3 },
6049 .result = ACCEPT,
6050 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6051 },
6052 {
6053 "helper access to variable memory: size possible = 0 allowed on != NULL map pointer (ARG_PTR_TO_MEM_OR_NULL)",
6054 .insns = {
6055 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6056 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6057 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6058 BPF_LD_MAP_FD(BPF_REG_1, 0),
6059 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6060 BPF_FUNC_map_lookup_elem),
6061 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
6062 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6063 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 0),
6064 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 8, 4),
6065 BPF_MOV64_IMM(BPF_REG_3, 0),
6066 BPF_MOV64_IMM(BPF_REG_4, 0),
6067 BPF_MOV64_IMM(BPF_REG_5, 0),
6068 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
6069 BPF_EXIT_INSN(),
6070 },
6071 .fixup_map1 = { 3 },
6072 .result = ACCEPT,
6073 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6074 },
6075 {
6076 "helper access to variable memory: size possible = 0 allowed on != NULL packet pointer (ARG_PTR_TO_MEM_OR_NULL)",
6077 .insns = {
6078 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
6079 offsetof(struct __sk_buff, data)),
6080 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
6081 offsetof(struct __sk_buff, data_end)),
6082 BPF_MOV64_REG(BPF_REG_0, BPF_REG_6),
6083 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
6084 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 7),
6085 BPF_MOV64_REG(BPF_REG_1, BPF_REG_6),
6086 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_6, 0),
6087 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 8, 4),
6088 BPF_MOV64_IMM(BPF_REG_3, 0),
6089 BPF_MOV64_IMM(BPF_REG_4, 0),
6090 BPF_MOV64_IMM(BPF_REG_5, 0),
6091 BPF_EMIT_CALL(BPF_FUNC_csum_diff),
6092 BPF_EXIT_INSN(),
6093 },
6094 .result = ACCEPT,
6095 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6096 },
6097 {
6098 "helper access to variable memory: size = 0 not allowed on NULL (!ARG_PTR_TO_MEM_OR_NULL)",
6099 .insns = {
6100 BPF_MOV64_IMM(BPF_REG_1, 0),
6101 BPF_MOV64_IMM(BPF_REG_2, 0),
6102 BPF_MOV64_IMM(BPF_REG_3, 0),
6103 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6104 BPF_EXIT_INSN(),
6105 },
6106 .errstr = "R1 type=inv expected=fp",
6107 .result = REJECT,
6108 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6109 },
6110 {
6111 "helper access to variable memory: size > 0 not allowed on NULL (!ARG_PTR_TO_MEM_OR_NULL)",
6112 .insns = {
6113 BPF_MOV64_IMM(BPF_REG_1, 0),
6114 BPF_MOV64_IMM(BPF_REG_2, 1),
6115 BPF_MOV64_IMM(BPF_REG_3, 0),
6116 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6117 BPF_EXIT_INSN(),
6118 },
6119 .errstr = "R1 type=inv expected=fp",
6120 .result = REJECT,
6121 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6122 },
6123 {
6124 "helper access to variable memory: size = 0 allowed on != NULL stack pointer (!ARG_PTR_TO_MEM_OR_NULL)",
6125 .insns = {
6126 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
6127 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
6128 BPF_MOV64_IMM(BPF_REG_2, 0),
6129 BPF_MOV64_IMM(BPF_REG_3, 0),
6130 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6131 BPF_EXIT_INSN(),
6132 },
6133 .result = ACCEPT,
6134 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6135 },
6136 {
6137 "helper access to variable memory: size = 0 allowed on != NULL map pointer (!ARG_PTR_TO_MEM_OR_NULL)",
6138 .insns = {
6139 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6140 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6141 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6142 BPF_LD_MAP_FD(BPF_REG_1, 0),
6143 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
6144 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
6145 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6146 BPF_MOV64_IMM(BPF_REG_2, 0),
6147 BPF_MOV64_IMM(BPF_REG_3, 0),
6148 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6149 BPF_EXIT_INSN(),
6150 },
6151 .fixup_map1 = { 3 },
6152 .result = ACCEPT,
6153 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6154 },
6155 {
6156 "helper access to variable memory: size possible = 0 allowed on != NULL stack pointer (!ARG_PTR_TO_MEM_OR_NULL)",
6157 .insns = {
6158 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6159 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6160 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6161 BPF_LD_MAP_FD(BPF_REG_1, 0),
6162 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
6163 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
6164 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 0),
6165 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 8, 4),
6166 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
6167 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -8),
6168 BPF_MOV64_IMM(BPF_REG_3, 0),
6169 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6170 BPF_EXIT_INSN(),
6171 },
6172 .fixup_map1 = { 3 },
6173 .result = ACCEPT,
6174 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6175 },
6176 {
6177 "helper access to variable memory: size possible = 0 allowed on != NULL map pointer (!ARG_PTR_TO_MEM_OR_NULL)",
6178 .insns = {
6179 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6180 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6181 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6182 BPF_LD_MAP_FD(BPF_REG_1, 0),
6183 BPF_EMIT_CALL(BPF_FUNC_map_lookup_elem),
6184 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
6185 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6186 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 0),
6187 BPF_JMP_IMM(BPF_JGT, BPF_REG_2, 8, 2),
6188 BPF_MOV64_IMM(BPF_REG_3, 0),
6189 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6190 BPF_EXIT_INSN(),
6191 },
6192 .fixup_map1 = { 3 },
6193 .result = ACCEPT,
6194 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6195 },
6196 {
6197 "helper access to variable memory: 8 bytes leak",
6198 .insns = {
6199 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
6200 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
6201 BPF_MOV64_IMM(BPF_REG_0, 0),
6202 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -64),
6203 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -56),
6204 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -48),
6205 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -40),
6206 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -24),
6207 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -16),
6208 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
6209 BPF_MOV64_IMM(BPF_REG_2, 0),
6210 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_2, -128),
6211 BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_10, -128),
6212 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 63),
6213 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 1),
6214 BPF_MOV64_IMM(BPF_REG_3, 0),
6215 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6216 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6217 BPF_EXIT_INSN(),
6218 },
6219 .errstr = "invalid indirect read from stack off -64+32 size 64",
6220 .result = REJECT,
6221 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6222 },
6223 {
6224 "helper access to variable memory: 8 bytes no leak (init memory)",
6225 .insns = {
6226 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
6227 BPF_MOV64_IMM(BPF_REG_0, 0),
6228 BPF_MOV64_IMM(BPF_REG_0, 0),
6229 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -64),
6230 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -56),
6231 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -48),
6232 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -40),
6233 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -32),
6234 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -24),
6235 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -16),
6236 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
6237 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -64),
6238 BPF_MOV64_IMM(BPF_REG_2, 0),
6239 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 32),
6240 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, 32),
6241 BPF_MOV64_IMM(BPF_REG_3, 0),
6242 BPF_EMIT_CALL(BPF_FUNC_probe_read),
6243 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6244 BPF_EXIT_INSN(),
6245 },
6246 .result = ACCEPT,
6247 .prog_type = BPF_PROG_TYPE_TRACEPOINT,
6248 },
6249 {
6250 "invalid and of negative number",
6251 .insns = {
6252 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6253 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6254 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6255 BPF_LD_MAP_FD(BPF_REG_1, 0),
6256 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6257 BPF_FUNC_map_lookup_elem),
6258 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
6259 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
6260 BPF_ALU64_IMM(BPF_AND, BPF_REG_1, -4),
6261 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 2),
6262 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6263 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
6264 offsetof(struct test_val, foo)),
6265 BPF_EXIT_INSN(),
6266 },
6267 .fixup_map2 = { 3 },
6268 .errstr = "R0 max value is outside of the array range",
6269 .result = REJECT,
6270 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
6271 },
6272 {
6273 "invalid range check",
6274 .insns = {
6275 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6276 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6277 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6278 BPF_LD_MAP_FD(BPF_REG_1, 0),
6279 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6280 BPF_FUNC_map_lookup_elem),
6281 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 12),
6282 BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0),
6283 BPF_MOV64_IMM(BPF_REG_9, 1),
6284 BPF_ALU32_IMM(BPF_MOD, BPF_REG_1, 2),
6285 BPF_ALU32_IMM(BPF_ADD, BPF_REG_1, 1),
6286 BPF_ALU32_REG(BPF_AND, BPF_REG_9, BPF_REG_1),
6287 BPF_ALU32_IMM(BPF_ADD, BPF_REG_9, 1),
6288 BPF_ALU32_IMM(BPF_RSH, BPF_REG_9, 1),
6289 BPF_MOV32_IMM(BPF_REG_3, 1),
6290 BPF_ALU32_REG(BPF_SUB, BPF_REG_3, BPF_REG_9),
6291 BPF_ALU32_IMM(BPF_MUL, BPF_REG_3, 0x10000000),
6292 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_3),
6293 BPF_STX_MEM(BPF_W, BPF_REG_0, BPF_REG_3, 0),
6294 BPF_MOV64_REG(BPF_REG_0, 0),
6295 BPF_EXIT_INSN(),
6296 },
6297 .fixup_map2 = { 3 },
6298 .errstr = "R0 max value is outside of the array range",
6299 .result = REJECT,
6300 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
6301 },
6302 {
6303 "map in map access",
6304 .insns = {
6305 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6306 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6307 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6308 BPF_LD_MAP_FD(BPF_REG_1, 0),
6309 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6310 BPF_FUNC_map_lookup_elem),
6311 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
6312 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6313 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6314 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6315 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6316 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6317 BPF_FUNC_map_lookup_elem),
6318 BPF_MOV64_IMM(BPF_REG_0, 0),
6319 BPF_EXIT_INSN(),
6320 },
6321 .fixup_map_in_map = { 3 },
6322 .result = ACCEPT,
6323 },
6324 {
6325 "invalid inner map pointer",
6326 .insns = {
6327 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6328 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6329 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6330 BPF_LD_MAP_FD(BPF_REG_1, 0),
6331 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6332 BPF_FUNC_map_lookup_elem),
6333 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
6334 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6335 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6336 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6337 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6338 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
6339 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6340 BPF_FUNC_map_lookup_elem),
6341 BPF_MOV64_IMM(BPF_REG_0, 0),
6342 BPF_EXIT_INSN(),
6343 },
6344 .fixup_map_in_map = { 3 },
6345 .errstr = "R1 pointer arithmetic on CONST_PTR_TO_MAP prohibited",
6346 .result = REJECT,
6347 },
6348 {
6349 "forgot null checking on the inner map pointer",
6350 .insns = {
6351 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6352 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6353 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6354 BPF_LD_MAP_FD(BPF_REG_1, 0),
6355 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6356 BPF_FUNC_map_lookup_elem),
6357 BPF_ST_MEM(0, BPF_REG_10, -4, 0),
6358 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6359 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -4),
6360 BPF_MOV64_REG(BPF_REG_1, BPF_REG_0),
6361 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6362 BPF_FUNC_map_lookup_elem),
6363 BPF_MOV64_IMM(BPF_REG_0, 0),
6364 BPF_EXIT_INSN(),
6365 },
6366 .fixup_map_in_map = { 3 },
6367 .errstr = "R1 type=map_value_or_null expected=map_ptr",
6368 .result = REJECT,
6369 },
6370 {
6371 "ld_abs: check calling conv, r1",
6372 .insns = {
6373 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6374 BPF_MOV64_IMM(BPF_REG_1, 0),
6375 BPF_LD_ABS(BPF_W, -0x200000),
6376 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
6377 BPF_EXIT_INSN(),
6378 },
6379 .errstr = "R1 !read_ok",
6380 .result = REJECT,
6381 },
6382 {
6383 "ld_abs: check calling conv, r2",
6384 .insns = {
6385 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6386 BPF_MOV64_IMM(BPF_REG_2, 0),
6387 BPF_LD_ABS(BPF_W, -0x200000),
6388 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
6389 BPF_EXIT_INSN(),
6390 },
6391 .errstr = "R2 !read_ok",
6392 .result = REJECT,
6393 },
6394 {
6395 "ld_abs: check calling conv, r3",
6396 .insns = {
6397 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6398 BPF_MOV64_IMM(BPF_REG_3, 0),
6399 BPF_LD_ABS(BPF_W, -0x200000),
6400 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
6401 BPF_EXIT_INSN(),
6402 },
6403 .errstr = "R3 !read_ok",
6404 .result = REJECT,
6405 },
6406 {
6407 "ld_abs: check calling conv, r4",
6408 .insns = {
6409 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6410 BPF_MOV64_IMM(BPF_REG_4, 0),
6411 BPF_LD_ABS(BPF_W, -0x200000),
6412 BPF_MOV64_REG(BPF_REG_0, BPF_REG_4),
6413 BPF_EXIT_INSN(),
6414 },
6415 .errstr = "R4 !read_ok",
6416 .result = REJECT,
6417 },
6418 {
6419 "ld_abs: check calling conv, r5",
6420 .insns = {
6421 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6422 BPF_MOV64_IMM(BPF_REG_5, 0),
6423 BPF_LD_ABS(BPF_W, -0x200000),
6424 BPF_MOV64_REG(BPF_REG_0, BPF_REG_5),
6425 BPF_EXIT_INSN(),
6426 },
6427 .errstr = "R5 !read_ok",
6428 .result = REJECT,
6429 },
6430 {
6431 "ld_abs: check calling conv, r7",
6432 .insns = {
6433 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6434 BPF_MOV64_IMM(BPF_REG_7, 0),
6435 BPF_LD_ABS(BPF_W, -0x200000),
6436 BPF_MOV64_REG(BPF_REG_0, BPF_REG_7),
6437 BPF_EXIT_INSN(),
6438 },
6439 .result = ACCEPT,
6440 },
6441 {
6442 "ld_abs: tests on r6 and skb data reload helper",
6443 .insns = {
6444 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6445 BPF_LD_ABS(BPF_B, 0),
6446 BPF_LD_ABS(BPF_H, 0),
6447 BPF_LD_ABS(BPF_W, 0),
6448 BPF_MOV64_REG(BPF_REG_7, BPF_REG_6),
6449 BPF_MOV64_IMM(BPF_REG_6, 0),
6450 BPF_MOV64_REG(BPF_REG_1, BPF_REG_7),
6451 BPF_MOV64_IMM(BPF_REG_2, 1),
6452 BPF_MOV64_IMM(BPF_REG_3, 2),
6453 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6454 BPF_FUNC_skb_vlan_push),
6455 BPF_MOV64_REG(BPF_REG_6, BPF_REG_7),
6456 BPF_LD_ABS(BPF_B, 0),
6457 BPF_LD_ABS(BPF_H, 0),
6458 BPF_LD_ABS(BPF_W, 0),
6459 BPF_MOV64_IMM(BPF_REG_0, 42),
6460 BPF_EXIT_INSN(),
6461 },
6462 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
6463 .result = ACCEPT,
6464 },
6465 {
6466 "ld_ind: check calling conv, r1",
6467 .insns = {
6468 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6469 BPF_MOV64_IMM(BPF_REG_1, 1),
6470 BPF_LD_IND(BPF_W, BPF_REG_1, -0x200000),
6471 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
6472 BPF_EXIT_INSN(),
6473 },
6474 .errstr = "R1 !read_ok",
6475 .result = REJECT,
6476 },
6477 {
6478 "ld_ind: check calling conv, r2",
6479 .insns = {
6480 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6481 BPF_MOV64_IMM(BPF_REG_2, 1),
6482 BPF_LD_IND(BPF_W, BPF_REG_2, -0x200000),
6483 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
6484 BPF_EXIT_INSN(),
6485 },
6486 .errstr = "R2 !read_ok",
6487 .result = REJECT,
6488 },
6489 {
6490 "ld_ind: check calling conv, r3",
6491 .insns = {
6492 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6493 BPF_MOV64_IMM(BPF_REG_3, 1),
6494 BPF_LD_IND(BPF_W, BPF_REG_3, -0x200000),
6495 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
6496 BPF_EXIT_INSN(),
6497 },
6498 .errstr = "R3 !read_ok",
6499 .result = REJECT,
6500 },
6501 {
6502 "ld_ind: check calling conv, r4",
6503 .insns = {
6504 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6505 BPF_MOV64_IMM(BPF_REG_4, 1),
6506 BPF_LD_IND(BPF_W, BPF_REG_4, -0x200000),
6507 BPF_MOV64_REG(BPF_REG_0, BPF_REG_4),
6508 BPF_EXIT_INSN(),
6509 },
6510 .errstr = "R4 !read_ok",
6511 .result = REJECT,
6512 },
6513 {
6514 "ld_ind: check calling conv, r5",
6515 .insns = {
6516 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6517 BPF_MOV64_IMM(BPF_REG_5, 1),
6518 BPF_LD_IND(BPF_W, BPF_REG_5, -0x200000),
6519 BPF_MOV64_REG(BPF_REG_0, BPF_REG_5),
6520 BPF_EXIT_INSN(),
6521 },
6522 .errstr = "R5 !read_ok",
6523 .result = REJECT,
6524 },
6525 {
6526 "ld_ind: check calling conv, r7",
6527 .insns = {
6528 BPF_MOV64_REG(BPF_REG_6, BPF_REG_1),
6529 BPF_MOV64_IMM(BPF_REG_7, 1),
6530 BPF_LD_IND(BPF_W, BPF_REG_7, -0x200000),
6531 BPF_MOV64_REG(BPF_REG_0, BPF_REG_7),
6532 BPF_EXIT_INSN(),
6533 },
6534 .result = ACCEPT,
6535 },
6536 {
6537 "check bpf_perf_event_data->sample_period byte load permitted",
6538 .insns = {
6539 BPF_MOV64_IMM(BPF_REG_0, 0),
6540 #if __BYTE_ORDER == __LITTLE_ENDIAN
6541 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
6542 offsetof(struct bpf_perf_event_data, sample_period)),
6543 #else
6544 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1,
6545 offsetof(struct bpf_perf_event_data, sample_period) + 7),
6546 #endif
6547 BPF_EXIT_INSN(),
6548 },
6549 .result = ACCEPT,
6550 .prog_type = BPF_PROG_TYPE_PERF_EVENT,
6551 },
6552 {
6553 "check bpf_perf_event_data->sample_period half load permitted",
6554 .insns = {
6555 BPF_MOV64_IMM(BPF_REG_0, 0),
6556 #if __BYTE_ORDER == __LITTLE_ENDIAN
6557 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6558 offsetof(struct bpf_perf_event_data, sample_period)),
6559 #else
6560 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6561 offsetof(struct bpf_perf_event_data, sample_period) + 6),
6562 #endif
6563 BPF_EXIT_INSN(),
6564 },
6565 .result = ACCEPT,
6566 .prog_type = BPF_PROG_TYPE_PERF_EVENT,
6567 },
6568 {
6569 "check bpf_perf_event_data->sample_period word load permitted",
6570 .insns = {
6571 BPF_MOV64_IMM(BPF_REG_0, 0),
6572 #if __BYTE_ORDER == __LITTLE_ENDIAN
6573 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
6574 offsetof(struct bpf_perf_event_data, sample_period)),
6575 #else
6576 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
6577 offsetof(struct bpf_perf_event_data, sample_period) + 4),
6578 #endif
6579 BPF_EXIT_INSN(),
6580 },
6581 .result = ACCEPT,
6582 .prog_type = BPF_PROG_TYPE_PERF_EVENT,
6583 },
6584 {
6585 "check bpf_perf_event_data->sample_period dword load permitted",
6586 .insns = {
6587 BPF_MOV64_IMM(BPF_REG_0, 0),
6588 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1,
6589 offsetof(struct bpf_perf_event_data, sample_period)),
6590 BPF_EXIT_INSN(),
6591 },
6592 .result = ACCEPT,
6593 .prog_type = BPF_PROG_TYPE_PERF_EVENT,
6594 },
6595 {
6596 "check skb->data half load not permitted",
6597 .insns = {
6598 BPF_MOV64_IMM(BPF_REG_0, 0),
6599 #if __BYTE_ORDER == __LITTLE_ENDIAN
6600 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6601 offsetof(struct __sk_buff, data)),
6602 #else
6603 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6604 offsetof(struct __sk_buff, data) + 2),
6605 #endif
6606 BPF_EXIT_INSN(),
6607 },
6608 .result = REJECT,
6609 .errstr = "invalid bpf_context access",
6610 },
6611 {
6612 "check skb->tc_classid half load not permitted for lwt prog",
6613 .insns = {
6614 BPF_MOV64_IMM(BPF_REG_0, 0),
6615 #if __BYTE_ORDER == __LITTLE_ENDIAN
6616 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6617 offsetof(struct __sk_buff, tc_classid)),
6618 #else
6619 BPF_LDX_MEM(BPF_H, BPF_REG_0, BPF_REG_1,
6620 offsetof(struct __sk_buff, tc_classid) + 2),
6621 #endif
6622 BPF_EXIT_INSN(),
6623 },
6624 .result = REJECT,
6625 .errstr = "invalid bpf_context access",
6626 .prog_type = BPF_PROG_TYPE_LWT_IN,
6627 },
6628 {
6629 "bounds checks mixing signed and unsigned, positive bounds",
6630 .insns = {
6631 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6632 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6633 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6634 BPF_LD_MAP_FD(BPF_REG_1, 0),
6635 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6636 BPF_FUNC_map_lookup_elem),
6637 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
6638 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6639 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6640 BPF_MOV64_IMM(BPF_REG_2, 2),
6641 BPF_JMP_REG(BPF_JGE, BPF_REG_2, BPF_REG_1, 3),
6642 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 4, 2),
6643 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6644 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6645 BPF_MOV64_IMM(BPF_REG_0, 0),
6646 BPF_EXIT_INSN(),
6647 },
6648 .fixup_map1 = { 3 },
6649 .errstr = "unbounded min value",
6650 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6651 .result = REJECT,
6652 },
6653 {
6654 "bounds checks mixing signed and unsigned",
6655 .insns = {
6656 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6657 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6658 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6659 BPF_LD_MAP_FD(BPF_REG_1, 0),
6660 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6661 BPF_FUNC_map_lookup_elem),
6662 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
6663 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6664 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6665 BPF_MOV64_IMM(BPF_REG_2, -1),
6666 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, 3),
6667 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6668 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6669 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6670 BPF_MOV64_IMM(BPF_REG_0, 0),
6671 BPF_EXIT_INSN(),
6672 },
6673 .fixup_map1 = { 3 },
6674 .errstr = "unbounded min value",
6675 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6676 .result = REJECT,
6677 },
6678 {
6679 "bounds checks mixing signed and unsigned, variant 2",
6680 .insns = {
6681 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6682 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6683 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6684 BPF_LD_MAP_FD(BPF_REG_1, 0),
6685 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6686 BPF_FUNC_map_lookup_elem),
6687 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6688 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6689 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6690 BPF_MOV64_IMM(BPF_REG_2, -1),
6691 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, 5),
6692 BPF_MOV64_IMM(BPF_REG_8, 0),
6693 BPF_ALU64_REG(BPF_ADD, BPF_REG_8, BPF_REG_1),
6694 BPF_JMP_IMM(BPF_JSGT, BPF_REG_8, 1, 2),
6695 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_8),
6696 BPF_ST_MEM(BPF_B, BPF_REG_8, 0, 0),
6697 BPF_MOV64_IMM(BPF_REG_0, 0),
6698 BPF_EXIT_INSN(),
6699 },
6700 .fixup_map1 = { 3 },
6701 .errstr = "unbounded min value",
6702 .errstr_unpriv = "R8 has unknown scalar with mixed signed bounds",
6703 .result = REJECT,
6704 },
6705 {
6706 "bounds checks mixing signed and unsigned, variant 3",
6707 .insns = {
6708 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6709 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6710 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6711 BPF_LD_MAP_FD(BPF_REG_1, 0),
6712 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6713 BPF_FUNC_map_lookup_elem),
6714 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 8),
6715 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6716 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6717 BPF_MOV64_IMM(BPF_REG_2, -1),
6718 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, 4),
6719 BPF_MOV64_REG(BPF_REG_8, BPF_REG_1),
6720 BPF_JMP_IMM(BPF_JSGT, BPF_REG_8, 1, 2),
6721 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_8),
6722 BPF_ST_MEM(BPF_B, BPF_REG_8, 0, 0),
6723 BPF_MOV64_IMM(BPF_REG_0, 0),
6724 BPF_EXIT_INSN(),
6725 },
6726 .fixup_map1 = { 3 },
6727 .errstr = "unbounded min value",
6728 .errstr_unpriv = "R8 has unknown scalar with mixed signed bounds",
6729 .result = REJECT,
6730 },
6731 {
6732 "bounds checks mixing signed and unsigned, variant 4",
6733 .insns = {
6734 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6735 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6736 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6737 BPF_LD_MAP_FD(BPF_REG_1, 0),
6738 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6739 BPF_FUNC_map_lookup_elem),
6740 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
6741 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6742 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6743 BPF_MOV64_IMM(BPF_REG_2, 1),
6744 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
6745 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6746 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6747 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6748 BPF_MOV64_IMM(BPF_REG_0, 0),
6749 BPF_EXIT_INSN(),
6750 },
6751 .fixup_map1 = { 3 },
6752 .result = ACCEPT,
6753 },
6754 {
6755 "bounds checks mixing signed and unsigned, variant 5",
6756 .insns = {
6757 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6758 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6759 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6760 BPF_LD_MAP_FD(BPF_REG_1, 0),
6761 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6762 BPF_FUNC_map_lookup_elem),
6763 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6764 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6765 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6766 BPF_MOV64_IMM(BPF_REG_2, -1),
6767 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, 5),
6768 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 4),
6769 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 4),
6770 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
6771 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6772 BPF_MOV64_IMM(BPF_REG_0, 0),
6773 BPF_EXIT_INSN(),
6774 },
6775 .fixup_map1 = { 3 },
6776 .errstr = "unbounded min value",
6777 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6778 .result = REJECT,
6779 },
6780 {
6781 "bounds checks mixing signed and unsigned, variant 6",
6782 .insns = {
6783 BPF_MOV64_IMM(BPF_REG_2, 0),
6784 BPF_MOV64_REG(BPF_REG_3, BPF_REG_10),
6785 BPF_ALU64_IMM(BPF_ADD, BPF_REG_3, -512),
6786 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6787 BPF_LDX_MEM(BPF_DW, BPF_REG_4, BPF_REG_10, -16),
6788 BPF_MOV64_IMM(BPF_REG_6, -1),
6789 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_6, 5),
6790 BPF_JMP_IMM(BPF_JSGT, BPF_REG_4, 1, 4),
6791 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 1),
6792 BPF_MOV64_IMM(BPF_REG_5, 0),
6793 BPF_ST_MEM(BPF_H, BPF_REG_10, -512, 0),
6794 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6795 BPF_FUNC_skb_load_bytes),
6796 BPF_MOV64_IMM(BPF_REG_0, 0),
6797 BPF_EXIT_INSN(),
6798 },
6799 .errstr = "R4 min value is negative, either use unsigned",
6800 .result = REJECT,
6801 },
6802 {
6803 "bounds checks mixing signed and unsigned, variant 7",
6804 .insns = {
6805 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6806 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6807 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6808 BPF_LD_MAP_FD(BPF_REG_1, 0),
6809 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6810 BPF_FUNC_map_lookup_elem),
6811 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7),
6812 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6813 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6814 BPF_MOV64_IMM(BPF_REG_2, 1024 * 1024 * 1024),
6815 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, 3),
6816 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6817 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6818 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6819 BPF_MOV64_IMM(BPF_REG_0, 0),
6820 BPF_EXIT_INSN(),
6821 },
6822 .fixup_map1 = { 3 },
6823 .result = ACCEPT,
6824 },
6825 {
6826 "bounds checks mixing signed and unsigned, variant 8",
6827 .insns = {
6828 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6829 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6830 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6831 BPF_LD_MAP_FD(BPF_REG_1, 0),
6832 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6833 BPF_FUNC_map_lookup_elem),
6834 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6835 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6836 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6837 BPF_MOV64_IMM(BPF_REG_2, -1),
6838 BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_1, 2),
6839 BPF_MOV64_IMM(BPF_REG_0, 0),
6840 BPF_EXIT_INSN(),
6841 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6842 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6843 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6844 BPF_MOV64_IMM(BPF_REG_0, 0),
6845 BPF_EXIT_INSN(),
6846 },
6847 .fixup_map1 = { 3 },
6848 .errstr = "unbounded min value",
6849 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6850 .result = REJECT,
6851 },
6852 {
6853 "bounds checks mixing signed and unsigned, variant 9",
6854 .insns = {
6855 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6856 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6857 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6858 BPF_LD_MAP_FD(BPF_REG_1, 0),
6859 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6860 BPF_FUNC_map_lookup_elem),
6861 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 10),
6862 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6863 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6864 BPF_LD_IMM64(BPF_REG_2, -9223372036854775808ULL),
6865 BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_1, 2),
6866 BPF_MOV64_IMM(BPF_REG_0, 0),
6867 BPF_EXIT_INSN(),
6868 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6869 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6870 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6871 BPF_MOV64_IMM(BPF_REG_0, 0),
6872 BPF_EXIT_INSN(),
6873 },
6874 .fixup_map1 = { 3 },
6875 .result = ACCEPT,
6876 },
6877 {
6878 "bounds checks mixing signed and unsigned, variant 10",
6879 .insns = {
6880 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6881 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6882 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6883 BPF_LD_MAP_FD(BPF_REG_1, 0),
6884 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6885 BPF_FUNC_map_lookup_elem),
6886 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6887 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6888 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6889 BPF_MOV64_IMM(BPF_REG_2, 0),
6890 BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_1, 2),
6891 BPF_MOV64_IMM(BPF_REG_0, 0),
6892 BPF_EXIT_INSN(),
6893 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6894 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6895 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6896 BPF_MOV64_IMM(BPF_REG_0, 0),
6897 BPF_EXIT_INSN(),
6898 },
6899 .fixup_map1 = { 3 },
6900 .errstr = "unbounded min value",
6901 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6902 .result = REJECT,
6903 },
6904 {
6905 "bounds checks mixing signed and unsigned, variant 11",
6906 .insns = {
6907 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6908 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6909 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6910 BPF_LD_MAP_FD(BPF_REG_1, 0),
6911 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6912 BPF_FUNC_map_lookup_elem),
6913 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6914 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6915 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6916 BPF_MOV64_IMM(BPF_REG_2, -1),
6917 BPF_JMP_REG(BPF_JGE, BPF_REG_2, BPF_REG_1, 2),
6918 /* Dead branch. */
6919 BPF_MOV64_IMM(BPF_REG_0, 0),
6920 BPF_EXIT_INSN(),
6921 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6922 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6923 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6924 BPF_MOV64_IMM(BPF_REG_0, 0),
6925 BPF_EXIT_INSN(),
6926 },
6927 .fixup_map1 = { 3 },
6928 .errstr = "unbounded min value",
6929 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6930 .result = REJECT,
6931 },
6932 {
6933 "bounds checks mixing signed and unsigned, variant 12",
6934 .insns = {
6935 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6936 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6937 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6938 BPF_LD_MAP_FD(BPF_REG_1, 0),
6939 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6940 BPF_FUNC_map_lookup_elem),
6941 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
6942 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6943 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6944 BPF_MOV64_IMM(BPF_REG_2, -6),
6945 BPF_JMP_REG(BPF_JGE, BPF_REG_2, BPF_REG_1, 2),
6946 BPF_MOV64_IMM(BPF_REG_0, 0),
6947 BPF_EXIT_INSN(),
6948 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
6949 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
6950 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6951 BPF_MOV64_IMM(BPF_REG_0, 0),
6952 BPF_EXIT_INSN(),
6953 },
6954 .fixup_map1 = { 3 },
6955 .errstr = "unbounded min value",
6956 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
6957 .result = REJECT,
6958 },
6959 {
6960 "bounds checks mixing signed and unsigned, variant 13",
6961 .insns = {
6962 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6963 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6964 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6965 BPF_LD_MAP_FD(BPF_REG_1, 0),
6966 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6967 BPF_FUNC_map_lookup_elem),
6968 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
6969 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
6970 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
6971 BPF_MOV64_IMM(BPF_REG_2, 2),
6972 BPF_JMP_REG(BPF_JGE, BPF_REG_2, BPF_REG_1, 2),
6973 BPF_MOV64_IMM(BPF_REG_7, 1),
6974 BPF_JMP_IMM(BPF_JSGT, BPF_REG_7, 0, 2),
6975 BPF_MOV64_IMM(BPF_REG_0, 0),
6976 BPF_EXIT_INSN(),
6977 BPF_ALU64_REG(BPF_ADD, BPF_REG_7, BPF_REG_1),
6978 BPF_JMP_IMM(BPF_JSGT, BPF_REG_7, 4, 2),
6979 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_7),
6980 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
6981 BPF_MOV64_IMM(BPF_REG_0, 0),
6982 BPF_EXIT_INSN(),
6983 },
6984 .fixup_map1 = { 3 },
6985 .errstr = "unbounded min value",
6986 .errstr_unpriv = "R7 has unknown scalar with mixed signed bounds",
6987 .result = REJECT,
6988 },
6989 {
6990 "bounds checks mixing signed and unsigned, variant 14",
6991 .insns = {
6992 BPF_LDX_MEM(BPF_W, BPF_REG_9, BPF_REG_1,
6993 offsetof(struct __sk_buff, mark)),
6994 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
6995 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
6996 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
6997 BPF_LD_MAP_FD(BPF_REG_1, 0),
6998 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
6999 BPF_FUNC_map_lookup_elem),
7000 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 8),
7001 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
7002 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
7003 BPF_MOV64_IMM(BPF_REG_2, -1),
7004 BPF_MOV64_IMM(BPF_REG_8, 2),
7005 BPF_JMP_IMM(BPF_JEQ, BPF_REG_9, 42, 6),
7006 BPF_JMP_REG(BPF_JSGT, BPF_REG_8, BPF_REG_1, 3),
7007 BPF_JMP_IMM(BPF_JSGT, BPF_REG_1, 1, 2),
7008 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7009 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
7010 BPF_MOV64_IMM(BPF_REG_0, 0),
7011 BPF_EXIT_INSN(),
7012 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_2, -3),
7013 BPF_JMP_IMM(BPF_JA, 0, 0, -7),
7014 },
7015 .fixup_map1 = { 4 },
7016 .errstr = "R0 invalid mem access 'inv'",
7017 .errstr_unpriv = "R0 invalid mem access 'inv'",
7018 .result = REJECT,
7019 },
7020 {
7021 "bounds checks mixing signed and unsigned, variant 15",
7022 .insns = {
7023 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7024 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7025 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7026 BPF_LD_MAP_FD(BPF_REG_1, 0),
7027 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7028 BPF_FUNC_map_lookup_elem),
7029 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7030 BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, -8),
7031 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_10, -16),
7032 BPF_MOV64_IMM(BPF_REG_2, -6),
7033 BPF_JMP_REG(BPF_JGE, BPF_REG_2, BPF_REG_1, 2),
7034 BPF_MOV64_IMM(BPF_REG_0, 0),
7035 BPF_EXIT_INSN(),
7036 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7037 BPF_JMP_IMM(BPF_JGT, BPF_REG_0, 1, 2),
7038 BPF_MOV64_IMM(BPF_REG_0, 0),
7039 BPF_EXIT_INSN(),
7040 BPF_ST_MEM(BPF_B, BPF_REG_0, 0, 0),
7041 BPF_MOV64_IMM(BPF_REG_0, 0),
7042 BPF_EXIT_INSN(),
7043 },
7044 .fixup_map1 = { 3 },
7045 .errstr = "unbounded min value",
7046 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
7047 .result = REJECT,
7048 .result_unpriv = REJECT,
7049 },
7050 {
7051 "subtraction bounds (map value) variant 1",
7052 .insns = {
7053 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7054 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7055 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7056 BPF_LD_MAP_FD(BPF_REG_1, 0),
7057 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7058 BPF_FUNC_map_lookup_elem),
7059 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
7060 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7061 BPF_JMP_IMM(BPF_JGT, BPF_REG_1, 0xff, 7),
7062 BPF_LDX_MEM(BPF_B, BPF_REG_3, BPF_REG_0, 1),
7063 BPF_JMP_IMM(BPF_JGT, BPF_REG_3, 0xff, 5),
7064 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_3),
7065 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 56),
7066 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7067 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7068 BPF_EXIT_INSN(),
7069 BPF_MOV64_IMM(BPF_REG_0, 0),
7070 BPF_EXIT_INSN(),
7071 },
7072 .fixup_map1 = { 3 },
7073 .errstr = "R0 max value is outside of the array range",
7074 .result = REJECT,
7075 },
7076 {
7077 "subtraction bounds (map value) variant 2",
7078 .insns = {
7079 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7080 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7081 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7082 BPF_LD_MAP_FD(BPF_REG_1, 0),
7083 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7084 BPF_FUNC_map_lookup_elem),
7085 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 8),
7086 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7087 BPF_JMP_IMM(BPF_JGT, BPF_REG_1, 0xff, 6),
7088 BPF_LDX_MEM(BPF_B, BPF_REG_3, BPF_REG_0, 1),
7089 BPF_JMP_IMM(BPF_JGT, BPF_REG_3, 0xff, 4),
7090 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_3),
7091 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7092 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7093 BPF_EXIT_INSN(),
7094 BPF_MOV64_IMM(BPF_REG_0, 0),
7095 BPF_EXIT_INSN(),
7096 },
7097 .fixup_map1 = { 3 },
7098 .errstr = "R0 min value is negative, either use unsigned index or do a if (index >=0) check.",
7099 .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds",
7100 .result = REJECT,
7101 },
7102 {
7103 "check subtraction on pointers for unpriv",
7104 .insns = {
7105 BPF_MOV64_IMM(BPF_REG_0, 0),
7106 BPF_LD_MAP_FD(BPF_REG_ARG1, 0),
7107 BPF_MOV64_REG(BPF_REG_ARG2, BPF_REG_FP),
7108 BPF_ALU64_IMM(BPF_ADD, BPF_REG_ARG2, -8),
7109 BPF_ST_MEM(BPF_DW, BPF_REG_ARG2, 0, 9),
7110 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7111 BPF_FUNC_map_lookup_elem),
7112 BPF_MOV64_REG(BPF_REG_9, BPF_REG_FP),
7113 BPF_ALU64_REG(BPF_SUB, BPF_REG_9, BPF_REG_0),
7114 BPF_LD_MAP_FD(BPF_REG_ARG1, 0),
7115 BPF_MOV64_REG(BPF_REG_ARG2, BPF_REG_FP),
7116 BPF_ALU64_IMM(BPF_ADD, BPF_REG_ARG2, -8),
7117 BPF_ST_MEM(BPF_DW, BPF_REG_ARG2, 0, 0),
7118 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7119 BPF_FUNC_map_lookup_elem),
7120 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
7121 BPF_EXIT_INSN(),
7122 BPF_STX_MEM(BPF_DW, BPF_REG_0, BPF_REG_9, 0),
7123 BPF_MOV64_IMM(BPF_REG_0, 0),
7124 BPF_EXIT_INSN(),
7125 },
7126 .fixup_map1 = { 1, 9 },
7127 .result = ACCEPT,
7128 .result_unpriv = REJECT,
7129 .errstr_unpriv = "R9 pointer -= pointer prohibited",
7130 },
7131 {
7132 "bounds check based on zero-extended MOV",
7133 .insns = {
7134 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7135 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7136 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7137 BPF_LD_MAP_FD(BPF_REG_1, 0),
7138 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7139 BPF_FUNC_map_lookup_elem),
7140 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7141 /* r2 = 0x0000'0000'ffff'ffff */
7142 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff),
7143 /* r2 = 0 */
7144 BPF_ALU64_IMM(BPF_RSH, BPF_REG_2, 32),
7145 /* no-op */
7146 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
7147 /* access at offset 0 */
7148 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7149 /* exit */
7150 BPF_MOV64_IMM(BPF_REG_0, 0),
7151 BPF_EXIT_INSN(),
7152 },
7153 .fixup_map1 = { 3 },
7154 .result = ACCEPT
7155 },
7156 {
7157 "bounds check based on sign-extended MOV. test1",
7158 .insns = {
7159 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7160 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7161 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7162 BPF_LD_MAP_FD(BPF_REG_1, 0),
7163 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7164 BPF_FUNC_map_lookup_elem),
7165 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7166 /* r2 = 0xffff'ffff'ffff'ffff */
7167 BPF_MOV64_IMM(BPF_REG_2, 0xffffffff),
7168 /* r2 = 0xffff'ffff */
7169 BPF_ALU64_IMM(BPF_RSH, BPF_REG_2, 32),
7170 /* r0 = <oob pointer> */
7171 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
7172 /* access to OOB pointer */
7173 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7174 /* exit */
7175 BPF_MOV64_IMM(BPF_REG_0, 0),
7176 BPF_EXIT_INSN(),
7177 },
7178 .fixup_map1 = { 3 },
7179 .errstr = "map_value pointer and 4294967295",
7180 .result = REJECT
7181 },
7182 {
7183 "bounds check based on sign-extended MOV. test2",
7184 .insns = {
7185 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7186 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7187 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7188 BPF_LD_MAP_FD(BPF_REG_1, 0),
7189 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7190 BPF_FUNC_map_lookup_elem),
7191 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7192 /* r2 = 0xffff'ffff'ffff'ffff */
7193 BPF_MOV64_IMM(BPF_REG_2, 0xffffffff),
7194 /* r2 = 0xfff'ffff */
7195 BPF_ALU64_IMM(BPF_RSH, BPF_REG_2, 36),
7196 /* r0 = <oob pointer> */
7197 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_2),
7198 /* access to OOB pointer */
7199 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7200 /* exit */
7201 BPF_MOV64_IMM(BPF_REG_0, 0),
7202 BPF_EXIT_INSN(),
7203 },
7204 .fixup_map1 = { 3 },
7205 .errstr = "R0 min value is outside of the array range",
7206 .result = REJECT
7207 },
7208 {
7209 "bounds check based on reg_off + var_off + insn_off. test1",
7210 .insns = {
7211 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
7212 offsetof(struct __sk_buff, mark)),
7213 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7214 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7215 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7216 BPF_LD_MAP_FD(BPF_REG_1, 0),
7217 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7218 BPF_FUNC_map_lookup_elem),
7219 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7220 BPF_ALU64_IMM(BPF_AND, BPF_REG_6, 1),
7221 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, (1 << 29) - 1),
7222 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_6),
7223 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, (1 << 29) - 1),
7224 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 3),
7225 BPF_MOV64_IMM(BPF_REG_0, 0),
7226 BPF_EXIT_INSN(),
7227 },
7228 .fixup_map1 = { 4 },
7229 .errstr = "value_size=8 off=1073741825",
7230 .result = REJECT,
7231 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
7232 },
7233 {
7234 "bounds check based on reg_off + var_off + insn_off. test2",
7235 .insns = {
7236 BPF_LDX_MEM(BPF_W, BPF_REG_6, BPF_REG_1,
7237 offsetof(struct __sk_buff, mark)),
7238 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7239 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7240 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7241 BPF_LD_MAP_FD(BPF_REG_1, 0),
7242 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7243 BPF_FUNC_map_lookup_elem),
7244 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4),
7245 BPF_ALU64_IMM(BPF_AND, BPF_REG_6, 1),
7246 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, (1 << 30) - 1),
7247 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_6),
7248 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, (1 << 29) - 1),
7249 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 3),
7250 BPF_MOV64_IMM(BPF_REG_0, 0),
7251 BPF_EXIT_INSN(),
7252 },
7253 .fixup_map1 = { 4 },
7254 .errstr = "value 1073741823",
7255 .result = REJECT,
7256 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
7257 },
7258 {
7259 "bounds check after truncation of non-boundary-crossing range",
7260 .insns = {
7261 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7262 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7263 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7264 BPF_LD_MAP_FD(BPF_REG_1, 0),
7265 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7266 BPF_FUNC_map_lookup_elem),
7267 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
7268 /* r1 = [0x00, 0xff] */
7269 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7270 BPF_MOV64_IMM(BPF_REG_2, 1),
7271 /* r2 = 0x10'0000'0000 */
7272 BPF_ALU64_IMM(BPF_LSH, BPF_REG_2, 36),
7273 /* r1 = [0x10'0000'0000, 0x10'0000'00ff] */
7274 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
7275 /* r1 = [0x10'7fff'ffff, 0x10'8000'00fe] */
7276 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x7fffffff),
7277 /* r1 = [0x00, 0xff] */
7278 BPF_ALU32_IMM(BPF_SUB, BPF_REG_1, 0x7fffffff),
7279 /* r1 = 0 */
7280 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 8),
7281 /* no-op */
7282 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7283 /* access at offset 0 */
7284 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7285 /* exit */
7286 BPF_MOV64_IMM(BPF_REG_0, 0),
7287 BPF_EXIT_INSN(),
7288 },
7289 .fixup_map1 = { 3 },
7290 .result = ACCEPT
7291 },
7292 {
7293 "bounds check after truncation of boundary-crossing range (1)",
7294 .insns = {
7295 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7296 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7297 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7298 BPF_LD_MAP_FD(BPF_REG_1, 0),
7299 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7300 BPF_FUNC_map_lookup_elem),
7301 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
7302 /* r1 = [0x00, 0xff] */
7303 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7304 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0xffffff80 >> 1),
7305 /* r1 = [0xffff'ff80, 0x1'0000'007f] */
7306 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0xffffff80 >> 1),
7307 /* r1 = [0xffff'ff80, 0xffff'ffff] or
7308 * [0x0000'0000, 0x0000'007f]
7309 */
7310 BPF_ALU32_IMM(BPF_ADD, BPF_REG_1, 0),
7311 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 0xffffff80 >> 1),
7312 /* r1 = [0x00, 0xff] or
7313 * [0xffff'ffff'0000'0080, 0xffff'ffff'ffff'ffff]
7314 */
7315 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 0xffffff80 >> 1),
7316 /* r1 = 0 or
7317 * [0x00ff'ffff'ff00'0000, 0x00ff'ffff'ffff'ffff]
7318 */
7319 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 8),
7320 /* no-op or OOB pointer computation */
7321 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7322 /* potentially OOB access */
7323 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7324 /* exit */
7325 BPF_MOV64_IMM(BPF_REG_0, 0),
7326 BPF_EXIT_INSN(),
7327 },
7328 .fixup_map1 = { 3 },
7329 /* not actually fully unbounded, but the bound is very high */
7330 .errstr = "R0 unbounded memory access",
7331 .result = REJECT
7332 },
7333 {
7334 "bounds check after truncation of boundary-crossing range (2)",
7335 .insns = {
7336 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7337 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7338 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7339 BPF_LD_MAP_FD(BPF_REG_1, 0),
7340 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7341 BPF_FUNC_map_lookup_elem),
7342 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 9),
7343 /* r1 = [0x00, 0xff] */
7344 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7345 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0xffffff80 >> 1),
7346 /* r1 = [0xffff'ff80, 0x1'0000'007f] */
7347 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0xffffff80 >> 1),
7348 /* r1 = [0xffff'ff80, 0xffff'ffff] or
7349 * [0x0000'0000, 0x0000'007f]
7350 * difference to previous test: truncation via MOV32
7351 * instead of ALU32.
7352 */
7353 BPF_MOV32_REG(BPF_REG_1, BPF_REG_1),
7354 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 0xffffff80 >> 1),
7355 /* r1 = [0x00, 0xff] or
7356 * [0xffff'ffff'0000'0080, 0xffff'ffff'ffff'ffff]
7357 */
7358 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 0xffffff80 >> 1),
7359 /* r1 = 0 or
7360 * [0x00ff'ffff'ff00'0000, 0x00ff'ffff'ffff'ffff]
7361 */
7362 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 8),
7363 /* no-op or OOB pointer computation */
7364 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7365 /* potentially OOB access */
7366 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7367 /* exit */
7368 BPF_MOV64_IMM(BPF_REG_0, 0),
7369 BPF_EXIT_INSN(),
7370 },
7371 .fixup_map1 = { 3 },
7372 /* not actually fully unbounded, but the bound is very high */
7373 .errstr = "R0 unbounded memory access",
7374 .result = REJECT
7375 },
7376 {
7377 "bounds check after wrapping 32-bit addition",
7378 .insns = {
7379 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7380 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7381 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7382 BPF_LD_MAP_FD(BPF_REG_1, 0),
7383 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7384 BPF_FUNC_map_lookup_elem),
7385 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5),
7386 /* r1 = 0x7fff'ffff */
7387 BPF_MOV64_IMM(BPF_REG_1, 0x7fffffff),
7388 /* r1 = 0xffff'fffe */
7389 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x7fffffff),
7390 /* r1 = 0 */
7391 BPF_ALU32_IMM(BPF_ADD, BPF_REG_1, 2),
7392 /* no-op */
7393 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7394 /* access at offset 0 */
7395 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7396 /* exit */
7397 BPF_MOV64_IMM(BPF_REG_0, 0),
7398 BPF_EXIT_INSN(),
7399 },
7400 .fixup_map1 = { 3 },
7401 .result = ACCEPT
7402 },
7403 {
7404 "bounds check after shift with oversized count operand",
7405 .insns = {
7406 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7407 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7408 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7409 BPF_LD_MAP_FD(BPF_REG_1, 0),
7410 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7411 BPF_FUNC_map_lookup_elem),
7412 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
7413 BPF_MOV64_IMM(BPF_REG_2, 32),
7414 BPF_MOV64_IMM(BPF_REG_1, 1),
7415 /* r1 = (u32)1 << (u32)32 = ? */
7416 BPF_ALU32_REG(BPF_LSH, BPF_REG_1, BPF_REG_2),
7417 /* r1 = [0x0000, 0xffff] */
7418 BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 0xffff),
7419 /* computes unknown pointer, potentially OOB */
7420 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7421 /* potentially OOB access */
7422 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7423 /* exit */
7424 BPF_MOV64_IMM(BPF_REG_0, 0),
7425 BPF_EXIT_INSN(),
7426 },
7427 .fixup_map1 = { 3 },
7428 .errstr = "R0 max value is outside of the array range",
7429 .result = REJECT
7430 },
7431 {
7432 "bounds check after right shift of maybe-negative number",
7433 .insns = {
7434 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7435 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7436 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7437 BPF_LD_MAP_FD(BPF_REG_1, 0),
7438 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7439 BPF_FUNC_map_lookup_elem),
7440 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
7441 /* r1 = [0x00, 0xff] */
7442 BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7443 /* r1 = [-0x01, 0xfe] */
7444 BPF_ALU64_IMM(BPF_SUB, BPF_REG_1, 1),
7445 /* r1 = 0 or 0xff'ffff'ffff'ffff */
7446 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 8),
7447 /* r1 = 0 or 0xffff'ffff'ffff */
7448 BPF_ALU64_IMM(BPF_RSH, BPF_REG_1, 8),
7449 /* computes unknown pointer, potentially OOB */
7450 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7451 /* potentially OOB access */
7452 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7453 /* exit */
7454 BPF_MOV64_IMM(BPF_REG_0, 0),
7455 BPF_EXIT_INSN(),
7456 },
7457 .fixup_map1 = { 3 },
7458 .errstr = "R0 unbounded memory access",
7459 .result = REJECT
7460 },
7461 {
7462 "bounds check after 32-bit right shift with 64-bit input",
7463 .insns = {
7464 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7465 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7466 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7467 BPF_LD_MAP_FD(BPF_REG_1, 0),
7468 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7469 BPF_FUNC_map_lookup_elem),
7470 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6),
7471 /* r1 = 2 */
7472 BPF_MOV64_IMM(BPF_REG_1, 2),
7473 /* r1 = 1<<32 */
7474 BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 31),
7475 /* r1 = 0 (NOT 2!) */
7476 BPF_ALU32_IMM(BPF_RSH, BPF_REG_1, 31),
7477 /* r1 = 0xffff'fffe (NOT 0!) */
7478 BPF_ALU32_IMM(BPF_SUB, BPF_REG_1, 2),
7479 /* computes OOB pointer */
7480 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7481 /* OOB access */
7482 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7483 /* exit */
7484 BPF_MOV64_IMM(BPF_REG_0, 0),
7485 BPF_EXIT_INSN(),
7486 },
7487 .fixup_map1 = { 3 },
7488 .errstr = "R0 invalid mem access",
7489 .result = REJECT,
7490 },
7491 {
7492 "bounds check map access with off+size signed 32bit overflow. test1",
7493 .insns = {
7494 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7495 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7496 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7497 BPF_LD_MAP_FD(BPF_REG_1, 0),
7498 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7499 BPF_FUNC_map_lookup_elem),
7500 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
7501 BPF_EXIT_INSN(),
7502 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0x7ffffffe),
7503 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 0),
7504 BPF_JMP_A(0),
7505 BPF_EXIT_INSN(),
7506 },
7507 .fixup_map1 = { 3 },
7508 .errstr = "map_value pointer and 2147483646",
7509 .result = REJECT
7510 },
7511 {
7512 "bounds check map access with off+size signed 32bit overflow. test2",
7513 .insns = {
7514 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7515 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7516 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7517 BPF_LD_MAP_FD(BPF_REG_1, 0),
7518 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7519 BPF_FUNC_map_lookup_elem),
7520 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
7521 BPF_EXIT_INSN(),
7522 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0x1fffffff),
7523 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0x1fffffff),
7524 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 0x1fffffff),
7525 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 0),
7526 BPF_JMP_A(0),
7527 BPF_EXIT_INSN(),
7528 },
7529 .fixup_map1 = { 3 },
7530 .errstr = "pointer offset 1073741822",
7531 .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range",
7532 .result = REJECT
7533 },
7534 {
7535 "bounds check map access with off+size signed 32bit overflow. test3",
7536 .insns = {
7537 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7538 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7539 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7540 BPF_LD_MAP_FD(BPF_REG_1, 0),
7541 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7542 BPF_FUNC_map_lookup_elem),
7543 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
7544 BPF_EXIT_INSN(),
7545 BPF_ALU64_IMM(BPF_SUB, BPF_REG_0, 0x1fffffff),
7546 BPF_ALU64_IMM(BPF_SUB, BPF_REG_0, 0x1fffffff),
7547 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 2),
7548 BPF_JMP_A(0),
7549 BPF_EXIT_INSN(),
7550 },
7551 .fixup_map1 = { 3 },
7552 .errstr = "pointer offset -1073741822",
7553 .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range",
7554 .result = REJECT
7555 },
7556 {
7557 "bounds check map access with off+size signed 32bit overflow. test4",
7558 .insns = {
7559 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7560 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7561 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7562 BPF_LD_MAP_FD(BPF_REG_1, 0),
7563 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7564 BPF_FUNC_map_lookup_elem),
7565 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
7566 BPF_EXIT_INSN(),
7567 BPF_MOV64_IMM(BPF_REG_1, 1000000),
7568 BPF_ALU64_IMM(BPF_MUL, BPF_REG_1, 1000000),
7569 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7570 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 2),
7571 BPF_JMP_A(0),
7572 BPF_EXIT_INSN(),
7573 },
7574 .fixup_map1 = { 3 },
7575 .errstr = "map_value pointer and 1000000000000",
7576 .result = REJECT
7577 },
7578 {
7579 "pointer/scalar confusion in state equality check (way 1)",
7580 .insns = {
7581 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7582 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7583 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7584 BPF_LD_MAP_FD(BPF_REG_1, 0),
7585 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7586 BPF_FUNC_map_lookup_elem),
7587 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 2),
7588 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 0),
7589 BPF_JMP_A(1),
7590 BPF_MOV64_REG(BPF_REG_0, BPF_REG_10),
7591 BPF_JMP_A(0),
7592 BPF_EXIT_INSN(),
7593 },
7594 .fixup_map1 = { 3 },
7595 .result = ACCEPT,
7596 .result_unpriv = REJECT,
7597 .errstr_unpriv = "R0 leaks addr as return value"
7598 },
7599 {
7600 "pointer/scalar confusion in state equality check (way 2)",
7601 .insns = {
7602 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7603 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7604 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7605 BPF_LD_MAP_FD(BPF_REG_1, 0),
7606 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7607 BPF_FUNC_map_lookup_elem),
7608 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 2),
7609 BPF_MOV64_REG(BPF_REG_0, BPF_REG_10),
7610 BPF_JMP_A(1),
7611 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_0, 0),
7612 BPF_EXIT_INSN(),
7613 },
7614 .fixup_map1 = { 3 },
7615 .result = ACCEPT,
7616 .result_unpriv = REJECT,
7617 .errstr_unpriv = "R0 leaks addr as return value"
7618 },
7619 {
7620 "variable-offset ctx access",
7621 .insns = {
7622 /* Get an unknown value */
7623 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1, 0),
7624 /* Make it small and 4-byte aligned */
7625 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 4),
7626 /* add it to skb. We now have either &skb->len or
7627 * &skb->pkt_type, but we don't know which
7628 */
7629 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2),
7630 /* dereference it */
7631 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0),
7632 BPF_EXIT_INSN(),
7633 },
7634 .errstr = "variable ctx access var_off=(0x0; 0x4)",
7635 .result = REJECT,
7636 .prog_type = BPF_PROG_TYPE_LWT_IN,
7637 },
7638 {
7639 "variable-offset stack access",
7640 .insns = {
7641 /* Fill the top 8 bytes of the stack */
7642 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7643 /* Get an unknown value */
7644 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1, 0),
7645 /* Make it small and 4-byte aligned */
7646 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 4),
7647 BPF_ALU64_IMM(BPF_SUB, BPF_REG_2, 8),
7648 /* add it to fp. We now have either fp-4 or fp-8, but
7649 * we don't know which
7650 */
7651 BPF_ALU64_REG(BPF_ADD, BPF_REG_2, BPF_REG_10),
7652 /* dereference it */
7653 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_2, 0),
7654 BPF_EXIT_INSN(),
7655 },
7656 .errstr = "variable stack access var_off=(0xfffffffffffffff8; 0x4)",
7657 .result = REJECT,
7658 .prog_type = BPF_PROG_TYPE_LWT_IN,
7659 },
7660 {
7661 "indirect variable-offset stack access",
7662 .insns = {
7663 /* Fill the top 8 bytes of the stack */
7664 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7665 /* Get an unknown value */
7666 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1, 0),
7667 /* Make it small and 4-byte aligned */
7668 BPF_ALU64_IMM(BPF_AND, BPF_REG_2, 4),
7669 BPF_ALU64_IMM(BPF_SUB, BPF_REG_2, 8),
7670 /* add it to fp. We now have either fp-4 or fp-8, but
7671 * we don't know which
7672 */
7673 BPF_ALU64_REG(BPF_ADD, BPF_REG_2, BPF_REG_10),
7674 /* dereference it indirectly */
7675 BPF_LD_MAP_FD(BPF_REG_1, 0),
7676 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7677 BPF_FUNC_map_lookup_elem),
7678 BPF_MOV64_IMM(BPF_REG_0, 0),
7679 BPF_EXIT_INSN(),
7680 },
7681 .fixup_map1 = { 5 },
7682 .errstr = "variable stack read R2",
7683 .result = REJECT,
7684 .prog_type = BPF_PROG_TYPE_LWT_IN,
7685 },
7686 {
7687 "direct stack access with 32-bit wraparound. test1",
7688 .insns = {
7689 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
7690 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x7fffffff),
7691 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x7fffffff),
7692 BPF_MOV32_IMM(BPF_REG_0, 0),
7693 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7694 BPF_EXIT_INSN()
7695 },
7696 .errstr = "fp pointer and 2147483647",
7697 .result = REJECT
7698 },
7699 {
7700 "direct stack access with 32-bit wraparound. test2",
7701 .insns = {
7702 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
7703 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x3fffffff),
7704 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x3fffffff),
7705 BPF_MOV32_IMM(BPF_REG_0, 0),
7706 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7707 BPF_EXIT_INSN()
7708 },
7709 .errstr = "fp pointer and 1073741823",
7710 .result = REJECT
7711 },
7712 {
7713 "direct stack access with 32-bit wraparound. test3",
7714 .insns = {
7715 BPF_MOV64_REG(BPF_REG_1, BPF_REG_10),
7716 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x1fffffff),
7717 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0x1fffffff),
7718 BPF_MOV32_IMM(BPF_REG_0, 0),
7719 BPF_STX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0),
7720 BPF_EXIT_INSN()
7721 },
7722 .errstr = "fp pointer offset 1073741822",
7723 .errstr_unpriv = "R1 stack pointer arithmetic goes out of range",
7724 .result = REJECT
7725 },
7726 {
7727 "liveness pruning and write screening",
7728 .insns = {
7729 /* Get an unknown value */
7730 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1, 0),
7731 /* branch conditions teach us nothing about R2 */
7732 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
7733 BPF_MOV64_IMM(BPF_REG_0, 0),
7734 BPF_JMP_IMM(BPF_JGE, BPF_REG_2, 0, 1),
7735 BPF_MOV64_IMM(BPF_REG_0, 0),
7736 BPF_EXIT_INSN(),
7737 },
7738 .errstr = "R0 !read_ok",
7739 .result = REJECT,
7740 .prog_type = BPF_PROG_TYPE_LWT_IN,
7741 },
7742 {
7743 "varlen_map_value_access pruning",
7744 .insns = {
7745 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
7746 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
7747 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
7748 BPF_LD_MAP_FD(BPF_REG_1, 0),
7749 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7750 BPF_FUNC_map_lookup_elem),
7751 BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 8),
7752 BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0),
7753 BPF_MOV32_IMM(BPF_REG_2, MAX_ENTRIES),
7754 BPF_JMP_REG(BPF_JSGT, BPF_REG_2, BPF_REG_1, 1),
7755 BPF_MOV32_IMM(BPF_REG_1, 0),
7756 BPF_ALU32_IMM(BPF_LSH, BPF_REG_1, 2),
7757 BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1),
7758 BPF_JMP_IMM(BPF_JA, 0, 0, 0),
7759 BPF_ST_MEM(BPF_DW, BPF_REG_0, 0,
7760 offsetof(struct test_val, foo)),
7761 BPF_EXIT_INSN(),
7762 },
7763 .fixup_map2 = { 3 },
7764 .errstr_unpriv = "R0 leaks addr",
7765 .errstr = "R0 unbounded memory access",
7766 .result_unpriv = REJECT,
7767 .result = REJECT,
7768 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
7769 },
7770 {
7771 "invalid 64-bit BPF_END",
7772 .insns = {
7773 BPF_MOV32_IMM(BPF_REG_0, 0),
7774 {
7775 .code = BPF_ALU64 | BPF_END | BPF_TO_LE,
7776 .dst_reg = BPF_REG_0,
7777 .src_reg = 0,
7778 .off = 0,
7779 .imm = 32,
7780 },
7781 BPF_EXIT_INSN(),
7782 },
7783 .errstr = "BPF_END uses reserved fields",
7784 .result = REJECT,
7785 },
7786 {
7787 "meta access, test1",
7788 .insns = {
7789 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7790 offsetof(struct xdp_md, data_meta)),
7791 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7792 offsetof(struct xdp_md, data)),
7793 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
7794 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7795 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
7796 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7797 BPF_MOV64_IMM(BPF_REG_0, 0),
7798 BPF_EXIT_INSN(),
7799 },
7800 .result = ACCEPT,
7801 .prog_type = BPF_PROG_TYPE_XDP,
7802 },
7803 {
7804 "meta access, test2",
7805 .insns = {
7806 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7807 offsetof(struct xdp_md, data_meta)),
7808 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7809 offsetof(struct xdp_md, data)),
7810 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
7811 BPF_ALU64_IMM(BPF_SUB, BPF_REG_0, 8),
7812 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
7813 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 8),
7814 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
7815 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0),
7816 BPF_MOV64_IMM(BPF_REG_0, 0),
7817 BPF_EXIT_INSN(),
7818 },
7819 .result = REJECT,
7820 .errstr = "invalid access to packet, off=-8",
7821 .prog_type = BPF_PROG_TYPE_XDP,
7822 },
7823 {
7824 "meta access, test3",
7825 .insns = {
7826 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7827 offsetof(struct xdp_md, data_meta)),
7828 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7829 offsetof(struct xdp_md, data_end)),
7830 BPF_MOV64_REG(BPF_REG_0, BPF_REG_2),
7831 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7832 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
7833 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7834 BPF_MOV64_IMM(BPF_REG_0, 0),
7835 BPF_EXIT_INSN(),
7836 },
7837 .result = REJECT,
7838 .errstr = "invalid access to packet",
7839 .prog_type = BPF_PROG_TYPE_XDP,
7840 },
7841 {
7842 "meta access, test4",
7843 .insns = {
7844 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7845 offsetof(struct xdp_md, data_meta)),
7846 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7847 offsetof(struct xdp_md, data_end)),
7848 BPF_LDX_MEM(BPF_W, BPF_REG_4, BPF_REG_1,
7849 offsetof(struct xdp_md, data)),
7850 BPF_MOV64_REG(BPF_REG_0, BPF_REG_4),
7851 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7852 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_3, 1),
7853 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7854 BPF_MOV64_IMM(BPF_REG_0, 0),
7855 BPF_EXIT_INSN(),
7856 },
7857 .result = REJECT,
7858 .errstr = "invalid access to packet",
7859 .prog_type = BPF_PROG_TYPE_XDP,
7860 },
7861 {
7862 "meta access, test5",
7863 .insns = {
7864 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7865 offsetof(struct xdp_md, data_meta)),
7866 BPF_LDX_MEM(BPF_W, BPF_REG_4, BPF_REG_1,
7867 offsetof(struct xdp_md, data)),
7868 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
7869 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7870 BPF_JMP_REG(BPF_JGT, BPF_REG_0, BPF_REG_4, 3),
7871 BPF_MOV64_IMM(BPF_REG_2, -8),
7872 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
7873 BPF_FUNC_xdp_adjust_meta),
7874 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_3, 0),
7875 BPF_MOV64_IMM(BPF_REG_0, 0),
7876 BPF_EXIT_INSN(),
7877 },
7878 .result = REJECT,
7879 .errstr = "R3 !read_ok",
7880 .prog_type = BPF_PROG_TYPE_XDP,
7881 },
7882 {
7883 "meta access, test6",
7884 .insns = {
7885 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7886 offsetof(struct xdp_md, data_meta)),
7887 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7888 offsetof(struct xdp_md, data)),
7889 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
7890 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7891 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
7892 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 8),
7893 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_0, 1),
7894 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7895 BPF_MOV64_IMM(BPF_REG_0, 0),
7896 BPF_EXIT_INSN(),
7897 },
7898 .result = REJECT,
7899 .errstr = "invalid access to packet",
7900 .prog_type = BPF_PROG_TYPE_XDP,
7901 },
7902 {
7903 "meta access, test7",
7904 .insns = {
7905 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7906 offsetof(struct xdp_md, data_meta)),
7907 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7908 offsetof(struct xdp_md, data)),
7909 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
7910 BPF_ALU64_IMM(BPF_ADD, BPF_REG_0, 8),
7911 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
7912 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 8),
7913 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
7914 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7915 BPF_MOV64_IMM(BPF_REG_0, 0),
7916 BPF_EXIT_INSN(),
7917 },
7918 .result = ACCEPT,
7919 .prog_type = BPF_PROG_TYPE_XDP,
7920 },
7921 {
7922 "meta access, test8",
7923 .insns = {
7924 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7925 offsetof(struct xdp_md, data_meta)),
7926 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7927 offsetof(struct xdp_md, data)),
7928 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
7929 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 0xFFFF),
7930 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
7931 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7932 BPF_MOV64_IMM(BPF_REG_0, 0),
7933 BPF_EXIT_INSN(),
7934 },
7935 .result = ACCEPT,
7936 .prog_type = BPF_PROG_TYPE_XDP,
7937 },
7938 {
7939 "meta access, test9",
7940 .insns = {
7941 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7942 offsetof(struct xdp_md, data_meta)),
7943 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7944 offsetof(struct xdp_md, data)),
7945 BPF_MOV64_REG(BPF_REG_4, BPF_REG_2),
7946 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 0xFFFF),
7947 BPF_ALU64_IMM(BPF_ADD, BPF_REG_4, 1),
7948 BPF_JMP_REG(BPF_JGT, BPF_REG_4, BPF_REG_3, 1),
7949 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
7950 BPF_MOV64_IMM(BPF_REG_0, 0),
7951 BPF_EXIT_INSN(),
7952 },
7953 .result = REJECT,
7954 .errstr = "invalid access to packet",
7955 .prog_type = BPF_PROG_TYPE_XDP,
7956 },
7957 {
7958 "meta access, test10",
7959 .insns = {
7960 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7961 offsetof(struct xdp_md, data_meta)),
7962 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7963 offsetof(struct xdp_md, data)),
7964 BPF_LDX_MEM(BPF_W, BPF_REG_4, BPF_REG_1,
7965 offsetof(struct xdp_md, data_end)),
7966 BPF_MOV64_IMM(BPF_REG_5, 42),
7967 BPF_MOV64_IMM(BPF_REG_6, 24),
7968 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_5, -8),
7969 BPF_STX_XADD(BPF_DW, BPF_REG_10, BPF_REG_6, -8),
7970 BPF_LDX_MEM(BPF_DW, BPF_REG_5, BPF_REG_10, -8),
7971 BPF_JMP_IMM(BPF_JGT, BPF_REG_5, 100, 6),
7972 BPF_ALU64_REG(BPF_ADD, BPF_REG_3, BPF_REG_5),
7973 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
7974 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
7975 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 8),
7976 BPF_JMP_REG(BPF_JGT, BPF_REG_6, BPF_REG_5, 1),
7977 BPF_LDX_MEM(BPF_B, BPF_REG_2, BPF_REG_2, 0),
7978 BPF_MOV64_IMM(BPF_REG_0, 0),
7979 BPF_EXIT_INSN(),
7980 },
7981 .result = REJECT,
7982 .errstr = "invalid access to packet",
7983 .prog_type = BPF_PROG_TYPE_XDP,
7984 },
7985 {
7986 "meta access, test11",
7987 .insns = {
7988 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
7989 offsetof(struct xdp_md, data_meta)),
7990 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
7991 offsetof(struct xdp_md, data)),
7992 BPF_MOV64_IMM(BPF_REG_5, 42),
7993 BPF_MOV64_IMM(BPF_REG_6, 24),
7994 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_5, -8),
7995 BPF_STX_XADD(BPF_DW, BPF_REG_10, BPF_REG_6, -8),
7996 BPF_LDX_MEM(BPF_DW, BPF_REG_5, BPF_REG_10, -8),
7997 BPF_JMP_IMM(BPF_JGT, BPF_REG_5, 100, 6),
7998 BPF_ALU64_REG(BPF_ADD, BPF_REG_2, BPF_REG_5),
7999 BPF_MOV64_REG(BPF_REG_5, BPF_REG_2),
8000 BPF_MOV64_REG(BPF_REG_6, BPF_REG_2),
8001 BPF_ALU64_IMM(BPF_ADD, BPF_REG_6, 8),
8002 BPF_JMP_REG(BPF_JGT, BPF_REG_6, BPF_REG_3, 1),
8003 BPF_LDX_MEM(BPF_B, BPF_REG_5, BPF_REG_5, 0),
8004 BPF_MOV64_IMM(BPF_REG_0, 0),
8005 BPF_EXIT_INSN(),
8006 },
8007 .result = ACCEPT,
8008 .prog_type = BPF_PROG_TYPE_XDP,
8009 },
8010 {
8011 "meta access, test12",
8012 .insns = {
8013 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8014 offsetof(struct xdp_md, data_meta)),
8015 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8016 offsetof(struct xdp_md, data)),
8017 BPF_LDX_MEM(BPF_W, BPF_REG_4, BPF_REG_1,
8018 offsetof(struct xdp_md, data_end)),
8019 BPF_MOV64_REG(BPF_REG_5, BPF_REG_3),
8020 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 16),
8021 BPF_JMP_REG(BPF_JGT, BPF_REG_5, BPF_REG_4, 5),
8022 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_3, 0),
8023 BPF_MOV64_REG(BPF_REG_5, BPF_REG_2),
8024 BPF_ALU64_IMM(BPF_ADD, BPF_REG_5, 16),
8025 BPF_JMP_REG(BPF_JGT, BPF_REG_5, BPF_REG_3, 1),
8026 BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_2, 0),
8027 BPF_MOV64_IMM(BPF_REG_0, 0),
8028 BPF_EXIT_INSN(),
8029 },
8030 .result = ACCEPT,
8031 .prog_type = BPF_PROG_TYPE_XDP,
8032 },
8033 {
8034 "arithmetic ops make PTR_TO_CTX unusable",
8035 .insns = {
8036 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1,
8037 offsetof(struct __sk_buff, data) -
8038 offsetof(struct __sk_buff, mark)),
8039 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
8040 offsetof(struct __sk_buff, mark)),
8041 BPF_EXIT_INSN(),
8042 },
8043 .errstr = "dereference of modified ctx ptr",
8044 .result = REJECT,
8045 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
8046 },
8047 {
8048 "pkt_end - pkt_start is allowed",
8049 .insns = {
8050 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
8051 offsetof(struct __sk_buff, data_end)),
8052 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8053 offsetof(struct __sk_buff, data)),
8054 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_2),
8055 BPF_EXIT_INSN(),
8056 },
8057 .result = ACCEPT,
8058 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
8059 },
8060 {
8061 "XDP pkt read, pkt_end mangling, bad access 1",
8062 .insns = {
8063 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8064 offsetof(struct xdp_md, data)),
8065 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8066 offsetof(struct xdp_md, data_end)),
8067 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8068 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8069 BPF_ALU64_IMM(BPF_ADD, BPF_REG_3, 8),
8070 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8071 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8072 BPF_MOV64_IMM(BPF_REG_0, 0),
8073 BPF_EXIT_INSN(),
8074 },
8075 .errstr = "R3 pointer arithmetic on PTR_TO_PACKET_END",
8076 .result = REJECT,
8077 .prog_type = BPF_PROG_TYPE_XDP,
8078 },
8079 {
8080 "XDP pkt read, pkt_end mangling, bad access 2",
8081 .insns = {
8082 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8083 offsetof(struct xdp_md, data)),
8084 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8085 offsetof(struct xdp_md, data_end)),
8086 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8087 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8088 BPF_ALU64_IMM(BPF_SUB, BPF_REG_3, 8),
8089 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8090 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8091 BPF_MOV64_IMM(BPF_REG_0, 0),
8092 BPF_EXIT_INSN(),
8093 },
8094 .errstr = "R3 pointer arithmetic on PTR_TO_PACKET_END",
8095 .result = REJECT,
8096 .prog_type = BPF_PROG_TYPE_XDP,
8097 },
8098 {
8099 "XDP pkt read, pkt_data' > pkt_end, good access",
8100 .insns = {
8101 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8102 offsetof(struct xdp_md, data)),
8103 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8104 offsetof(struct xdp_md, data_end)),
8105 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8106 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8107 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8108 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8109 BPF_MOV64_IMM(BPF_REG_0, 0),
8110 BPF_EXIT_INSN(),
8111 },
8112 .result = ACCEPT,
8113 .prog_type = BPF_PROG_TYPE_XDP,
8114 },
8115 {
8116 "XDP pkt read, pkt_data' > pkt_end, bad access 1",
8117 .insns = {
8118 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8119 offsetof(struct xdp_md, data)),
8120 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8121 offsetof(struct xdp_md, data_end)),
8122 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8123 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8124 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8125 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8126 BPF_MOV64_IMM(BPF_REG_0, 0),
8127 BPF_EXIT_INSN(),
8128 },
8129 .errstr = "R1 offset is outside of the packet",
8130 .result = REJECT,
8131 .prog_type = BPF_PROG_TYPE_XDP,
8132 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8133 },
8134 {
8135 "XDP pkt read, pkt_data' > pkt_end, bad access 2",
8136 .insns = {
8137 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8138 offsetof(struct xdp_md, data)),
8139 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8140 offsetof(struct xdp_md, data_end)),
8141 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8142 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8143 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 0),
8144 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8145 BPF_MOV64_IMM(BPF_REG_0, 0),
8146 BPF_EXIT_INSN(),
8147 },
8148 .errstr = "R1 offset is outside of the packet",
8149 .result = REJECT,
8150 .prog_type = BPF_PROG_TYPE_XDP,
8151 },
8152 {
8153 "XDP pkt read, pkt_end > pkt_data', good access",
8154 .insns = {
8155 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8156 offsetof(struct xdp_md, data)),
8157 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8158 offsetof(struct xdp_md, data_end)),
8159 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8160 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8161 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8162 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8163 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8164 BPF_MOV64_IMM(BPF_REG_0, 0),
8165 BPF_EXIT_INSN(),
8166 },
8167 .result = ACCEPT,
8168 .prog_type = BPF_PROG_TYPE_XDP,
8169 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8170 },
8171 {
8172 "XDP pkt read, pkt_end > pkt_data', bad access 1",
8173 .insns = {
8174 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8175 offsetof(struct xdp_md, data)),
8176 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8177 offsetof(struct xdp_md, data_end)),
8178 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8179 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8180 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8181 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8182 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8183 BPF_MOV64_IMM(BPF_REG_0, 0),
8184 BPF_EXIT_INSN(),
8185 },
8186 .errstr = "R1 offset is outside of the packet",
8187 .result = REJECT,
8188 .prog_type = BPF_PROG_TYPE_XDP,
8189 },
8190 {
8191 "XDP pkt read, pkt_end > pkt_data', bad access 2",
8192 .insns = {
8193 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8194 offsetof(struct xdp_md, data)),
8195 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8196 offsetof(struct xdp_md, data_end)),
8197 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8198 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8199 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8200 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8201 BPF_MOV64_IMM(BPF_REG_0, 0),
8202 BPF_EXIT_INSN(),
8203 },
8204 .errstr = "R1 offset is outside of the packet",
8205 .result = REJECT,
8206 .prog_type = BPF_PROG_TYPE_XDP,
8207 },
8208 {
8209 "XDP pkt read, pkt_data' < pkt_end, good access",
8210 .insns = {
8211 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8212 offsetof(struct xdp_md, data)),
8213 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8214 offsetof(struct xdp_md, data_end)),
8215 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8216 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8217 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8218 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8219 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8220 BPF_MOV64_IMM(BPF_REG_0, 0),
8221 BPF_EXIT_INSN(),
8222 },
8223 .result = ACCEPT,
8224 .prog_type = BPF_PROG_TYPE_XDP,
8225 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8226 },
8227 {
8228 "XDP pkt read, pkt_data' < pkt_end, bad access 1",
8229 .insns = {
8230 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8231 offsetof(struct xdp_md, data)),
8232 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8233 offsetof(struct xdp_md, data_end)),
8234 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8235 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8236 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8237 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8238 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8239 BPF_MOV64_IMM(BPF_REG_0, 0),
8240 BPF_EXIT_INSN(),
8241 },
8242 .errstr = "R1 offset is outside of the packet",
8243 .result = REJECT,
8244 .prog_type = BPF_PROG_TYPE_XDP,
8245 },
8246 {
8247 "XDP pkt read, pkt_data' < pkt_end, bad access 2",
8248 .insns = {
8249 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8250 offsetof(struct xdp_md, data)),
8251 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8252 offsetof(struct xdp_md, data_end)),
8253 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8254 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8255 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8256 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8257 BPF_MOV64_IMM(BPF_REG_0, 0),
8258 BPF_EXIT_INSN(),
8259 },
8260 .errstr = "R1 offset is outside of the packet",
8261 .result = REJECT,
8262 .prog_type = BPF_PROG_TYPE_XDP,
8263 },
8264 {
8265 "XDP pkt read, pkt_end < pkt_data', good access",
8266 .insns = {
8267 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8268 offsetof(struct xdp_md, data)),
8269 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8270 offsetof(struct xdp_md, data_end)),
8271 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8272 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8273 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 1),
8274 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8275 BPF_MOV64_IMM(BPF_REG_0, 0),
8276 BPF_EXIT_INSN(),
8277 },
8278 .result = ACCEPT,
8279 .prog_type = BPF_PROG_TYPE_XDP,
8280 },
8281 {
8282 "XDP pkt read, pkt_end < pkt_data', bad access 1",
8283 .insns = {
8284 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8285 offsetof(struct xdp_md, data)),
8286 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8287 offsetof(struct xdp_md, data_end)),
8288 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8289 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8290 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 1),
8291 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8292 BPF_MOV64_IMM(BPF_REG_0, 0),
8293 BPF_EXIT_INSN(),
8294 },
8295 .errstr = "R1 offset is outside of the packet",
8296 .result = REJECT,
8297 .prog_type = BPF_PROG_TYPE_XDP,
8298 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8299 },
8300 {
8301 "XDP pkt read, pkt_end < pkt_data', bad access 2",
8302 .insns = {
8303 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8304 offsetof(struct xdp_md, data)),
8305 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8306 offsetof(struct xdp_md, data_end)),
8307 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8308 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8309 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 0),
8310 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8311 BPF_MOV64_IMM(BPF_REG_0, 0),
8312 BPF_EXIT_INSN(),
8313 },
8314 .errstr = "R1 offset is outside of the packet",
8315 .result = REJECT,
8316 .prog_type = BPF_PROG_TYPE_XDP,
8317 },
8318 {
8319 "XDP pkt read, pkt_data' >= pkt_end, good access",
8320 .insns = {
8321 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8322 offsetof(struct xdp_md, data)),
8323 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8324 offsetof(struct xdp_md, data_end)),
8325 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8326 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8327 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 1),
8328 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8329 BPF_MOV64_IMM(BPF_REG_0, 0),
8330 BPF_EXIT_INSN(),
8331 },
8332 .result = ACCEPT,
8333 .prog_type = BPF_PROG_TYPE_XDP,
8334 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8335 },
8336 {
8337 "XDP pkt read, pkt_data' >= pkt_end, bad access 1",
8338 .insns = {
8339 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8340 offsetof(struct xdp_md, data)),
8341 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8342 offsetof(struct xdp_md, data_end)),
8343 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8344 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8345 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 1),
8346 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8347 BPF_MOV64_IMM(BPF_REG_0, 0),
8348 BPF_EXIT_INSN(),
8349 },
8350 .errstr = "R1 offset is outside of the packet",
8351 .result = REJECT,
8352 .prog_type = BPF_PROG_TYPE_XDP,
8353 },
8354 {
8355 "XDP pkt read, pkt_data' >= pkt_end, bad access 2",
8356 .insns = {
8357 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8358 offsetof(struct xdp_md, data)),
8359 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8360 offsetof(struct xdp_md, data_end)),
8361 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8362 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8363 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 0),
8364 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8365 BPF_MOV64_IMM(BPF_REG_0, 0),
8366 BPF_EXIT_INSN(),
8367 },
8368 .errstr = "R1 offset is outside of the packet",
8369 .result = REJECT,
8370 .prog_type = BPF_PROG_TYPE_XDP,
8371 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8372 },
8373 {
8374 "XDP pkt read, pkt_end >= pkt_data', good access",
8375 .insns = {
8376 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8377 offsetof(struct xdp_md, data)),
8378 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8379 offsetof(struct xdp_md, data_end)),
8380 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8381 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8382 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8383 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8384 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8385 BPF_MOV64_IMM(BPF_REG_0, 0),
8386 BPF_EXIT_INSN(),
8387 },
8388 .result = ACCEPT,
8389 .prog_type = BPF_PROG_TYPE_XDP,
8390 },
8391 {
8392 "XDP pkt read, pkt_end >= pkt_data', bad access 1",
8393 .insns = {
8394 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8395 offsetof(struct xdp_md, data)),
8396 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8397 offsetof(struct xdp_md, data_end)),
8398 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8399 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8400 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8401 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8402 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8403 BPF_MOV64_IMM(BPF_REG_0, 0),
8404 BPF_EXIT_INSN(),
8405 },
8406 .errstr = "R1 offset is outside of the packet",
8407 .result = REJECT,
8408 .prog_type = BPF_PROG_TYPE_XDP,
8409 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8410 },
8411 {
8412 "XDP pkt read, pkt_end >= pkt_data', bad access 2",
8413 .insns = {
8414 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8415 offsetof(struct xdp_md, data)),
8416 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8417 offsetof(struct xdp_md, data_end)),
8418 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8419 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8420 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8421 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8422 BPF_MOV64_IMM(BPF_REG_0, 0),
8423 BPF_EXIT_INSN(),
8424 },
8425 .errstr = "R1 offset is outside of the packet",
8426 .result = REJECT,
8427 .prog_type = BPF_PROG_TYPE_XDP,
8428 },
8429 {
8430 "XDP pkt read, pkt_data' <= pkt_end, good access",
8431 .insns = {
8432 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8433 offsetof(struct xdp_md, data)),
8434 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8435 offsetof(struct xdp_md, data_end)),
8436 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8437 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8438 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8439 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8440 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8441 BPF_MOV64_IMM(BPF_REG_0, 0),
8442 BPF_EXIT_INSN(),
8443 },
8444 .result = ACCEPT,
8445 .prog_type = BPF_PROG_TYPE_XDP,
8446 },
8447 {
8448 "XDP pkt read, pkt_data' <= pkt_end, bad access 1",
8449 .insns = {
8450 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8451 offsetof(struct xdp_md, data)),
8452 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8453 offsetof(struct xdp_md, data_end)),
8454 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8455 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8456 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8457 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8458 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8459 BPF_MOV64_IMM(BPF_REG_0, 0),
8460 BPF_EXIT_INSN(),
8461 },
8462 .errstr = "R1 offset is outside of the packet",
8463 .result = REJECT,
8464 .prog_type = BPF_PROG_TYPE_XDP,
8465 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8466 },
8467 {
8468 "XDP pkt read, pkt_data' <= pkt_end, bad access 2",
8469 .insns = {
8470 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8471 offsetof(struct xdp_md, data)),
8472 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8473 offsetof(struct xdp_md, data_end)),
8474 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8475 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8476 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8477 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8478 BPF_MOV64_IMM(BPF_REG_0, 0),
8479 BPF_EXIT_INSN(),
8480 },
8481 .errstr = "R1 offset is outside of the packet",
8482 .result = REJECT,
8483 .prog_type = BPF_PROG_TYPE_XDP,
8484 },
8485 {
8486 "XDP pkt read, pkt_end <= pkt_data', good access",
8487 .insns = {
8488 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8489 offsetof(struct xdp_md, data)),
8490 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8491 offsetof(struct xdp_md, data_end)),
8492 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8493 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8494 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 1),
8495 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8496 BPF_MOV64_IMM(BPF_REG_0, 0),
8497 BPF_EXIT_INSN(),
8498 },
8499 .result = ACCEPT,
8500 .prog_type = BPF_PROG_TYPE_XDP,
8501 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8502 },
8503 {
8504 "XDP pkt read, pkt_end <= pkt_data', bad access 1",
8505 .insns = {
8506 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8507 offsetof(struct xdp_md, data)),
8508 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8509 offsetof(struct xdp_md, data_end)),
8510 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8511 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8512 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 1),
8513 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8514 BPF_MOV64_IMM(BPF_REG_0, 0),
8515 BPF_EXIT_INSN(),
8516 },
8517 .errstr = "R1 offset is outside of the packet",
8518 .result = REJECT,
8519 .prog_type = BPF_PROG_TYPE_XDP,
8520 },
8521 {
8522 "XDP pkt read, pkt_end <= pkt_data', bad access 2",
8523 .insns = {
8524 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8525 offsetof(struct xdp_md, data)),
8526 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8527 offsetof(struct xdp_md, data_end)),
8528 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8529 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8530 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 0),
8531 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8532 BPF_MOV64_IMM(BPF_REG_0, 0),
8533 BPF_EXIT_INSN(),
8534 },
8535 .errstr = "R1 offset is outside of the packet",
8536 .result = REJECT,
8537 .prog_type = BPF_PROG_TYPE_XDP,
8538 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8539 },
8540 {
8541 "XDP pkt read, pkt_meta' > pkt_data, good access",
8542 .insns = {
8543 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8544 offsetof(struct xdp_md, data_meta)),
8545 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8546 offsetof(struct xdp_md, data)),
8547 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8548 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8549 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8550 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8551 BPF_MOV64_IMM(BPF_REG_0, 0),
8552 BPF_EXIT_INSN(),
8553 },
8554 .result = ACCEPT,
8555 .prog_type = BPF_PROG_TYPE_XDP,
8556 },
8557 {
8558 "XDP pkt read, pkt_meta' > pkt_data, bad access 1",
8559 .insns = {
8560 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8561 offsetof(struct xdp_md, data_meta)),
8562 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8563 offsetof(struct xdp_md, data)),
8564 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8565 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8566 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 1),
8567 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8568 BPF_MOV64_IMM(BPF_REG_0, 0),
8569 BPF_EXIT_INSN(),
8570 },
8571 .errstr = "R1 offset is outside of the packet",
8572 .result = REJECT,
8573 .prog_type = BPF_PROG_TYPE_XDP,
8574 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8575 },
8576 {
8577 "XDP pkt read, pkt_meta' > pkt_data, bad access 2",
8578 .insns = {
8579 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8580 offsetof(struct xdp_md, data_meta)),
8581 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8582 offsetof(struct xdp_md, data)),
8583 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8584 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8585 BPF_JMP_REG(BPF_JGT, BPF_REG_1, BPF_REG_3, 0),
8586 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8587 BPF_MOV64_IMM(BPF_REG_0, 0),
8588 BPF_EXIT_INSN(),
8589 },
8590 .errstr = "R1 offset is outside of the packet",
8591 .result = REJECT,
8592 .prog_type = BPF_PROG_TYPE_XDP,
8593 },
8594 {
8595 "XDP pkt read, pkt_data > pkt_meta', good access",
8596 .insns = {
8597 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8598 offsetof(struct xdp_md, data_meta)),
8599 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8600 offsetof(struct xdp_md, data)),
8601 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8602 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8603 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8604 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8605 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8606 BPF_MOV64_IMM(BPF_REG_0, 0),
8607 BPF_EXIT_INSN(),
8608 },
8609 .result = ACCEPT,
8610 .prog_type = BPF_PROG_TYPE_XDP,
8611 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8612 },
8613 {
8614 "XDP pkt read, pkt_data > pkt_meta', bad access 1",
8615 .insns = {
8616 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8617 offsetof(struct xdp_md, data_meta)),
8618 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8619 offsetof(struct xdp_md, data)),
8620 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8621 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8622 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8623 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8624 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8625 BPF_MOV64_IMM(BPF_REG_0, 0),
8626 BPF_EXIT_INSN(),
8627 },
8628 .errstr = "R1 offset is outside of the packet",
8629 .result = REJECT,
8630 .prog_type = BPF_PROG_TYPE_XDP,
8631 },
8632 {
8633 "XDP pkt read, pkt_data > pkt_meta', bad access 2",
8634 .insns = {
8635 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8636 offsetof(struct xdp_md, data_meta)),
8637 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8638 offsetof(struct xdp_md, data)),
8639 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8640 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8641 BPF_JMP_REG(BPF_JGT, BPF_REG_3, BPF_REG_1, 1),
8642 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8643 BPF_MOV64_IMM(BPF_REG_0, 0),
8644 BPF_EXIT_INSN(),
8645 },
8646 .errstr = "R1 offset is outside of the packet",
8647 .result = REJECT,
8648 .prog_type = BPF_PROG_TYPE_XDP,
8649 },
8650 {
8651 "XDP pkt read, pkt_meta' < pkt_data, good access",
8652 .insns = {
8653 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8654 offsetof(struct xdp_md, data_meta)),
8655 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8656 offsetof(struct xdp_md, data)),
8657 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8658 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8659 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8660 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8661 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8662 BPF_MOV64_IMM(BPF_REG_0, 0),
8663 BPF_EXIT_INSN(),
8664 },
8665 .result = ACCEPT,
8666 .prog_type = BPF_PROG_TYPE_XDP,
8667 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8668 },
8669 {
8670 "XDP pkt read, pkt_meta' < pkt_data, bad access 1",
8671 .insns = {
8672 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8673 offsetof(struct xdp_md, data_meta)),
8674 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8675 offsetof(struct xdp_md, data)),
8676 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8677 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8678 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8679 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8680 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8681 BPF_MOV64_IMM(BPF_REG_0, 0),
8682 BPF_EXIT_INSN(),
8683 },
8684 .errstr = "R1 offset is outside of the packet",
8685 .result = REJECT,
8686 .prog_type = BPF_PROG_TYPE_XDP,
8687 },
8688 {
8689 "XDP pkt read, pkt_meta' < pkt_data, bad access 2",
8690 .insns = {
8691 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8692 offsetof(struct xdp_md, data_meta)),
8693 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8694 offsetof(struct xdp_md, data)),
8695 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8696 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8697 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 1),
8698 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8699 BPF_MOV64_IMM(BPF_REG_0, 0),
8700 BPF_EXIT_INSN(),
8701 },
8702 .errstr = "R1 offset is outside of the packet",
8703 .result = REJECT,
8704 .prog_type = BPF_PROG_TYPE_XDP,
8705 },
8706 {
8707 "XDP pkt read, pkt_data < pkt_meta', good access",
8708 .insns = {
8709 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8710 offsetof(struct xdp_md, data_meta)),
8711 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8712 offsetof(struct xdp_md, data)),
8713 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8714 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8715 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 1),
8716 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8717 BPF_MOV64_IMM(BPF_REG_0, 0),
8718 BPF_EXIT_INSN(),
8719 },
8720 .result = ACCEPT,
8721 .prog_type = BPF_PROG_TYPE_XDP,
8722 },
8723 {
8724 "XDP pkt read, pkt_data < pkt_meta', bad access 1",
8725 .insns = {
8726 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8727 offsetof(struct xdp_md, data_meta)),
8728 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8729 offsetof(struct xdp_md, data)),
8730 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8731 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8732 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 1),
8733 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8734 BPF_MOV64_IMM(BPF_REG_0, 0),
8735 BPF_EXIT_INSN(),
8736 },
8737 .errstr = "R1 offset is outside of the packet",
8738 .result = REJECT,
8739 .prog_type = BPF_PROG_TYPE_XDP,
8740 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8741 },
8742 {
8743 "XDP pkt read, pkt_data < pkt_meta', bad access 2",
8744 .insns = {
8745 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8746 offsetof(struct xdp_md, data_meta)),
8747 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8748 offsetof(struct xdp_md, data)),
8749 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8750 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8751 BPF_JMP_REG(BPF_JLT, BPF_REG_3, BPF_REG_1, 0),
8752 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8753 BPF_MOV64_IMM(BPF_REG_0, 0),
8754 BPF_EXIT_INSN(),
8755 },
8756 .errstr = "R1 offset is outside of the packet",
8757 .result = REJECT,
8758 .prog_type = BPF_PROG_TYPE_XDP,
8759 },
8760 {
8761 "XDP pkt read, pkt_meta' >= pkt_data, good access",
8762 .insns = {
8763 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8764 offsetof(struct xdp_md, data_meta)),
8765 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8766 offsetof(struct xdp_md, data)),
8767 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8768 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8769 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 1),
8770 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8771 BPF_MOV64_IMM(BPF_REG_0, 0),
8772 BPF_EXIT_INSN(),
8773 },
8774 .result = ACCEPT,
8775 .prog_type = BPF_PROG_TYPE_XDP,
8776 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8777 },
8778 {
8779 "XDP pkt read, pkt_meta' >= pkt_data, bad access 1",
8780 .insns = {
8781 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8782 offsetof(struct xdp_md, data_meta)),
8783 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8784 offsetof(struct xdp_md, data)),
8785 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8786 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8787 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 1),
8788 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8789 BPF_MOV64_IMM(BPF_REG_0, 0),
8790 BPF_EXIT_INSN(),
8791 },
8792 .errstr = "R1 offset is outside of the packet",
8793 .result = REJECT,
8794 .prog_type = BPF_PROG_TYPE_XDP,
8795 },
8796 {
8797 "XDP pkt read, pkt_meta' >= pkt_data, bad access 2",
8798 .insns = {
8799 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8800 offsetof(struct xdp_md, data_meta)),
8801 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8802 offsetof(struct xdp_md, data)),
8803 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8804 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8805 BPF_JMP_REG(BPF_JGE, BPF_REG_1, BPF_REG_3, 0),
8806 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8807 BPF_MOV64_IMM(BPF_REG_0, 0),
8808 BPF_EXIT_INSN(),
8809 },
8810 .errstr = "R1 offset is outside of the packet",
8811 .result = REJECT,
8812 .prog_type = BPF_PROG_TYPE_XDP,
8813 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8814 },
8815 {
8816 "XDP pkt read, pkt_data >= pkt_meta', good access",
8817 .insns = {
8818 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8819 offsetof(struct xdp_md, data_meta)),
8820 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8821 offsetof(struct xdp_md, data)),
8822 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8823 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8824 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8825 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8826 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8827 BPF_MOV64_IMM(BPF_REG_0, 0),
8828 BPF_EXIT_INSN(),
8829 },
8830 .result = ACCEPT,
8831 .prog_type = BPF_PROG_TYPE_XDP,
8832 },
8833 {
8834 "XDP pkt read, pkt_data >= pkt_meta', bad access 1",
8835 .insns = {
8836 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8837 offsetof(struct xdp_md, data_meta)),
8838 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8839 offsetof(struct xdp_md, data)),
8840 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8841 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8842 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8843 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8844 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8845 BPF_MOV64_IMM(BPF_REG_0, 0),
8846 BPF_EXIT_INSN(),
8847 },
8848 .errstr = "R1 offset is outside of the packet",
8849 .result = REJECT,
8850 .prog_type = BPF_PROG_TYPE_XDP,
8851 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8852 },
8853 {
8854 "XDP pkt read, pkt_data >= pkt_meta', bad access 2",
8855 .insns = {
8856 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8857 offsetof(struct xdp_md, data_meta)),
8858 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8859 offsetof(struct xdp_md, data)),
8860 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8861 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8862 BPF_JMP_REG(BPF_JGE, BPF_REG_3, BPF_REG_1, 1),
8863 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8864 BPF_MOV64_IMM(BPF_REG_0, 0),
8865 BPF_EXIT_INSN(),
8866 },
8867 .errstr = "R1 offset is outside of the packet",
8868 .result = REJECT,
8869 .prog_type = BPF_PROG_TYPE_XDP,
8870 },
8871 {
8872 "XDP pkt read, pkt_meta' <= pkt_data, good access",
8873 .insns = {
8874 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8875 offsetof(struct xdp_md, data_meta)),
8876 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8877 offsetof(struct xdp_md, data)),
8878 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8879 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8880 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8881 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8882 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8883 BPF_MOV64_IMM(BPF_REG_0, 0),
8884 BPF_EXIT_INSN(),
8885 },
8886 .result = ACCEPT,
8887 .prog_type = BPF_PROG_TYPE_XDP,
8888 },
8889 {
8890 "XDP pkt read, pkt_meta' <= pkt_data, bad access 1",
8891 .insns = {
8892 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8893 offsetof(struct xdp_md, data_meta)),
8894 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8895 offsetof(struct xdp_md, data)),
8896 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8897 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8898 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8899 BPF_JMP_IMM(BPF_JA, 0, 0, 1),
8900 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -4),
8901 BPF_MOV64_IMM(BPF_REG_0, 0),
8902 BPF_EXIT_INSN(),
8903 },
8904 .errstr = "R1 offset is outside of the packet",
8905 .result = REJECT,
8906 .prog_type = BPF_PROG_TYPE_XDP,
8907 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8908 },
8909 {
8910 "XDP pkt read, pkt_meta' <= pkt_data, bad access 2",
8911 .insns = {
8912 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8913 offsetof(struct xdp_md, data_meta)),
8914 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8915 offsetof(struct xdp_md, data)),
8916 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8917 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8918 BPF_JMP_REG(BPF_JLE, BPF_REG_1, BPF_REG_3, 1),
8919 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8920 BPF_MOV64_IMM(BPF_REG_0, 0),
8921 BPF_EXIT_INSN(),
8922 },
8923 .errstr = "R1 offset is outside of the packet",
8924 .result = REJECT,
8925 .prog_type = BPF_PROG_TYPE_XDP,
8926 },
8927 {
8928 "XDP pkt read, pkt_data <= pkt_meta', good access",
8929 .insns = {
8930 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8931 offsetof(struct xdp_md, data_meta)),
8932 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8933 offsetof(struct xdp_md, data)),
8934 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8935 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8936 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 1),
8937 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8938 BPF_MOV64_IMM(BPF_REG_0, 0),
8939 BPF_EXIT_INSN(),
8940 },
8941 .result = ACCEPT,
8942 .prog_type = BPF_PROG_TYPE_XDP,
8943 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8944 },
8945 {
8946 "XDP pkt read, pkt_data <= pkt_meta', bad access 1",
8947 .insns = {
8948 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8949 offsetof(struct xdp_md, data_meta)),
8950 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8951 offsetof(struct xdp_md, data)),
8952 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8953 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8954 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 1),
8955 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_1, -8),
8956 BPF_MOV64_IMM(BPF_REG_0, 0),
8957 BPF_EXIT_INSN(),
8958 },
8959 .errstr = "R1 offset is outside of the packet",
8960 .result = REJECT,
8961 .prog_type = BPF_PROG_TYPE_XDP,
8962 },
8963 {
8964 "XDP pkt read, pkt_data <= pkt_meta', bad access 2",
8965 .insns = {
8966 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
8967 offsetof(struct xdp_md, data_meta)),
8968 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
8969 offsetof(struct xdp_md, data)),
8970 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
8971 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
8972 BPF_JMP_REG(BPF_JLE, BPF_REG_3, BPF_REG_1, 0),
8973 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, -5),
8974 BPF_MOV64_IMM(BPF_REG_0, 0),
8975 BPF_EXIT_INSN(),
8976 },
8977 .errstr = "R1 offset is outside of the packet",
8978 .result = REJECT,
8979 .prog_type = BPF_PROG_TYPE_XDP,
8980 .flags = F_NEEDS_EFFICIENT_UNALIGNED_ACCESS,
8981 },
8982 {
8983 "check deducing bounds from const, 1",
8984 .insns = {
8985 BPF_MOV64_IMM(BPF_REG_0, 1),
8986 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 1, 0),
8987 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
8988 BPF_EXIT_INSN(),
8989 },
8990 .result = REJECT,
8991 .errstr = "R0 tried to subtract pointer from scalar",
8992 },
8993 {
8994 "check deducing bounds from const, 2",
8995 .insns = {
8996 BPF_MOV64_IMM(BPF_REG_0, 1),
8997 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 1, 1),
8998 BPF_EXIT_INSN(),
8999 BPF_JMP_IMM(BPF_JSLE, BPF_REG_0, 1, 1),
9000 BPF_EXIT_INSN(),
9001 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_0),
9002 BPF_EXIT_INSN(),
9003 },
9004 .result = ACCEPT,
9005 },
9006 {
9007 "check deducing bounds from const, 3",
9008 .insns = {
9009 BPF_MOV64_IMM(BPF_REG_0, 0),
9010 BPF_JMP_IMM(BPF_JSLE, BPF_REG_0, 0, 0),
9011 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
9012 BPF_EXIT_INSN(),
9013 },
9014 .result = REJECT,
9015 .errstr = "R0 tried to subtract pointer from scalar",
9016 },
9017 {
9018 "check deducing bounds from const, 4",
9019 .insns = {
9020 BPF_MOV64_IMM(BPF_REG_0, 0),
9021 BPF_JMP_IMM(BPF_JSLE, BPF_REG_0, 0, 1),
9022 BPF_EXIT_INSN(),
9023 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 1),
9024 BPF_EXIT_INSN(),
9025 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_0),
9026 BPF_EXIT_INSN(),
9027 },
9028 .result = ACCEPT,
9029 },
9030 {
9031 "check deducing bounds from const, 5",
9032 .insns = {
9033 BPF_MOV64_IMM(BPF_REG_0, 0),
9034 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 1),
9035 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
9036 BPF_EXIT_INSN(),
9037 },
9038 .result = REJECT,
9039 .errstr = "R0 tried to subtract pointer from scalar",
9040 },
9041 {
9042 "check deducing bounds from const, 6",
9043 .insns = {
9044 BPF_MOV64_IMM(BPF_REG_0, 0),
9045 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 1),
9046 BPF_EXIT_INSN(),
9047 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
9048 BPF_EXIT_INSN(),
9049 },
9050 .result = REJECT,
9051 .errstr = "R0 tried to subtract pointer from scalar",
9052 },
9053 {
9054 "check deducing bounds from const, 7",
9055 .insns = {
9056 BPF_MOV64_IMM(BPF_REG_0, ~0),
9057 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 0),
9058 BPF_ALU64_REG(BPF_SUB, BPF_REG_1, BPF_REG_0),
9059 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
9060 offsetof(struct __sk_buff, mark)),
9061 BPF_EXIT_INSN(),
9062 },
9063 .result = REJECT,
9064 .errstr = "dereference of modified ctx ptr",
9065 },
9066 {
9067 "check deducing bounds from const, 8",
9068 .insns = {
9069 BPF_MOV64_IMM(BPF_REG_0, ~0),
9070 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 1),
9071 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0),
9072 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1,
9073 offsetof(struct __sk_buff, mark)),
9074 BPF_EXIT_INSN(),
9075 },
9076 .result = REJECT,
9077 .errstr = "dereference of modified ctx ptr",
9078 },
9079 {
9080 "check deducing bounds from const, 9",
9081 .insns = {
9082 BPF_MOV64_IMM(BPF_REG_0, 0),
9083 BPF_JMP_IMM(BPF_JSGE, BPF_REG_0, 0, 0),
9084 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
9085 BPF_EXIT_INSN(),
9086 },
9087 .result = REJECT,
9088 .errstr = "R0 tried to subtract pointer from scalar",
9089 },
9090 {
9091 "check deducing bounds from const, 10",
9092 .insns = {
9093 BPF_MOV64_IMM(BPF_REG_0, 0),
9094 BPF_JMP_IMM(BPF_JSLE, BPF_REG_0, 0, 0),
9095 /* Marks reg as unknown. */
9096 BPF_ALU64_IMM(BPF_NEG, BPF_REG_0, 0),
9097 BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1),
9098 BPF_EXIT_INSN(),
9099 },
9100 .result = REJECT,
9101 .errstr = "math between ctx pointer and register with unbounded min value is not allowed",
9102 },
9103 {
9104 "bpf_exit with invalid return code. test1",
9105 .insns = {
9106 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0),
9107 BPF_EXIT_INSN(),
9108 },
9109 .errstr = "R0 has value (0x0; 0xffffffff)",
9110 .result = REJECT,
9111 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9112 },
9113 {
9114 "bpf_exit with invalid return code. test2",
9115 .insns = {
9116 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0),
9117 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 1),
9118 BPF_EXIT_INSN(),
9119 },
9120 .result = ACCEPT,
9121 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9122 },
9123 {
9124 "bpf_exit with invalid return code. test3",
9125 .insns = {
9126 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0),
9127 BPF_ALU64_IMM(BPF_AND, BPF_REG_0, 3),
9128 BPF_EXIT_INSN(),
9129 },
9130 .errstr = "R0 has value (0x0; 0x3)",
9131 .result = REJECT,
9132 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9133 },
9134 {
9135 "bpf_exit with invalid return code. test4",
9136 .insns = {
9137 BPF_MOV64_IMM(BPF_REG_0, 1),
9138 BPF_EXIT_INSN(),
9139 },
9140 .result = ACCEPT,
9141 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9142 },
9143 {
9144 "bpf_exit with invalid return code. test5",
9145 .insns = {
9146 BPF_MOV64_IMM(BPF_REG_0, 2),
9147 BPF_EXIT_INSN(),
9148 },
9149 .errstr = "R0 has value (0x2; 0x0)",
9150 .result = REJECT,
9151 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9152 },
9153 {
9154 "bpf_exit with invalid return code. test6",
9155 .insns = {
9156 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9157 BPF_EXIT_INSN(),
9158 },
9159 .errstr = "R0 is not a known value (ctx)",
9160 .result = REJECT,
9161 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9162 },
9163 {
9164 "bpf_exit with invalid return code. test7",
9165 .insns = {
9166 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0),
9167 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1, 4),
9168 BPF_ALU64_REG(BPF_MUL, BPF_REG_0, BPF_REG_2),
9169 BPF_EXIT_INSN(),
9170 },
9171 .errstr = "R0 has unknown scalar value",
9172 .result = REJECT,
9173 .prog_type = BPF_PROG_TYPE_CGROUP_SOCK,
9174 },
9175 {
9176 "xadd/w check unaligned stack",
9177 .insns = {
9178 BPF_MOV64_IMM(BPF_REG_0, 1),
9179 BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_0, -8),
9180 BPF_STX_XADD(BPF_W, BPF_REG_10, BPF_REG_0, -7),
9181 BPF_LDX_MEM(BPF_DW, BPF_REG_0, BPF_REG_10, -8),
9182 BPF_EXIT_INSN(),
9183 },
9184 .result = REJECT,
9185 .errstr = "misaligned stack access off",
9186 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
9187 },
9188 {
9189 "xadd/w check unaligned map",
9190 .insns = {
9191 BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0),
9192 BPF_MOV64_REG(BPF_REG_2, BPF_REG_10),
9193 BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8),
9194 BPF_LD_MAP_FD(BPF_REG_1, 0),
9195 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
9196 BPF_FUNC_map_lookup_elem),
9197 BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1),
9198 BPF_EXIT_INSN(),
9199 BPF_MOV64_IMM(BPF_REG_1, 1),
9200 BPF_STX_XADD(BPF_W, BPF_REG_0, BPF_REG_1, 3),
9201 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0, 3),
9202 BPF_EXIT_INSN(),
9203 },
9204 .fixup_map1 = { 3 },
9205 .result = REJECT,
9206 .errstr = "misaligned value access off",
9207 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
9208 },
9209 {
9210 "xadd/w check unaligned pkt",
9211 .insns = {
9212 BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
9213 offsetof(struct xdp_md, data)),
9214 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1,
9215 offsetof(struct xdp_md, data_end)),
9216 BPF_MOV64_REG(BPF_REG_1, BPF_REG_2),
9217 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 8),
9218 BPF_JMP_REG(BPF_JLT, BPF_REG_1, BPF_REG_3, 2),
9219 BPF_MOV64_IMM(BPF_REG_0, 99),
9220 BPF_JMP_IMM(BPF_JA, 0, 0, 6),
9221 BPF_MOV64_IMM(BPF_REG_0, 1),
9222 BPF_ST_MEM(BPF_W, BPF_REG_2, 0, 0),
9223 BPF_ST_MEM(BPF_W, BPF_REG_2, 3, 0),
9224 BPF_STX_XADD(BPF_W, BPF_REG_2, BPF_REG_0, 1),
9225 BPF_STX_XADD(BPF_W, BPF_REG_2, BPF_REG_0, 2),
9226 BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_2, 1),
9227 BPF_EXIT_INSN(),
9228 },
9229 .result = REJECT,
9230 .errstr = "BPF_XADD stores into R2 packet",
9231 .prog_type = BPF_PROG_TYPE_XDP,
9232 },
9233 {
9234 "pass unmodified ctx pointer to helper",
9235 .insns = {
9236 BPF_MOV64_IMM(BPF_REG_2, 0),
9237 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
9238 BPF_FUNC_csum_update),
9239 BPF_MOV64_IMM(BPF_REG_0, 0),
9240 BPF_EXIT_INSN(),
9241 },
9242 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
9243 .result = ACCEPT,
9244 },
9245 {
9246 "pass modified ctx pointer to helper, 1",
9247 .insns = {
9248 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -612),
9249 BPF_MOV64_IMM(BPF_REG_2, 0),
9250 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
9251 BPF_FUNC_csum_update),
9252 BPF_MOV64_IMM(BPF_REG_0, 0),
9253 BPF_EXIT_INSN(),
9254 },
9255 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
9256 .result = REJECT,
9257 .errstr = "dereference of modified ctx ptr",
9258 },
9259 {
9260 "pass modified ctx pointer to helper, 2",
9261 .insns = {
9262 BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -612),
9263 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
9264 BPF_FUNC_get_socket_cookie),
9265 BPF_MOV64_IMM(BPF_REG_0, 0),
9266 BPF_EXIT_INSN(),
9267 },
9268 .result_unpriv = REJECT,
9269 .result = REJECT,
9270 .errstr_unpriv = "dereference of modified ctx ptr",
9271 .errstr = "dereference of modified ctx ptr",
9272 },
9273 {
9274 "pass modified ctx pointer to helper, 3",
9275 .insns = {
9276 BPF_LDX_MEM(BPF_W, BPF_REG_3, BPF_REG_1, 0),
9277 BPF_ALU64_IMM(BPF_AND, BPF_REG_3, 4),
9278 BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_3),
9279 BPF_MOV64_IMM(BPF_REG_2, 0),
9280 BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
9281 BPF_FUNC_csum_update),
9282 BPF_MOV64_IMM(BPF_REG_0, 0),
9283 BPF_EXIT_INSN(),
9284 },
9285 .prog_type = BPF_PROG_TYPE_SCHED_CLS,
9286 .result = REJECT,
9287 .errstr = "variable ctx access var_off=(0x0; 0x4)",
9288 },
9289 {
9290 "masking, test out of bounds 1",
9291 .insns = {
9292 BPF_MOV32_IMM(BPF_REG_1, 5),
9293 BPF_MOV32_IMM(BPF_REG_2, 5 - 1),
9294 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9295 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9296 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9297 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9298 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9299 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9300 BPF_EXIT_INSN(),
9301 },
9302 .result = ACCEPT,
9303 },
9304 {
9305 "masking, test out of bounds 2",
9306 .insns = {
9307 BPF_MOV32_IMM(BPF_REG_1, 1),
9308 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9309 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9310 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9311 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9312 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9313 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9314 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9315 BPF_EXIT_INSN(),
9316 },
9317 .result = ACCEPT,
9318 },
9319 {
9320 "masking, test out of bounds 3",
9321 .insns = {
9322 BPF_MOV32_IMM(BPF_REG_1, 0xffffffff),
9323 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9324 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9325 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9326 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9327 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9328 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9329 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9330 BPF_EXIT_INSN(),
9331 },
9332 .result = ACCEPT,
9333 },
9334 {
9335 "masking, test out of bounds 4",
9336 .insns = {
9337 BPF_MOV32_IMM(BPF_REG_1, 0xffffffff),
9338 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9339 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9340 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9341 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9342 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9343 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9344 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9345 BPF_EXIT_INSN(),
9346 },
9347 .result = ACCEPT,
9348 },
9349 {
9350 "masking, test out of bounds 5",
9351 .insns = {
9352 BPF_MOV32_IMM(BPF_REG_1, -1),
9353 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9354 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9355 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9356 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9357 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9358 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9359 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9360 BPF_EXIT_INSN(),
9361 },
9362 .result = ACCEPT,
9363 },
9364 {
9365 "masking, test out of bounds 6",
9366 .insns = {
9367 BPF_MOV32_IMM(BPF_REG_1, -1),
9368 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9369 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9370 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9371 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9372 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9373 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9374 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9375 BPF_EXIT_INSN(),
9376 },
9377 .result = ACCEPT,
9378 },
9379 {
9380 "masking, test out of bounds 7",
9381 .insns = {
9382 BPF_MOV64_IMM(BPF_REG_1, 5),
9383 BPF_MOV32_IMM(BPF_REG_2, 5 - 1),
9384 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9385 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9386 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9387 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9388 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9389 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9390 BPF_EXIT_INSN(),
9391 },
9392 .result = ACCEPT,
9393 },
9394 {
9395 "masking, test out of bounds 8",
9396 .insns = {
9397 BPF_MOV64_IMM(BPF_REG_1, 1),
9398 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9399 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9400 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9401 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9402 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9403 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9404 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9405 BPF_EXIT_INSN(),
9406 },
9407 .result = ACCEPT,
9408 },
9409 {
9410 "masking, test out of bounds 9",
9411 .insns = {
9412 BPF_MOV64_IMM(BPF_REG_1, 0xffffffff),
9413 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9414 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9415 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9416 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9417 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9418 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9419 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9420 BPF_EXIT_INSN(),
9421 },
9422 .result = ACCEPT,
9423 },
9424 {
9425 "masking, test out of bounds 10",
9426 .insns = {
9427 BPF_MOV64_IMM(BPF_REG_1, 0xffffffff),
9428 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9429 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9430 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9431 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9432 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9433 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9434 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9435 BPF_EXIT_INSN(),
9436 },
9437 .result = ACCEPT,
9438 },
9439 {
9440 "masking, test out of bounds 11",
9441 .insns = {
9442 BPF_MOV64_IMM(BPF_REG_1, -1),
9443 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9444 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9445 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9446 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9447 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9448 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9449 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9450 BPF_EXIT_INSN(),
9451 },
9452 .result = ACCEPT,
9453 },
9454 {
9455 "masking, test out of bounds 12",
9456 .insns = {
9457 BPF_MOV64_IMM(BPF_REG_1, -1),
9458 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9459 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9460 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9461 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9462 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9463 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9464 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9465 BPF_EXIT_INSN(),
9466 },
9467 .result = ACCEPT,
9468 },
9469 {
9470 "masking, test in bounds 1",
9471 .insns = {
9472 BPF_MOV32_IMM(BPF_REG_1, 4),
9473 BPF_MOV32_IMM(BPF_REG_2, 5 - 1),
9474 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9475 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9476 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9477 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9478 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9479 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9480 BPF_EXIT_INSN(),
9481 },
9482 .result = ACCEPT,
9483 },
9484 {
9485 "masking, test in bounds 2",
9486 .insns = {
9487 BPF_MOV32_IMM(BPF_REG_1, 0),
9488 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9489 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9490 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9491 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9492 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9493 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9494 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9495 BPF_EXIT_INSN(),
9496 },
9497 .result = ACCEPT,
9498 },
9499 {
9500 "masking, test in bounds 3",
9501 .insns = {
9502 BPF_MOV32_IMM(BPF_REG_1, 0xfffffffe),
9503 BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1),
9504 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9505 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9506 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9507 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9508 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9509 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9510 BPF_EXIT_INSN(),
9511 },
9512 .result = ACCEPT,
9513 },
9514 {
9515 "masking, test in bounds 4",
9516 .insns = {
9517 BPF_MOV32_IMM(BPF_REG_1, 0xabcde),
9518 BPF_MOV32_IMM(BPF_REG_2, 0xabcdef - 1),
9519 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9520 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9521 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9522 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9523 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9524 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9525 BPF_EXIT_INSN(),
9526 },
9527 .result = ACCEPT,
9528 },
9529 {
9530 "masking, test in bounds 5",
9531 .insns = {
9532 BPF_MOV32_IMM(BPF_REG_1, 0),
9533 BPF_MOV32_IMM(BPF_REG_2, 1 - 1),
9534 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9535 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9536 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9537 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9538 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9539 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9540 BPF_EXIT_INSN(),
9541 },
9542 .result = ACCEPT,
9543 },
9544 {
9545 "masking, test in bounds 6",
9546 .insns = {
9547 BPF_MOV32_IMM(BPF_REG_1, 46),
9548 BPF_MOV32_IMM(BPF_REG_2, 47 - 1),
9549 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1),
9550 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1),
9551 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9552 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9553 BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2),
9554 BPF_MOV64_REG(BPF_REG_0, BPF_REG_1),
9555 BPF_EXIT_INSN(),
9556 },
9557 .result = ACCEPT,
9558 },
9559 {
9560 "masking, test in bounds 7",
9561 .insns = {
9562 BPF_MOV64_IMM(BPF_REG_3, -46),
9563 BPF_ALU64_IMM(BPF_MUL, BPF_REG_3, -1),
9564 BPF_MOV32_IMM(BPF_REG_2, 47 - 1),
9565 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_3),
9566 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_3),
9567 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9568 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9569 BPF_ALU64_REG(BPF_AND, BPF_REG_3, BPF_REG_2),
9570 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
9571 BPF_EXIT_INSN(),
9572 },
9573 .result = ACCEPT,
9574 },
9575 {
9576 "masking, test in bounds 8",
9577 .insns = {
9578 BPF_MOV64_IMM(BPF_REG_3, -47),
9579 BPF_ALU64_IMM(BPF_MUL, BPF_REG_3, -1),
9580 BPF_MOV32_IMM(BPF_REG_2, 47 - 1),
9581 BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_3),
9582 BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_3),
9583 BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0),
9584 BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63),
9585 BPF_ALU64_REG(BPF_AND, BPF_REG_3, BPF_REG_2),
9586 BPF_MOV64_REG(BPF_REG_0, BPF_REG_3),
9587 BPF_EXIT_INSN(),
9588 },
9589 .result = ACCEPT,
9590 },
9591 };
9592
9593 static int probe_filter_length(const struct bpf_insn *fp)
9594 {
9595 int len;
9596
9597 for (len = MAX_INSNS - 1; len > 0; --len)
9598 if (fp[len].code != 0 || fp[len].imm != 0)
9599 break;
9600 return len + 1;
9601 }
9602
9603 static int create_map(uint32_t size_value, uint32_t max_elem)
9604 {
9605 int fd;
9606
9607 fd = bpf_create_map(BPF_MAP_TYPE_HASH, sizeof(long long),
9608 size_value, max_elem, BPF_F_NO_PREALLOC);
9609 if (fd < 0)
9610 printf("Failed to create hash map '%s'!\n", strerror(errno));
9611
9612 return fd;
9613 }
9614
9615 static int create_prog_array(void)
9616 {
9617 int fd;
9618
9619 fd = bpf_create_map(BPF_MAP_TYPE_PROG_ARRAY, sizeof(int),
9620 sizeof(int), 4, 0);
9621 if (fd < 0)
9622 printf("Failed to create prog array '%s'!\n", strerror(errno));
9623
9624 return fd;
9625 }
9626
9627 static int create_map_in_map(void)
9628 {
9629 int inner_map_fd, outer_map_fd;
9630
9631 inner_map_fd = bpf_create_map(BPF_MAP_TYPE_ARRAY, sizeof(int),
9632 sizeof(int), 1, 0);
9633 if (inner_map_fd < 0) {
9634 printf("Failed to create array '%s'!\n", strerror(errno));
9635 return inner_map_fd;
9636 }
9637
9638 outer_map_fd = bpf_create_map_in_map(BPF_MAP_TYPE_ARRAY_OF_MAPS, NULL,
9639 sizeof(int), inner_map_fd, 1, 0);
9640 if (outer_map_fd < 0)
9641 printf("Failed to create array of maps '%s'!\n",
9642 strerror(errno));
9643
9644 close(inner_map_fd);
9645
9646 return outer_map_fd;
9647 }
9648
9649 static char bpf_vlog[32768];
9650
9651 static void do_test_fixup(struct bpf_test *test, struct bpf_insn *prog,
9652 int *map_fds)
9653 {
9654 int *fixup_map1 = test->fixup_map1;
9655 int *fixup_map2 = test->fixup_map2;
9656 int *fixup_prog = test->fixup_prog;
9657 int *fixup_map_in_map = test->fixup_map_in_map;
9658
9659 /* Allocating HTs with 1 elem is fine here, since we only test
9660 * for verifier and not do a runtime lookup, so the only thing
9661 * that really matters is value size in this case.
9662 */
9663 if (*fixup_map1) {
9664 map_fds[0] = create_map(sizeof(long long), 1);
9665 do {
9666 prog[*fixup_map1].imm = map_fds[0];
9667 fixup_map1++;
9668 } while (*fixup_map1);
9669 }
9670
9671 if (*fixup_map2) {
9672 map_fds[1] = create_map(sizeof(struct test_val), 1);
9673 do {
9674 prog[*fixup_map2].imm = map_fds[1];
9675 fixup_map2++;
9676 } while (*fixup_map2);
9677 }
9678
9679 if (*fixup_prog) {
9680 map_fds[2] = create_prog_array();
9681 do {
9682 prog[*fixup_prog].imm = map_fds[2];
9683 fixup_prog++;
9684 } while (*fixup_prog);
9685 }
9686
9687 if (*fixup_map_in_map) {
9688 map_fds[3] = create_map_in_map();
9689 do {
9690 prog[*fixup_map_in_map].imm = map_fds[3];
9691 fixup_map_in_map++;
9692 } while (*fixup_map_in_map);
9693 }
9694 }
9695
9696 static void do_test_single(struct bpf_test *test, bool unpriv,
9697 int *passes, int *errors)
9698 {
9699 int fd_prog, expected_ret, reject_from_alignment;
9700 struct bpf_insn *prog = test->insns;
9701 int prog_len = probe_filter_length(prog);
9702 int prog_type = test->prog_type;
9703 int map_fds[MAX_NR_MAPS];
9704 const char *expected_err;
9705 int i;
9706
9707 for (i = 0; i < MAX_NR_MAPS; i++)
9708 map_fds[i] = -1;
9709
9710 do_test_fixup(test, prog, map_fds);
9711
9712 fd_prog = bpf_verify_program(prog_type ? : BPF_PROG_TYPE_SOCKET_FILTER,
9713 prog, prog_len, test->flags & F_LOAD_WITH_STRICT_ALIGNMENT,
9714 "GPL", 0, bpf_vlog, sizeof(bpf_vlog), 1);
9715
9716 expected_ret = unpriv && test->result_unpriv != UNDEF ?
9717 test->result_unpriv : test->result;
9718 expected_err = unpriv && test->errstr_unpriv ?
9719 test->errstr_unpriv : test->errstr;
9720
9721 reject_from_alignment = fd_prog < 0 &&
9722 (test->flags & F_NEEDS_EFFICIENT_UNALIGNED_ACCESS) &&
9723 strstr(bpf_vlog, "misaligned");
9724 #ifdef CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS
9725 if (reject_from_alignment) {
9726 printf("FAIL\nFailed due to alignment despite having efficient unaligned access: '%s'!\n",
9727 strerror(errno));
9728 goto fail_log;
9729 }
9730 #endif
9731 if (expected_ret == ACCEPT) {
9732 if (fd_prog < 0 && !reject_from_alignment) {
9733 printf("FAIL\nFailed to load prog '%s'!\n",
9734 strerror(errno));
9735 goto fail_log;
9736 }
9737 } else {
9738 if (fd_prog >= 0) {
9739 printf("FAIL\nUnexpected success to load!\n");
9740 goto fail_log;
9741 }
9742 if (!strstr(bpf_vlog, expected_err) && !reject_from_alignment) {
9743 printf("FAIL\nUnexpected error message!\n");
9744 goto fail_log;
9745 }
9746 }
9747
9748 (*passes)++;
9749 printf("OK%s\n", reject_from_alignment ?
9750 " (NOTE: reject due to unknown alignment)" : "");
9751 close_fds:
9752 close(fd_prog);
9753 for (i = 0; i < MAX_NR_MAPS; i++)
9754 close(map_fds[i]);
9755 sched_yield();
9756 return;
9757 fail_log:
9758 (*errors)++;
9759 printf("%s", bpf_vlog);
9760 goto close_fds;
9761 }
9762
9763 static bool is_admin(void)
9764 {
9765 cap_t caps;
9766 cap_flag_value_t sysadmin = CAP_CLEAR;
9767 const cap_value_t cap_val = CAP_SYS_ADMIN;
9768
9769 #ifdef CAP_IS_SUPPORTED
9770 if (!CAP_IS_SUPPORTED(CAP_SETFCAP)) {
9771 perror("cap_get_flag");
9772 return false;
9773 }
9774 #endif
9775 caps = cap_get_proc();
9776 if (!caps) {
9777 perror("cap_get_proc");
9778 return false;
9779 }
9780 if (cap_get_flag(caps, cap_val, CAP_EFFECTIVE, &sysadmin))
9781 perror("cap_get_flag");
9782 if (cap_free(caps))
9783 perror("cap_free");
9784 return (sysadmin == CAP_SET);
9785 }
9786
9787 static int set_admin(bool admin)
9788 {
9789 cap_t caps;
9790 const cap_value_t cap_val = CAP_SYS_ADMIN;
9791 int ret = -1;
9792
9793 caps = cap_get_proc();
9794 if (!caps) {
9795 perror("cap_get_proc");
9796 return -1;
9797 }
9798 if (cap_set_flag(caps, CAP_EFFECTIVE, 1, &cap_val,
9799 admin ? CAP_SET : CAP_CLEAR)) {
9800 perror("cap_set_flag");
9801 goto out;
9802 }
9803 if (cap_set_proc(caps)) {
9804 perror("cap_set_proc");
9805 goto out;
9806 }
9807 ret = 0;
9808 out:
9809 if (cap_free(caps))
9810 perror("cap_free");
9811 return ret;
9812 }
9813
9814 static int do_test(bool unpriv, unsigned int from, unsigned int to)
9815 {
9816 int i, passes = 0, errors = 0;
9817
9818 for (i = from; i < to; i++) {
9819 struct bpf_test *test = &tests[i];
9820
9821 /* Program types that are not supported by non-root we
9822 * skip right away.
9823 */
9824 if (!test->prog_type) {
9825 if (!unpriv)
9826 set_admin(false);
9827 printf("#%d/u %s ", i, test->descr);
9828 do_test_single(test, true, &passes, &errors);
9829 if (!unpriv)
9830 set_admin(true);
9831 }
9832
9833 if (!unpriv) {
9834 printf("#%d/p %s ", i, test->descr);
9835 do_test_single(test, false, &passes, &errors);
9836 }
9837 }
9838
9839 printf("Summary: %d PASSED, %d FAILED\n", passes, errors);
9840 return errors ? EXIT_FAILURE : EXIT_SUCCESS;
9841 }
9842
9843 int main(int argc, char **argv)
9844 {
9845 struct rlimit rinf = { RLIM_INFINITY, RLIM_INFINITY };
9846 struct rlimit rlim = { 1 << 20, 1 << 20 };
9847 unsigned int from = 0, to = ARRAY_SIZE(tests);
9848 bool unpriv = !is_admin();
9849
9850 if (argc == 3) {
9851 unsigned int l = atoi(argv[argc - 2]);
9852 unsigned int u = atoi(argv[argc - 1]);
9853
9854 if (l < to && u < to) {
9855 from = l;
9856 to = u + 1;
9857 }
9858 } else if (argc == 2) {
9859 unsigned int t = atoi(argv[argc - 1]);
9860
9861 if (t < to) {
9862 from = t;
9863 to = t + 1;
9864 }
9865 }
9866
9867 setrlimit(RLIMIT_MEMLOCK, unpriv ? &rlim : &rinf);
9868 return do_test(unpriv, from, to);
9869 }