]> err.no Git - util-linux/commitdiff
libblkid: add UBI volume support
authorCorentin Chary <corentincj@iksaif.net>
Mon, 24 Aug 2009 11:11:54 +0000 (13:11 +0200)
committerKarel Zak <kzak@redhat.com>
Thu, 24 Sep 2009 13:42:48 +0000 (15:42 +0200)
Probe UBI volume under /dev (or /devfs, /devices).
ubi_ctrl skip is hardcoded, maybe we should find a
cleaner way to do that. Also change probe.c to handle
char devices.

[kzak@redhat.com: - rebase the patch to the current HEAD]

Signed-off-by: Corentin Chary <corentincj@iksaif.net>
Signed-off-by: Karel Zak <kzak@redhat.com>
shlibs/blkid/src/blkidP.h
shlibs/blkid/src/devname.c
shlibs/blkid/src/probe.c

index 40002c5c600b2feec9782c27ba355a8b8705e5bf..68116c0ca0136f17419104b52b0726b507541c50 100644 (file)
@@ -294,6 +294,7 @@ extern char *blkid_strndup(const char *s, const int length);
 /*
  * Priority settings for different types of devices
  */
+#define BLKID_PRI_UBI  50
 #define BLKID_PRI_DM   40
 #define BLKID_PRI_EVMS 30
 #define BLKID_PRI_LVM  20
index f0672ddcd0e036f0b0cdcd0d76290a67d848c343..1acb9d5a43c8dcb15cc69238c1c36ddc421dfb4d 100644 (file)
@@ -229,7 +229,9 @@ static void probe_one(blkid_cache cache, const char *ptname,
                    dev->bid_devno == devno)
                        goto set_pri;
 
-               if (stat(device, &st) == 0 && S_ISBLK(st.st_mode) &&
+               if (stat(device, &st) == 0 &&
+                   (S_ISBLK(st.st_mode) ||
+                    (S_ISCHR(st.st_mode) && !strncmp(ptname, "ubi", 3))) &&
                    st.st_rdev == devno) {
                        devname = blkid_strdup(device);
                        goto get_dev;
@@ -388,6 +390,57 @@ evms_probe_all(blkid_cache cache, int only_if_new)
        return num;
 }
 
+static void
+ubi_probe_all(blkid_cache cache, int only_if_new)
+{
+       const char **dirname;
+
+       for (dirname = dirlist; *dirname; dirname++) {
+               DBG(DEBUG_DEVNAME, printf("probing UBI volumes under %s\n",
+                                         *dirname));
+
+               DIR             *dir;
+               struct dirent   *iter;
+
+               dir = opendir(*dirname);
+               if (dir == NULL)
+                       continue ;
+
+               while ((iter = readdir(dir)) != NULL) {
+                       char            *name, *device;
+                       struct stat     st;
+                       dev_t           dev;
+
+                       name = iter->d_name;
+
+                       if (!strcmp(name, ".") || !strcmp(name, "..") ||
+                           !strstr(name, "ubi"))
+                               continue;
+                       if (!strcmp(name, "ubi_ctrl"))
+                               continue;
+                       device = malloc(strlen(*dirname) + strlen(name) + 2);
+                       if (!device)
+                               break ;
+                       sprintf(device, "%s/%s", *dirname, name);
+                       if (stat(device, &st))
+                               break ;
+
+                       if (!(st.st_rdev & 0xFF)) { // It's an UBI Device
+                               free(device);
+                               continue ;
+                       }
+                       dev = st.st_rdev;
+                       DBG(DEBUG_DEVNAME, printf("UBI vol %s: devno 0x%04X\n",
+                                                 device,
+                                                 (int) dev));
+                       probe_one(cache, name, dev, BLKID_PRI_UBI,
+                                 only_if_new);
+                       free(device);
+               }
+               closedir(dir);
+       }
+}
+
 /*
  * Read the device data for all available block devices in the system.
  */
@@ -419,6 +472,7 @@ static int probe_all(blkid_cache cache, int only_if_new)
 #ifdef VG_DIR
        lvm_probe_all(cache, only_if_new);
 #endif
+       ubi_probe_all(cache, only_if_new);
 
        proc = fopen(PROC_PARTITIONS, "r");
        if (!proc)
index bac49771e127f437c5cfcff93eb66e849f4d3888..89c16a201e0864147bf0a77771c9482a281e2544 100644 (file)
@@ -522,12 +522,17 @@ int blkid_probe_set_device(blkid_probe pr, int fd,
 
                pr->mode = sb.st_mode;
 
-               if (S_ISBLK(sb.st_mode)) {
+               if (S_ISBLK(sb.st_mode))
                        blkdev_get_size(fd, (unsigned long long *) &pr->size);
+               else if (S_ISCHR(sb.st_mode))
+                       pr->size = 1;           /* UBI devices are char... */
+               else
+                       pr->size = sb.st_size;  /* regular file */
+
+               if (S_ISBLK(sb.st_mode) || S_ISCHR(sb.st_mode))
                        pr->devno = sb.st_rdev;
-               } else
-                       pr->size = sb.st_size;
        }
+
        if (!pr->size)
                return -1;
 
@@ -842,7 +847,8 @@ dev_t blkid_probe_get_devno(blkid_probe pr)
        if (!pr->devno) {
                struct stat sb;
 
-               if (fstat(pr->fd, &sb) == 0 && S_ISBLK(sb.st_mode))
+               if (fstat(pr->fd, &sb) == 0 &&
+                   (S_ISBLK(sb.st_mode) || S_ISCHR(sb.st_mode)))
                        pr->devno = sb.st_rdev;
        }
        return pr->devno;