1// SPDX-License-Identifier: GPL-2.0
2/* Converted from tools/testing/selftests/bpf/verifier/bounds_deduction.c */
3
4#include <linux/bpf.h>
5#include <bpf/bpf_helpers.h>
6#include "bpf_misc.h"
7
8SEC("socket")
9__description("check deducing bounds from const, 1")
10__failure __msg("R0 tried to subtract pointer from scalar")
11__msg_unpriv("R1 has pointer with unsupported alu operation")
12__naked void deducing_bounds_from_const_1(void)
13{
14	asm volatile ("					\
15	r0 = 1;						\
16	if r0 s>= 1 goto l0_%=;				\
17l0_%=:	r0 -= r1;					\
18	exit;						\
19"	::: __clobber_all);
20}
21
22SEC("socket")
23__description("check deducing bounds from const, 2")
24__success __failure_unpriv
25__msg_unpriv("R1 has pointer with unsupported alu operation")
26__retval(1)
27__naked void deducing_bounds_from_const_2(void)
28{
29	asm volatile ("					\
30	r0 = 1;						\
31	if r0 s>= 1 goto l0_%=;				\
32	exit;						\
33l0_%=:	if r0 s<= 1 goto l1_%=;				\
34	exit;						\
35l1_%=:	r1 -= r0;					\
36	exit;						\
37"	::: __clobber_all);
38}
39
40SEC("socket")
41__description("check deducing bounds from const, 3")
42__failure __msg("R0 tried to subtract pointer from scalar")
43__msg_unpriv("R1 has pointer with unsupported alu operation")
44__naked void deducing_bounds_from_const_3(void)
45{
46	asm volatile ("					\
47	r0 = 0;						\
48	if r0 s<= 0 goto l0_%=;				\
49l0_%=:	r0 -= r1;					\
50	exit;						\
51"	::: __clobber_all);
52}
53
54SEC("socket")
55__description("check deducing bounds from const, 4")
56__success __failure_unpriv
57__msg_unpriv("R6 has pointer with unsupported alu operation")
58__retval(0)
59__naked void deducing_bounds_from_const_4(void)
60{
61	asm volatile ("					\
62	r6 = r1;					\
63	r0 = 0;						\
64	if r0 s<= 0 goto l0_%=;				\
65	exit;						\
66l0_%=:	if r0 s>= 0 goto l1_%=;				\
67	exit;						\
68l1_%=:	r6 -= r0;					\
69	exit;						\
70"	::: __clobber_all);
71}
72
73SEC("socket")
74__description("check deducing bounds from const, 5")
75__failure __msg("R0 tried to subtract pointer from scalar")
76__msg_unpriv("R1 has pointer with unsupported alu operation")
77__naked void deducing_bounds_from_const_5(void)
78{
79	asm volatile ("					\
80	r0 = 0;						\
81	if r0 s>= 1 goto l0_%=;				\
82	r0 -= r1;					\
83l0_%=:	exit;						\
84"	::: __clobber_all);
85}
86
87SEC("socket")
88__description("check deducing bounds from const, 6")
89__failure __msg("R0 tried to subtract pointer from scalar")
90__msg_unpriv("R1 has pointer with unsupported alu operation")
91__naked void deducing_bounds_from_const_6(void)
92{
93	asm volatile ("					\
94	r0 = 0;						\
95	if r0 s>= 0 goto l0_%=;				\
96	exit;						\
97l0_%=:	r0 -= r1;					\
98	exit;						\
99"	::: __clobber_all);
100}
101
102SEC("socket")
103__description("check deducing bounds from const, 7")
104__failure __msg("dereference of modified ctx ptr")
105__msg_unpriv("R1 has pointer with unsupported alu operation")
106__flag(BPF_F_ANY_ALIGNMENT)
107__naked void deducing_bounds_from_const_7(void)
108{
109	asm volatile ("					\
110	r0 = %[__imm_0];				\
111	if r0 s>= 0 goto l0_%=;				\
112l0_%=:	r1 -= r0;					\
113	r0 = *(u32*)(r1 + %[__sk_buff_mark]);		\
114	exit;						\
115"	:
116	: __imm_const(__imm_0, ~0),
117	  __imm_const(__sk_buff_mark, offsetof(struct __sk_buff, mark))
118	: __clobber_all);
119}
120
121SEC("socket")
122__description("check deducing bounds from const, 8")
123__failure __msg("negative offset ctx ptr R1 off=-1 disallowed")
124__msg_unpriv("R1 has pointer with unsupported alu operation")
125__flag(BPF_F_ANY_ALIGNMENT)
126__naked void deducing_bounds_from_const_8(void)
127{
128	asm volatile ("					\
129	r0 = %[__imm_0];				\
130	if r0 s>= 0 goto l0_%=;				\
131	r1 += r0;					\
132l0_%=:	r0 = *(u32*)(r1 + %[__sk_buff_mark]);		\
133	exit;						\
134"	:
135	: __imm_const(__imm_0, ~0),
136	  __imm_const(__sk_buff_mark, offsetof(struct __sk_buff, mark))
137	: __clobber_all);
138}
139
140SEC("socket")
141__description("check deducing bounds from const, 9")
142__failure __msg("R0 tried to subtract pointer from scalar")
143__msg_unpriv("R1 has pointer with unsupported alu operation")
144__naked void deducing_bounds_from_const_9(void)
145{
146	asm volatile ("					\
147	r0 = 0;						\
148	if r0 s>= 0 goto l0_%=;				\
149l0_%=:	r0 -= r1;					\
150	exit;						\
151"	::: __clobber_all);
152}
153
154SEC("socket")
155__description("check deducing bounds from const, 10")
156__failure
157__msg("math between ctx pointer and register with unbounded min value is not allowed")
158__failure_unpriv
159__naked void deducing_bounds_from_const_10(void)
160{
161	asm volatile ("					\
162	r0 = 0;						\
163	if r0 s<= 0 goto l0_%=;				\
164l0_%=:	/* Marks reg as unknown. */			\
165	r0 = -r0;					\
166	r0 -= r1;					\
167	exit;						\
168"	::: __clobber_all);
169}
170
171char _license[] SEC("license") = "GPL";
172