BOOLEAN bAllocatedSymLinkBuffer = FALSE;
UNICODE_STRING uniRelativeName, uniNoOpName;
AFSObjectInfoCB *pCurrentObject = NULL;
+ AFSObjectInfoCB *pParentObjectInfo = NULL;
AFSVolumeCB *pCurrentVolume = *VolumeCB;
BOOLEAN bReleaseCurrentVolume = TRUE;
BOOLEAN bSubstitutedName = FALSE;
uniSearchName.Length = uniSearchName.MaximumLength = 0;
uniSearchName.Buffer = NULL;
- ASSERT( pCurrentVolume->VolumeReferenceCount > 1);
-
while( TRUE)
{
+ ASSERT( pCurrentVolume->VolumeReferenceCount > 1);
+
+ ASSERT( pDirEntry->DirOpenReferenceCount > 0);
+
//
// Check our total link count for this name array
//
if( !NT_SUCCESS( ntStatus))
{
- AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
- AFS_TRACE_LEVEL_ERROR,
- "AFSLocateNameEntry (FO: %08lX) Failed to evaluate parent %wZ FID %08lX-%08lX-%08lX-%08lX Status %08lX\n",
- FileObject,
- &pDirEntry->NameInformation.FileName,
- pCurrentObject->FileId.Cell,
- pCurrentObject->FileId.Volume,
- pCurrentObject->FileId.Vnode,
- pCurrentObject->FileId.Unique,
- ntStatus);
+ if ( ntStatus == STATUS_NOT_A_DIRECTORY)
+ {
+
+ if ( pCurrentObject->ParentObjectInformation == NULL)
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_ERROR,
+ "AFSLocateNameEntry (FO: %08lX) Failed to evaluate object %wZ FID %08lX-%08lX-%08lX-%08lX PARENT NULL Status %08lX\n",
+ FileObject,
+ &pDirEntry->NameInformation.FileName,
+ pCurrentObject->FileId.Cell,
+ pCurrentObject->FileId.Volume,
+ pCurrentObject->FileId.Vnode,
+ pCurrentObject->FileId.Unique,
+ ntStatus);
+ }
+ else
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_ERROR,
+ "AFSLocateNameEntry (FO: %08lX) Failed to evaluate object %wZ FID %08lX-%08lX-%08lX-%08lX PARENT %08lX-%08lX-%08lX-%08lX Status %08lX\n",
+ FileObject,
+ &pDirEntry->NameInformation.FileName,
+ pCurrentObject->FileId.Cell,
+ pCurrentObject->FileId.Volume,
+ pCurrentObject->FileId.Vnode,
+ pCurrentObject->FileId.Unique,
+ pCurrentObject->ParentObjectInformation->FileId.Cell,
+ pCurrentObject->ParentObjectInformation->FileId.Volume,
+ pCurrentObject->ParentObjectInformation->FileId.Vnode,
+ pCurrentObject->ParentObjectInformation->FileId.Unique,
+ ntStatus);
+ }
+ }
+ else
+ {
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_ERROR,
+ "AFSLocateNameEntry (FO: %08lX) Failed to evaluate parent %wZ FID %08lX-%08lX-%08lX-%08lX Status %08lX\n",
+ FileObject,
+ &pDirEntry->NameInformation.FileName,
+ pCurrentObject->FileId.Cell,
+ pCurrentObject->FileId.Volume,
+ pCurrentObject->FileId.Vnode,
+ pCurrentObject->FileId.Unique,
+ ntStatus);
+ }
try_return( ntStatus);
}
try_return( ntStatus);
}
+ AFSAcquireExcl( pCurrentObject->Specific.Directory.DirectoryNodeHdr.TreeLock,
+ TRUE);
+
AFSAcquireExcl( &pDirEntry->NonPaged->Lock,
TRUE);
// Directory TreeLock should be exclusively held
//
- AFSAcquireExcl( pCurrentObject->Specific.Directory.DirectoryNodeHdr.TreeLock,
- TRUE);
-
ntStatus = AFSVerifyEntry( AuthGroup,
pDirEntry);
continue;
}
}
+ else
+ {
+
+ AFSReleaseResource( pCurrentObject->Specific.Directory.DirectoryNodeHdr.TreeLock);
+ }
//
// If we were given a zero length target name then deny access to the entry
if( pTmpBuffer != NULL)
{
- AFSExFreePool( pTmpBuffer);
+ AFSExFreePoolWithTag( pTmpBuffer, 0);
}
AFSReleaseResource( &pDirEntry->NonPaged->Lock);
// Dereference the current entry ..
//
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ ASSERT( lCount >= 0);
+
//
// OK, need to back up one entry for the correct parent since the current
// entry we are on is the symlink itself
// Increment our reference on this dir entry
//
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
pCurrentObject->FileId.Vnode,
pCurrentObject->FileId.Unique);
+ if ( !AFSIsAbsoluteAFSName( &pDirEntry->NameInformation.TargetName))
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_ERROR,
+ "AFSLocateNameEntry Name %wZ contains invalid server name\n",
+ &pDirEntry->NameInformation.TargetName);
+
+ //
+ // The correct response would be STATUS_OBJECT_PATH_INVALID
+ // but that prevents cmd.exe from performing a recursive
+ // directory enumeration when opening a directory entry
+ // that represents a symlink to an invalid path is discovered.
+ //
+
+ AFSReleaseResource( &pDirEntry->NonPaged->Lock);
+
+ try_return( ntStatus = STATUS_OBJECT_PATH_NOT_FOUND);
+ }
+
//
// We'll substitute this name into the current process name
// starting at where we sit in the path
//
RtlCopyMemory( uniTempName.Buffer,
- pDirEntry->NameInformation.TargetName.Buffer,
- pDirEntry->NameInformation.TargetName.Length);
+ &pDirEntry->NameInformation.TargetName.Buffer[ AFSMountRootName.Length/sizeof( WCHAR)],
+ pDirEntry->NameInformation.TargetName.Length - AFSMountRootName.Length);
- uniTempName.Length = pDirEntry->NameInformation.TargetName.Length;
+ uniTempName.Length = pDirEntry->NameInformation.TargetName.Length - AFSMountRootName.Length;
//
// And now any remaining portion of the name
if( pTmpBuffer != NULL)
{
- AFSExFreePool( pTmpBuffer);
+ AFSExFreePoolWithTag( pTmpBuffer, 0);
}
AFSReleaseResource( &pDirEntry->NonPaged->Lock);
// Dereference our current dir entry
//
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ ASSERT( lCount >= 0);
+
pDirEntry = pCurrentVolume->DirectoryCB;
//
// Reference the new dir entry
//
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
pNameArray->LinkCount = lLinkCount;
- //
- // Process over the \\<Global root> portion of the name
- //
-
- FsRtlDissectName( uniPathName,
- &uniComponentName,
- &uniRemainingPath);
-
- if( RtlCompareUnicodeString( &uniComponentName,
- &AFSServerName,
- TRUE) != 0)
- {
-
- AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
- AFS_TRACE_LEVEL_ERROR,
- "AFSLocateNameEntry Name %wZ contains invalid server name\n",
- &uniPathName);
-
- //
- // The correct response would be STATUS_OBJECT_PATH_INVALID
- // but that prevents cmd.exe from performing a recursive
- // directory enumeration when opening a directory entry
- // that represents a symlink to an invalid path is discovered.
- //
- try_return( ntStatus = STATUS_OBJECT_PATH_NOT_FOUND);
- }
-
- uniPathName = uniRemainingPath;
-
pParentDirEntry = NULL;
}
AFS_TRACE_LEVEL_VERBOSE,
"AFSLocateNameEntry Decrement2 count on volume %08lX Cnt %d\n",
pCurrentVolume,
- pCurrentVolume->VolumeReferenceCount);
+ lCount);
ntStatus = AFSBuildMountPointTarget( AuthGroup,
pDirEntry,
ASSERT( pCurrentVolume->VolumeReferenceCount > 1);
//
- // Replace the current name for the mp with the volume root of the target
- //
-
- AFSReplaceCurrentElement( pNameArray,
- pCurrentVolume->DirectoryCB);
-
- //
// We want to restart processing here on the new parent ...
// Deref and ref count the entries
//
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ ASSERT( lCount >= 0);
+
pDirEntry = pCurrentVolume->DirectoryCB;
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ //
+ // The name array stores both the mount point and the target.
+ // Insert the target.
+ //
+
+ AFSInsertNextElement( pNameArray,
+ pDirEntry);
+
pParentDirEntry = NULL;
//
uniSearchName.Buffer != NULL)
{
- AFSExFreePool( uniSearchName.Buffer);
+ AFSExFreePoolWithTag( uniSearchName.Buffer, 0);
bSubstituteName = FALSE;
//
// Need to back up one entry in the name array
//
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ ASSERT( lCount >= 0);
+
pDirEntry = AFSBackupEntry( NameArray);
if( pDirEntry == NULL)
try_return(ntStatus = STATUS_OBJECT_PATH_INVALID);
}
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSLocateNameEntry Increment4 count on %wZ DE %p Ccb %p Cnt %d\n",
+ &pDirEntry->NameInformation.FileName,
+ pDirEntry,
+ NULL,
+ lCount);
if( BooleanFlagOn( pDirEntry->ObjectInformation->Flags, AFS_OBJECT_ROOT_VOLUME))
{
ASSERT( pParentDirEntry != pDirEntry);
}
- AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
- AFS_TRACE_LEVEL_VERBOSE,
- "AFSLocateNameEntry Increment4 count on %wZ DE %p Ccb %p Cnt %d\n",
- &pDirEntry->NameInformation.FileName,
- pDirEntry,
- NULL,
- pDirEntry->OpenReferenceCount);
-
uniPathName = uniRemainingPath;
continue;
// a lookup in the short name tree
//
- if( RtlIsNameLegalDOS8Dot3( &uniSearchName,
+ if( !BooleanFlagOn( pDevExt->DeviceFlags, AFS_DEVICE_FLAG_DISABLE_SHORTNAMES) &&
+ RtlIsNameLegalDOS8Dot3( &uniSearchName,
NULL,
NULL))
{
&pDirEntry);
}
+ if ( pDirEntry == NULL &&
+ pParentDirEntry->ObjectInformation->VolumeCB == AFSGlobalRoot)
+ {
+
+ //
+ // Check with the service to see if this is a valid cell name
+ // that can be automatically resolved. Drop the shared TreeLock
+ // since AFSCheckCellName must acquire it exclusively.
+ //
+
+ AFSReleaseResource( pParentDirEntry->ObjectInformation->Specific.Directory.DirectoryNodeHdr.TreeLock);
+
+ ntStatus = AFSCheckCellName( AuthGroup,
+ &uniSearchName,
+ &pDirEntry);
+
+ AFSAcquireShared( pParentDirEntry->ObjectInformation->Specific.Directory.DirectoryNodeHdr.TreeLock,
+ TRUE);
+ }
+
if( pDirEntry == NULL)
{
if( bSubstituteName)
{
- AFSExFreePool( uniSearchName.Buffer);
+ AFSExFreePoolWithTag( uniSearchName.Buffer, 0);
uniSearchName = uniComponentName;
pDirEntry->CaseInsensitiveList.fLink != NULL)
{
+ //
+ // Increment our dir entry ref count since we will decrement it on exit
+ //
+
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSLocateNameEntry Increment5 count on %wZ DE %p Ccb %p Cnt %d\n",
+ &pDirEntry->NameInformation.FileName,
+ pDirEntry,
+ NULL,
+ lCount);
+
AFSReleaseResource( pParentDirEntry->ObjectInformation->Specific.Directory.DirectoryNodeHdr.TreeLock);
try_return(ntStatus = STATUS_OBJECT_NAME_COLLISION);
// Increment our dir entry ref count
//
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
// on the entry
//
- ASSERT( pCurrentObject->ParentObjectInformation != NULL);
+ pParentObjectInfo = pCurrentObject->ParentObjectInformation;
- AFSAcquireExcl( pCurrentObject->ParentObjectInformation->Specific.Directory.DirectoryNodeHdr.TreeLock,
+ ASSERT( pParentObjectInfo != NULL);
+
+ AFSAcquireExcl( pParentObjectInfo->Specific.Directory.DirectoryNodeHdr.TreeLock,
TRUE);
AFSAcquireExcl( pCurrentObject->VolumeCB->ObjectInfoTree.TreeLock,
TRUE);
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSLocateNameEntry Decrement count on %wZ DE %p Ccb %p Cnt %d\n",
+ &pDirEntry->NameInformation.FileName,
+ pDirEntry,
+ NULL,
+ lCount);
+
+ ASSERT( lCount >= 0);
- if( lCount == 0)
+ if( lCount <= 0)
{
AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING|AFS_SUBSYSTEM_CLEANUP_PROCESSING,
// Remove and delete the directory entry from the parent list
//
- AFSDeleteDirEntry( pCurrentObject->ParentObjectInformation,
+ AFSDeleteDirEntry( pParentObjectInfo,
pDirEntry);
- if( pCurrentObject->ObjectReferenceCount == 0)
+ AFSAcquireShared( &pCurrentObject->NonPagedInfo->ObjectInfoLock,
+ TRUE);
+
+ if( pCurrentObject->ObjectReferenceCount <= 0)
{
if( BooleanFlagOn( pCurrentObject->Flags, AFS_OBJECT_INSERTED_HASH_TREE))
ClearFlag( pCurrentObject->Flags, AFS_OBJECT_INSERTED_HASH_TREE);
}
}
+
+ AFSReleaseResource( &pCurrentObject->NonPagedInfo->ObjectInfoLock);
}
else
{
SetFlag( pDirEntry->Flags, AFS_DIR_ENTRY_DELETED);
- AFSRemoveNameEntry( pCurrentObject->ParentObjectInformation,
+ AFSRemoveNameEntry( pParentObjectInfo,
pDirEntry);
}
- AFSReleaseResource( pCurrentObject->ParentObjectInformation->Specific.Directory.DirectoryNodeHdr.TreeLock);
+ AFSReleaseResource( pParentObjectInfo->Specific.Directory.DirectoryNodeHdr.TreeLock);
AFSReleaseResource( pCurrentObject->VolumeCB->ObjectInfoTree.TreeLock);
// Decrement the previous parent
//
- lCount = InterlockedDecrement( &pParentDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pParentDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
NULL,
lCount);
+ ASSERT( lCount >= 0);
+
//
// If we ended up substituting a name in the component then update
// the full path and update the pointers
//
if( pCurrentObject->FileType == AFS_FILE_TYPE_SYMLINK &&
- pCurrentObject->TargetFileId.Vnode == 0 &&
- pCurrentObject->TargetFileId.Unique == 0 &&
- pDirEntry->NameInformation.TargetName.Length == 0)
+ ( pCurrentObject->TargetFileId.Vnode == 0 ||
+ pDirEntry->NameInformation.TargetName.Length == 0))
{
ntStatus = AFSValidateSymLink( AuthGroup,
if( pDirEntry != NULL)
{
- lCount = InterlockedDecrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
pDirEntry,
NULL,
lCount);
+
+ ASSERT( lCount >= 0);
}
else if( pParentDirEntry != NULL)
{
- lCount = InterlockedDecrement( &pParentDirEntry->OpenReferenceCount);
+ lCount = InterlockedDecrement( &pParentDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
pParentDirEntry,
NULL,
lCount);
+
+ ASSERT( lCount >= 0);
}
if( bReleaseCurrentVolume)
if( RootPathName->Buffer != uniFullPathName.Buffer)
{
- AFSExFreePool( uniFullPathName.Buffer);
+ AFSExFreePoolWithTag( uniFullPathName.Buffer, 0);
}
}
else
&(*ParentDirectoryCB)->NameInformation.FileName,
*ParentDirectoryCB,
NULL,
- (*ParentDirectoryCB)->OpenReferenceCount);
+ (*ParentDirectoryCB)->DirOpenReferenceCount);
}
if( *DirectoryCB != NULL)
&(*DirectoryCB)->NameInformation.FileName,
*DirectoryCB,
NULL,
- (*DirectoryCB)->OpenReferenceCount);
+ (*DirectoryCB)->DirOpenReferenceCount);
}
}
uniSearchName.Buffer != NULL)
{
- AFSExFreePool( uniSearchName.Buffer);
+ AFSExFreePoolWithTag( uniSearchName.Buffer, 0);
}
}
AFSDeleteDirEntry( ParentObjectInfo,
pDirNode);
- lCount = InterlockedIncrement( &pExistingDirNode->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pExistingDirNode->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
// Need to tear down this entry and rebuild it below
//
- if( pExistingDirNode->OpenReferenceCount == 0)
+ if( pExistingDirNode->DirOpenReferenceCount <= 0)
{
AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
pDirNode,
TRUE);
- lCount = InterlockedIncrement( &pDirNode->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirNode->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
__Enter
{
- AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING | AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
- "AFSDeleteDirEntry Deleting dir entry in parent %08lX Entry %08lX %wZ FID %08lX-%08lX-%08lX-%08lX\n",
+ "AFSDeleteDirEntry Deleting dir entry in parent %08lX Entry %08lX %wZ FID %08lX-%08lX-%08lX-%08lX RefCount %08lX\n",
ParentObjectInfo,
DirEntry,
&DirEntry->NameInformation.FileName,
DirEntry->ObjectInformation->FileId.Cell,
DirEntry->ObjectInformation->FileId.Volume,
DirEntry->ObjectInformation->FileId.Vnode,
- DirEntry->ObjectInformation->FileId.Unique);
+ DirEntry->ObjectInformation->FileId.Unique,
+ DirEntry->DirOpenReferenceCount);
+
+ ASSERT( DirEntry->DirOpenReferenceCount == 0);
AFSRemoveDirNodeFromParent( ParentObjectInfo,
DirEntry,
if( BooleanFlagOn( DirEntry->Flags, AFS_DIR_RELEASE_NAME_BUFFER))
{
- AFSExFreePool( DirEntry->NameInformation.FileName.Buffer);
+ AFSExFreePoolWithTag( DirEntry->NameInformation.FileName.Buffer, 0);
}
if( BooleanFlagOn( DirEntry->Flags, AFS_DIR_RELEASE_TARGET_NAME_BUFFER))
{
- AFSExFreePool( DirEntry->NameInformation.TargetName.Buffer);
+ AFSExFreePoolWithTag( DirEntry->NameInformation.TargetName.Buffer, 0);
}
//
ASSERT( DirEntry->ObjectInformation->ObjectReferenceCount > 0);
- lCount = InterlockedDecrement( &DirEntry->ObjectInformation->ObjectReferenceCount);
-
- if( lCount == 0)
- {
- SetFlag( DirEntry->ObjectInformation->Flags, AFS_OBJECT_FLAGS_DELETED);
- }
+ lCount = AFSObjectInfoDecrement( DirEntry->ObjectInformation);
AFSDbgLogMsg( AFS_SUBSYSTEM_OBJECT_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
"AFSDeleteDirEntry Decrement count on object %08lX Cnt %d\n",
DirEntry->ObjectInformation,
- DirEntry->ObjectInformation->ObjectReferenceCount);
+ lCount);
+
+ if( BooleanFlagOn( DirEntry->Flags, AFS_DIR_ENTRY_DELETED) &&
+ DirEntry->ObjectInformation->Links == 0)
+ {
+
+ SetFlag( DirEntry->ObjectInformation->Flags, AFS_OBJECT_FLAGS_DELETED);
+ }
ExDeleteResourceLite( &DirEntry->NonPaged->Lock);
- AFSExFreePool( DirEntry->NonPaged);
+ AFSExFreePoolWithTag( DirEntry->NonPaged, AFS_DIR_ENTRY_NP_TAG);
//
// Free up the dir entry
//
- AFSExFreePool( DirEntry);
+ AFSExFreePoolWithTag( DirEntry, AFS_DIR_ENTRY_TAG);
}
return ntStatus;
"AFSParseName (%08lX) Failed to initialize name array\n",
Irp);
- AFSExFreePool( uniFullName.Buffer);
+ AFSExFreePoolWithTag( uniFullName.Buffer, 0);
try_return( ntStatus = STATUS_INSUFFICIENT_RESOURCES);
}
"AFSParseName (%08lX) Failed to initialize name array\n",
Irp);
- AFSExFreePool( uniFullName.Buffer);
+ AFSExFreePoolWithTag( uniFullName.Buffer, 0);
try_return( ntStatus = STATUS_INSUFFICIENT_RESOURCES);
}
"AFSParseName (%08lX) Failed to populate name array\n",
Irp);
- AFSExFreePool( uniFullName.Buffer);
+ AFSExFreePoolWithTag( uniFullName.Buffer, 0);
try_return( ntStatus);
}
*ParentDirectoryCB = pDirEntry;
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
"AFSParseName (%08lX) Returning global root access\n",
Irp);
- lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->OpenReferenceCount);
+ lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
"AFSParseName (%08lX) Returning global root access\n",
Irp);
- lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->OpenReferenceCount);
+ lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
"AFSParseName (%08lX) Returning root PIOCtl access\n",
Irp);
- lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->OpenReferenceCount);
+ lCount = InterlockedIncrement( &AFSGlobalRoot->DirectoryCB->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
ClearFlag( *ParseFlags, AFS_PARSE_FLAG_ROOT_ACCESS);
- lCount = InterlockedIncrement( &pDirEntry->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirEntry->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
// a lookup in the short name tree
//
- if( RtlIsNameLegalDOS8Dot3( &uniComponentName,
+ if( !BooleanFlagOn( pDeviceExt->DeviceFlags, AFS_DEVICE_FLAG_DISABLE_SHORTNAMES) &&
+ RtlIsNameLegalDOS8Dot3( &uniComponentName,
NULL,
NULL))
{
AFSReleaseResource( AFSGlobalRoot->ObjectInformation.Specific.Directory.DirectoryNodeHdr.TreeLock);
}
+
//
// Be sure we are starting from the correct volume
//
pVolumeCB = pDirEntry->ObjectInformation->VolumeCB;
//
+ // Init our name array
+ //
+
+ pNameArray = AFSInitNameArray( AFSGlobalRoot->DirectoryCB,
+ 0);
+
+ if( pNameArray == NULL)
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSParseName (%08lX) Failed to initialize name array\n",
+ Irp);
+
+ try_return( ntStatus = STATUS_INSUFFICIENT_RESOURCES);
+ }
+
+ ntStatus = AFSInsertNextElement( pNameArray,
+ pVolumeCB->DirectoryCB);
+
+ if ( ntStatus)
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSParseName (%08lX) Failed to insert name array element\n",
+ Irp);
+
+ try_return( ntStatus);
+ }
+
+ //
// In this case don't add back in the 'share' name since that is where we are
// starting. Just put the leading slash back in
//
pVolumeCB = AFSGlobalRoot;
//
+ // Init our name array
+ //
+
+ pNameArray = AFSInitNameArray( AFSGlobalRoot->DirectoryCB,
+ 0);
+ if( pNameArray == NULL)
+ {
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSParseName (%08lX) Failed to initialize name array\n",
+ Irp);
+
+ try_return( ntStatus = STATUS_INSUFFICIENT_RESOURCES);
+ }
+
+ //
// Add back in the 'share' portion of the name since we will parse it out on return
//
uniRemainingPath.Length += sizeof( WCHAR);
uniRemainingPath.MaximumLength += sizeof( WCHAR);
- lCount = InterlockedIncrement( &pVolumeCB->DirectoryCB->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pVolumeCB->DirectoryCB->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
&pVolumeCB->DirectoryCB->NameInformation.FileName,
pVolumeCB->DirectoryCB,
NULL,
- lCount = pVolumeCB->DirectoryCB->OpenReferenceCount);
+ lCount);
//
// Pass back the parent being the volume root
//
*ParentDirectoryCB = pVolumeCB->DirectoryCB;
- }
-
- //
- // Init our name array
- //
- pNameArray = AFSInitNameArray( pVolumeCB->DirectoryCB,
- 0);
-
- if( pNameArray == NULL)
- {
-
- AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
- AFS_TRACE_LEVEL_VERBOSE,
- "AFSParseName (%08lX) Failed to initialize name array\n",
- Irp);
-
- try_return( ntStatus = STATUS_INSUFFICIENT_RESOURCES);
}
//
&(*ParentDirectoryCB)->NameInformation.FileName,
*ParentDirectoryCB,
NULL,
- (*ParentDirectoryCB)->OpenReferenceCount);
+ (*ParentDirectoryCB)->DirOpenReferenceCount);
}
}
if( !NT_SUCCESS( ntStatus))
{
+ AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
+ AFS_TRACE_LEVEL_WARNING,
+ "AFSCheckCellName entry %wZ does not exist parent FID %08lX-%08lX-%08lX-%08lX Status %08lX\n",
+ CellName,
+ AFSGlobalRoot->ObjectInformation.FileId.Cell,
+ AFSGlobalRoot->ObjectInformation.FileId.Volume,
+ AFSGlobalRoot->ObjectInformation.FileId.Vnode,
+ AFSGlobalRoot->ObjectInformation.FileId.Unique,
+ ntStatus);
+
try_return( ntStatus);
}
*ShareDirEntry = pVolumeCB->DirectoryCB;
- lCount = InterlockedIncrement( &pVolumeCB->DirectoryCB->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pVolumeCB->DirectoryCB->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
lCount);
lCount = InterlockedDecrement( &pVolumeCB->VolumeReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSCheckCellName Increment count on volume %08lX Cnt %d\n",
+ pVolumeCB,
+ lCount);
}
else
{
AFSGlobalRoot->ObjectInformation.FileId.Vnode,
AFSGlobalRoot->ObjectInformation.FileId.Unique);
- lCount = InterlockedIncrement( &pDirNode->OpenReferenceCount);
+ lCount = InterlockedIncrement( &pDirNode->DirOpenReferenceCount);
AFSDbgLogMsg( AFS_SUBSYSTEM_DIRENTRY_REF_COUNTING,
AFS_TRACE_LEVEL_VERBOSE,
if( pDirEnumEntry != NULL)
{
- AFSExFreePool( pDirEnumEntry);
+ AFSExFreePoolWithTag( pDirEnumEntry, AFS_GENERIC_MEMORY_31_TAG);
}
}
AFSVolumeCB *pVolumeCB = NULL;
AFSFileID stTargetFileID;
LONG lCount;
+ BOOLEAN bReleaseVolumeLock = FALSE;
__Enter
{
try_return( ntStatus);
}
- }
- else
- {
//
- // Check if this volume has been deleted or taken offline
+ // pVolumeCB->VolumeLock held exclusive and
+ // pVolumeCB->VolumeReferenceCount has been incremented
+ // pVolumeCB->RootFcb == NULL
//
- if( BooleanFlagOn( pVolumeCB->Flags, AFS_VOLUME_FLAGS_OFFLINE))
- {
-
- AFSReleaseResource( &pDevExt->Specific.RDR.VolumeTreeLock);
-
- try_return( ntStatus = STATUS_FILE_IS_OFFLINE);
- }
+ bReleaseVolumeLock = TRUE;
+ }
+ else
+ {
//
- // Just to ensure that things don't get torn down AND we don't create a
- // deadlock with invalidation
+ // AFSInitVolume returns with a VolumeReferenceCount
+ // obtain one to match
//
lCount = InterlockedIncrement( &pVolumeCB->VolumeReferenceCount);
- AFSReleaseResource( &pDevExt->Specific.RDR.VolumeTreeLock);
-
- AFSAcquireExcl( pVolumeCB->VolumeLock,
- TRUE);
+ AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSBuildMountPointTarget Increment count on volume %08lX Cnt %d\n",
+ pVolumeCB,
+ lCount);
- lCount = InterlockedDecrement( &pVolumeCB->VolumeReferenceCount);
+ AFSReleaseResource( &pDevExt->Specific.RDR.VolumeTreeLock);
}
if( pVolumeCB->RootFcb == NULL)
{
+ if ( bReleaseVolumeLock == FALSE)
+ {
+
+ AFSAcquireExcl( pVolumeCB->VolumeLock,
+ TRUE);
+
+ bReleaseVolumeLock = TRUE;
+ }
+
//
// Initialize the root fcb for this volume
//
if( !NT_SUCCESS( ntStatus))
{
+ lCount = InterlockedDecrement( &pVolumeCB->VolumeReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSBuildMountPoint Decrement count on volume %08lX Cnt %d\n",
+ pVolumeCB,
+ lCount);
+
AFSReleaseResource( pVolumeCB->VolumeLock);
try_return( ntStatus);
AFSReleaseResource( &pVolumeCB->RootFcb->NPFcb->Resource);
}
+ if ( bReleaseVolumeLock == TRUE)
+ {
+
+ AFSReleaseResource( pVolumeCB->VolumeLock);
+ }
+
AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
AFS_TRACE_LEVEL_VERBOSE_2,
"AFSBuildMountPointTarget Evaluated target of %wZ FID %08lX-%08lX-%08lX-%08lX as root volume\n",
pVolumeCB->ObjectInformation.FileId.Vnode,
pVolumeCB->ObjectInformation.FileId.Unique);
- lCount = InterlockedIncrement( &pVolumeCB->VolumeReferenceCount);
-
- AFSReleaseResource( pVolumeCB->VolumeLock);
-
- AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
- AFS_TRACE_LEVEL_VERBOSE,
- "AFSBuildMountPointTarget Increment count on volume %08lX Cnt %d\n",
- pVolumeCB,
- lCount);
-
*TargetVolumeCB = pVolumeCB;
try_exit:
if( pDirEntry)
{
- AFSExFreePool( pDirEntry);
+ AFSExFreePoolWithTag( pDirEntry, AFS_GENERIC_MEMORY_2_TAG);
}
}
ULONGLONG ullIndex = 0;
AFSVolumeCB *pVolumeCB = NULL;
LONG lCount;
+ BOOLEAN bReleaseVolumeLock = FALSE;
__Enter
{
//
AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
- AFS_TRACE_LEVEL_VERBOSE_2,
+ AFS_TRACE_LEVEL_VERBOSE_2,
"AFSBuildRootVolume Initializing root for FID %08lX-%08lX-%08lX-%08lX\n",
FileId->Cell,
FileId->Volume,
try_return( ntStatus);
}
+
+ //
+ // pVolumeCB->VolumeLock is held exclusive
+ // pVolumeCB->VolumeReferenceCount has been incremented
+ // pVolumeCB->RootFcb == NULL
+ //
+
+ bReleaseVolumeLock = TRUE;
}
else
{
//
- // Just to ensure that things don't get torn down AND we don't create a
- // deadlock with invalidation
+ // AFSInitVolume returns with a VolumeReferenceCount
+ // obtain one to match
//
lCount = InterlockedIncrement( &pVolumeCB->VolumeReferenceCount);
- AFSReleaseResource( &pDevExt->Specific.RDR.VolumeTreeLock);
-
- AFSAcquireExcl( pVolumeCB->VolumeLock,
- TRUE);
+ AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSBuildRootVolume Increment count on volume %08lX Cnt %d\n",
+ pVolumeCB,
+ lCount);
- lCount = InterlockedDecrement( &pVolumeCB->VolumeReferenceCount);
+ AFSReleaseResource( &pDevExt->Specific.RDR.VolumeTreeLock);
}
if( pVolumeCB->RootFcb == NULL)
{
+ if ( bReleaseVolumeLock == FALSE)
+ {
+
+ AFSAcquireExcl( pVolumeCB->VolumeLock,
+ TRUE);
+
+ bReleaseVolumeLock = TRUE;
+ }
+
//
// Initialize the root fcb for this volume
//
if( !NT_SUCCESS( ntStatus))
{
+ lCount = InterlockedDecrement( &pVolumeCB->VolumeReferenceCount);
+
+ AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
+ AFS_TRACE_LEVEL_VERBOSE,
+ "AFSBuildRootVolume Decrement count on volume %08lX Cnt %d\n",
+ pVolumeCB,
+ lCount);
+
AFSReleaseResource( pVolumeCB->VolumeLock);
try_return( ntStatus);
AFSReleaseResource( &pVolumeCB->RootFcb->NPFcb->Resource);
}
+ if ( bReleaseVolumeLock == TRUE)
+ {
+
+ AFSReleaseResource( pVolumeCB->VolumeLock);
+ }
+
AFSDbgLogMsg( AFS_SUBSYSTEM_FILE_PROCESSING,
AFS_TRACE_LEVEL_VERBOSE_2,
"AFSBuildRootVolume Evaluated target of %wZ FID %08lX-%08lX-%08lX-%08lX as root volume\n",
pVolumeCB->ObjectInformation.FileId.Vnode,
pVolumeCB->ObjectInformation.FileId.Unique);
- lCount = InterlockedIncrement( &pVolumeCB->VolumeReferenceCount);
-
- AFSReleaseResource( pVolumeCB->VolumeLock);
-
- AFSDbgLogMsg( AFS_SUBSYSTEM_VOLUME_REF_COUNTING,
- AFS_TRACE_LEVEL_VERBOSE,
- "AFSBuildRootVolume Increment count on volume %08lX Cnt %d\n",
- pVolumeCB,
- lCount);
-
*TargetVolumeCB = pVolumeCB;
try_exit:
NTSTATUS ntStatus = STATUS_INVALID_DEVICE_REQUEST;
UNICODE_STRING uniReparseName;
UNICODE_STRING uniMUPDeviceName;
+ UNICODE_STRING uniIOMgrDeviceName;
AFSDirEnumEntry *pDirEntry = NULL;
__Enter
RtlInitUnicodeString( &uniMUPDeviceName,
L"\\Device\\MUP");
+ RtlInitUnicodeString( &uniIOMgrDeviceName,
+ L"\\??\\");
+
uniReparseName.Length = 0;
uniReparseName.Buffer = NULL;
// Start building the name
//
- RtlCopyMemory( uniReparseName.Buffer,
- uniMUPDeviceName.Buffer,
- uniMUPDeviceName.Length);
+ if ( DirEntry->NameInformation.TargetName.Buffer[ 0] != L'\\' &&
+ DirEntry->NameInformation.TargetName.Buffer[ 1] == L':')
+ {
- uniReparseName.Length = uniMUPDeviceName.Length;
+ RtlCopyMemory( uniReparseName.Buffer,
+ uniIOMgrDeviceName.Buffer,
+ uniIOMgrDeviceName.Length);
- if( DirEntry->NameInformation.TargetName.Buffer[ 0] != L'\\')
+ uniReparseName.Length = uniIOMgrDeviceName.Length;
+ }
+ else
{
- uniReparseName.Buffer[ uniReparseName.Length/sizeof( WCHAR)] = L'\\';
+ RtlCopyMemory( uniReparseName.Buffer,
+ uniMUPDeviceName.Buffer,
+ uniMUPDeviceName.Length);
+
+ uniReparseName.Length = uniMUPDeviceName.Length;
+
+ if( DirEntry->NameInformation.TargetName.Buffer[ 0] != L'\\')
+ {
+
+ uniReparseName.Buffer[ uniReparseName.Length/sizeof( WCHAR)] = L'\\';
- uniReparseName.Length += sizeof( WCHAR);
+ uniReparseName.Length += sizeof( WCHAR);
+ }
}
RtlCopyMemory( &uniReparseName.Buffer[ uniReparseName.Length/sizeof( WCHAR)],
if( FileObject->FileName.Buffer != NULL)
{
- AFSExFreePool( FileObject->FileName.Buffer);
+ AFSExFreePoolWithTag( FileObject->FileName.Buffer, 0);
}
FileObject->FileName = uniReparseName;
if ( pDirEntry)
{
- AFSExFreePool( pDirEntry);
+ AFSExFreePoolWithTag( pDirEntry, AFS_GENERIC_MEMORY_2_TAG);
}
}