]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
cgroup: use device_path_parse_major_minor() also for block device paths
authorLennart Poettering <lennart@poettering.net>
Mon, 2 Jul 2018 16:20:03 +0000 (18:20 +0200)
committerLennart Poettering <lennart@poettering.net>
Thu, 29 Nov 2018 19:21:39 +0000 (20:21 +0100)
Not only when we populate the "devices" cgroup controller we need
major/minor numbers, but for the io/blkio one it's the same, hence let's
use the same logic for both.

src/core/cgroup.c

index 72af5e855f6eab75ab756021e81dd80e41607ab6..11f9611b71b190462d01227de5c2edb8d6306c36 100644 (file)
@@ -376,16 +376,23 @@ int cgroup_add_device_allow(CGroupContext *c, const char *dev, const char *mode)
 }
 
 static int lookup_block_device(const char *p, dev_t *ret) {
-        struct stat st;
+        struct stat st = {};
         int r;
 
         assert(p);
         assert(ret);
 
-        if (stat(p, &st) < 0)
-                return log_warning_errno(errno, "Couldn't stat device '%s': %m", p);
-
-        if (S_ISBLK(st.st_mode))
+        r = device_path_parse_major_minor(p, &st.st_mode, &st.st_rdev);
+        if (r == -ENODEV) { /* not a parsable device node, need to go to disk */
+                if (stat(p, &st) < 0)
+                        return log_warning_errno(errno, "Couldn't stat device '%s': %m", p);
+        } else if (r < 0)
+                return log_warning_errno(r, "Failed to parse major/minor from path '%s': %m", p);
+
+        if (S_ISCHR(st.st_mode)) {
+                log_warning("Device node '%s' is a character device, but block device needed.", p);
+                return -ENOTBLK;
+        } else if (S_ISBLK(st.st_mode))
                 *ret = st.st_rdev;
         else if (major(st.st_dev) != 0)
                 *ret = st.st_dev; /* If this is not a device node then use the block device this file is stored on */