File autofs-5.0.6-fix-umount-recovery-of-busy-direct-mount.patch of Package autofs.openSUSE_11.4_Update
autofs-5.0.6 - fix umount recovery of busy direct mount
From: Ian Kent <raven@themaw.net>
Reported by Leonardo Chiquitto (along with a problem analysis that lead
to the resolution). Thanks for the effort Leonardo.
When umounting direct mounts at exit, if any are busy and contain offset
trigger mounts automount will try and re-mount them when the umount fails
so they can be used to re-construct the mount tree at restart. But this
fails because the kernel communication pipe, which is used as a parameter
when mounting the offsets, has already been closed. To fix this all we
need do is delay closing the kernel pipe file handle until after the
direct mounts have been umounted since this doesn't affect the in use
status of the mounts.
---
CHANGELOG | 1 +
daemon/direct.c | 18 +++++++++---------
2 files changed, 10 insertions(+), 9 deletions(-)
Index: autofs-5.0.5/CHANGELOG
===================================================================
--- autofs-5.0.5.orig/CHANGELOG
+++ autofs-5.0.5/CHANGELOG
@@ -97,6 +97,7 @@
- check scandir() return value.
- duplicate parent options for included maps.
- fix remount deadlock.
+- fix umount recovery of busy direct mount.
03/09/2009 autofs-5.0.5
-----------------------
Index: autofs-5.0.5/daemon/direct.c
===================================================================
--- autofs-5.0.5.orig/daemon/direct.c
+++ autofs-5.0.5/daemon/direct.c
@@ -193,15 +193,6 @@ int umount_autofs_direct(struct autofs_p
struct mnt_list *mnts;
struct mapent *me, *ne;
- close(ap->state_pipe[0]);
- close(ap->state_pipe[1]);
- if (ap->pipefd >= 0)
- close(ap->pipefd);
- if (ap->kpipefd >= 0) {
- close(ap->kpipefd);
- ap->kpipefd = -1;
- }
-
mnts = tree_make_mnt_tree(_PROC_MOUNTS, "/");
pthread_cleanup_push(mnts_cleanup, mnts);
nc = ap->entry->master->nc;
@@ -231,6 +222,15 @@ int umount_autofs_direct(struct autofs_p
pthread_cleanup_pop(1);
pthread_cleanup_pop(1);
+ close(ap->state_pipe[0]);
+ close(ap->state_pipe[1]);
+ if (ap->pipefd >= 0)
+ close(ap->pipefd);
+ if (ap->kpipefd >= 0) {
+ close(ap->kpipefd);
+ ap->kpipefd = -1;
+ }
+
return 0;
}