1 // SPDX-License-Identifier: GPL-2.0
2 /* Converted from tools/testing/selftests/bpf/verifier/cgroup_storage.c */
3
4 #include <linux/bpf.h>
5 #include <bpf/bpf_helpers.h>
6 #include "../../../include/linux/filter.h"
7 #include "bpf_misc.h"
8
9 struct {
10 __uint(type, BPF_MAP_TYPE_CGROUP_STORAGE);
11 __uint(max_entries, 0);
12 __type(key, struct bpf_cgroup_storage_key);
13 __type(value, char[TEST_DATA_LEN]);
14 } cgroup_storage SEC(".maps");
15
16 struct {
17 __uint(type, BPF_MAP_TYPE_HASH);
18 __uint(max_entries, 1);
19 __type(key, long long);
20 __type(value, long long);
21 } map_hash_8b SEC(".maps");
22
23 struct {
24 __uint(type, BPF_MAP_TYPE_PERCPU_CGROUP_STORAGE);
25 __uint(max_entries, 0);
26 __type(key, struct bpf_cgroup_storage_key);
27 __type(value, char[64]);
28 } percpu_cgroup_storage SEC(".maps");
29
30 SEC("cgroup/skb")
31 __description("valid cgroup storage access")
32 __success __success_unpriv __retval(0)
valid_cgroup_storage_access(void)33 __naked void valid_cgroup_storage_access(void)
34 {
35 asm volatile (" \
36 r2 = 0; \
37 r1 = %[cgroup_storage] ll; \
38 call %[bpf_get_local_storage]; \
39 r1 = *(u32*)(r0 + 0); \
40 r0 = r1; \
41 r0 &= 1; \
42 exit; \
43 " :
44 : __imm(bpf_get_local_storage),
45 __imm_addr(cgroup_storage)
46 : __clobber_all);
47 }
48
49 SEC("cgroup/skb")
50 __description("invalid cgroup storage access 1")
51 __failure __msg("cannot pass map_type 1 into func bpf_get_local_storage")
52 __failure_unpriv
invalid_cgroup_storage_access_1(void)53 __naked void invalid_cgroup_storage_access_1(void)
54 {
55 asm volatile (" \
56 r2 = 0; \
57 r1 = %[map_hash_8b] ll; \
58 call %[bpf_get_local_storage]; \
59 r1 = *(u32*)(r0 + 0); \
60 r0 = r1; \
61 r0 &= 1; \
62 exit; \
63 " :
64 : __imm(bpf_get_local_storage),
65 __imm_addr(map_hash_8b)
66 : __clobber_all);
67 }
68
69 SEC("cgroup/skb")
70 __description("invalid cgroup storage access 2")
71 __failure __msg("fd 1 is not pointing to valid bpf_map")
72 __failure_unpriv
invalid_cgroup_storage_access_2(void)73 __naked void invalid_cgroup_storage_access_2(void)
74 {
75 asm volatile (" \
76 r2 = 0; \
77 .8byte %[ld_map_fd]; \
78 .8byte 0; \
79 call %[bpf_get_local_storage]; \
80 r0 &= 1; \
81 exit; \
82 " :
83 : __imm(bpf_get_local_storage),
84 __imm_insn(ld_map_fd, BPF_RAW_INSN(BPF_LD | BPF_DW | BPF_IMM, BPF_REG_1, BPF_PSEUDO_MAP_FD, 0, 1))
85 : __clobber_all);
86 }
87
88 SEC("cgroup/skb")
89 __description("invalid cgroup storage access 3")
90 __failure __msg("invalid access to map value, value_size=64 off=256 size=4")
91 __failure_unpriv
invalid_cgroup_storage_access_3(void)92 __naked void invalid_cgroup_storage_access_3(void)
93 {
94 asm volatile (" \
95 r2 = 0; \
96 r1 = %[cgroup_storage] ll; \
97 call %[bpf_get_local_storage]; \
98 r1 = *(u32*)(r0 + 256); \
99 r1 += 1; \
100 r0 = 0; \
101 exit; \
102 " :
103 : __imm(bpf_get_local_storage),
104 __imm_addr(cgroup_storage)
105 : __clobber_all);
106 }
107
108 SEC("cgroup/skb")
109 __description("invalid cgroup storage access 4")
110 __failure __msg("invalid access to map value, value_size=64 off=-2 size=4")
111 __failure_unpriv
__flag(BPF_F_ANY_ALIGNMENT)112 __flag(BPF_F_ANY_ALIGNMENT)
113 __naked void invalid_cgroup_storage_access_4(void)
114 {
115 asm volatile (" \
116 r2 = 0; \
117 r1 = %[cgroup_storage] ll; \
118 call %[bpf_get_local_storage]; \
119 r1 = *(u32*)(r0 - 2); \
120 r0 = r1; \
121 r1 += 1; \
122 exit; \
123 " :
124 : __imm(bpf_get_local_storage),
125 __imm_addr(cgroup_storage)
126 : __clobber_all);
127 }
128
129 SEC("cgroup/skb")
130 __description("invalid cgroup storage access 5")
131 __failure __msg("get_local_storage() doesn't support non-zero flags")
132 __failure_unpriv
invalid_cgroup_storage_access_5(void)133 __naked void invalid_cgroup_storage_access_5(void)
134 {
135 asm volatile (" \
136 r2 = 7; \
137 r1 = %[cgroup_storage] ll; \
138 call %[bpf_get_local_storage]; \
139 r1 = *(u32*)(r0 + 0); \
140 r0 = r1; \
141 r0 &= 1; \
142 exit; \
143 " :
144 : __imm(bpf_get_local_storage),
145 __imm_addr(cgroup_storage)
146 : __clobber_all);
147 }
148
149 SEC("cgroup/skb")
150 __description("invalid cgroup storage access 6")
151 __failure __msg("get_local_storage() doesn't support non-zero flags")
152 __msg_unpriv("R2 leaks addr into helper function")
invalid_cgroup_storage_access_6(void)153 __naked void invalid_cgroup_storage_access_6(void)
154 {
155 asm volatile (" \
156 r2 = r1; \
157 r1 = %[cgroup_storage] ll; \
158 call %[bpf_get_local_storage]; \
159 r1 = *(u32*)(r0 + 0); \
160 r0 = r1; \
161 r0 &= 1; \
162 exit; \
163 " :
164 : __imm(bpf_get_local_storage),
165 __imm_addr(cgroup_storage)
166 : __clobber_all);
167 }
168
169 SEC("cgroup/skb")
170 __description("valid per-cpu cgroup storage access")
171 __success __success_unpriv __retval(0)
per_cpu_cgroup_storage_access(void)172 __naked void per_cpu_cgroup_storage_access(void)
173 {
174 asm volatile (" \
175 r2 = 0; \
176 r1 = %[percpu_cgroup_storage] ll; \
177 call %[bpf_get_local_storage]; \
178 r1 = *(u32*)(r0 + 0); \
179 r0 = r1; \
180 r0 &= 1; \
181 exit; \
182 " :
183 : __imm(bpf_get_local_storage),
184 __imm_addr(percpu_cgroup_storage)
185 : __clobber_all);
186 }
187
188 SEC("cgroup/skb")
189 __description("invalid per-cpu cgroup storage access 1")
190 __failure __msg("cannot pass map_type 1 into func bpf_get_local_storage")
191 __failure_unpriv
cpu_cgroup_storage_access_1(void)192 __naked void cpu_cgroup_storage_access_1(void)
193 {
194 asm volatile (" \
195 r2 = 0; \
196 r1 = %[map_hash_8b] ll; \
197 call %[bpf_get_local_storage]; \
198 r1 = *(u32*)(r0 + 0); \
199 r0 = r1; \
200 r0 &= 1; \
201 exit; \
202 " :
203 : __imm(bpf_get_local_storage),
204 __imm_addr(map_hash_8b)
205 : __clobber_all);
206 }
207
208 SEC("cgroup/skb")
209 __description("invalid per-cpu cgroup storage access 2")
210 __failure __msg("fd 1 is not pointing to valid bpf_map")
211 __failure_unpriv
cpu_cgroup_storage_access_2(void)212 __naked void cpu_cgroup_storage_access_2(void)
213 {
214 asm volatile (" \
215 r2 = 0; \
216 .8byte %[ld_map_fd]; \
217 .8byte 0; \
218 call %[bpf_get_local_storage]; \
219 r0 &= 1; \
220 exit; \
221 " :
222 : __imm(bpf_get_local_storage),
223 __imm_insn(ld_map_fd, BPF_RAW_INSN(BPF_LD | BPF_DW | BPF_IMM, BPF_REG_1, BPF_PSEUDO_MAP_FD, 0, 1))
224 : __clobber_all);
225 }
226
227 SEC("cgroup/skb")
228 __description("invalid per-cpu cgroup storage access 3")
229 __failure __msg("invalid access to map value, value_size=64 off=256 size=4")
230 __failure_unpriv
cpu_cgroup_storage_access_3(void)231 __naked void cpu_cgroup_storage_access_3(void)
232 {
233 asm volatile (" \
234 r2 = 0; \
235 r1 = %[percpu_cgroup_storage] ll; \
236 call %[bpf_get_local_storage]; \
237 r1 = *(u32*)(r0 + 256); \
238 r1 += 1; \
239 r0 = 0; \
240 exit; \
241 " :
242 : __imm(bpf_get_local_storage),
243 __imm_addr(percpu_cgroup_storage)
244 : __clobber_all);
245 }
246
247 SEC("cgroup/skb")
248 __description("invalid per-cpu cgroup storage access 4")
249 __failure __msg("invalid access to map value, value_size=64 off=-2 size=4")
250 __failure_unpriv
__flag(BPF_F_ANY_ALIGNMENT)251 __flag(BPF_F_ANY_ALIGNMENT)
252 __naked void cpu_cgroup_storage_access_4(void)
253 {
254 asm volatile (" \
255 r2 = 0; \
256 r1 = %[cgroup_storage] ll; \
257 call %[bpf_get_local_storage]; \
258 r1 = *(u32*)(r0 - 2); \
259 r0 = r1; \
260 r1 += 1; \
261 exit; \
262 " :
263 : __imm(bpf_get_local_storage),
264 __imm_addr(cgroup_storage)
265 : __clobber_all);
266 }
267
268 SEC("cgroup/skb")
269 __description("invalid per-cpu cgroup storage access 5")
270 __failure __msg("get_local_storage() doesn't support non-zero flags")
271 __failure_unpriv
cpu_cgroup_storage_access_5(void)272 __naked void cpu_cgroup_storage_access_5(void)
273 {
274 asm volatile (" \
275 r2 = 7; \
276 r1 = %[percpu_cgroup_storage] ll; \
277 call %[bpf_get_local_storage]; \
278 r1 = *(u32*)(r0 + 0); \
279 r0 = r1; \
280 r0 &= 1; \
281 exit; \
282 " :
283 : __imm(bpf_get_local_storage),
284 __imm_addr(percpu_cgroup_storage)
285 : __clobber_all);
286 }
287
288 SEC("cgroup/skb")
289 __description("invalid per-cpu cgroup storage access 6")
290 __failure __msg("get_local_storage() doesn't support non-zero flags")
291 __msg_unpriv("R2 leaks addr into helper function")
cpu_cgroup_storage_access_6(void)292 __naked void cpu_cgroup_storage_access_6(void)
293 {
294 asm volatile (" \
295 r2 = r1; \
296 r1 = %[percpu_cgroup_storage] ll; \
297 call %[bpf_get_local_storage]; \
298 r1 = *(u32*)(r0 + 0); \
299 r0 = r1; \
300 r0 &= 1; \
301 exit; \
302 " :
303 : __imm(bpf_get_local_storage),
304 __imm_addr(percpu_cgroup_storage)
305 : __clobber_all);
306 }
307
308 char _license[] SEC("license") = "GPL";
309