]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
libmount: fix parsing of mountinfo from 2.6.39
authorKarel Zak <kzak@redhat.com>
Tue, 5 Apr 2011 12:17:51 +0000 (14:17 +0200)
committerKarel Zak <kzak@redhat.com>
Tue, 5 Apr 2011 12:17:51 +0000 (14:17 +0200)
The /proc/self/mountinfo file uses " - " field as a separator between
optional fields and next fields in the file. The '-' char could be
used in the fields (for example in UUIDs), so it's necessary to check
for whole " - " string rather than for '-' char only.

Reported-by: "Aneesh Kumar K. V" <aneesh.kumar@linux.vnet.ibm.com>
Signed-off-by: Karel Zak <kzak@redhat.com>
shlibs/mount/src/tab_parse.c

index 1bf88db56f1277360fc170316178036c8853790c..be85d4711510a40edf9eda9ebe65607b23ea9073 100644 (file)
@@ -113,9 +113,9 @@ static int mnt_parse_table_line(struct libmnt_fs *fs, char *s)
  */
 static int mnt_parse_mountinfo_line(struct libmnt_fs *fs, char *s)
 {
-       int rc;
+       int rc, end = 0;
        unsigned int maj, min;
-       char *fstype, *src;
+       char *fstype, *src, *p;
 
        rc = sscanf(s,  "%u "           /* (1) id */
                        "%u "           /* (2) parent */
@@ -123,11 +123,7 @@ static int mnt_parse_mountinfo_line(struct libmnt_fs *fs, char *s)
                        "%ms "          /* (4) mountroot */
                        "%ms "          /* (5) target */
                        "%ms"           /* (6) vfs options (fs-independent) */
-                       "%*[^-]"        /* (7) optional fields */
-                       "- "            /* (8) separator */
-                       "%ms "          /* (9) FS type */
-                       "%ms "          /* (10) source */
-                       "%ms",          /* (11) fs options (fs specific) */
+                       "%n",           /* number of read bytes */
 
                        &fs->id,
                        &fs->parent,
@@ -135,11 +131,28 @@ static int mnt_parse_mountinfo_line(struct libmnt_fs *fs, char *s)
                        &fs->root,
                        &fs->target,
                        &fs->vfs_optstr,
+                       &end);
+
+       if (rc >= 7 && end > 0)
+               s += end;
+
+       /* (7) optional fields, terminated by " - " */
+       p = strstr(s, " - ");
+       if (!p) {
+               DBG(TAB, mnt_debug("mountinfo parse error: not found separator"));
+               return -EINVAL;
+       }
+       s = p + 3;
+
+       rc += sscanf(s, "%ms "          /* (8) FS type */
+                       "%ms "          /* (9) source */
+                       "%ms",          /* (10) fs options (fs specific) */
+
                        &fstype,
                        &src,
                        &fs->fs_optstr);
 
-       if (rc == 10) {
+       if (rc >= 10) {
                fs->flags |= MNT_FS_KERNEL;
                fs->devno = makedev(maj, min);