Author: cgutman Date: Sun Oct 16 22:21:41 2011 New Revision: 54167
URL: http://svn.reactos.org/svn/reactos?rev=54167&view=rev Log: [TCPIP] - Prevent corruption of the search context list using a combination of references and broader spin lock usage - Fixes bug 6506
Modified: trunk/reactos/drivers/network/tcpip/tcpip/fileobjs.c
Modified: trunk/reactos/drivers/network/tcpip/tcpip/fileobjs.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/network/tcpip/tcpip... ============================================================================== --- trunk/reactos/drivers/network/tcpip/tcpip/fileobjs.c [iso-8859-1] (original) +++ trunk/reactos/drivers/network/tcpip/tcpip/fileobjs.c [iso-8859-1] Sun Oct 16 22:21:41 2011 @@ -35,10 +35,20 @@ USHORT Protocol, PAF_SEARCH SearchContext) { + KIRQL OldIrql; + SearchContext->Address = Address; SearchContext->Port = Port; - SearchContext->Next = AddressFileListHead.Flink; SearchContext->Protocol = Protocol; + + TcpipAcquireSpinLock(&AddressFileListLock, &OldIrql); + + SearchContext->Next = AddressFileListHead.Flink; + + if (!IsListEmpty(&AddressFileListHead)) + ReferenceObject(CONTAINING_RECORD(SearchContext->Next, ADDRESS_FILE, ListEntry)); + + TcpipReleaseSpinLock(&AddressFileListLock, OldIrql);
return AddrSearchNext(SearchContext); } @@ -104,13 +114,19 @@ KIRQL OldIrql; PADDRESS_FILE Current = NULL; BOOLEAN Found = FALSE; - - if (IsListEmpty(SearchContext->Next)) + + TcpipAcquireSpinLock(&AddressFileListLock, &OldIrql); + + if (SearchContext->Next == &AddressFileListHead) + { + TcpipReleaseSpinLock(&AddressFileListLock, OldIrql); return NULL; + } + + /* Remove the extra reference we added to keep this address file in memory */ + DereferenceObject(CONTAINING_RECORD(SearchContext->Next, ADDRESS_FILE, ListEntry));
CurrentEntry = SearchContext->Next; - - TcpipAcquireSpinLock(&AddressFileListLock, &OldIrql);
while (CurrentEntry != &AddressFileListHead) { Current = CONTAINING_RECORD(CurrentEntry, ADDRESS_FILE, ListEntry); @@ -136,13 +152,22 @@ CurrentEntry = CurrentEntry->Flink; }
+ if (Found) + { + SearchContext->Next = CurrentEntry->Flink; + + if (SearchContext->Next != &AddressFileListHead) + { + /* Reference the next address file to prevent the link from disappearing behind our back */ + ReferenceObject(CONTAINING_RECORD(SearchContext->Next, ADDRESS_FILE, ListEntry)); + } + } + else + Current = NULL; + TcpipReleaseSpinLock(&AddressFileListLock, OldIrql);
- if (Found) { - SearchContext->Next = CurrentEntry->Flink; - return Current; - } else - return NULL; + return Current; }
VOID AddrFileFree(