]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
selinux: add apis to set labels/fix labels per fd instead of path
authorLennart Poettering <lennart@poettering.net>
Mon, 14 Sep 2020 19:54:20 +0000 (21:54 +0200)
committerLennart Poettering <lennart@poettering.net>
Mon, 28 Sep 2020 16:45:54 +0000 (18:45 +0200)
src/basic/selinux-util.c
src/basic/selinux-util.h

index 9b3b15d387d452e6387ae619bf1840f659465f54..41913fc655c50a9f7b63fa3e411205f47cff7316 100644 (file)
@@ -205,14 +205,11 @@ static int mac_selinux_reload(int seqno) {
 
 int mac_selinux_fix_container(const char *path, const char *inside_path, LabelFixFlags flags) {
 
+        assert(path);
+        assert(inside_path);
+
 #if HAVE_SELINUX
-        char procfs_path[STRLEN("/proc/self/fd/") + DECIMAL_STR_MAX(int)];
-        _cleanup_freecon_ char* fcon = NULL;
         _cleanup_close_ int fd = -1;
-        struct stat st;
-        int r;
-
-        assert(path);
 
         /* if mac_selinux_init() wasn't called before we are a NOOP */
         if (!label_hnd)
@@ -227,6 +224,27 @@ int mac_selinux_fix_container(const char *path, const char *inside_path, LabelFi
                 return -errno;
         }
 
+        return mac_selinux_fix_container_fd(fd, path, inside_path, flags);
+#endif
+
+        return 0;
+}
+
+int mac_selinux_fix_container_fd(int fd, const char *path, const char *inside_path, LabelFixFlags flags) {
+
+        assert(fd >= 0);
+        assert(inside_path);
+
+#if HAVE_SELINUX
+        char procfs_path[STRLEN("/proc/self/fd/") + DECIMAL_STR_MAX(int)];
+        _cleanup_freecon_ char* fcon = NULL;
+        struct stat st;
+        int r;
+
+        /* if mac_selinux_init() wasn't called before we are a NOOP */
+        if (!label_hnd)
+                return 0;
+
         if (fstat(fd, &st) < 0)
                 return -errno;
 
@@ -234,12 +252,11 @@ int mac_selinux_fix_container(const char *path, const char *inside_path, LabelFi
         mac_selinux_maybe_reload();
 
         if (selabel_lookup_raw(label_hnd, &fcon, inside_path, st.st_mode) < 0) {
-                r = -errno;
-
                 /* If there's no label to set, then exit without warning */
-                if (r == -ENOENT)
+                if (errno == ENOENT)
                         return 0;
 
+                r = -errno;
                 goto fail;
         }
 
@@ -247,16 +264,16 @@ int mac_selinux_fix_container(const char *path, const char *inside_path, LabelFi
         if (setfilecon_raw(procfs_path, fcon) < 0) {
                 _cleanup_freecon_ char *oldcon = NULL;
 
-                r = -errno;
-
                 /* If the FS doesn't support labels, then exit without warning */
-                if (r == -EOPNOTSUPP)
+                if (ERRNO_IS_NOT_SUPPORTED(errno))
                         return 0;
 
                 /* It the FS is read-only and we were told to ignore failures caused by that, suppress error */
-                if (r == -EROFS && (flags & LABEL_IGNORE_EROFS))
+                if (errno == EROFS && (flags & LABEL_IGNORE_EROFS))
                         return 0;
 
+                r = -errno;
+
                 /* If the old label is identical to the new one, suppress any kind of error */
                 if (getfilecon_raw(procfs_path, &oldcon) >= 0 && streq(fcon, oldcon))
                         return 0;
@@ -267,7 +284,7 @@ int mac_selinux_fix_container(const char *path, const char *inside_path, LabelFi
         return 0;
 
 fail:
-        return log_enforcing_errno(r, "Unable to fix SELinux security context of %s (%s): %m", path, inside_path);
+        return log_enforcing_errno(r, "Unable to fix SELinux security context of %s (%s): %m", strna(path), strna(inside_path));
 #endif
 
         return 0;
@@ -275,11 +292,12 @@ fail:
 
 int mac_selinux_apply(const char *path, const char *label) {
 
+        assert(path);
+
 #if HAVE_SELINUX
         if (!mac_selinux_use())
                 return 0;
 
-        assert(path);
         assert(label);
 
         if (setfilecon(path, label) < 0)
@@ -288,6 +306,22 @@ int mac_selinux_apply(const char *path, const char *label) {
         return 0;
 }
 
+int mac_selinux_apply_fd(int fd, const char *path, const char *label) {
+
+        assert(fd >= 0);
+
+#if HAVE_SELINUX
+        if (!mac_selinux_use())
+                return 0;
+
+        assert(label);
+
+        if (fsetfilecon(fd, label) < 0)
+                return log_enforcing_errno(errno, "Failed to set SELinux security context %s on path %s: %m", label, strna(path));
+#endif
+        return 0;
+}
+
 int mac_selinux_get_create_label_from_exe(const char *exe, char **label) {
 #if HAVE_SELINUX
         _cleanup_freecon_ char *mycon = NULL, *fcon = NULL;
index a982289f6aa9912bfd98818339b649f5419e2638..43d22b914fd914494c4076eaa86dd0f0f8bc7c5f 100644 (file)
@@ -28,7 +28,13 @@ static inline int mac_selinux_fix(const char *path, LabelFixFlags flags) {
         return mac_selinux_fix_container(path, path, flags);
 }
 
+int mac_selinux_fix_container_fd(int fd, const char *path, const char *inside_path, LabelFixFlags flags);
+static inline int mac_selinux_fix_fd(int fd, const char *path, LabelFixFlags flags) {
+        return mac_selinux_fix_container_fd(fd, path, path, flags);
+}
+
 int mac_selinux_apply(const char *path, const char *label);
+int mac_selinux_apply_fd(int fd, const char *path, const char *label);
 
 int mac_selinux_get_create_label_from_exe(const char *exe, char **label);
 int mac_selinux_get_our_label(char **label);