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/tcpi…
==============================================================================
--- 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(