summaryrefslogtreecommitdiffstats
path: root/lib/test_bpf.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/test_bpf.c')
-rw-r--r--lib/test_bpf.c570
1 files changed, 358 insertions, 212 deletions
diff --git a/lib/test_bpf.c b/lib/test_bpf.c
index 8e157806df7a..317f231462d4 100644
--- a/lib/test_bpf.c
+++ b/lib/test_bpf.c
@@ -386,116 +386,6 @@ static int bpf_fill_ld_abs_get_processor_id(struct bpf_test *self)
386 return 0; 386 return 0;
387} 387}
388 388
389#define PUSH_CNT 68
390/* test: {skb->data[0], vlan_push} x 68 + {skb->data[0], vlan_pop} x 68 */
391static int bpf_fill_ld_abs_vlan_push_pop(struct bpf_test *self)
392{
393 unsigned int len = BPF_MAXINSNS;
394 struct bpf_insn *insn;
395 int i = 0, j, k = 0;
396
397 insn = kmalloc_array(len, sizeof(*insn), GFP_KERNEL);
398 if (!insn)
399 return -ENOMEM;
400
401 insn[i++] = BPF_MOV64_REG(R6, R1);
402loop:
403 for (j = 0; j < PUSH_CNT; j++) {
404 insn[i++] = BPF_LD_ABS(BPF_B, 0);
405 insn[i] = BPF_JMP_IMM(BPF_JNE, R0, 0x34, len - i - 2);
406 i++;
407 insn[i++] = BPF_MOV64_REG(R1, R6);
408 insn[i++] = BPF_MOV64_IMM(R2, 1);
409 insn[i++] = BPF_MOV64_IMM(R3, 2);
410 insn[i++] = BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
411 bpf_skb_vlan_push_proto.func - __bpf_call_base);
412 insn[i] = BPF_JMP_IMM(BPF_JNE, R0, 0, len - i - 2);
413 i++;
414 }
415
416 for (j = 0; j < PUSH_CNT; j++) {
417 insn[i++] = BPF_LD_ABS(BPF_B, 0);
418 insn[i] = BPF_JMP_IMM(BPF_JNE, R0, 0x34, len - i - 2);
419 i++;
420 insn[i++] = BPF_MOV64_REG(R1, R6);
421 insn[i++] = BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
422 bpf_skb_vlan_pop_proto.func - __bpf_call_base);
423 insn[i] = BPF_JMP_IMM(BPF_JNE, R0, 0, len - i - 2);
424 i++;
425 }
426 if (++k < 5)
427 goto loop;
428
429 for (; i < len - 1; i++)
430 insn[i] = BPF_ALU32_IMM(BPF_MOV, R0, 0xbef);
431
432 insn[len - 1] = BPF_EXIT_INSN();
433
434 self->u.ptr.insns = insn;
435 self->u.ptr.len = len;
436
437 return 0;
438}
439
440static int bpf_fill_ld_abs_vlan_push_pop2(struct bpf_test *self)
441{
442 struct bpf_insn *insn;
443
444 insn = kmalloc_array(16, sizeof(*insn), GFP_KERNEL);
445 if (!insn)
446 return -ENOMEM;
447
448 /* Due to func address being non-const, we need to
449 * assemble this here.
450 */
451 insn[0] = BPF_MOV64_REG(R6, R1);
452 insn[1] = BPF_LD_ABS(BPF_B, 0);
453 insn[2] = BPF_LD_ABS(BPF_H, 0);
454 insn[3] = BPF_LD_ABS(BPF_W, 0);
455 insn[4] = BPF_MOV64_REG(R7, R6);
456 insn[5] = BPF_MOV64_IMM(R6, 0);
457 insn[6] = BPF_MOV64_REG(R1, R7);
458 insn[7] = BPF_MOV64_IMM(R2, 1);
459 insn[8] = BPF_MOV64_IMM(R3, 2);
460 insn[9] = BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0,
461 bpf_skb_vlan_push_proto.func - __bpf_call_base);
462 insn[10] = BPF_MOV64_REG(R6, R7);
463 insn[11] = BPF_LD_ABS(BPF_B, 0);
464 insn[12] = BPF_LD_ABS(BPF_H, 0);
465 insn[13] = BPF_LD_ABS(BPF_W, 0);
466 insn[14] = BPF_MOV64_IMM(R0, 42);
467 insn[15] = BPF_EXIT_INSN();
468
469 self->u.ptr.insns = insn;
470 self->u.ptr.len = 16;
471
472 return 0;
473}
474
475static int bpf_fill_jump_around_ld_abs(struct bpf_test *self)
476{
477 unsigned int len = BPF_MAXINSNS;
478 struct bpf_insn *insn;
479 int i = 0;
480
481 insn = kmalloc_array(len, sizeof(*insn), GFP_KERNEL);
482 if (!insn)
483 return -ENOMEM;
484
485 insn[i++] = BPF_MOV64_REG(R6, R1);
486 insn[i++] = BPF_LD_ABS(BPF_B, 0);
487 insn[i] = BPF_JMP_IMM(BPF_JEQ, R0, 10, len - i - 2);
488 i++;
489 while (i < len - 1)
490 insn[i++] = BPF_LD_ABS(BPF_B, 1);
491 insn[i] = BPF_EXIT_INSN();
492
493 self->u.ptr.insns = insn;
494 self->u.ptr.len = len;
495
496 return 0;
497}
498
499static int __bpf_fill_stxdw(struct bpf_test *self, int size) 389static int __bpf_fill_stxdw(struct bpf_test *self, int size)
500{ 390{
501 unsigned int len = BPF_MAXINSNS; 391 unsigned int len = BPF_MAXINSNS;
@@ -1988,40 +1878,6 @@ static struct bpf_test tests[] = {
1988 { { 0, -1 } } 1878 { { 0, -1 } }
1989 }, 1879 },
1990 { 1880 {
1991 "INT: DIV + ABS",
1992 .u.insns_int = {
1993 BPF_ALU64_REG(BPF_MOV, R6, R1),
1994 BPF_LD_ABS(BPF_B, 3),
1995 BPF_ALU64_IMM(BPF_MOV, R2, 2),
1996 BPF_ALU32_REG(BPF_DIV, R0, R2),
1997 BPF_ALU64_REG(BPF_MOV, R8, R0),
1998 BPF_LD_ABS(BPF_B, 4),
1999 BPF_ALU64_REG(BPF_ADD, R8, R0),
2000 BPF_LD_IND(BPF_B, R8, -70),
2001 BPF_EXIT_INSN(),
2002 },
2003 INTERNAL,
2004 { 10, 20, 30, 40, 50 },
2005 { { 4, 0 }, { 5, 10 } }
2006 },
2007 {
2008 /* This one doesn't go through verifier, but is just raw insn
2009 * as opposed to cBPF tests from here. Thus div by 0 tests are
2010 * done in test_verifier in BPF kselftests.
2011 */
2012 "INT: DIV by -1",
2013 .u.insns_int = {
2014 BPF_ALU64_REG(BPF_MOV, R6, R1),
2015 BPF_ALU64_IMM(BPF_MOV, R7, -1),
2016 BPF_LD_ABS(BPF_B, 3),
2017 BPF_ALU32_REG(BPF_DIV, R0, R7),
2018 BPF_EXIT_INSN(),
2019 },
2020 INTERNAL,
2021 { 10, 20, 30, 40, 50 },
2022 { { 3, 0 }, { 4, 0 } }
2023 },
2024 {
2025 "check: missing ret", 1881 "check: missing ret",
2026 .u.insns = { 1882 .u.insns = {
2027 BPF_STMT(BPF_LD | BPF_IMM, 1), 1883 BPF_STMT(BPF_LD | BPF_IMM, 1),
@@ -2383,50 +2239,6 @@ static struct bpf_test tests[] = {
2383 { }, 2239 { },
2384 { { 0, 1 } } 2240 { { 0, 1 } }
2385 }, 2241 },
2386 {
2387 "nmap reduced",
2388 .u.insns_int = {
2389 BPF_MOV64_REG(R6, R1),
2390 BPF_LD_ABS(BPF_H, 12),
2391 BPF_JMP_IMM(BPF_JNE, R0, 0x806, 28),
2392 BPF_LD_ABS(BPF_H, 12),
2393 BPF_JMP_IMM(BPF_JNE, R0, 0x806, 26),
2394 BPF_MOV32_IMM(R0, 18),
2395 BPF_STX_MEM(BPF_W, R10, R0, -64),
2396 BPF_LDX_MEM(BPF_W, R7, R10, -64),
2397 BPF_LD_IND(BPF_W, R7, 14),
2398 BPF_STX_MEM(BPF_W, R10, R0, -60),
2399 BPF_MOV32_IMM(R0, 280971478),
2400 BPF_STX_MEM(BPF_W, R10, R0, -56),
2401 BPF_LDX_MEM(BPF_W, R7, R10, -56),
2402 BPF_LDX_MEM(BPF_W, R0, R10, -60),
2403 BPF_ALU32_REG(BPF_SUB, R0, R7),
2404 BPF_JMP_IMM(BPF_JNE, R0, 0, 15),
2405 BPF_LD_ABS(BPF_H, 12),
2406 BPF_JMP_IMM(BPF_JNE, R0, 0x806, 13),
2407 BPF_MOV32_IMM(R0, 22),
2408 BPF_STX_MEM(BPF_W, R10, R0, -56),
2409 BPF_LDX_MEM(BPF_W, R7, R10, -56),
2410 BPF_LD_IND(BPF_H, R7, 14),
2411 BPF_STX_MEM(BPF_W, R10, R0, -52),
2412 BPF_MOV32_IMM(R0, 17366),
2413 BPF_STX_MEM(BPF_W, R10, R0, -48),
2414 BPF_LDX_MEM(BPF_W, R7, R10, -48),
2415 BPF_LDX_MEM(BPF_W, R0, R10, -52),
2416 BPF_ALU32_REG(BPF_SUB, R0, R7),
2417 BPF_JMP_IMM(BPF_JNE, R0, 0, 2),
2418 BPF_MOV32_IMM(R0, 256),
2419 BPF_EXIT_INSN(),
2420 BPF_MOV32_IMM(R0, 0),
2421 BPF_EXIT_INSN(),
2422 },
2423 INTERNAL,
2424 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0x08, 0x06, 0, 0,
2425 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2426 0x10, 0xbf, 0x48, 0xd6, 0x43, 0xd6},
2427 { { 38, 256 } },
2428 .stack_depth = 64,
2429 },
2430 /* BPF_ALU | BPF_MOV | BPF_X */ 2242 /* BPF_ALU | BPF_MOV | BPF_X */
2431 { 2243 {
2432 "ALU_MOV_X: dst = 2", 2244 "ALU_MOV_X: dst = 2",
@@ -5485,22 +5297,6 @@ static struct bpf_test tests[] = {
5485 { { 1, 0xbee } }, 5297 { { 1, 0xbee } },
5486 .fill_helper = bpf_fill_ld_abs_get_processor_id, 5298 .fill_helper = bpf_fill_ld_abs_get_processor_id,
5487 }, 5299 },
5488 {
5489 "BPF_MAXINSNS: ld_abs+vlan_push/pop",
5490 { },
5491 INTERNAL,
5492 { 0x34 },
5493 { { ETH_HLEN, 0xbef } },
5494 .fill_helper = bpf_fill_ld_abs_vlan_push_pop,
5495 },
5496 {
5497 "BPF_MAXINSNS: jump around ld_abs",
5498 { },
5499 INTERNAL,
5500 { 10, 11 },
5501 { { 2, 10 } },
5502 .fill_helper = bpf_fill_jump_around_ld_abs,
5503 },
5504 /* 5300 /*
5505 * LD_IND / LD_ABS on fragmented SKBs 5301 * LD_IND / LD_ABS on fragmented SKBs
5506 */ 5302 */
@@ -5683,6 +5479,53 @@ static struct bpf_test tests[] = {
5683 { {0x40, 0x05 } }, 5479 { {0x40, 0x05 } },
5684 }, 5480 },
5685 { 5481 {
5482 "LD_IND byte positive offset, all ff",
5483 .u.insns = {
5484 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5485 BPF_STMT(BPF_LD | BPF_IND | BPF_B, 0x1),
5486 BPF_STMT(BPF_RET | BPF_A, 0x0),
5487 },
5488 CLASSIC,
5489 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5490 { {0x40, 0xff } },
5491 },
5492 {
5493 "LD_IND byte positive offset, out of bounds",
5494 .u.insns = {
5495 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5496 BPF_STMT(BPF_LD | BPF_IND | BPF_B, 0x1),
5497 BPF_STMT(BPF_RET | BPF_A, 0x0),
5498 },
5499 CLASSIC,
5500 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5501 { {0x3f, 0 }, },
5502 },
5503 {
5504 "LD_IND byte negative offset, out of bounds",
5505 .u.insns = {
5506 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5507 BPF_STMT(BPF_LD | BPF_IND | BPF_B, -0x3f),
5508 BPF_STMT(BPF_RET | BPF_A, 0x0),
5509 },
5510 CLASSIC,
5511 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5512 { {0x3f, 0 } },
5513 },
5514 {
5515 "LD_IND byte negative offset, multiple calls",
5516 .u.insns = {
5517 BPF_STMT(BPF_LDX | BPF_IMM, 0x3b),
5518 BPF_STMT(BPF_LD | BPF_IND | BPF_B, SKF_LL_OFF + 1),
5519 BPF_STMT(BPF_LD | BPF_IND | BPF_B, SKF_LL_OFF + 2),
5520 BPF_STMT(BPF_LD | BPF_IND | BPF_B, SKF_LL_OFF + 3),
5521 BPF_STMT(BPF_LD | BPF_IND | BPF_B, SKF_LL_OFF + 4),
5522 BPF_STMT(BPF_RET | BPF_A, 0x0),
5523 },
5524 CLASSIC,
5525 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5526 { {0x40, 0x82 }, },
5527 },
5528 {
5686 "LD_IND halfword positive offset", 5529 "LD_IND halfword positive offset",
5687 .u.insns = { 5530 .u.insns = {
5688 BPF_STMT(BPF_LDX | BPF_IMM, 0x20), 5531 BPF_STMT(BPF_LDX | BPF_IMM, 0x20),
@@ -5731,6 +5574,39 @@ static struct bpf_test tests[] = {
5731 { {0x40, 0x66cc } }, 5574 { {0x40, 0x66cc } },
5732 }, 5575 },
5733 { 5576 {
5577 "LD_IND halfword positive offset, all ff",
5578 .u.insns = {
5579 BPF_STMT(BPF_LDX | BPF_IMM, 0x3d),
5580 BPF_STMT(BPF_LD | BPF_IND | BPF_H, 0x1),
5581 BPF_STMT(BPF_RET | BPF_A, 0x0),
5582 },
5583 CLASSIC,
5584 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5585 { {0x40, 0xffff } },
5586 },
5587 {
5588 "LD_IND halfword positive offset, out of bounds",
5589 .u.insns = {
5590 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5591 BPF_STMT(BPF_LD | BPF_IND | BPF_H, 0x1),
5592 BPF_STMT(BPF_RET | BPF_A, 0x0),
5593 },
5594 CLASSIC,
5595 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5596 { {0x3f, 0 }, },
5597 },
5598 {
5599 "LD_IND halfword negative offset, out of bounds",
5600 .u.insns = {
5601 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5602 BPF_STMT(BPF_LD | BPF_IND | BPF_H, -0x3f),
5603 BPF_STMT(BPF_RET | BPF_A, 0x0),
5604 },
5605 CLASSIC,
5606 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5607 { {0x3f, 0 } },
5608 },
5609 {
5734 "LD_IND word positive offset", 5610 "LD_IND word positive offset",
5735 .u.insns = { 5611 .u.insns = {
5736 BPF_STMT(BPF_LDX | BPF_IMM, 0x20), 5612 BPF_STMT(BPF_LDX | BPF_IMM, 0x20),
@@ -5821,6 +5697,39 @@ static struct bpf_test tests[] = {
5821 { {0x40, 0x66cc77dd } }, 5697 { {0x40, 0x66cc77dd } },
5822 }, 5698 },
5823 { 5699 {
5700 "LD_IND word positive offset, all ff",
5701 .u.insns = {
5702 BPF_STMT(BPF_LDX | BPF_IMM, 0x3b),
5703 BPF_STMT(BPF_LD | BPF_IND | BPF_W, 0x1),
5704 BPF_STMT(BPF_RET | BPF_A, 0x0),
5705 },
5706 CLASSIC,
5707 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5708 { {0x40, 0xffffffff } },
5709 },
5710 {
5711 "LD_IND word positive offset, out of bounds",
5712 .u.insns = {
5713 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5714 BPF_STMT(BPF_LD | BPF_IND | BPF_W, 0x1),
5715 BPF_STMT(BPF_RET | BPF_A, 0x0),
5716 },
5717 CLASSIC,
5718 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5719 { {0x3f, 0 }, },
5720 },
5721 {
5722 "LD_IND word negative offset, out of bounds",
5723 .u.insns = {
5724 BPF_STMT(BPF_LDX | BPF_IMM, 0x3e),
5725 BPF_STMT(BPF_LD | BPF_IND | BPF_W, -0x3f),
5726 BPF_STMT(BPF_RET | BPF_A, 0x0),
5727 },
5728 CLASSIC,
5729 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5730 { {0x3f, 0 } },
5731 },
5732 {
5824 "LD_ABS byte", 5733 "LD_ABS byte",
5825 .u.insns = { 5734 .u.insns = {
5826 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, 0x20), 5735 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, 0x20),
@@ -5838,6 +5747,68 @@ static struct bpf_test tests[] = {
5838 { {0x40, 0xcc } }, 5747 { {0x40, 0xcc } },
5839 }, 5748 },
5840 { 5749 {
5750 "LD_ABS byte positive offset, all ff",
5751 .u.insns = {
5752 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, 0x3f),
5753 BPF_STMT(BPF_RET | BPF_A, 0x0),
5754 },
5755 CLASSIC,
5756 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5757 { {0x40, 0xff } },
5758 },
5759 {
5760 "LD_ABS byte positive offset, out of bounds",
5761 .u.insns = {
5762 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, 0x3f),
5763 BPF_STMT(BPF_RET | BPF_A, 0x0),
5764 },
5765 CLASSIC,
5766 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5767 { {0x3f, 0 }, },
5768 },
5769 {
5770 "LD_ABS byte negative offset, out of bounds load",
5771 .u.insns = {
5772 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, -1),
5773 BPF_STMT(BPF_RET | BPF_A, 0x0),
5774 },
5775 CLASSIC | FLAG_EXPECTED_FAIL,
5776 .expected_errcode = -EINVAL,
5777 },
5778 {
5779 "LD_ABS byte negative offset, in bounds",
5780 .u.insns = {
5781 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3f),
5782 BPF_STMT(BPF_RET | BPF_A, 0x0),
5783 },
5784 CLASSIC,
5785 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5786 { {0x40, 0x82 }, },
5787 },
5788 {
5789 "LD_ABS byte negative offset, out of bounds",
5790 .u.insns = {
5791 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3f),
5792 BPF_STMT(BPF_RET | BPF_A, 0x0),
5793 },
5794 CLASSIC,
5795 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5796 { {0x3f, 0 }, },
5797 },
5798 {
5799 "LD_ABS byte negative offset, multiple calls",
5800 .u.insns = {
5801 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3c),
5802 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3d),
5803 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3e),
5804 BPF_STMT(BPF_LD | BPF_ABS | BPF_B, SKF_LL_OFF + 0x3f),
5805 BPF_STMT(BPF_RET | BPF_A, 0x0),
5806 },
5807 CLASSIC,
5808 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5809 { {0x40, 0x82 }, },
5810 },
5811 {
5841 "LD_ABS halfword", 5812 "LD_ABS halfword",
5842 .u.insns = { 5813 .u.insns = {
5843 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, 0x22), 5814 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, 0x22),
@@ -5872,6 +5843,55 @@ static struct bpf_test tests[] = {
5872 { {0x40, 0x99ff } }, 5843 { {0x40, 0x99ff } },
5873 }, 5844 },
5874 { 5845 {
5846 "LD_ABS halfword positive offset, all ff",
5847 .u.insns = {
5848 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, 0x3e),
5849 BPF_STMT(BPF_RET | BPF_A, 0x0),
5850 },
5851 CLASSIC,
5852 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5853 { {0x40, 0xffff } },
5854 },
5855 {
5856 "LD_ABS halfword positive offset, out of bounds",
5857 .u.insns = {
5858 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, 0x3f),
5859 BPF_STMT(BPF_RET | BPF_A, 0x0),
5860 },
5861 CLASSIC,
5862 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5863 { {0x3f, 0 }, },
5864 },
5865 {
5866 "LD_ABS halfword negative offset, out of bounds load",
5867 .u.insns = {
5868 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, -1),
5869 BPF_STMT(BPF_RET | BPF_A, 0x0),
5870 },
5871 CLASSIC | FLAG_EXPECTED_FAIL,
5872 .expected_errcode = -EINVAL,
5873 },
5874 {
5875 "LD_ABS halfword negative offset, in bounds",
5876 .u.insns = {
5877 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, SKF_LL_OFF + 0x3e),
5878 BPF_STMT(BPF_RET | BPF_A, 0x0),
5879 },
5880 CLASSIC,
5881 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5882 { {0x40, 0x1982 }, },
5883 },
5884 {
5885 "LD_ABS halfword negative offset, out of bounds",
5886 .u.insns = {
5887 BPF_STMT(BPF_LD | BPF_ABS | BPF_H, SKF_LL_OFF + 0x3e),
5888 BPF_STMT(BPF_RET | BPF_A, 0x0),
5889 },
5890 CLASSIC,
5891 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5892 { {0x3f, 0 }, },
5893 },
5894 {
5875 "LD_ABS word", 5895 "LD_ABS word",
5876 .u.insns = { 5896 .u.insns = {
5877 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, 0x1c), 5897 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, 0x1c),
@@ -5939,6 +5959,140 @@ static struct bpf_test tests[] = {
5939 }, 5959 },
5940 { {0x40, 0x88ee99ff } }, 5960 { {0x40, 0x88ee99ff } },
5941 }, 5961 },
5962 {
5963 "LD_ABS word positive offset, all ff",
5964 .u.insns = {
5965 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, 0x3c),
5966 BPF_STMT(BPF_RET | BPF_A, 0x0),
5967 },
5968 CLASSIC,
5969 { [0x3c] = 0xff, [0x3d] = 0xff, [0x3e] = 0xff, [0x3f] = 0xff },
5970 { {0x40, 0xffffffff } },
5971 },
5972 {
5973 "LD_ABS word positive offset, out of bounds",
5974 .u.insns = {
5975 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, 0x3f),
5976 BPF_STMT(BPF_RET | BPF_A, 0x0),
5977 },
5978 CLASSIC,
5979 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5980 { {0x3f, 0 }, },
5981 },
5982 {
5983 "LD_ABS word negative offset, out of bounds load",
5984 .u.insns = {
5985 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, -1),
5986 BPF_STMT(BPF_RET | BPF_A, 0x0),
5987 },
5988 CLASSIC | FLAG_EXPECTED_FAIL,
5989 .expected_errcode = -EINVAL,
5990 },
5991 {
5992 "LD_ABS word negative offset, in bounds",
5993 .u.insns = {
5994 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, SKF_LL_OFF + 0x3c),
5995 BPF_STMT(BPF_RET | BPF_A, 0x0),
5996 },
5997 CLASSIC,
5998 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
5999 { {0x40, 0x25051982 }, },
6000 },
6001 {
6002 "LD_ABS word negative offset, out of bounds",
6003 .u.insns = {
6004 BPF_STMT(BPF_LD | BPF_ABS | BPF_W, SKF_LL_OFF + 0x3c),
6005 BPF_STMT(BPF_RET | BPF_A, 0x0),
6006 },
6007 CLASSIC,
6008 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6009 { {0x3f, 0 }, },
6010 },
6011 {
6012 "LDX_MSH standalone, preserved A",
6013 .u.insns = {
6014 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6015 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3c),
6016 BPF_STMT(BPF_RET | BPF_A, 0x0),
6017 },
6018 CLASSIC,
6019 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6020 { {0x40, 0xffeebbaa }, },
6021 },
6022 {
6023 "LDX_MSH standalone, preserved A 2",
6024 .u.insns = {
6025 BPF_STMT(BPF_LD | BPF_IMM, 0x175e9d63),
6026 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3c),
6027 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3d),
6028 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3e),
6029 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3f),
6030 BPF_STMT(BPF_RET | BPF_A, 0x0),
6031 },
6032 CLASSIC,
6033 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6034 { {0x40, 0x175e9d63 }, },
6035 },
6036 {
6037 "LDX_MSH standalone, test result 1",
6038 .u.insns = {
6039 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6040 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3c),
6041 BPF_STMT(BPF_MISC | BPF_TXA, 0),
6042 BPF_STMT(BPF_RET | BPF_A, 0x0),
6043 },
6044 CLASSIC,
6045 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6046 { {0x40, 0x14 }, },
6047 },
6048 {
6049 "LDX_MSH standalone, test result 2",
6050 .u.insns = {
6051 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6052 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x3e),
6053 BPF_STMT(BPF_MISC | BPF_TXA, 0),
6054 BPF_STMT(BPF_RET | BPF_A, 0x0),
6055 },
6056 CLASSIC,
6057 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6058 { {0x40, 0x24 }, },
6059 },
6060 {
6061 "LDX_MSH standalone, negative offset",
6062 .u.insns = {
6063 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6064 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, -1),
6065 BPF_STMT(BPF_MISC | BPF_TXA, 0),
6066 BPF_STMT(BPF_RET | BPF_A, 0x0),
6067 },
6068 CLASSIC,
6069 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6070 { {0x40, 0 }, },
6071 },
6072 {
6073 "LDX_MSH standalone, negative offset 2",
6074 .u.insns = {
6075 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6076 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, SKF_LL_OFF + 0x3e),
6077 BPF_STMT(BPF_MISC | BPF_TXA, 0),
6078 BPF_STMT(BPF_RET | BPF_A, 0x0),
6079 },
6080 CLASSIC,
6081 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6082 { {0x40, 0x24 }, },
6083 },
6084 {
6085 "LDX_MSH standalone, out of bounds",
6086 .u.insns = {
6087 BPF_STMT(BPF_LD | BPF_IMM, 0xffeebbaa),
6088 BPF_STMT(BPF_LDX | BPF_B | BPF_MSH, 0x40),
6089 BPF_STMT(BPF_MISC | BPF_TXA, 0),
6090 BPF_STMT(BPF_RET | BPF_A, 0x0),
6091 },
6092 CLASSIC,
6093 { [0x3c] = 0x25, [0x3d] = 0x05, [0x3e] = 0x19, [0x3f] = 0x82 },
6094 { {0x40, 0 }, },
6095 },
5942 /* 6096 /*
5943 * verify that the interpreter or JIT correctly sets A and X 6097 * verify that the interpreter or JIT correctly sets A and X
5944 * to 0. 6098 * to 0.
@@ -6127,14 +6281,6 @@ static struct bpf_test tests[] = {
6127 {}, 6281 {},
6128 { {0x1, 0x42 } }, 6282 { {0x1, 0x42 } },
6129 }, 6283 },
6130 {
6131 "LD_ABS with helper changing skb data",
6132 { },
6133 INTERNAL,
6134 { 0x34 },
6135 { { ETH_HLEN, 42 } },
6136 .fill_helper = bpf_fill_ld_abs_vlan_push_pop2,
6137 },
6138 /* Checking interpreter vs JIT wrt signed extended imms. */ 6284 /* Checking interpreter vs JIT wrt signed extended imms. */
6139 { 6285 {
6140 "JNE signed compare, test 1", 6286 "JNE signed compare, test 1",