]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
bpf: do not freeze if bpf lsm fails to set up
authorJulia Kartseva <hex@fb.com>
Thu, 6 Jan 2022 00:34:56 +0000 (16:34 -0800)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Fri, 7 Jan 2022 07:25:45 +0000 (16:25 +0900)
BPF LSM is cgroup unaware and it's set up is happening in core manager.
It occures that the current implementation is too restrictive and causes
pid 1 to freeze.
Instead:
* in bpf_lsm_setup set manager->restrict_fs pointer last,
so it is an indicator that the set up was successful
* check for manager->restrict_fs before applying unit options

src/core/bpf-lsm.c
src/core/execute.c
src/core/manager.c

index 79d17b0751e38c7e70d35895dc1a2c9b9293bcc2..e0333963c5368ae61519e253d0ffb5a3552f5ab9 100644 (file)
@@ -176,7 +176,7 @@ int lsm_bpf_supported(void) {
 }
 
 int lsm_bpf_setup(Manager *m) {
-        struct restrict_fs_bpf *obj;
+        _cleanup_(restrict_fs_bpf_freep) struct restrict_fs_bpf *obj = NULL;
         _cleanup_(bpf_link_freep) struct bpf_link *link = NULL;
         int r;
 
@@ -186,17 +186,16 @@ int lsm_bpf_setup(Manager *m) {
         if (r < 0)
                 return r;
 
-        m->restrict_fs = obj;
-
-        link = sym_bpf_program__attach_lsm(m->restrict_fs->progs.restrict_filesystems);
+        link = sym_bpf_program__attach_lsm(obj->progs.restrict_filesystems);
         r = sym_libbpf_get_error(link);
         if (r != 0)
                 return log_error_errno(r, "Failed to link '%s' LSM BPF program: %m",
-                                       sym_bpf_program__name(m->restrict_fs->progs.restrict_filesystems));
+                                       sym_bpf_program__name(obj->progs.restrict_filesystems));
 
         log_info("LSM BPF program attached");
 
-        m->restrict_fs->links.restrict_filesystems = TAKE_PTR(link);
+        obj->links.restrict_filesystems = TAKE_PTR(link);
+        m->restrict_fs = TAKE_PTR(obj);
 
         return 0;
 }
@@ -210,6 +209,10 @@ int lsm_bpf_unit_restrict_filesystems(Unit *u, const Set *filesystems, bool allo
         assert(filesystems);
         assert(u);
 
+        if (!u->manager->restrict_fs)
+                return log_unit_error_errno(u, SYNTHETIC_ERRNO(EINVAL),
+                                            "Restrict filesystems BPF object is not set, BPF LSM setup has failed?");
+
         int inner_map_fd = sym_bpf_create_map(
                         BPF_MAP_TYPE_HASH,
                         sizeof(uint32_t),
index e3b9134c3d69bf067fb6505054304d6598c0d6d6..4c96c30cf476566b4e7c11f6136459f50e925e13 100644 (file)
@@ -1732,9 +1732,16 @@ static int apply_lock_personality(const Unit* u, const ExecContext *c) {
 
 #if HAVE_LIBBPF
 static bool skip_lsm_bpf_unsupported(const Unit* u, const char* msg) {
+        assert(u);
+        assert(u->manager);
+
         if (lsm_bpf_supported())
                 return false;
 
+        /* lsm_bpf_setup succeeded */
+        if (u->manager->restrict_fs)
+                return false;
+
         log_unit_debug(u, "LSM BPF not supported, skipping %s", msg);
         return true;
 }
index 601e15f68920677124cc2568fedf2e10592aa36a..12c49e7fca414a6f65cb2af7b2c5f816979f0efa 100644 (file)
@@ -933,7 +933,7 @@ int manager_new(UnitFileScope scope, ManagerTestRunFlags test_run_flags, Manager
                 if (MANAGER_IS_SYSTEM(m) && lsm_bpf_supported()) {
                         r = lsm_bpf_setup(m);
                         if (r < 0)
-                                return r;
+                                log_warning_errno(r, "Failed to setup LSM BPF, ignoring: %m");
                 }
 #endif
         }