Blame SOURCES/bz1095944-safe-umount-option.patch

c608c9
diff --git a/heartbeat/Filesystem b/heartbeat/Filesystem
c608c9
index 9209818..6a852df 100755
c608c9
--- a/heartbeat/Filesystem
c608c9
+++ b/heartbeat/Filesystem
c608c9
@@ -196,6 +196,26 @@ Only set this to "true" if you know what you are doing!
c608c9
 <content type="boolean" default="$OCF_RESKEY_force_clones_default" />
c608c9
 </parameter>
c608c9
 
c608c9
+<parameter name="force_unmount">
c608c9
+<longdesc lang="en">
c608c9
+This option allows specifying how to handle processes that are
c608c9
+currently accessing the mount directory.
c608c9
+
c608c9
+"true"  : Default value, kill processes accessing mount point
c608c9
+"safe"  : Kill processes accessing mount point using methods that
c608c9
+          avoid functions that could potentially block during process
c608c9
+          detection 
c608c9
+"false" : Do not kill any processes.
c608c9
+
c608c9
+The 'safe' option uses shell logic to walk the /procs/ directory
c608c9
+for pids using the mount point while the default option uses the
c608c9
+fuser cli tool. fuser is known to perform operations that can potentially
c608c9
+block if unresponsive nfs mounts are in use on the system.
c608c9
+</longdesc>
c608c9
+<shortdesc lang="en">Kill processes before unmount</shortdesc>
c608c9
+<content type="boolean" default="true" />
c608c9
+</parameter>
c608c9
+
c608c9
 </parameters>
c608c9
 
c608c9
 <actions>
c608c9
@@ -701,6 +721,25 @@ Filesystem_notify() {
c608c9
 	done
c608c9
 }
c608c9
 
c608c9
+get_pids()
c608c9
+{
c608c9
+	local dir=$1
c608c9
+	local procs
c608c9
+	local mmap_procs
c608c9
+
c608c9
+	if ocf_is_true  "$FORCE_UNMOUNT"; then
c608c9
+		if [ "X${HOSTOS}" = "XOpenBSD" ];then
c608c9
+			fstat | grep $dir | awk '{print $3}'
c608c9
+		else
c608c9
+			$FUSER -m $dir 2>/dev/null
c608c9
+		fi
c608c9
+	elif [ "$FORCE_UNMOUNT" = "safe" ]; then
c608c9
+		procs=$(find /proc/[0-9]*/ -type l -lname "${dir}/*" -or -lname "${dir}" 2>/dev/null | awk -F/ '{print $3}')
c608c9
+		mmap_procs=$(grep " ${dir}" /proc/[0-9]*/maps | awk -F/ '{print $3}')
c608c9
+		echo -e "${procs}\n${mmap_procs}" | sort | uniq
c608c9
+	fi
c608c9
+}
c608c9
+
c608c9
 signal_processes() {
c608c9
 	local dir=$1
c608c9
 	local sig=$2
c608c9
@@ -708,15 +747,9 @@ signal_processes() {
c608c9
 	# fuser returns a non-zero return code if none of the
c608c9
 	# specified files is accessed or in case of a fatal 
c608c9
 	# error.
c608c9
-	pids=$(
c608c9
-		if [ "X${HOSTOS}" = "XOpenBSD" ];then
c608c9
-			fstat | grep $dir | awk '{print $3}'
c608c9
-		else
c608c9
-			$FUSER -m $dir 2>/dev/null
c608c9
-		fi
c608c9
-	)
c608c9
+	pids=$(get_pids "$dir")
c608c9
 	if [ -z "$pids" ]; then
c608c9
-		ocf_log info "No processes on $dir were signalled"
c608c9
+		ocf_log info "No processes on $dir were signalled. force_unmount is set to '$FORCE_UNMOUNT'"
c608c9
 		return
c608c9
 	fi
c608c9
 	for pid in $pids; do
c608c9
@@ -1002,6 +1035,11 @@ if [ $# -ne 1 ]; then
c608c9
 fi
c608c9
 
c608c9
 # Check the OCF_RESKEY_ environment variables...
c608c9
+FORCE_UNMOUNT="yes"
c608c9
+if [ -n "${OCF_RESKEY_force_unmount}" ]; then
c608c9
+	FORCE_UNMOUNT=$OCF_RESKEY_force_unmount
c608c9
+fi
c608c9
+
c608c9
 DEVICE=$OCF_RESKEY_device
c608c9
 FSTYPE=$OCF_RESKEY_fstype
c608c9
 if [ ! -z "$OCF_RESKEY_options" ]; then