Windows: Prevent lock inversion SetFileRenameInfo
authorJeffrey Altman <jaltman@your-file-system.com>
Tue, 4 Dec 2012 21:57:36 +0000 (16:57 -0500)
committerJeffrey Altman <jaltman@your-file-system.com>
Wed, 5 Dec 2012 20:15:50 +0000 (12:15 -0800)
SetFileRenameInfo calls MmForceSectionClosed() which can call
back to the afs redirector via the Cleanup processing.  AFSCleanup()
requires an exclusive hold of Fcb->Resource so we must obtain the
lock first in AFSSetFileRenameInfo() prior to obtaining the
SectionObjectResource.

Change-Id: If679eeb107f04153a26659971b7f2455eef97c9a
Reviewed-on: http://gerrit.openafs.org/8603
Tested-by: Jeffrey Altman <jaltman@your-file-system.com>
Reviewed-by: Jeffrey Altman <jaltman@your-file-system.com>

src/WINNT/afsrdr/kernel/lib/AFSFileInfo.cpp

index f9ffcdf..2a96300 100644 (file)
@@ -3152,6 +3152,22 @@ AFSSetRenameInfo( IN PIRP Irp)
 
                 pTargetFcb = pTargetDirEntry->ObjectInformation->Fcb;
 
+                //
+                // MmForceSectionClosed() can eventually call back into AFSCleanup
+                // which will need to acquire Fcb->Resource exclusively.  Failure
+                // to obtain it here before holding the SectionObjectResource will
+                // permit the locks to be obtained out of order risking a deadlock.
+                //
+
+                AFSDbgLogMsg( AFS_SUBSYSTEM_LOCK_PROCESSING,
+                              AFS_TRACE_LEVEL_VERBOSE,
+                              "AFSSetRenameInfo Acquiring Fcb lock %08lX EXCL %08lX\n",
+                              &pTargetFcb->NPFcb->Resource,
+                              PsGetCurrentThread());
+
+                AFSAcquireExcl( &pTargetFcb->NPFcb->Resource,
+                                TRUE);
+
                 AFSDbgLogMsg( AFS_SUBSYSTEM_LOCK_PROCESSING,
                               AFS_TRACE_LEVEL_VERBOSE,
                               "AFSSetRenameInfo Acquiring Fcb SectionObject lock %08lX EXCL %08lX\n",
@@ -3182,6 +3198,14 @@ AFSSetRenameInfo( IN PIRP Irp)
                               PsGetCurrentThread());
 
                 AFSReleaseResource( &pTargetFcb->NPFcb->SectionObjectResource);
+
+                AFSDbgLogMsg( AFS_SUBSYSTEM_LOCK_PROCESSING,
+                              AFS_TRACE_LEVEL_VERBOSE,
+                              "AFSSetRenameInfo Releasing Fcb lock %08lX EXCL %08lX\n",
+                              &pTargetFcb->NPFcb->Resource,
+                              PsGetCurrentThread());
+
+                AFSReleaseResource( &pTargetFcb->NPFcb->Resource);
             }
 
             ASSERT( pTargetDirEntry->DirOpenReferenceCount > 0);