summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMiklos Szeredi <miklos@szeredi.hu>2010-04-26 15:34:56 +0000
committerMiklos Szeredi <miklos@szeredi.hu>2010-04-26 15:34:56 +0000
commit7140585ba73f9232e3a7951ee3ab0c83c483f997 (patch)
tree9b699127653a5e698650720c7c0acf6b0a6bde90
parentc6cc2b46a6aa5ddb2e1e51744b765574fcf2f415 (diff)
downloadfuse_2_7_bugfix.tar.gz
* Fix checking for symlinks in umount from /tmp. Reported by Alfuse_2_7_bugfix
Viro * Fix umounting if /tmp is a symlink. Reported by Franco Broi * Fix stack alignment for clone()
-rw-r--r--ChangeLog15
-rw-r--r--configure.in2
-rw-r--r--kernel/configure.ac2
-rw-r--r--lib/Makefile.am2
-rw-r--r--util/fusermount.c55
5 files changed, 54 insertions, 22 deletions
diff --git a/ChangeLog b/ChangeLog
index 883a44a..ea040fa 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,18 @@
+2010-04-26 Miklos Szeredi <miklos@szeredi.hu>
+
+ * Released 2.7.6
+
+2010-04-26 Miklos Szeredi <miklos@szeredi.hu>
+
+ * Fix checking for symlinks in umount from /tmp. Reported by Al
+ Viro
+
+ * Fix umounting if /tmp is a symlink. Reported by Franco Broi
+
+2010-02-03 Miklos Szeredi <miklos@szeredi.hu>
+
+ * Fix stack alignment for clone()
+
2010-01-26 Miklos Szeredi <miklos@szeredi.hu>
* Released 2.7.5
diff --git a/configure.in b/configure.in
index 00dc73f..d736f2f 100644
--- a/configure.in
+++ b/configure.in
@@ -1,4 +1,4 @@
-AC_INIT(fuse, 2.7.5)
+AC_INIT(fuse, 2.7.6)
AC_CANONICAL_TARGET
AM_INIT_AUTOMAKE
AM_CONFIG_HEADER(include/config.h)
diff --git a/kernel/configure.ac b/kernel/configure.ac
index bfc476b..9ce26e6 100644
--- a/kernel/configure.ac
+++ b/kernel/configure.ac
@@ -1,4 +1,4 @@
-AC_INIT(fuse-kernel, 2.7.5)
+AC_INIT(fuse-kernel, 2.7.6)
AC_CONFIG_HEADERS([config.h])
AC_PROG_INSTALL
diff --git a/lib/Makefile.am b/lib/Makefile.am
index 54a2e8b..db4d4fb 100644
--- a/lib/Makefile.am
+++ b/lib/Makefile.am
@@ -34,7 +34,7 @@ libfuse_la_SOURCES = \
$(iconv_source) \
$(mount_source)
-libfuse_la_LDFLAGS = @libfuse_libs@ -version-number 2:7:5 \
+libfuse_la_LDFLAGS = @libfuse_libs@ -version-number 2:7:6 \
-Wl,--version-script,$(srcdir)/fuse_versionscript
libulockmgr_la_SOURCES = ulockmgr.c
diff --git a/util/fusermount.c b/util/fusermount.c
index 8c4d1dc..098cc75 100644
--- a/util/fusermount.c
+++ b/util/fusermount.c
@@ -41,8 +41,8 @@
#ifndef MS_REC
#define MS_REC 16384
#endif
-#ifndef MS_SLAVE
-#define MS_SLAVE (1<<19)
+#ifndef MS_PRIVATE
+#define MS_PRIVATE (1<<18)
#endif
static const char *progname;
@@ -200,15 +200,16 @@ static int may_unmount(const char *mnt, int quiet)
* killed for any reason, mounts are automatically cleaned up.
*
* First make sure nothing is propagated back into the parent
- * namespace by marking all mounts "slave".
+ * namespace by marking all mounts "private".
*
* Then bind mount parent onto a stable base where the user can't move
- * it around. Use "/tmp", since it will almost certainly exist, but
- * anything similar would do as well.
+ * it around.
*
* Finally check /proc/mounts for an entry matching the requested
* mountpoint. If it's found then we are OK, and the user can't move
- * it around within the parent directory as rename() will return EBUSY.
+ * it around within the parent directory as rename() will return
+ * EBUSY. Be careful to ignore any mounts that existed before the
+ * bind.
*/
static int check_is_mount_child(void *p)
{
@@ -220,21 +221,27 @@ static int check_is_mount_child(void *p)
int found;
FILE *fp;
struct mntent *entp;
+ int count;
- res = mount("", "/", "", MS_SLAVE | MS_REC, NULL);
+ res = mount("", "/", "", MS_PRIVATE | MS_REC, NULL);
if (res == -1) {
- fprintf(stderr, "%s: failed to mark mounts slave: %s\n",
+ fprintf(stderr, "%s: failed to mark mounts private: %s\n",
progname, strerror(errno));
return 1;
}
- res = mount(".", "/tmp", "", MS_BIND | MS_REC, NULL);
- if (res == -1) {
- fprintf(stderr, "%s: failed to bind parent to /tmp: %s\n",
- progname, strerror(errno));
+ fp = setmntent(procmounts, "r");
+ if (fp == NULL) {
+ fprintf(stderr, "%s: failed to open %s: %s\n", progname,
+ procmounts, strerror(errno));
return 1;
}
+ count = 0;
+ while ((entp = getmntent(fp)) != NULL)
+ count++;
+ endmntent(fp);
+
fp = setmntent(procmounts, "r");
if (fp == NULL) {
fprintf(stderr, "%s: failed to open %s: %s\n", progname,
@@ -242,10 +249,21 @@ static int check_is_mount_child(void *p)
return 1;
}
+ res = mount(".", "/", "", MS_BIND | MS_REC, NULL);
+ if (res == -1) {
+ fprintf(stderr, "%s: failed to bind parent to /: %s\n",
+ progname, strerror(errno));
+ return 1;
+ }
+
found = 0;
while ((entp = getmntent(fp)) != NULL) {
- if (strncmp(entp->mnt_dir, "/tmp/", 5) == 0 &&
- strcmp(entp->mnt_dir + 5, last) == 0) {
+ if (count > 0) {
+ count--;
+ continue;
+ }
+ if (entp->mnt_dir[0] == '/' &&
+ strcmp(entp->mnt_dir + 1, last) == 0) {
found = 1;
break;
}
@@ -262,9 +280,8 @@ static int check_is_mount_child(void *p)
static pid_t clone_newns(void *a)
{
- long long buf[16384];
- size_t stacksize = sizeof(buf) / 2;
- char *stack = ((char *) buf) + stacksize;
+ char buf[131072];
+ char *stack = buf + (sizeof(buf) / 2 - ((size_t) buf & 15));
#ifdef __ia64__
extern int __clone2(int (*fn)(void *),
@@ -272,8 +289,8 @@ static pid_t clone_newns(void *a)
int flags, void *arg, pid_t *ptid,
void *tls, pid_t *ctid);
- return __clone2(check_is_mount_child, stack, stacksize, CLONE_NEWNS, a,
- NULL, NULL, NULL);
+ return __clone2(check_is_mount_child, stack, sizeof(buf) / 2,
+ CLONE_NEWNS, a, NULL, NULL, NULL);
#else
return clone(check_is_mount_child, stack, CLONE_NEWNS, a);
#endif