1 /* SPDX-License-Identifier: GPL-2.0 */ 2 #ifndef _BPF_CGROUP_H 3 #define _BPF_CGROUP_H 4 5 #include <linux/bpf.h> 6 #include <linux/errno.h> 7 #include <linux/jump_label.h> 8 #include <linux/percpu.h> 9 #include <linux/rbtree.h> 10 #include <uapi/linux/bpf.h> 11 12 struct sock; 13 struct sockaddr; 14 struct cgroup; 15 struct sk_buff; 16 struct bpf_map; 17 struct bpf_prog; 18 struct bpf_sock_ops_kern; 19 struct bpf_cgroup_storage; 20 struct ctl_table; 21 struct ctl_table_header; 22 23 #ifdef CONFIG_CGROUP_BPF 24 25 extern struct static_key_false cgroup_bpf_enabled_key; 26 #define cgroup_bpf_enabled static_branch_unlikely(&cgroup_bpf_enabled_key) 27 28 DECLARE_PER_CPU(struct bpf_cgroup_storage*, 29 bpf_cgroup_storage[MAX_BPF_CGROUP_STORAGE_TYPE]); 30 31 #define for_each_cgroup_storage_type(stype) \ 32 for (stype = 0; stype < MAX_BPF_CGROUP_STORAGE_TYPE; stype++) 33 34 struct bpf_cgroup_storage_map; 35 36 struct bpf_storage_buffer { 37 struct rcu_head rcu; 38 char data[0]; 39 }; 40 41 struct bpf_cgroup_storage { 42 union { 43 struct bpf_storage_buffer *buf; 44 void __percpu *percpu_buf; 45 }; 46 struct bpf_cgroup_storage_map *map; 47 struct bpf_cgroup_storage_key key; 48 struct list_head list; 49 struct rb_node node; 50 struct rcu_head rcu; 51 }; 52 53 struct bpf_prog_list { 54 struct list_head node; 55 struct bpf_prog *prog; 56 struct bpf_cgroup_storage *storage[MAX_BPF_CGROUP_STORAGE_TYPE]; 57 }; 58 59 struct bpf_prog_array; 60 61 struct cgroup_bpf { 62 /* array of effective progs in this cgroup */ 63 struct bpf_prog_array __rcu *effective[MAX_BPF_ATTACH_TYPE]; 64 65 /* attached progs to this cgroup and attach flags 66 * when flags == 0 or BPF_F_ALLOW_OVERRIDE the progs list will 67 * have either zero or one element 68 * when BPF_F_ALLOW_MULTI the list can have up to BPF_CGROUP_MAX_PROGS 69 */ 70 struct list_head progs[MAX_BPF_ATTACH_TYPE]; 71 u32 flags[MAX_BPF_ATTACH_TYPE]; 72 73 /* temp storage for effective prog array used by prog_attach/detach */ 74 struct bpf_prog_array __rcu *inactive; 75 }; 76 77 void cgroup_bpf_put(struct cgroup *cgrp); 78 int cgroup_bpf_inherit(struct cgroup *cgrp); 79 80 int __cgroup_bpf_attach(struct cgroup *cgrp, struct bpf_prog *prog, 81 enum bpf_attach_type type, u32 flags); 82 int __cgroup_bpf_detach(struct cgroup *cgrp, struct bpf_prog *prog, 83 enum bpf_attach_type type); 84 int __cgroup_bpf_query(struct cgroup *cgrp, const union bpf_attr *attr, 85 union bpf_attr __user *uattr); 86 87 /* Wrapper for __cgroup_bpf_*() protected by cgroup_mutex */ 88 int cgroup_bpf_attach(struct cgroup *cgrp, struct bpf_prog *prog, 89 enum bpf_attach_type type, u32 flags); 90 int cgroup_bpf_detach(struct cgroup *cgrp, struct bpf_prog *prog, 91 enum bpf_attach_type type, u32 flags); 92 int cgroup_bpf_query(struct cgroup *cgrp, const union bpf_attr *attr, 93 union bpf_attr __user *uattr); 94 95 int __cgroup_bpf_run_filter_skb(struct sock *sk, 96 struct sk_buff *skb, 97 enum bpf_attach_type type); 98 99 int __cgroup_bpf_run_filter_sk(struct sock *sk, 100 enum bpf_attach_type type); 101 102 int __cgroup_bpf_run_filter_sock_addr(struct sock *sk, 103 struct sockaddr *uaddr, 104 enum bpf_attach_type type, 105 void *t_ctx); 106 107 int __cgroup_bpf_run_filter_sock_ops(struct sock *sk, 108 struct bpf_sock_ops_kern *sock_ops, 109 enum bpf_attach_type type); 110 111 int __cgroup_bpf_check_dev_permission(short dev_type, u32 major, u32 minor, 112 short access, enum bpf_attach_type type); 113 114 int __cgroup_bpf_run_filter_sysctl(struct ctl_table_header *head, 115 struct ctl_table *table, int write, 116 void __user *buf, size_t *pcount, 117 loff_t *ppos, void **new_buf, 118 enum bpf_attach_type type); 119 120 static inline enum bpf_cgroup_storage_type cgroup_storage_type( 121 struct bpf_map *map) 122 { 123 if (map->map_type == BPF_MAP_TYPE_PERCPU_CGROUP_STORAGE) 124 return BPF_CGROUP_STORAGE_PERCPU; 125 126 return BPF_CGROUP_STORAGE_SHARED; 127 } 128 129 static inline void bpf_cgroup_storage_set(struct bpf_cgroup_storage 130 *storage[MAX_BPF_CGROUP_STORAGE_TYPE]) 131 { 132 enum bpf_cgroup_storage_type stype; 133 134 for_each_cgroup_storage_type(stype) 135 this_cpu_write(bpf_cgroup_storage[stype], storage[stype]); 136 } 137 138 struct bpf_cgroup_storage *bpf_cgroup_storage_alloc(struct bpf_prog *prog, 139 enum bpf_cgroup_storage_type stype); 140 void bpf_cgroup_storage_free(struct bpf_cgroup_storage *storage); 141 void bpf_cgroup_storage_link(struct bpf_cgroup_storage *storage, 142 struct cgroup *cgroup, 143 enum bpf_attach_type type); 144 void bpf_cgroup_storage_unlink(struct bpf_cgroup_storage *storage); 145 int bpf_cgroup_storage_assign(struct bpf_prog *prog, struct bpf_map *map); 146 void bpf_cgroup_storage_release(struct bpf_prog *prog, struct bpf_map *map); 147 148 int bpf_percpu_cgroup_storage_copy(struct bpf_map *map, void *key, void *value); 149 int bpf_percpu_cgroup_storage_update(struct bpf_map *map, void *key, 150 void *value, u64 flags); 151 152 /* Wrappers for __cgroup_bpf_run_filter_skb() guarded by cgroup_bpf_enabled. */ 153 #define BPF_CGROUP_RUN_PROG_INET_INGRESS(sk, skb) \ 154 ({ \ 155 int __ret = 0; \ 156 if (cgroup_bpf_enabled) \ 157 __ret = __cgroup_bpf_run_filter_skb(sk, skb, \ 158 BPF_CGROUP_INET_INGRESS); \ 159 \ 160 __ret; \ 161 }) 162 163 #define BPF_CGROUP_RUN_PROG_INET_EGRESS(sk, skb) \ 164 ({ \ 165 int __ret = 0; \ 166 if (cgroup_bpf_enabled && sk && sk == skb->sk) { \ 167 typeof(sk) __sk = sk_to_full_sk(sk); \ 168 if (sk_fullsock(__sk)) \ 169 __ret = __cgroup_bpf_run_filter_skb(__sk, skb, \ 170 BPF_CGROUP_INET_EGRESS); \ 171 } \ 172 __ret; \ 173 }) 174 175 #define BPF_CGROUP_RUN_SK_PROG(sk, type) \ 176 ({ \ 177 int __ret = 0; \ 178 if (cgroup_bpf_enabled) { \ 179 __ret = __cgroup_bpf_run_filter_sk(sk, type); \ 180 } \ 181 __ret; \ 182 }) 183 184 #define BPF_CGROUP_RUN_PROG_INET_SOCK(sk) \ 185 BPF_CGROUP_RUN_SK_PROG(sk, BPF_CGROUP_INET_SOCK_CREATE) 186 187 #define BPF_CGROUP_RUN_PROG_INET4_POST_BIND(sk) \ 188 BPF_CGROUP_RUN_SK_PROG(sk, BPF_CGROUP_INET4_POST_BIND) 189 190 #define BPF_CGROUP_RUN_PROG_INET6_POST_BIND(sk) \ 191 BPF_CGROUP_RUN_SK_PROG(sk, BPF_CGROUP_INET6_POST_BIND) 192 193 #define BPF_CGROUP_RUN_SA_PROG(sk, uaddr, type) \ 194 ({ \ 195 int __ret = 0; \ 196 if (cgroup_bpf_enabled) \ 197 __ret = __cgroup_bpf_run_filter_sock_addr(sk, uaddr, type, \ 198 NULL); \ 199 __ret; \ 200 }) 201 202 #define BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, type, t_ctx) \ 203 ({ \ 204 int __ret = 0; \ 205 if (cgroup_bpf_enabled) { \ 206 lock_sock(sk); \ 207 __ret = __cgroup_bpf_run_filter_sock_addr(sk, uaddr, type, \ 208 t_ctx); \ 209 release_sock(sk); \ 210 } \ 211 __ret; \ 212 }) 213 214 #define BPF_CGROUP_RUN_PROG_INET4_BIND(sk, uaddr) \ 215 BPF_CGROUP_RUN_SA_PROG(sk, uaddr, BPF_CGROUP_INET4_BIND) 216 217 #define BPF_CGROUP_RUN_PROG_INET6_BIND(sk, uaddr) \ 218 BPF_CGROUP_RUN_SA_PROG(sk, uaddr, BPF_CGROUP_INET6_BIND) 219 220 #define BPF_CGROUP_PRE_CONNECT_ENABLED(sk) (cgroup_bpf_enabled && \ 221 sk->sk_prot->pre_connect) 222 223 #define BPF_CGROUP_RUN_PROG_INET4_CONNECT(sk, uaddr) \ 224 BPF_CGROUP_RUN_SA_PROG(sk, uaddr, BPF_CGROUP_INET4_CONNECT) 225 226 #define BPF_CGROUP_RUN_PROG_INET6_CONNECT(sk, uaddr) \ 227 BPF_CGROUP_RUN_SA_PROG(sk, uaddr, BPF_CGROUP_INET6_CONNECT) 228 229 #define BPF_CGROUP_RUN_PROG_INET4_CONNECT_LOCK(sk, uaddr) \ 230 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_INET4_CONNECT, NULL) 231 232 #define BPF_CGROUP_RUN_PROG_INET6_CONNECT_LOCK(sk, uaddr) \ 233 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_INET6_CONNECT, NULL) 234 235 #define BPF_CGROUP_RUN_PROG_UDP4_SENDMSG_LOCK(sk, uaddr, t_ctx) \ 236 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_UDP4_SENDMSG, t_ctx) 237 238 #define BPF_CGROUP_RUN_PROG_UDP6_SENDMSG_LOCK(sk, uaddr, t_ctx) \ 239 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_UDP6_SENDMSG, t_ctx) 240 241 #define BPF_CGROUP_RUN_PROG_UDP4_RECVMSG_LOCK(sk, uaddr) \ 242 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_UDP4_RECVMSG, NULL) 243 244 #define BPF_CGROUP_RUN_PROG_UDP6_RECVMSG_LOCK(sk, uaddr) \ 245 BPF_CGROUP_RUN_SA_PROG_LOCK(sk, uaddr, BPF_CGROUP_UDP6_RECVMSG, NULL) 246 247 #define BPF_CGROUP_RUN_PROG_SOCK_OPS(sock_ops) \ 248 ({ \ 249 int __ret = 0; \ 250 if (cgroup_bpf_enabled && (sock_ops)->sk) { \ 251 typeof(sk) __sk = sk_to_full_sk((sock_ops)->sk); \ 252 if (__sk && sk_fullsock(__sk)) \ 253 __ret = __cgroup_bpf_run_filter_sock_ops(__sk, \ 254 sock_ops, \ 255 BPF_CGROUP_SOCK_OPS); \ 256 } \ 257 __ret; \ 258 }) 259 260 #define BPF_CGROUP_RUN_PROG_DEVICE_CGROUP(type, major, minor, access) \ 261 ({ \ 262 int __ret = 0; \ 263 if (cgroup_bpf_enabled) \ 264 __ret = __cgroup_bpf_check_dev_permission(type, major, minor, \ 265 access, \ 266 BPF_CGROUP_DEVICE); \ 267 \ 268 __ret; \ 269 }) 270 271 272 #define BPF_CGROUP_RUN_PROG_SYSCTL(head, table, write, buf, count, pos, nbuf) \ 273 ({ \ 274 int __ret = 0; \ 275 if (cgroup_bpf_enabled) \ 276 __ret = __cgroup_bpf_run_filter_sysctl(head, table, write, \ 277 buf, count, pos, nbuf, \ 278 BPF_CGROUP_SYSCTL); \ 279 __ret; \ 280 }) 281 282 int cgroup_bpf_prog_attach(const union bpf_attr *attr, 283 enum bpf_prog_type ptype, struct bpf_prog *prog); 284 int cgroup_bpf_prog_detach(const union bpf_attr *attr, 285 enum bpf_prog_type ptype); 286 int cgroup_bpf_prog_query(const union bpf_attr *attr, 287 union bpf_attr __user *uattr); 288 #else 289 290 struct bpf_prog; 291 struct cgroup_bpf {}; 292 static inline void cgroup_bpf_put(struct cgroup *cgrp) {} 293 static inline int cgroup_bpf_inherit(struct cgroup *cgrp) { return 0; } 294 295 static inline int cgroup_bpf_prog_attach(const union bpf_attr *attr, 296 enum bpf_prog_type ptype, 297 struct bpf_prog *prog) 298 { 299 return -EINVAL; 300 } 301 302 static inline int cgroup_bpf_prog_detach(const union bpf_attr *attr, 303 enum bpf_prog_type ptype) 304 { 305 return -EINVAL; 306 } 307 308 static inline int cgroup_bpf_prog_query(const union bpf_attr *attr, 309 union bpf_attr __user *uattr) 310 { 311 return -EINVAL; 312 } 313 314 static inline void bpf_cgroup_storage_set( 315 struct bpf_cgroup_storage *storage[MAX_BPF_CGROUP_STORAGE_TYPE]) {} 316 static inline int bpf_cgroup_storage_assign(struct bpf_prog *prog, 317 struct bpf_map *map) { return 0; } 318 static inline void bpf_cgroup_storage_release(struct bpf_prog *prog, 319 struct bpf_map *map) {} 320 static inline struct bpf_cgroup_storage *bpf_cgroup_storage_alloc( 321 struct bpf_prog *prog, enum bpf_cgroup_storage_type stype) { return NULL; } 322 static inline void bpf_cgroup_storage_free( 323 struct bpf_cgroup_storage *storage) {} 324 static inline int bpf_percpu_cgroup_storage_copy(struct bpf_map *map, void *key, 325 void *value) { 326 return 0; 327 } 328 static inline int bpf_percpu_cgroup_storage_update(struct bpf_map *map, 329 void *key, void *value, u64 flags) { 330 return 0; 331 } 332 333 #define cgroup_bpf_enabled (0) 334 #define BPF_CGROUP_PRE_CONNECT_ENABLED(sk) (0) 335 #define BPF_CGROUP_RUN_PROG_INET_INGRESS(sk,skb) ({ 0; }) 336 #define BPF_CGROUP_RUN_PROG_INET_EGRESS(sk,skb) ({ 0; }) 337 #define BPF_CGROUP_RUN_PROG_INET_SOCK(sk) ({ 0; }) 338 #define BPF_CGROUP_RUN_PROG_INET4_BIND(sk, uaddr) ({ 0; }) 339 #define BPF_CGROUP_RUN_PROG_INET6_BIND(sk, uaddr) ({ 0; }) 340 #define BPF_CGROUP_RUN_PROG_INET4_POST_BIND(sk) ({ 0; }) 341 #define BPF_CGROUP_RUN_PROG_INET6_POST_BIND(sk) ({ 0; }) 342 #define BPF_CGROUP_RUN_PROG_INET4_CONNECT(sk, uaddr) ({ 0; }) 343 #define BPF_CGROUP_RUN_PROG_INET4_CONNECT_LOCK(sk, uaddr) ({ 0; }) 344 #define BPF_CGROUP_RUN_PROG_INET6_CONNECT(sk, uaddr) ({ 0; }) 345 #define BPF_CGROUP_RUN_PROG_INET6_CONNECT_LOCK(sk, uaddr) ({ 0; }) 346 #define BPF_CGROUP_RUN_PROG_UDP4_SENDMSG_LOCK(sk, uaddr, t_ctx) ({ 0; }) 347 #define BPF_CGROUP_RUN_PROG_UDP6_SENDMSG_LOCK(sk, uaddr, t_ctx) ({ 0; }) 348 #define BPF_CGROUP_RUN_PROG_UDP4_RECVMSG_LOCK(sk, uaddr) ({ 0; }) 349 #define BPF_CGROUP_RUN_PROG_UDP6_RECVMSG_LOCK(sk, uaddr) ({ 0; }) 350 #define BPF_CGROUP_RUN_PROG_SOCK_OPS(sock_ops) ({ 0; }) 351 #define BPF_CGROUP_RUN_PROG_DEVICE_CGROUP(type,major,minor,access) ({ 0; }) 352 #define BPF_CGROUP_RUN_PROG_SYSCTL(head,table,write,buf,count,pos,nbuf) ({ 0; }) 353 354 #define for_each_cgroup_storage_type(stype) for (; false; ) 355 356 #endif /* CONFIG_CGROUP_BPF */ 357 358 #endif /* _BPF_CGROUP_H */ 359