]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
lib/sysfs; add sysfs_partno_to_devno()
authorKarel Zak <kzak@redhat.com>
Mon, 13 Aug 2012 20:06:18 +0000 (22:06 +0200)
committerKarel Zak <kzak@redhat.com>
Mon, 13 Aug 2012 20:06:18 +0000 (22:06 +0200)
Signed-off-by: Karel Zak <kzak@redhat.com>
include/sysfs.h
lib/sysfs.c

index 19cf9e8e04be534af7dd941320cc76ce798bbe7c..9e47a5571fdd94b4df48d0aa4c52893354ecbe3b 100644 (file)
@@ -57,6 +57,7 @@ extern char *sysfs_strdup(struct sysfs_cxt *cxt, const char *attr);
 
 extern int sysfs_count_dirents(struct sysfs_cxt *cxt, const char *attr);
 extern int sysfs_count_partitions(struct sysfs_cxt *cxt, const char *devname);
+extern dev_t sysfs_partno_to_devno(struct sysfs_cxt *cxt, int partno);
 extern char *sysfs_get_slave(struct sysfs_cxt *cxt);
 
 extern int sysfs_is_partition_dirent(DIR *dir, struct dirent *d,
index 92e7b0e137f9c23637df68013ed26e9713f2ceba..b468e884014575f14319f33f20a66a6139cb615d 100644 (file)
@@ -320,6 +320,45 @@ int sysfs_is_partition_dirent(DIR *dir, struct dirent *d, const char *parent_nam
        return faccessat(dirfd(dir), path, R_OK, 0) == 0;
 }
 
+/*
+ * Copnverts @partno (partition number) to devno of the partition. The @cxt
+ * handles wholedisk device.
+ *
+ * Note that this code does not expect any special format of the
+ * partitions devnames.
+ */
+dev_t sysfs_partno_to_devno(struct sysfs_cxt *cxt, int partno)
+{
+       DIR *dir;
+       struct dirent *d;
+       char path[256];
+       dev_t devno = 0;
+
+       dir = sysfs_opendir(cxt, NULL);
+       if (!dir)
+               return 0;
+
+       while ((d = xreaddir(dir))) {
+               int n, maj, min;
+
+               if (!sysfs_is_partition_dirent(dir, d, NULL))
+                       continue;
+
+               snprintf(path, sizeof(path), "%s/partition", d->d_name);
+               if (sysfs_read_int(cxt, path, &n) || n != partno)
+                       continue;
+
+               snprintf(path, sizeof(path), "%s/dev", d->d_name);
+               if (sysfs_scanf(cxt, path, "%d:%d", &maj, &min) == 2)
+                       devno = makedev(maj, min);
+               break;
+       }
+
+       closedir(dir);
+       return devno;
+}
+
+
 int sysfs_scanf(struct sysfs_cxt *cxt,  const char *attr, const char *fmt, ...)
 {
        FILE *f = sysfs_fopen(cxt, attr);
@@ -605,7 +644,7 @@ int main(int argc, char *argv[])
        char *devname;
        dev_t devno;
        char path[PATH_MAX];
-       int i;
+       int i, is_part;
        uint64_t u64;
        ssize_t len;
 
@@ -618,12 +657,13 @@ int main(int argc, char *argv[])
        if (!devno)
                err(EXIT_FAILURE, "failed to read devno");
 
+       is_part = sysfs_devno_has_attribute(devno, "partition");
+
        printf("NAME: %s\n", devname);
-       printf("DEVNO: %u\n", (unsigned int) devno);
+       printf("DEVNO: %u (%d:%d)\n", (unsigned int) devno, major(devno), minor(devno));
        printf("DEVNOPATH: %s\n", sysfs_devno_path(devno, path, sizeof(path)));
        printf("DEVPATH: %s\n", sysfs_devno_to_devpath(devno, path, sizeof(path)));
-       printf("PARTITION: %s\n",
-               sysfs_devno_has_attribute(devno, "partition") ? "YES" : "NOT");
+       printf("PARTITION: %s\n", is_part ? "YES" : "NOT");
 
        if (sysfs_init(&cxt, devno, NULL))
                return EXIT_FAILURE;
@@ -634,6 +674,15 @@ int main(int argc, char *argv[])
                printf("DEVNOLINK: %s\n", path);
        }
 
+       if (!is_part) {
+               printf("First 5 partitions:\n");
+               for (i = 1; i <= 5; i++) {
+                       dev_t dev = sysfs_partno_to_devno(&cxt, i);
+                       if (dev)
+                               printf("\t#%d %d:%d\n", i, major(dev), minor(dev));
+               }
+       }
+
        printf("SLAVES: %d\n", sysfs_count_dirents(&cxt, "slaves"));
 
        if (sysfs_read_u64(&cxt, "size", &u64))