~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/tools/testing/selftests/bpf/progs/refcounted_kptr_fail.c

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 // SPDX-License-Identifier: GPL-2.0
  2 #include <vmlinux.h>
  3 #include <bpf/bpf_tracing.h>
  4 #include <bpf/bpf_helpers.h>
  5 #include <bpf/bpf_core_read.h>
  6 #include "bpf_experimental.h"
  7 #include "bpf_misc.h"
  8 
  9 struct node_acquire {
 10         long key;
 11         long data;
 12         struct bpf_rb_node node;
 13         struct bpf_refcount refcount;
 14 };
 15 
 16 extern void bpf_rcu_read_lock(void) __ksym;
 17 extern void bpf_rcu_read_unlock(void) __ksym;
 18 
 19 #define private(name) SEC(".data." #name) __hidden __attribute__((aligned(8)))
 20 private(A) struct bpf_spin_lock glock;
 21 private(A) struct bpf_rb_root groot __contains(node_acquire, node);
 22 
 23 static bool less(struct bpf_rb_node *a, const struct bpf_rb_node *b)
 24 {
 25         struct node_acquire *node_a;
 26         struct node_acquire *node_b;
 27 
 28         node_a = container_of(a, struct node_acquire, node);
 29         node_b = container_of(b, struct node_acquire, node);
 30 
 31         return node_a->key < node_b->key;
 32 }
 33 
 34 SEC("?tc")
 35 __failure __regex("Unreleased reference id=4 alloc_insn=[0-9]+")
 36 long rbtree_refcounted_node_ref_escapes(void *ctx)
 37 {
 38         struct node_acquire *n, *m;
 39 
 40         n = bpf_obj_new(typeof(*n));
 41         if (!n)
 42                 return 1;
 43 
 44         bpf_spin_lock(&glock);
 45         bpf_rbtree_add(&groot, &n->node, less);
 46         /* m becomes an owning ref but is never drop'd or added to a tree */
 47         m = bpf_refcount_acquire(n);
 48         bpf_spin_unlock(&glock);
 49         if (!m)
 50                 return 2;
 51 
 52         m->key = 2;
 53         return 0;
 54 }
 55 
 56 SEC("?tc")
 57 __failure __msg("Possibly NULL pointer passed to trusted arg0")
 58 long refcount_acquire_maybe_null(void *ctx)
 59 {
 60         struct node_acquire *n, *m;
 61 
 62         n = bpf_obj_new(typeof(*n));
 63         /* Intentionally not testing !n
 64          * it's MAYBE_NULL for refcount_acquire
 65          */
 66         m = bpf_refcount_acquire(n);
 67         if (m)
 68                 bpf_obj_drop(m);
 69         if (n)
 70                 bpf_obj_drop(n);
 71 
 72         return 0;
 73 }
 74 
 75 SEC("?tc")
 76 __failure __regex("Unreleased reference id=3 alloc_insn=[0-9]+")
 77 long rbtree_refcounted_node_ref_escapes_owning_input(void *ctx)
 78 {
 79         struct node_acquire *n, *m;
 80 
 81         n = bpf_obj_new(typeof(*n));
 82         if (!n)
 83                 return 1;
 84 
 85         /* m becomes an owning ref but is never drop'd or added to a tree */
 86         m = bpf_refcount_acquire(n);
 87         m->key = 2;
 88 
 89         bpf_spin_lock(&glock);
 90         bpf_rbtree_add(&groot, &n->node, less);
 91         bpf_spin_unlock(&glock);
 92 
 93         return 0;
 94 }
 95 
 96 SEC("?fentry.s/bpf_testmod_test_read")
 97 __failure __msg("function calls are not allowed while holding a lock")
 98 int BPF_PROG(rbtree_fail_sleepable_lock_across_rcu,
 99              struct file *file, struct kobject *kobj,
100              struct bin_attribute *bin_attr, char *buf, loff_t off, size_t len)
101 {
102         struct node_acquire *n;
103 
104         n = bpf_obj_new(typeof(*n));
105         if (!n)
106                 return 0;
107 
108         /* spin_{lock,unlock} are in different RCU CS */
109         bpf_rcu_read_lock();
110         bpf_spin_lock(&glock);
111         bpf_rbtree_add(&groot, &n->node, less);
112         bpf_rcu_read_unlock();
113 
114         bpf_rcu_read_lock();
115         bpf_spin_unlock(&glock);
116         bpf_rcu_read_unlock();
117 
118         return 0;
119 }
120 
121 char _license[] SEC("license") = "GPL";
122 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php