summaryrefslogtreecommitdiffstats
path: root/mount/fstab.c
diff options
context:
space:
mode:
authorValerie Aurora2010-08-04 02:09:19 +0200
committerKarel Zak2010-08-04 11:46:25 +0200
commit5d79666f8f7563ed9904a7ce2087f430ee2702b6 (patch)
treed08764576220783c6fdccc633b6ab314e8a24877 /mount/fstab.c
parentlibblkid: remove dead code section (diff)
downloadkernel-qcow2-util-linux-5d79666f8f7563ed9904a7ce2087f430ee2702b6.tar.gz
kernel-qcow2-util-linux-5d79666f8f7563ed9904a7ce2087f430ee2702b6.tar.xz
kernel-qcow2-util-linux-5d79666f8f7563ed9904a7ce2087f430ee2702b6.zip
mount: get most recently mounted fs from /etc/mtab.
I spent most of the day tracking down this subtle remount bug. I think this is the correct solution but I'd appreciate some double-checking. I suspect this bug will munge the mount options whenever you remount a file system mounted on the same mountpoint as another file system, using the mountpoint as the handle. -VAL commit c010b3a0783430e2b94f3b3dc0929ae299e383eb Author: Valerie Aurora <vaurora@redhat.com> Date: Tue Aug 3 16:32:52 2010 -0700 mount: get most recently mounted fs from /etc/mtab. In mount, when using /etc/mtab to lookup a mount entry, get the most recently mounted entry instead of the first mounted entry. You want to manipulate the most recent mount, not a covered mount. See comment to umount_one_bw(). This bug has been util-linux-ng since the first git checkin. It finally showed up on my system with the change to stop using SETLOOP_AUTOCLEAR if /etc/mtab is writable (commit af092544). If you do a remount of a file system mounted on the same dir as another file system, it will take the options from the first mount and write them out to /etc/mtab as the options to the second mount - including, in the case of a loop device, loop=/dev/loop0. Then when you umount the second mount, it grabs the line from /etc/mtab and tries to tear down the loop device, which complains because it is still in use by the first mount. Reproducible test case (on a system with writable /etc/mtab): mount -o loop,ro /tmp/ro /mnt mount -t tmpfs tmpfs /mnt mount -o remount,ro /mnt cat /etc/mtab | tail -2 Signed-off-by: Valerie Aurora <vaurora@redhat.com>
Diffstat (limited to 'mount/fstab.c')
-rw-r--r--mount/fstab.c18
1 files changed, 18 insertions, 0 deletions
diff --git a/mount/fstab.c b/mount/fstab.c
index 97d64a2c8..bfb2e5d35 100644
--- a/mount/fstab.c
+++ b/mount/fstab.c
@@ -216,6 +216,24 @@ getmntfile (const char *name) {
}
/*
+ * Given the name NAME, and the place MCPREV we found it last time,
+ * try to find it in mtab.
+ */
+struct mntentchn *
+getmntfilebackward (const char *name, struct mntentchn *mcprev) {
+ struct mntentchn *mc, *mc0;
+
+ mc0 = mtab_head();
+ if (!mcprev)
+ mcprev = mc0;
+ for (mc = mcprev->prev; mc && mc != mc0; mc = mc->prev)
+ if (streq(mc->m.mnt_dir, name) ||
+ streq(mc->m.mnt_fsname, name))
+ return mc;
+ return NULL;
+}
+
+/*
* Given the directory name NAME, and the place MCPREV we found it last time,
* try to find more occurrences.
*/