implemented sweeping of handle tables Modified: trunk/reactos/ntoskrnl/ex/handle.c Modified: trunk/reactos/ntoskrnl/include/internal/ex.h Modified: trunk/reactos/ntoskrnl/ob/handle.c Modified: trunk/reactos/ntoskrnl/rtl/libsupp.c _____
Modified: trunk/reactos/ntoskrnl/ex/handle.c --- trunk/reactos/ntoskrnl/ex/handle.c 2005-12-07 16:50:17 UTC (rev 19950) +++ trunk/reactos/ntoskrnl/ex/handle.c 2005-12-07 17:06:48 UTC (rev 19951) @@ -11,7 +11,6 @@
* * - the last entry of a subhandle list should be reserved for auditing * - * ExSweepHandleTable (???) * ExReferenceHandleDebugInfo * ExSnapShotHandleTables * ExpMoveFreeHandles (???) @@ -163,63 +162,12 @@ return HandleTable; }
-static BOOLEAN -ExLockHandleTableEntryNoDestructionCheck(IN PHANDLE_TABLE HandleTable, - IN PHANDLE_TABLE_ENTRY Entry) -{ - ULONG_PTR Current, New; - - PAGED_CODE(); - - DPRINT("Entering handle table entry 0x%p lock...\n", Entry); - - ASSERT(HandleTable); - ASSERT(Entry); - - for(;;) - { - Current = (volatile ULONG_PTR)Entry->u1.Object; - - if(!Current) - { - DPRINT("Attempted to lock empty handle table entry 0x%p or handle table shut down\n", Entry); - break; - } - - if(!(Current & EX_HANDLE_ENTRY_LOCKED)) - { - New = Current | EX_HANDLE_ENTRY_LOCKED; - if(InterlockedCompareExchangePointer(&Entry->u1.Object, - (PVOID)New, - (PVOID)Current) == (PVOID)Current) - { - DPRINT("SUCCESS handle table 0x%p entry 0x%p lock\n", HandleTable, Entry); - /* we acquired the lock */ - return TRUE; - } - } - - /* wait about 5ms at maximum so we don't wait forever in unfortunate - co-incidences where releasing the lock in another thread happens right - before we're waiting on the contention event to get pulsed, which might - never happen again... */ - KeWaitForSingleObject(&HandleTable->HandleContentionEvent, - Executive, - KernelMode, - FALSE, - &ExpHandleShortWait); - } - - return FALSE; -} - VOID -ExDestroyHandleTable(IN PHANDLE_TABLE HandleTable, - IN PEX_DESTROY_HANDLE_CALLBACK DestroyHandleCallback OPTIONAL, - IN PVOID Context OPTIONAL) +ExSweepHandleTable(IN PHANDLE_TABLE HandleTable, + IN PEX_SWEEP_HANDLE_CALLBACK SweepHandleCallback OPTIONAL, + IN PVOID Context OPTIONAL) { PHANDLE_TABLE_ENTRY **tlp, **lasttlp, *mlp, *lastmlp; - PEPROCESS QuotaProcess;
PAGED_CODE();
@@ -238,38 +186,30 @@ EVENT_INCREMENT, FALSE);
- /* remove the handle table from the global handle table list */ - ExAcquireHandleTableListLock(); - RemoveEntryList(&HandleTable->HandleTableList); - ExReleaseHandleTableListLock(); - /* call the callback function to cleanup the objects associated with the handle table */ - if(DestroyHandleCallback != NULL) + for(tlp = HandleTable->Table, lasttlp = HandleTable->Table + N_TOPLEVEL_POINTERS; + tlp != lasttlp; + tlp++) { - for(tlp = HandleTable->Table, lasttlp = HandleTable->Table + N_TOPLEVEL_POINTERS; - tlp != lasttlp; - tlp++) + if((*tlp) != NULL) { - if((*tlp) != NULL) + for(mlp = *tlp, lastmlp = (*tlp) + N_MIDDLELEVEL_POINTERS; + mlp != lastmlp; + mlp++) { - for(mlp = *tlp, lastmlp = (*tlp) + N_MIDDLELEVEL_POINTERS; - mlp != lastmlp; - mlp++) + if((*mlp) != NULL) { - if((*mlp) != NULL) - { - PHANDLE_TABLE_ENTRY curee, laste; + PHANDLE_TABLE_ENTRY curee, laste;
- for(curee = *mlp, laste = *mlp + N_SUBHANDLE_ENTRIES; - curee != laste; - curee++) + for(curee = *mlp, laste = *mlp + N_SUBHANDLE_ENTRIES; + curee != laste; + curee++) + { + if(curee->u1.Object != NULL && SweepHandleCallback != NULL) { - if(curee->u1.Object != NULL && ExLockHandleTableEntryNoDestructionCheck(HandleTable, curee)) - { - DestroyHandleCallback(HandleTable, curee->u1.Object, curee->u2.GrantedAccess, Context); - ExUnlockHandleTableEntry(HandleTable, curee); - } + curee->u1.ObAttributes |= EX_HANDLE_ENTRY_LOCKED; + SweepHandleCallback(HandleTable, curee->u1.Object, curee->u2.GrantedAccess, Context); } } } @@ -277,6 +217,34 @@ } }
+ ExReleaseHandleTableLock(HandleTable); + + KeLeaveCriticalRegion(); +} + +VOID +ExDestroyHandleTable(IN PHANDLE_TABLE HandleTable) +{ + PHANDLE_TABLE_ENTRY **tlp, **lasttlp, *mlp, *lastmlp; + PEPROCESS QuotaProcess; + + PAGED_CODE(); + + ASSERT(HandleTable); + ASSERT(HandleTable->Flags & EX_HANDLE_TABLE_CLOSING); + + KeEnterCriticalRegion(); + + /* at this point the table should not be queried or altered anymore, + no locks should be necessary */ + + ASSERT(HandleTable->Flags & EX_HANDLE_TABLE_CLOSING); + + /* remove the handle table from the global handle table list */ + ExAcquireHandleTableListLock(); + RemoveEntryList(&HandleTable->HandleTableList); + ExReleaseHandleTableListLock(); + QuotaProcess = HandleTable->QuotaProcess;
/* free the tables */ @@ -310,8 +278,6 @@ } }
- ExReleaseHandleTableLock(HandleTable); - KeLeaveCriticalRegion();
/* free the handle table */ @@ -408,9 +374,7 @@
ExReleaseHandleTableLock(SourceHandleTable);
- ExDestroyHandleTable(HandleTable, - NULL, - NULL); + ExDestroyHandleTable(HandleTable); /* allocate an empty handle table */ return ExCreateHandleTable(QuotaProcess); } _____
Modified: trunk/reactos/ntoskrnl/include/internal/ex.h --- trunk/reactos/ntoskrnl/include/internal/ex.h 2005-12-07 16:50:17 UTC (rev 19950) +++ trunk/reactos/ntoskrnl/include/internal/ex.h 2005-12-07 17:06:48 UTC (rev 19951) @@ -91,7 +91,7 @@
EX_HANDLE_ENTRY_INHERITABLE | \ EX_HANDLE_ENTRY_AUDITONCLOSE)
-typedef VOID (STDCALL PEX_DESTROY_HANDLE_CALLBACK)( +typedef VOID (STDCALL PEX_SWEEP_HANDLE_CALLBACK)( PHANDLE_TABLE HandleTable, PVOID Object, ULONG GrantedAccess, @@ -118,8 +118,13 @@
VOID ExDestroyHandleTable( + IN PHANDLE_TABLE HandleTable +); + +VOID +ExSweepHandleTable( IN PHANDLE_TABLE HandleTable, - IN PEX_DESTROY_HANDLE_CALLBACK DestroyHandleCallback OPTIONAL, + IN PEX_SWEEP_HANDLE_CALLBACK SweepHandleCallback OPTIONAL, IN PVOID Context OPTIONAL );
_____
Modified: trunk/reactos/ntoskrnl/ob/handle.c --- trunk/reactos/ntoskrnl/ob/handle.c 2005-12-07 16:50:17 UTC (rev 19950) +++ trunk/reactos/ntoskrnl/ob/handle.c 2005-12-07 17:06:48 UTC (rev 19951) @@ -504,10 +504,10 @@
}
static VOID STDCALL -DeleteHandleCallback(PHANDLE_TABLE HandleTable, - PVOID Object, - ULONG GrantedAccess, - PVOID Context) +SweepHandleCallback(PHANDLE_TABLE HandleTable, + PVOID Object, + ULONG GrantedAccess, + PVOID Context) { POBJECT_HEADER ObjectHeader; PVOID ObjectBody; @@ -580,9 +580,12 @@ { PAGED_CODE();
- ExDestroyHandleTable(Process->ObjectTable, - DeleteHandleCallback, - Process); + /* FIXME - Temporary hack: sweep and destroy here, needs to be fixed!!! */ + ExSweepHandleTable(Process->ObjectTable, + SweepHandleCallback, + Process); + ExDestroyHandleTable(Process->ObjectTable); + Process->ObjectTable = NULL; }
_____
Modified: trunk/reactos/ntoskrnl/rtl/libsupp.c --- trunk/reactos/ntoskrnl/rtl/libsupp.c 2005-12-07 16:50:17 UTC (rev 19950) +++ trunk/reactos/ntoskrnl/rtl/libsupp.c 2005-12-07 17:06:48 UTC (rev 19951) @@ -225,23 +225,15 @@
return (AtomTable->ExHandleTable != NULL); }
-static VOID STDCALL -AtomDeleteHandleCallback(PHANDLE_TABLE HandleTable, - PVOID Object, - ULONG GrantedAccess, - PVOID Context) -{ - return; -} - VOID RtlpDestroyAtomHandleTable(PRTL_ATOM_TABLE AtomTable) { if (AtomTable->ExHandleTable) { - ExDestroyHandleTable(AtomTable->ExHandleTable, - AtomDeleteHandleCallback, - AtomTable); + ExSweepHandleTable(AtomTable->ExHandleTable, + NULL, + NULL); + ExDestroyHandleTable(AtomTable->ExHandleTable); AtomTable->ExHandleTable = NULL; } }