Sophie

Sophie

distrib > Scientific%20Linux > 5x > x86_64 > by-pkgid > 130701790bf2d95e902edf16031ff596 > files > 225

autofs-5.0.1-0.rc2.164.el5_8.src.rpm

diff --git a/daemon/spawn.c b/daemon/spawn.c
index 0ed873e..78d69c6 100644
--- a/daemon/spawn.c
+++ b/daemon/spawn.c
@@ -25,6 +25,7 @@
 #include <time.h>
 #include <sys/wait.h>
 #include <sys/stat.h>
+#include <sys/mount.h>
 
 #include "automount.h"
 
@@ -308,6 +309,8 @@ int spawn_mount(unsigned logopt, ...)
 	while (retries--) {
 		ret = do_spawn(logopt, options, prog, (const char **) argv);
 		if (ret & MTAB_NOTUPDATED) {
+			struct timespec tm = {3, 0};
+
 			/*
 			 * If the mount succeeded but the mtab was not
 			 * updated, then retry the mount with the -f (fake)
@@ -329,6 +332,9 @@ int spawn_mount(unsigned logopt, ...)
 				argv[argc - 1] = argv[argc - 2];
 				argv[argc - 2] = arg_fake;
 			}
+
+			nanosleep(&tm, NULL);
+
 			continue;
 		}
 		break;
@@ -336,9 +342,16 @@ int spawn_mount(unsigned logopt, ...)
 
 	/* This is not a fatal error */
 	if (ret == MTAB_NOTUPDATED) {
-		warn(logopt, "Unable to update the mtab file, /proc/mounts "
-		     "and /etc/mtab will differ");
-		ret = 0;
+		/*
+		 * Version 5 requires that /etc/mtab be in sync with
+		 * /proc/mounts. If we're unable to update matb after
+		 * retrying then we have no choice but umount the mount
+		 * and return a fail.
+		 */
+		warn(logopt,
+		     "Unable to update the mtab file, forcing mount fail!");
+		umount(argv[argc]);
+		ret = MNT_FORCE_FAIL;
 	}
 
 	return ret;
@@ -395,6 +408,8 @@ int spawn_bind_mount(unsigned logopt, ...)
 	while (retries--) {
 		ret = do_spawn(logopt, options, prog, (const char **) argv);
 		if (ret & MTAB_NOTUPDATED) {
+			struct timespec tm = {3, 0};
+
 			/*
 			 * If the mount succeeded but the mtab was not
 			 * updated, then retry the mount with the -f (fake)
@@ -416,6 +431,9 @@ int spawn_bind_mount(unsigned logopt, ...)
 				argv[argc - 1] = argv[argc - 2];
 				argv[argc - 2] = arg_fake;
 			}
+
+			nanosleep(&tm, NULL);
+
 			continue;
 		}
 		break;
@@ -423,9 +441,16 @@ int spawn_bind_mount(unsigned logopt, ...)
 
 	/* This is not a fatal error */
 	if (ret == MTAB_NOTUPDATED) {
-		warn(logopt, "Unable to update the mtab file, /proc/mounts "
-		     "and /etc/mtab will differ");
-		ret = 0;
+		/*
+		 * Version 5 requires that /etc/mtab be in sync with
+		 * /proc/mounts. If we're unable to update matb after
+		 * retrying then we have no choice but umount the mount
+		 * and return a fail.
+		 */
+		warn(logopt,
+		     "Unable to update the mtab file, forcing mount fail!");
+		umount(argv[argc]);
+		ret = MNT_FORCE_FAIL;
 	}
 
 	return ret;
diff --git a/include/automount.h b/include/automount.h
index 4887da6..fa5cd97 100644
--- a/include/automount.h
+++ b/include/automount.h
@@ -78,6 +78,7 @@ int load_autofs4_module(void);
 #define MOUNTED_LOCK	_PATH_MOUNTED "~"	/* mounts' lock file */
 #define MTAB_NOTUPDATED 0x1000			/* mtab succeded but not updated */
 #define NOT_MOUNTED     0x0100			/* path notmounted */
+#define MNT_FORCE_FAIL	-1
 #define _PROC_MOUNTS	"/proc/mounts"
 
 /* Constants for lookup modules */
diff --git a/modules/mount_bind.c b/modules/mount_bind.c
index 04284f5..ef973e1 100644
--- a/modules/mount_bind.c
+++ b/modules/mount_bind.c
@@ -147,7 +147,7 @@ int mount_mount(struct autofs_point *ap, const char *root, const char *name, int
 			if ((!ap->ghost && name_len) || !existed)
 				rmdir_path(ap, fullpath, ap->dev);
 
-			return 1;
+			return err;
 		} else {
 			debug(ap->logopt,
 			      MODPREFIX "mounted %s type %s on %s",
diff --git a/modules/mount_nfs.c b/modules/mount_nfs.c
index bad21fc..0e7aebe 100644
--- a/modules/mount_nfs.c
+++ b/modules/mount_nfs.c
@@ -233,6 +233,10 @@ int mount_mount(struct autofs_point *ap, const char *root, const char *name, int
 				return 0;
 			}
 
+			/* Failed to update mtab, don't try any more */
+			if (err == MNT_FORCE_FAIL)
+				goto forced_fail;
+
 			/* No hostname, can't be NFS */
 			if (!this->name) {
 				this = this->next;
@@ -275,6 +279,7 @@ int mount_mount(struct autofs_point *ap, const char *root, const char *name, int
 		this = this->next;
 	}
 
+forced_fail:
 	free_host_list(&hosts);
 	ap->ghost = save_ghost;