Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

bpf, selftests: Add various ringbuf tests with invalid offset

Assert that the verifier is rejecting invalid offsets on the ringbuf entries:

# ./test_verifier | grep ring
#947/u ringbuf: invalid reservation offset 1 OK
#947/p ringbuf: invalid reservation offset 1 OK
#948/u ringbuf: invalid reservation offset 2 OK
#948/p ringbuf: invalid reservation offset 2 OK

Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
Acked-by: John Fastabend <john.fastabend@gmail.com>
Acked-by: Alexei Starovoitov <ast@kernel.org>

+64
+64
tools/testing/selftests/bpf/verifier/ringbuf.c
··· 1 + { 2 + "ringbuf: invalid reservation offset 1", 3 + .insns = { 4 + /* reserve 8 byte ringbuf memory */ 5 + BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), 6 + BPF_LD_MAP_FD(BPF_REG_1, 0), 7 + BPF_MOV64_IMM(BPF_REG_2, 8), 8 + BPF_MOV64_IMM(BPF_REG_3, 0), 9 + BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, BPF_FUNC_ringbuf_reserve), 10 + /* store a pointer to the reserved memory in R6 */ 11 + BPF_MOV64_REG(BPF_REG_6, BPF_REG_0), 12 + /* check whether the reservation was successful */ 13 + BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7), 14 + /* spill R6(mem) into the stack */ 15 + BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_6, -8), 16 + /* fill it back in R7 */ 17 + BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_10, -8), 18 + /* should be able to access *(R7) = 0 */ 19 + BPF_ST_MEM(BPF_DW, BPF_REG_7, 0, 0), 20 + /* submit the reserved ringbuf memory */ 21 + BPF_MOV64_REG(BPF_REG_1, BPF_REG_7), 22 + /* add invalid offset to reserved ringbuf memory */ 23 + BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0xcafe), 24 + BPF_MOV64_IMM(BPF_REG_2, 0), 25 + BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, BPF_FUNC_ringbuf_submit), 26 + BPF_MOV64_IMM(BPF_REG_0, 0), 27 + BPF_EXIT_INSN(), 28 + }, 29 + .fixup_map_ringbuf = { 1 }, 30 + .result = REJECT, 31 + .errstr = "dereference of modified mem ptr R1", 32 + }, 33 + { 34 + "ringbuf: invalid reservation offset 2", 35 + .insns = { 36 + /* reserve 8 byte ringbuf memory */ 37 + BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), 38 + BPF_LD_MAP_FD(BPF_REG_1, 0), 39 + BPF_MOV64_IMM(BPF_REG_2, 8), 40 + BPF_MOV64_IMM(BPF_REG_3, 0), 41 + BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, BPF_FUNC_ringbuf_reserve), 42 + /* store a pointer to the reserved memory in R6 */ 43 + BPF_MOV64_REG(BPF_REG_6, BPF_REG_0), 44 + /* check whether the reservation was successful */ 45 + BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7), 46 + /* spill R6(mem) into the stack */ 47 + BPF_STX_MEM(BPF_DW, BPF_REG_10, BPF_REG_6, -8), 48 + /* fill it back in R7 */ 49 + BPF_LDX_MEM(BPF_DW, BPF_REG_7, BPF_REG_10, -8), 50 + /* add invalid offset to reserved ringbuf memory */ 51 + BPF_ALU64_IMM(BPF_ADD, BPF_REG_7, 0xcafe), 52 + /* should be able to access *(R7) = 0 */ 53 + BPF_ST_MEM(BPF_DW, BPF_REG_7, 0, 0), 54 + /* submit the reserved ringbuf memory */ 55 + BPF_MOV64_REG(BPF_REG_1, BPF_REG_7), 56 + BPF_MOV64_IMM(BPF_REG_2, 0), 57 + BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, BPF_FUNC_ringbuf_submit), 58 + BPF_MOV64_IMM(BPF_REG_0, 0), 59 + BPF_EXIT_INSN(), 60 + }, 61 + .fixup_map_ringbuf = { 1 }, 62 + .result = REJECT, 63 + .errstr = "R7 min value is outside of the allowed memory range", 64 + },