mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 18:33:10 +00:00
- Add function documentation header to ObpDeleteHandle, comment and re-format the function, and simplify the code to reduce some code duplication.
- Call the OkayToClose Procedure, if one is present, to allow the object owner a chance to disallow closing this handle. I believe this is required for properly protecting Winsta/Desktop handles (instead of using the regular protection mode, since that one can be bypassed). Thomas, get to work! svn path=/trunk/; revision=22246
This commit is contained in:
parent
18ed42b8a4
commit
21baa4ddb6
2 changed files with 61 additions and 27 deletions
|
@ -230,7 +230,9 @@ typedef NTSTATUS
|
||||||
|
|
||||||
typedef NTSTATUS
|
typedef NTSTATUS
|
||||||
(NTAPI *OB_OKAYTOCLOSE_METHOD)(
|
(NTAPI *OB_OKAYTOCLOSE_METHOD)(
|
||||||
VOID
|
IN PEPROCESS Process OPTIONAL,
|
||||||
|
IN PVOID Object,
|
||||||
|
IN HANDLE Handle
|
||||||
);
|
);
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
|
@ -241,54 +241,86 @@ ObpDecrementHandleCount(IN PVOID ObjectBody,
|
||||||
ObjectType->TotalNumberOfHandles--;
|
ObjectType->TotalNumberOfHandles--;
|
||||||
}
|
}
|
||||||
|
|
||||||
static NTSTATUS
|
/*++
|
||||||
|
* @name ObpDeleteHandle
|
||||||
|
*
|
||||||
|
* The ObpDeleteHandle routine <FILLMEIN>
|
||||||
|
*
|
||||||
|
* @param Handle
|
||||||
|
* <FILLMEIN>.
|
||||||
|
*
|
||||||
|
* @return <FILLMEIN>.
|
||||||
|
*
|
||||||
|
* @remarks None.
|
||||||
|
*
|
||||||
|
*--*/
|
||||||
|
NTSTATUS
|
||||||
|
NTAPI
|
||||||
ObpDeleteHandle(HANDLE Handle)
|
ObpDeleteHandle(HANDLE Handle)
|
||||||
{
|
{
|
||||||
PHANDLE_TABLE_ENTRY HandleEntry;
|
PHANDLE_TABLE_ENTRY HandleEntry;
|
||||||
PVOID Body;
|
PVOID Body;
|
||||||
|
POBJECT_TYPE ObjectType;
|
||||||
POBJECT_HEADER ObjectHeader;
|
POBJECT_HEADER ObjectHeader;
|
||||||
PHANDLE_TABLE ObjectTable;
|
PHANDLE_TABLE ObjectTable;
|
||||||
ACCESS_MASK GrantedAccess;
|
ACCESS_MASK GrantedAccess;
|
||||||
|
NTSTATUS Status = STATUS_INVALID_HANDLE;
|
||||||
PAGED_CODE();
|
PAGED_CODE();
|
||||||
|
|
||||||
DPRINT("ObpDeleteHandle(Handle %p)\n",Handle);
|
/*
|
||||||
|
* Get the object table of the current process/
|
||||||
|
* NOTE: We might actually be attached to the system process
|
||||||
|
*/
|
||||||
ObjectTable = PsGetCurrentProcess()->ObjectTable;
|
ObjectTable = PsGetCurrentProcess()->ObjectTable;
|
||||||
|
|
||||||
|
/* Enter a critical region while touching the handle locks */
|
||||||
KeEnterCriticalRegion();
|
KeEnterCriticalRegion();
|
||||||
|
|
||||||
HandleEntry = ExMapHandleToPointer(ObjectTable,
|
/* Get the entry for this handle */
|
||||||
Handle);
|
HandleEntry = ExMapHandleToPointer(ObjectTable, Handle);
|
||||||
if(HandleEntry != NULL)
|
if(HandleEntry)
|
||||||
{
|
{
|
||||||
if(HandleEntry->ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE)
|
/* Get the object data */
|
||||||
{
|
|
||||||
ExUnlockHandleTableEntry(ObjectTable,
|
|
||||||
HandleEntry);
|
|
||||||
|
|
||||||
KeLeaveCriticalRegion();
|
|
||||||
|
|
||||||
return STATUS_HANDLE_NOT_CLOSABLE;
|
|
||||||
}
|
|
||||||
|
|
||||||
ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
|
ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
|
||||||
|
ObjectType = ObjectHeader->Type;
|
||||||
Body = &ObjectHeader->Body;
|
Body = &ObjectHeader->Body;
|
||||||
GrantedAccess = HandleEntry->GrantedAccess;
|
GrantedAccess = HandleEntry->GrantedAccess;
|
||||||
|
|
||||||
/* destroy and unlock the handle entry */
|
/* Check if the object has an Okay To Close procedure */
|
||||||
ExDestroyHandleByEntry(ObjectTable,
|
if (ObjectType->TypeInfo.OkayToCloseProcedure)
|
||||||
HandleEntry,
|
{
|
||||||
Handle);
|
/* Call it and check if it's not letting us close it */
|
||||||
|
if (!ObjectType->TypeInfo.OkayToCloseProcedure(PsGetCurrentProcess(),
|
||||||
ObpDecrementHandleCount(Body, PsGetCurrentProcess(), GrantedAccess);
|
Body,
|
||||||
|
Handle))
|
||||||
|
{
|
||||||
|
/* Fail */
|
||||||
|
ExUnlockHandleTableEntry(ObjectTable, HandleEntry);
|
||||||
KeLeaveCriticalRegion();
|
KeLeaveCriticalRegion();
|
||||||
|
return STATUS_HANDLE_NOT_CLOSABLE;
|
||||||
return STATUS_SUCCESS;
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The callback allowed us to close it, but does the handle itself? */
|
||||||
|
if(HandleEntry->ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE)
|
||||||
|
{
|
||||||
|
/* Fail */
|
||||||
|
ExUnlockHandleTableEntry(ObjectTable, HandleEntry);
|
||||||
KeLeaveCriticalRegion();
|
KeLeaveCriticalRegion();
|
||||||
return STATUS_INVALID_HANDLE;
|
return STATUS_HANDLE_NOT_CLOSABLE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Destroy and unlock the handle entry */
|
||||||
|
ExDestroyHandleByEntry(ObjectTable, HandleEntry, Handle);
|
||||||
|
|
||||||
|
/* Now decrement the handle count */
|
||||||
|
ObpDecrementHandleCount(Body, PsGetCurrentProcess(), GrantedAccess);
|
||||||
|
Status = STATUS_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Leave the critical region and return the status */
|
||||||
|
KeLeaveCriticalRegion();
|
||||||
|
return Status;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*++
|
/*++
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue