]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
libmount: be robust when work with loopdev backing file paths
authorKarel Zak <kzak@redhat.com>
Mon, 5 Aug 2013 13:24:30 +0000 (15:24 +0200)
committerKarel Zak <kzak@redhat.com>
Mon, 5 Aug 2013 13:35:39 +0000 (15:35 +0200)
It's usually unnecessary as we compare devno and ino, but let's
use absolute paths for situations when it's necessary to compare
paths as strings.

Signed-off-by: Karel Zak <kzak@redhat.com>
libmount/src/context_loopdev.c
libmount/src/context_umount.c

index 37fadb70bca3e5d43b35146e5625333d683f97dc..44a7216b8d912a5994bf85aaa95b1e1a52bd9a13 100644 (file)
@@ -86,6 +86,8 @@ is_mounted_same_loopfile(struct libmnt_context *cxt,
        struct libmnt_iter itr;
        struct libmnt_fs *fs;
        struct libmnt_cache *cache;
+       const char *bf;
+       int rc = 0;
 
        assert(cxt);
        assert(cxt->fs);
@@ -100,39 +102,36 @@ is_mounted_same_loopfile(struct libmnt_context *cxt,
        cache = mnt_context_get_cache(cxt);
        mnt_reset_iter(&itr, MNT_ITER_BACKWARD);
 
+       bf = cache ? mnt_resolve_path(backing_file, cache) : backing_file;
+
        /* Search for a mountpoint node in mtab, proceed if any of these have the
         * loop option set or the device is a loop device
         */
-       while (mnt_table_next_fs(tb, &itr, &fs) == 0) {
+       while (rc == 0 && mnt_table_next_fs(tb, &itr, &fs) == 0) {
                const char *src = mnt_fs_get_source(fs);
                const char *opts = mnt_fs_get_user_options(fs);
                char *val;
                size_t len;
-               int res = 0;
 
                if (!src || !mnt_fs_match_target(fs, target, cache))
                        continue;
 
+               rc = 0;
+
                if (strncmp(src, "/dev/loop", 9) == 0) {
-                       res = loopdev_is_used((char *) src, backing_file,
-                                       offset, LOOPDEV_FL_OFFSET);
+                       rc = loopdev_is_used((char *) src, bf, offset, LOOPDEV_FL_OFFSET);
 
                } else if (opts && (cxt->user_mountflags & MNT_MS_LOOP) &&
                    mnt_optstr_get_option(opts, "loop", &val, &len) == 0 && val) {
 
                        val = strndup(val, len);
-                       res = loopdev_is_used((char *) val, backing_file,
-                                       offset, LOOPDEV_FL_OFFSET);
+                       rc = loopdev_is_used((char *) val, bf, offset, LOOPDEV_FL_OFFSET);
                        free(val);
                }
-
-               if (res) {
-                       DBG(CXT, mnt_debug_h(cxt, "%s already mounted", backing_file));
-                       return 1;
-               }
        }
-
-       return 0;
+       if (rc)
+               DBG(CXT, mnt_debug_h(cxt, "%s already mounted", backing_file));
+       return rc;
 }
 
 int mnt_context_setup_loopdev(struct libmnt_context *cxt)
index b02902c45af1bd04eb55cfb9afe225ed14422312..2e912c0dcd1ab47238e10d87686b90cfd0fab9ba 100644 (file)
@@ -162,11 +162,9 @@ try_loopdev:
 
                if (stat(tgt, &st) == 0 && S_ISREG(st.st_mode)) {
                        int count;
+                       const char *bf = cache ? mnt_resolve_path(tgt, cache) : tgt;
 
-                       cn_tgt = mnt_resolve_path(tgt, cache);
-                       count = loopdev_count_by_backing_file(cn_tgt, &loopdev);
-                       if (!cache)
-                               free(cn_tgt);
+                       count = loopdev_count_by_backing_file(bf, &loopdev);
                        if (count == 1) {
                                DBG(CXT, mnt_debug_h(cxt,
                                        "umount: %s --> %s (retry)", tgt, loopdev));
@@ -361,7 +359,9 @@ static int evaluate_permissions(struct libmnt_context *cxt)
                 */
                fs = mnt_table_find_target(fstab, tgt, MNT_ITER_FORWARD);
                if (fs) {
-                       const char *dev = mnt_fs_get_srcpath(cxt->fs);          /* devname from mtab */
+                       struct libmnt_cache *cache = mnt_context_get_cache(cxt);
+                       const char *sp = mnt_fs_get_srcpath(cxt->fs);           /* devname from mtab */
+                       const char *dev = sp && cache ? mnt_resolve_path(sp, cache) : sp;
 
                        if (!dev || !is_associated_fs(dev, fs))
                                fs = NULL;