- Make ObpReleaseCapturedName an actual function and rename it to ObpFreeObjectNameBuffer. Fix a bug in this function which was causing it to attempt freeing the UNICODE_STRING structure instead of the actual buffer.

- Implement ObpAllocateObjectNameBuffer instead of inlined code in ObpCaptureObjectAttributes. Enable usage of the Name Buffer Lookaside List since the bug in ObpFreeObjectNameBuffer has now been fixed. This should result in significant speedup and less fragmentation of pool memory.
- Allocate object names in the paged pool instead of non-paged pool, if we can't use the lookaside list.

svn path=/trunk/; revision=25389
This commit is contained in:
Alex Ionescu 2007-01-08 21:02:22 +00:00
parent 00207351ec
commit 9de4aee541
7 changed files with 82 additions and 62 deletions

View file

@ -577,7 +577,7 @@ Cleanup:
ReleaseCapturedUnicodeString(&CapturedClass, ReleaseCapturedUnicodeString(&CapturedClass,
PreviousMode); PreviousMode);
} }
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
if (FreeRemainingPath) RtlFreeUnicodeString(&RemainingPath); if (FreeRemainingPath) RtlFreeUnicodeString(&RemainingPath);
//if (Object != NULL) ObDereferenceObject(Object); //if (Object != NULL) ObDereferenceObject(Object);
@ -1384,7 +1384,7 @@ NtOpenKey(OUT PHANDLE KeyHandle,
PostOpenKeyInfo.Status = Status; PostOpenKeyInfo.Status = Status;
CmiCallRegisteredCallbacks (RegNtPostOpenKey, &PostOpenKeyInfo); CmiCallRegisteredCallbacks (RegNtPostOpenKey, &PostOpenKeyInfo);
ObpReleaseCapturedAttributes(&ObjectCreateInfo); ObpReleaseCapturedAttributes(&ObjectCreateInfo);
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
return Status; return Status;
} }
@ -1436,7 +1436,7 @@ openkey_cleanup:
PostOpenKeyInfo.Object = NT_SUCCESS(Status) ? (PVOID)Object : NULL; PostOpenKeyInfo.Object = NT_SUCCESS(Status) ? (PVOID)Object : NULL;
PostOpenKeyInfo.Status = Status; PostOpenKeyInfo.Status = Status;
CmiCallRegisteredCallbacks (RegNtPostOpenKey, &PostOpenKeyInfo); CmiCallRegisteredCallbacks (RegNtPostOpenKey, &PostOpenKeyInfo);
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
if (Object) if (Object)
{ {

View file

@ -548,7 +548,7 @@ CmiConnectHive(IN POBJECT_ATTRIBUTES KeyObjectAttributes,
/* Yields a new reference */ /* Yields a new reference */
ObpReleaseCapturedAttributes(&ObjectCreateInfo); ObpReleaseCapturedAttributes(&ObjectCreateInfo);
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
return Status; return Status;

View file

@ -288,6 +288,12 @@ ObFreeObjectCreateInfoBuffer(
IN POBJECT_CREATE_INFORMATION ObjectCreateInfo IN POBJECT_CREATE_INFORMATION ObjectCreateInfo
); );
VOID
NTAPI
ObpFreeObjectNameBuffer(
IN PUNICODE_STRING Name
);
// //
// DOS Devices Functions // DOS Devices Functions
// //

View file

@ -130,7 +130,7 @@ ObpAllocateCapturedAttributes(IN PP_NPAGED_LOOKASIDE_NUMBER Type)
} }
VOID VOID
static __inline FORCEINLINE
ObpFreeCapturedAttributes(IN PVOID Buffer, ObpFreeCapturedAttributes(IN PVOID Buffer,
IN PP_NPAGED_LOOKASIDE_NUMBER Type) IN PP_NPAGED_LOOKASIDE_NUMBER Type)
{ {
@ -168,23 +168,7 @@ ObpFreeCapturedAttributes(IN PVOID Buffer,
} }
VOID VOID
static __inline FORCEINLINE
ObpReleaseCapturedName(IN PUNICODE_STRING Name)
{
/* We know this is a pool-allocation if the size doesn't match */
if (Name->MaximumLength != 248)
{
ExFreePool(Name->Buffer);
}
else
{
/* Otherwise, free from the lookaside */
ObpFreeCapturedAttributes(Name, LookasideNameBufferList);
}
}
VOID
static __inline
ObpFreeAndReleaseCapturedAttributes(IN POBJECT_CREATE_INFORMATION ObjectCreateInfo) ObpFreeAndReleaseCapturedAttributes(IN POBJECT_CREATE_INFORMATION ObjectCreateInfo)
{ {
/* First release the attributes, then free them from the lookaside list */ /* First release the attributes, then free them from the lookaside list */

View file

@ -2090,7 +2090,7 @@ Cleanup:
Quickie: Quickie:
/* Release the object attributes and temporary buffer */ /* Release the object attributes and temporary buffer */
ObpReleaseCapturedAttributes(&TempBuffer->ObjectCreateInfo); ObpReleaseCapturedAttributes(&TempBuffer->ObjectCreateInfo);
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
ExFreePool(TempBuffer); ExFreePool(TempBuffer);
/* Return status */ /* Return status */
@ -2673,9 +2673,7 @@ NTSTATUS
NTAPI NTAPI
NtClose(IN HANDLE Handle) NtClose(IN HANDLE Handle)
{ {
// /* Call the internal API */
// Call the internal API
//
return ObpCloseHandle(Handle, ExGetPreviousMode()); return ObpCloseHandle(Handle, ExGetPreviousMode());
} }

View file

@ -285,17 +285,70 @@ ObpSetPermanentObject(IN PVOID ObjectBody,
} }
} }
PWCHAR
NTAPI
ObpAllocateObjectNameBuffer(IN ULONG Length,
IN BOOLEAN UseLookaside,
IN OUT PUNICODE_STRING ObjectName)
{
ULONG MaximumLength;
PVOID Buffer;
/* Set the maximum length to the length plus the terminator */
MaximumLength = Length + sizeof(UNICODE_NULL);
/* Check if we should use the lookaside buffer */
if (!(UseLookaside) || (MaximumLength > 248))
{
/* Nope, allocate directly from pool */
Buffer = ExAllocatePoolWithTag(PagedPool,
MaximumLength,
OB_NAME_TAG);
}
else
{
/* Allocate from the lookaside */
//MaximumLength = 248; <= hack, we should actually set this...!
Buffer = ObpAllocateCapturedAttributes(LookasideNameBufferList);
}
/* Setup the string */
ObjectName->Length = (USHORT)Length;
ObjectName->MaximumLength = (USHORT)MaximumLength;
ObjectName->Buffer = Buffer;
return Buffer;
}
VOID
NTAPI
ObpFreeObjectNameBuffer(IN PUNICODE_STRING Name)
{
PVOID Buffer = Name->Buffer;
/* We know this is a pool-allocation if the size doesn't match */
if (Name->MaximumLength != 248)
{
/* Free it from the pool */
ExFreePool(Buffer);
}
else
{
/* Otherwise, free from the lookaside */
ObpFreeCapturedAttributes(Buffer, LookasideNameBufferList);
}
}
NTSTATUS NTSTATUS
NTAPI NTAPI
ObpCaptureObjectName(IN OUT PUNICODE_STRING CapturedName, ObpCaptureObjectName(IN OUT PUNICODE_STRING CapturedName,
IN PUNICODE_STRING ObjectName, IN PUNICODE_STRING ObjectName,
IN KPROCESSOR_MODE AccessMode, IN KPROCESSOR_MODE AccessMode,
IN BOOLEAN AllocateFromLookaside) IN BOOLEAN UseLookaside)
{ {
NTSTATUS Status = STATUS_SUCCESS; NTSTATUS Status = STATUS_SUCCESS;
ULONG StringLength, MaximumLength; ULONG StringLength;
PWCHAR StringBuffer = NULL; PWCHAR StringBuffer = NULL;
UNICODE_STRING LocalName = {0}; /* <= GCC 4.0 + Optimizer */ UNICODE_STRING LocalName;
PAGED_CODE(); PAGED_CODE();
/* Initialize the Input String */ /* Initialize the Input String */
@ -331,41 +384,20 @@ ObpCaptureObjectName(IN OUT PUNICODE_STRING CapturedName,
} }
else else
{ {
/* Set the maximum length to the length plus the terminator */ /* Allocate the string buffer */
MaximumLength = StringLength + sizeof(UNICODE_NULL); StringBuffer = ObpAllocateObjectNameBuffer(StringLength,
UseLookaside,
/* Check if we should use the lookaside buffer */ CapturedName);
//if (!(AllocateFromLookaside) || (MaximumLength > 248)) if (!StringBuffer)
{ {
/* Nope, allocate directly from pool */ /* Set failure code */
StringBuffer = ExAllocatePoolWithTag(NonPagedPool, Status = STATUS_INSUFFICIENT_RESOURCES;
MaximumLength,
OB_NAME_TAG);
}
//else
{
/* Allocate from the lookaside */
// MaximumLength = 248;
// StringBuffer =
// ObpAllocateCapturedAttributes(LookasideNameBufferList);
}
/* Setup the string */
CapturedName->Length = (USHORT)StringLength;
CapturedName->MaximumLength = (USHORT)MaximumLength;
CapturedName->Buffer = StringBuffer;
/* Make sure we have a buffer */
if (StringBuffer)
{
/* Copy the string and null-terminate it */
RtlMoveMemory(StringBuffer, LocalName.Buffer, StringLength);
StringBuffer[StringLength / sizeof(WCHAR)] = UNICODE_NULL;
} }
else else
{ {
/* Fail */ /* Copy the name */
Status = STATUS_INSUFFICIENT_RESOURCES; RtlMoveMemory(StringBuffer, LocalName.Buffer, StringLength);
StringBuffer[StringLength / sizeof(WCHAR)] = UNICODE_NULL;
} }
} }
} }
@ -875,7 +907,7 @@ ObCreateObject(IN KPROCESSOR_MODE ProbeMode OPTIONAL,
/* Release the Capture Info, we don't need it */ /* Release the Capture Info, we don't need it */
ObpReleaseCapturedAttributes(ObjectCreateInfo); ObpReleaseCapturedAttributes(ObjectCreateInfo);
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); if (ObjectName.Buffer) ObpFreeObjectNameBuffer(&ObjectName);
} }
/* We failed, so release the Buffer */ /* We failed, so release the Buffer */

View file

@ -454,7 +454,7 @@ ObReferenceObjectByName(IN PUNICODE_STRING ObjectPath,
Quickie: Quickie:
/* Free the captured name if we had one, and return status */ /* Free the captured name if we had one, and return status */
if (ObjectName.Buffer) ObpReleaseCapturedName(&ObjectName); ObpFreeObjectNameBuffer(&ObjectName);
return Status; return Status;
} }