From: NeilBrown <neilb@suse.com>
Subject: NFS: Don't drop directory dentry which is in use
References: bsc#993127
Patch-mainline: Never, code significantly changed

If a process is blocked waiting on the NFS server to validate a file
(in nfs_lookup_revalidate) and it gets kill, then the RPC request will
fail with EIO.  This should not be taken to indicate a problem with
the file, but it is.

This problem has been fixed upstream by removing the d_drop() call,
after making various VFS changes so that the dentry will be discarded cleanly
when that is appropriate.  In particular, the dentry refcount is checked in a
suitably safe way and the dentry only dropped when the count is zero.

Including all those changes into SLE11 seems too intrusive, so I have
taken a simpler approach.

If a directy dentry is in use beyond the looked, whether mounted or
cwd or otherwise, we don't d_drop() it just because of an error.

The extra IS_ROOT() test is not directly related but is worth fixing.
It is from
 Commit: a3f432bfd06a ("nfs: use IS_ROOT not DCACHE_DISCONNECTED")
which is in 3.13 and has already been applied to SLE12.

Signed-off-by: NeilBrown <neilb@suse.com>

---
 fs/nfs/dir.c |    5 +++++
 1 file changed, 5 insertions(+)

--- a/fs/nfs/dir.c
+++ b/fs/nfs/dir.c
@@ -1270,7 +1270,12 @@ out_zap_parent:
 			goto out_valid;
 		if (dentry->d_flags & DCACHE_DISCONNECTED)
 			goto out_valid;
+		if (IS_ROOT(dentry))
+			goto out_valid;
 		shrink_dcache_parent(dentry);
+		if (dentry->d_lockref.count > 1)
+			/* possibly mounted, too dangerous to drop */
+			goto out_valid;
 	}
 	d_drop(dentry);
 	dput(parent);
