1 // SPDX-License-Identifier: GPL-2.0-only
2 /* Copyright (c) 2011-2014 PLUMgrid, http://plumgrid.com
5 #include <linux/rcupdate.h>
6 #include <linux/random.h>
8 #include <linux/topology.h>
9 #include <linux/ktime.h>
10 #include <linux/sched.h>
11 #include <linux/uidgid.h>
12 #include <linux/filter.h>
13 #include <linux/ctype.h>
14 #include <linux/jiffies.h>
16 #include "../../lib/kstrtox.h"
18 /* If kernel subsystem is allowing eBPF programs to call this function,
19 * inside its own verifier_ops->get_func_proto() callback it should return
20 * bpf_map_lookup_elem_proto, so that verifier can properly check the arguments
22 * Different map implementations will rely on rcu in map methods
23 * lookup/update/delete, therefore eBPF programs must run under rcu lock
24 * if program is allowed to access maps, so check rcu_read_lock_held in
25 * all three functions.
27 BPF_CALL_2(bpf_map_lookup_elem
, struct bpf_map
*, map
, void *, key
)
29 WARN_ON_ONCE(!rcu_read_lock_held());
30 return (unsigned long) map
->ops
->map_lookup_elem(map
, key
);
33 const struct bpf_func_proto bpf_map_lookup_elem_proto
= {
34 .func
= bpf_map_lookup_elem
,
37 .ret_type
= RET_PTR_TO_MAP_VALUE_OR_NULL
,
38 .arg1_type
= ARG_CONST_MAP_PTR
,
39 .arg2_type
= ARG_PTR_TO_MAP_KEY
,
42 BPF_CALL_4(bpf_map_update_elem
, struct bpf_map
*, map
, void *, key
,
43 void *, value
, u64
, flags
)
45 WARN_ON_ONCE(!rcu_read_lock_held());
46 return map
->ops
->map_update_elem(map
, key
, value
, flags
);
49 const struct bpf_func_proto bpf_map_update_elem_proto
= {
50 .func
= bpf_map_update_elem
,
53 .ret_type
= RET_INTEGER
,
54 .arg1_type
= ARG_CONST_MAP_PTR
,
55 .arg2_type
= ARG_PTR_TO_MAP_KEY
,
56 .arg3_type
= ARG_PTR_TO_MAP_VALUE
,
57 .arg4_type
= ARG_ANYTHING
,
60 BPF_CALL_2(bpf_map_delete_elem
, struct bpf_map
*, map
, void *, key
)
62 WARN_ON_ONCE(!rcu_read_lock_held());
63 return map
->ops
->map_delete_elem(map
, key
);
66 const struct bpf_func_proto bpf_map_delete_elem_proto
= {
67 .func
= bpf_map_delete_elem
,
70 .ret_type
= RET_INTEGER
,
71 .arg1_type
= ARG_CONST_MAP_PTR
,
72 .arg2_type
= ARG_PTR_TO_MAP_KEY
,
75 BPF_CALL_3(bpf_map_push_elem
, struct bpf_map
*, map
, void *, value
, u64
, flags
)
77 return map
->ops
->map_push_elem(map
, value
, flags
);
80 const struct bpf_func_proto bpf_map_push_elem_proto
= {
81 .func
= bpf_map_push_elem
,
84 .ret_type
= RET_INTEGER
,
85 .arg1_type
= ARG_CONST_MAP_PTR
,
86 .arg2_type
= ARG_PTR_TO_MAP_VALUE
,
87 .arg3_type
= ARG_ANYTHING
,
90 BPF_CALL_2(bpf_map_pop_elem
, struct bpf_map
*, map
, void *, value
)
92 return map
->ops
->map_pop_elem(map
, value
);
95 const struct bpf_func_proto bpf_map_pop_elem_proto
= {
96 .func
= bpf_map_pop_elem
,
98 .ret_type
= RET_INTEGER
,
99 .arg1_type
= ARG_CONST_MAP_PTR
,
100 .arg2_type
= ARG_PTR_TO_UNINIT_MAP_VALUE
,
103 BPF_CALL_2(bpf_map_peek_elem
, struct bpf_map
*, map
, void *, value
)
105 return map
->ops
->map_peek_elem(map
, value
);
108 const struct bpf_func_proto bpf_map_peek_elem_proto
= {
109 .func
= bpf_map_pop_elem
,
111 .ret_type
= RET_INTEGER
,
112 .arg1_type
= ARG_CONST_MAP_PTR
,
113 .arg2_type
= ARG_PTR_TO_UNINIT_MAP_VALUE
,
116 const struct bpf_func_proto bpf_get_prandom_u32_proto
= {
117 .func
= bpf_user_rnd_u32
,
119 .ret_type
= RET_INTEGER
,
122 BPF_CALL_0(bpf_get_smp_processor_id
)
124 return smp_processor_id();
127 const struct bpf_func_proto bpf_get_smp_processor_id_proto
= {
128 .func
= bpf_get_smp_processor_id
,
130 .ret_type
= RET_INTEGER
,
133 BPF_CALL_0(bpf_get_numa_node_id
)
135 return numa_node_id();
138 const struct bpf_func_proto bpf_get_numa_node_id_proto
= {
139 .func
= bpf_get_numa_node_id
,
141 .ret_type
= RET_INTEGER
,
144 BPF_CALL_0(bpf_ktime_get_ns
)
146 /* NMI safe access to clock monotonic */
147 return ktime_get_mono_fast_ns();
150 const struct bpf_func_proto bpf_ktime_get_ns_proto
= {
151 .func
= bpf_ktime_get_ns
,
153 .ret_type
= RET_INTEGER
,
156 BPF_CALL_0(bpf_get_current_pid_tgid
)
158 struct task_struct
*task
= current
;
163 return (u64
) task
->tgid
<< 32 | task
->pid
;
166 const struct bpf_func_proto bpf_get_current_pid_tgid_proto
= {
167 .func
= bpf_get_current_pid_tgid
,
169 .ret_type
= RET_INTEGER
,
172 BPF_CALL_0(bpf_get_current_uid_gid
)
174 struct task_struct
*task
= current
;
181 current_uid_gid(&uid
, &gid
);
182 return (u64
) from_kgid(&init_user_ns
, gid
) << 32 |
183 from_kuid(&init_user_ns
, uid
);
186 const struct bpf_func_proto bpf_get_current_uid_gid_proto
= {
187 .func
= bpf_get_current_uid_gid
,
189 .ret_type
= RET_INTEGER
,
192 BPF_CALL_2(bpf_get_current_comm
, char *, buf
, u32
, size
)
194 struct task_struct
*task
= current
;
199 strncpy(buf
, task
->comm
, size
);
201 /* Verifier guarantees that size > 0. For task->comm exceeding
202 * size, guarantee that buf is %NUL-terminated. Unconditionally
203 * done here to save the size test.
208 memset(buf
, 0, size
);
212 const struct bpf_func_proto bpf_get_current_comm_proto
= {
213 .func
= bpf_get_current_comm
,
215 .ret_type
= RET_INTEGER
,
216 .arg1_type
= ARG_PTR_TO_UNINIT_MEM
,
217 .arg2_type
= ARG_CONST_SIZE
,
220 #if defined(CONFIG_QUEUED_SPINLOCKS) || defined(CONFIG_BPF_ARCH_SPINLOCK)
222 static inline void __bpf_spin_lock(struct bpf_spin_lock
*lock
)
224 arch_spinlock_t
*l
= (void *)lock
;
227 arch_spinlock_t lock
;
228 } u
= { .lock
= __ARCH_SPIN_LOCK_UNLOCKED
};
230 compiletime_assert(u
.val
== 0, "__ARCH_SPIN_LOCK_UNLOCKED not 0");
231 BUILD_BUG_ON(sizeof(*l
) != sizeof(__u32
));
232 BUILD_BUG_ON(sizeof(*lock
) != sizeof(__u32
));
236 static inline void __bpf_spin_unlock(struct bpf_spin_lock
*lock
)
238 arch_spinlock_t
*l
= (void *)lock
;
245 static inline void __bpf_spin_lock(struct bpf_spin_lock
*lock
)
247 atomic_t
*l
= (void *)lock
;
249 BUILD_BUG_ON(sizeof(*l
) != sizeof(*lock
));
251 atomic_cond_read_relaxed(l
, !VAL
);
252 } while (atomic_xchg(l
, 1));
255 static inline void __bpf_spin_unlock(struct bpf_spin_lock
*lock
)
257 atomic_t
*l
= (void *)lock
;
259 atomic_set_release(l
, 0);
264 static DEFINE_PER_CPU(unsigned long, irqsave_flags
);
266 notrace
BPF_CALL_1(bpf_spin_lock
, struct bpf_spin_lock
*, lock
)
270 local_irq_save(flags
);
271 __bpf_spin_lock(lock
);
272 __this_cpu_write(irqsave_flags
, flags
);
276 const struct bpf_func_proto bpf_spin_lock_proto
= {
277 .func
= bpf_spin_lock
,
279 .ret_type
= RET_VOID
,
280 .arg1_type
= ARG_PTR_TO_SPIN_LOCK
,
283 notrace
BPF_CALL_1(bpf_spin_unlock
, struct bpf_spin_lock
*, lock
)
287 flags
= __this_cpu_read(irqsave_flags
);
288 __bpf_spin_unlock(lock
);
289 local_irq_restore(flags
);
293 const struct bpf_func_proto bpf_spin_unlock_proto
= {
294 .func
= bpf_spin_unlock
,
296 .ret_type
= RET_VOID
,
297 .arg1_type
= ARG_PTR_TO_SPIN_LOCK
,
300 void copy_map_value_locked(struct bpf_map
*map
, void *dst
, void *src
,
303 struct bpf_spin_lock
*lock
;
306 lock
= src
+ map
->spin_lock_off
;
308 lock
= dst
+ map
->spin_lock_off
;
310 ____bpf_spin_lock(lock
);
311 copy_map_value(map
, dst
, src
);
312 ____bpf_spin_unlock(lock
);
316 BPF_CALL_0(bpf_jiffies64
)
318 return get_jiffies_64();
321 const struct bpf_func_proto bpf_jiffies64_proto
= {
322 .func
= bpf_jiffies64
,
324 .ret_type
= RET_INTEGER
,
327 #ifdef CONFIG_CGROUPS
328 BPF_CALL_0(bpf_get_current_cgroup_id
)
330 struct cgroup
*cgrp
= task_dfl_cgroup(current
);
332 return cgroup_id(cgrp
);
335 const struct bpf_func_proto bpf_get_current_cgroup_id_proto
= {
336 .func
= bpf_get_current_cgroup_id
,
338 .ret_type
= RET_INTEGER
,
341 #ifdef CONFIG_CGROUP_BPF
342 DECLARE_PER_CPU(struct bpf_cgroup_storage
*,
343 bpf_cgroup_storage
[MAX_BPF_CGROUP_STORAGE_TYPE
]);
345 BPF_CALL_2(bpf_get_local_storage
, struct bpf_map
*, map
, u64
, flags
)
347 /* flags argument is not used now,
348 * but provides an ability to extend the API.
349 * verifier checks that its value is correct.
351 enum bpf_cgroup_storage_type stype
= cgroup_storage_type(map
);
352 struct bpf_cgroup_storage
*storage
;
355 storage
= this_cpu_read(bpf_cgroup_storage
[stype
]);
357 if (stype
== BPF_CGROUP_STORAGE_SHARED
)
358 ptr
= &READ_ONCE(storage
->buf
)->data
[0];
360 ptr
= this_cpu_ptr(storage
->percpu_buf
);
362 return (unsigned long)ptr
;
365 const struct bpf_func_proto bpf_get_local_storage_proto
= {
366 .func
= bpf_get_local_storage
,
368 .ret_type
= RET_PTR_TO_MAP_VALUE
,
369 .arg1_type
= ARG_CONST_MAP_PTR
,
370 .arg2_type
= ARG_ANYTHING
,
374 #define BPF_STRTOX_BASE_MASK 0x1F
376 static int __bpf_strtoull(const char *buf
, size_t buf_len
, u64 flags
,
377 unsigned long long *res
, bool *is_negative
)
379 unsigned int base
= flags
& BPF_STRTOX_BASE_MASK
;
380 const char *cur_buf
= buf
;
381 size_t cur_len
= buf_len
;
382 unsigned int consumed
;
386 if (!buf
|| !buf_len
|| !res
|| !is_negative
)
389 if (base
!= 0 && base
!= 8 && base
!= 10 && base
!= 16)
392 if (flags
& ~BPF_STRTOX_BASE_MASK
)
395 while (cur_buf
< buf
+ buf_len
&& isspace(*cur_buf
))
398 *is_negative
= (cur_buf
< buf
+ buf_len
&& *cur_buf
== '-');
402 consumed
= cur_buf
- buf
;
407 cur_len
= min(cur_len
, sizeof(str
) - 1);
408 memcpy(str
, cur_buf
, cur_len
);
412 cur_buf
= _parse_integer_fixup_radix(cur_buf
, &base
);
413 val_len
= _parse_integer(cur_buf
, base
, res
);
415 if (val_len
& KSTRTOX_OVERFLOW
)
422 consumed
+= cur_buf
- str
;
427 static int __bpf_strtoll(const char *buf
, size_t buf_len
, u64 flags
,
430 unsigned long long _res
;
434 err
= __bpf_strtoull(buf
, buf_len
, flags
, &_res
, &is_negative
);
438 if ((long long)-_res
> 0)
442 if ((long long)_res
< 0)
449 BPF_CALL_4(bpf_strtol
, const char *, buf
, size_t, buf_len
, u64
, flags
,
455 err
= __bpf_strtoll(buf
, buf_len
, flags
, &_res
);
458 if (_res
!= (long)_res
)
464 const struct bpf_func_proto bpf_strtol_proto
= {
467 .ret_type
= RET_INTEGER
,
468 .arg1_type
= ARG_PTR_TO_MEM
,
469 .arg2_type
= ARG_CONST_SIZE
,
470 .arg3_type
= ARG_ANYTHING
,
471 .arg4_type
= ARG_PTR_TO_LONG
,
474 BPF_CALL_4(bpf_strtoul
, const char *, buf
, size_t, buf_len
, u64
, flags
,
475 unsigned long *, res
)
477 unsigned long long _res
;
481 err
= __bpf_strtoull(buf
, buf_len
, flags
, &_res
, &is_negative
);
486 if (_res
!= (unsigned long)_res
)
492 const struct bpf_func_proto bpf_strtoul_proto
= {
495 .ret_type
= RET_INTEGER
,
496 .arg1_type
= ARG_PTR_TO_MEM
,
497 .arg2_type
= ARG_CONST_SIZE
,
498 .arg3_type
= ARG_ANYTHING
,
499 .arg4_type
= ARG_PTR_TO_LONG
,