]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
sched_ext: Convert cgroup BPF support to use cgroup_lifetime_notifier
authorTejun Heo <tj@kernel.org>
Wed, 14 May 2025 04:46:12 +0000 (00:46 -0400)
committerTejun Heo <tj@kernel.org>
Thu, 22 May 2025 19:20:19 +0000 (09:20 -1000)
Replace explicit cgroup_bpf_inherit/offline() calls from cgroup
creation/destruction paths with notification callback registered on
cgroup_lifetime_notifier.

Signed-off-by: Tejun Heo <tj@kernel.org>
include/linux/bpf-cgroup.h
kernel/bpf/cgroup.c
kernel/cgroup/cgroup.c

index 9de7adb6829485267b6cf0d19fcddfc8037ffea2..60d1511b4f4d9fd49a5cd9cc0bdd9548d2359486 100644 (file)
@@ -114,8 +114,7 @@ struct bpf_prog_list {
        u32 flags;
 };
 
-int cgroup_bpf_inherit(struct cgroup *cgrp);
-void cgroup_bpf_offline(struct cgroup *cgrp);
+void __init cgroup_bpf_lifetime_notifier_init(void);
 
 int __cgroup_bpf_run_filter_skb(struct sock *sk,
                                struct sk_buff *skb,
@@ -431,8 +430,10 @@ const struct bpf_func_proto *
 cgroup_current_func_proto(enum bpf_func_id func_id, const struct bpf_prog *prog);
 #else
 
-static inline int cgroup_bpf_inherit(struct cgroup *cgrp) { return 0; }
-static inline void cgroup_bpf_offline(struct cgroup *cgrp) {}
+static inline void cgroup_bpf_lifetime_notifier_init(void)
+{
+       return;
+}
 
 static inline int cgroup_bpf_prog_attach(const union bpf_attr *attr,
                                         enum bpf_prog_type ptype,
index 84f58f3d028a3e215bf9d32aaa941d56c7fb2adf..cad0194552fb237b8eefeb28f34249c3d38f3b63 100644 (file)
@@ -41,6 +41,19 @@ static int __init cgroup_bpf_wq_init(void)
 }
 core_initcall(cgroup_bpf_wq_init);
 
+static int cgroup_bpf_lifetime_notify(struct notifier_block *nb,
+                                     unsigned long action, void *data);
+
+static struct notifier_block cgroup_bpf_lifetime_nb = {
+       .notifier_call = cgroup_bpf_lifetime_notify,
+};
+
+void __init cgroup_bpf_lifetime_notifier_init(void)
+{
+       BUG_ON(blocking_notifier_chain_register(&cgroup_lifetime_notifier,
+                                               &cgroup_bpf_lifetime_nb));
+}
+
 /* __always_inline is necessary to prevent indirect call through run_prog
  * function pointer.
  */
@@ -206,7 +219,7 @@ bpf_cgroup_atype_find(enum bpf_attach_type attach_type, u32 attach_btf_id)
 }
 #endif /* CONFIG_BPF_LSM */
 
-void cgroup_bpf_offline(struct cgroup *cgrp)
+static void cgroup_bpf_offline(struct cgroup *cgrp)
 {
        cgroup_get(cgrp);
        percpu_ref_kill(&cgrp->bpf.refcnt);
@@ -491,7 +504,7 @@ static void activate_effective_progs(struct cgroup *cgrp,
  * cgroup_bpf_inherit() - inherit effective programs from parent
  * @cgrp: the cgroup to modify
  */
-int cgroup_bpf_inherit(struct cgroup *cgrp)
+static int cgroup_bpf_inherit(struct cgroup *cgrp)
 {
 /* has to use marco instead of const int, since compiler thinks
  * that array below is variable length
@@ -534,6 +547,27 @@ cleanup:
        return -ENOMEM;
 }
 
+static int cgroup_bpf_lifetime_notify(struct notifier_block *nb,
+                                     unsigned long action, void *data)
+{
+       struct cgroup *cgrp = data;
+       int ret = 0;
+
+       if (cgrp->root != &cgrp_dfl_root)
+               return NOTIFY_OK;
+
+       switch (action) {
+       case CGROUP_LIFETIME_ONLINE:
+               ret = cgroup_bpf_inherit(cgrp);
+               break;
+       case CGROUP_LIFETIME_OFFLINE:
+               cgroup_bpf_offline(cgrp);
+               break;
+       }
+
+       return notifier_from_errno(ret);
+}
+
 static int update_effective_progs(struct cgroup *cgrp,
                                  enum cgroup_bpf_attach_type atype)
 {
index 3e993db7e0269072ad7b6a4640e94537ae862216..47568981262f8c38402a2b4a70a9119b8a3e97aa 100644 (file)
@@ -2143,11 +2143,6 @@ int cgroup_setup_root(struct cgroup_root *root, u16 ss_mask)
        if (ret)
                goto exit_stats;
 
-       if (root == &cgrp_dfl_root) {
-               ret = cgroup_bpf_inherit(root_cgrp);
-               WARN_ON_ONCE(ret);
-       }
-
        ret = blocking_notifier_call_chain(&cgroup_lifetime_notifier,
                                           CGROUP_LIFETIME_ONLINE, root_cgrp);
        WARN_ON_ONCE(notifier_to_errno(ret));
@@ -5739,20 +5734,12 @@ static struct cgroup *cgroup_create(struct cgroup *parent, const char *name,
 
        cgrp->self.serial_nr = css_serial_nr_next++;
 
-       if (cgrp->root == &cgrp_dfl_root) {
-               ret = cgroup_bpf_inherit(cgrp);
-               if (ret)
-                       goto out_psi_free;
-       }
-
        ret = blocking_notifier_call_chain_robust(&cgroup_lifetime_notifier,
                                                  CGROUP_LIFETIME_ONLINE,
                                                  CGROUP_LIFETIME_OFFLINE, cgrp);
        ret = notifier_to_errno(ret);
-       if (ret) {
-               cgroup_bpf_offline(cgrp);
+       if (ret)
                goto out_psi_free;
-       }
 
        /* allocation complete, commit to creation */
        spin_lock_irq(&css_set_lock);
@@ -6045,9 +6032,6 @@ static int cgroup_destroy_locked(struct cgroup *cgrp)
 
        cgroup1_check_for_release(parent);
 
-       if (cgrp->root == &cgrp_dfl_root)
-               cgroup_bpf_offline(cgrp);
-
        ret = blocking_notifier_call_chain(&cgroup_lifetime_notifier,
                                           CGROUP_LIFETIME_OFFLINE, cgrp);
        WARN_ON_ONCE(notifier_to_errno(ret));
@@ -6206,6 +6190,8 @@ int __init cgroup_init(void)
        hash_add(css_set_table, &init_css_set.hlist,
                 css_set_hash(init_css_set.subsys));
 
+       cgroup_bpf_lifetime_notifier_init();
+
        BUG_ON(cgroup_setup_root(&cgrp_dfl_root, 0));
 
        cgroup_unlock();