Author: tfaber
Date: Mon Feb 16 13:17:04 2015
New Revision: 66316
URL: http://svn.reactos.org/svn/reactos?rev=66316&view=rev
Log:
[ROSAUTOTEST]
- Abstract unidirectional anonymous pipes into a CPipe class
- Abstract a process with redirected output into a CPipedProcess class
- Use these abstractions to avoid polling for output from test processes. Instead, use blocking read operations to yield the CPU while waiting for data.
ROSTESTS-144 #resolve
Added:
trunk/rostests/rosautotest/CPipe.cpp (with props)
trunk/rostests/rosautotest/CPipe.h (with props)
trunk/rostests/rosautotest/CPipedProcess.cpp (with props)
trunk/rostests/rosautotest/CPipedProcess.h (with props)
Modified:
trunk/rostests/rosautotest/CMakeLists.txt
trunk/rostests/rosautotest/CWineTest.cpp
trunk/rostests/rosautotest/CWineTest.h
trunk/rostests/rosautotest/precomp.h
Modified: trunk/rostests/rosautotest/CMakeLists.txt
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CMakeLists.tx…
==============================================================================
--- trunk/rostests/rosautotest/CMakeLists.txt [iso-8859-1] (original)
+++ trunk/rostests/rosautotest/CMakeLists.txt [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -6,6 +6,8 @@
CFatalException.cpp
CInvalidParameterException.cpp
CJournaledTestList.cpp
+ CPipe.cpp
+ CPipedProcess.cpp
CProcess.cpp
CSimpleException.cpp
CTest.cpp
Added: trunk/rostests/rosautotest/CPipe.cpp
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CPipe.cpp?rev…
==============================================================================
--- trunk/rostests/rosautotest/CPipe.cpp (added)
+++ trunk/rostests/rosautotest/CPipe.cpp [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -0,0 +1,143 @@
+/*
+ * PROJECT: ReactOS Automatic Testing Utility
+ * LICENSE: GNU GPLv2 or any later version as published by the Free Software Foundation
+ * PURPOSE: Class that managed an unidirectional anonymous byte stream pipe
+ * COPYRIGHT: Copyright 2015 Thomas Faber <thomas.faber(a)reactos.org>
+ */
+
+#include "precomp.h"
+
+/**
+ * Constructs a CPipe object and initializes read and write handles.
+ */
+CPipe::CPipe()
+{
+ SECURITY_ATTRIBUTES SecurityAttributes;
+
+ SecurityAttributes.nLength = sizeof(SecurityAttributes);
+ SecurityAttributes.bInheritHandle = TRUE;
+ SecurityAttributes.lpSecurityDescriptor = NULL;
+
+ if(!CreatePipe(&m_hReadPipe, &m_hWritePipe, &SecurityAttributes, 0))
+ FATAL("CreatePipe failed\n");
+}
+
+/**
+ * Destructs a CPipe object and closes all open handles.
+ */
+CPipe::~CPipe()
+{
+ if (m_hReadPipe)
+ CloseHandle(m_hReadPipe);
+ if (m_hWritePipe)
+ CloseHandle(m_hWritePipe);
+}
+
+/**
+ * Closes a CPipe's read pipe, leaving the write pipe unchanged.
+ */
+void
+CPipe::CloseReadPipe()
+{
+ if (!m_hReadPipe)
+ FATAL("Trying to close already closed read pipe");
+ CloseHandle(m_hReadPipe);
+}
+
+/**
+ * Closes a CPipe's write pipe, leaving the read pipe unchanged.
+ */
+void
+CPipe::CloseWritePipe()
+{
+ if (!m_hWritePipe)
+ FATAL("Trying to close already closed write pipe");
+ CloseHandle(m_hWritePipe);
+}
+
+/**
+ * Reads data from a pipe without advancing the read offset and/or retrieves information about available data.
+ *
+ * This function must not be called after CloseReadPipe.
+ *
+ * @param Buffer
+ * An optional buffer to read pipe data into.
+ *
+ * @param BufferSize
+ * The size of the buffer specified in Buffer, or 0 if no read should be performed.
+ *
+ * @param BytesRead
+ * On return, the number of bytes actually read from the pipe into Buffer.
+ *
+ * @param TotalBytesAvailable
+ * On return, the total number of bytes available to read from the pipe.
+ *
+ * @return
+ * True on success, false on failure; call GetLastError for error information.
+ *
+ * @see PeekNamedPipe
+ */
+bool
+CPipe::Peek(PVOID Buffer, DWORD BufferSize, PDWORD BytesRead, PDWORD TotalBytesAvailable)
+{
+ if (!m_hReadPipe)
+ FATAL("Trying to peek from a closed read pipe");
+
+ return PeekNamedPipe(m_hReadPipe, Buffer, BufferSize, BytesRead, TotalBytesAvailable, NULL);
+}
+
+/**
+ * Reads data from the read pipe, advancing the read offset accordingly.
+ *
+ * This function must not be called after CloseReadPipe.
+ *
+ * @param Buffer
+ * Buffer to read pipe data into.
+ *
+ * @param NumberOfBytesToRead
+ * The number of bytes to read into Buffer.
+ *
+ * @param NumberOfBytesRead
+ * On return, the number of bytes actually read from the pipe into Buffer.
+ *
+ * @return
+ * True on success, false on failure; call GetLastError for error information.
+ *
+ * @see ReadFile
+ */
+bool
+CPipe::Read(PVOID Buffer, DWORD NumberOfBytesToRead, PDWORD NumberOfBytesRead)
+{
+ if (!m_hReadPipe)
+ FATAL("Trying to read from a closed read pipe");
+
+ return ReadFile(m_hReadPipe, Buffer, NumberOfBytesToRead, NumberOfBytesRead, NULL);
+}
+
+/**
+ * Writes data to the write pipe.
+ *
+ * This function must not be called after CloseWritePipe.
+ *
+ * @param Buffer
+ * Buffer containing the data to write.
+ *
+ * @param NumberOfBytesToWrite
+ * The number of bytes to write to the pipe from Buffer.
+ *
+ * @param NumberOfBytesWritten
+ * On return, the number of bytes actually written to the pipe.
+ *
+ * @return
+ * True on success, false on failure; call GetLastError for error information.
+ *
+ * @see WriteFile
+ */
+bool
+CPipe::Write(LPCVOID Buffer, DWORD NumberOfBytesToWrite, PDWORD NumberOfBytesWritten)
+{
+ if (!m_hWritePipe)
+ FATAL("Trying to write to a closed write pipe");
+
+ return WriteFile(m_hWritePipe, Buffer, NumberOfBytesToWrite, NumberOfBytesWritten, NULL);
+}
Propchange: trunk/rostests/rosautotest/CPipe.cpp
------------------------------------------------------------------------------
svn:eol-style = native
Added: trunk/rostests/rosautotest/CPipe.h
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CPipe.h?rev=6…
==============================================================================
--- trunk/rostests/rosautotest/CPipe.h (added)
+++ trunk/rostests/rosautotest/CPipe.h [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -0,0 +1,26 @@
+/*
+ * PROJECT: ReactOS Automatic Testing Utility
+ * LICENSE: GNU GPLv2 or any later version as published by the Free Software Foundation
+ * PURPOSE: Class that managed an unidirectional anonymous byte stream pipe
+ * COPYRIGHT: Copyright 2015 Thomas Faber <thomas.faber(a)reactos.org>
+ */
+
+class CPipe
+{
+private:
+ HANDLE m_hReadPipe;
+ HANDLE m_hWritePipe;
+
+public:
+ CPipe();
+ ~CPipe();
+
+ void CloseReadPipe();
+ void CloseWritePipe();
+
+ bool Peek(PVOID Buffer, DWORD BufferSize, PDWORD BytesRead, PDWORD TotalBytesAvailable);
+ bool Read(PVOID Buffer, DWORD NumberOfBytesToRead, PDWORD NumberOfBytesRead);
+ bool Write(LPCVOID Buffer, DWORD NumberOfBytesToWrite, PDWORD NumberOfBytesWritten);
+
+ friend class CPipedProcess;
+};
Propchange: trunk/rostests/rosautotest/CPipe.h
------------------------------------------------------------------------------
svn:eol-style = native
Added: trunk/rostests/rosautotest/CPipedProcess.cpp
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CPipedProcess…
==============================================================================
--- trunk/rostests/rosautotest/CPipedProcess.cpp (added)
+++ trunk/rostests/rosautotest/CPipedProcess.cpp [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -0,0 +1,42 @@
+/*
+ * PROJECT: ReactOS Automatic Testing Utility
+ * LICENSE: GNU GPLv2 or any later version as published by the Free Software Foundation
+ * PURPOSE: Class that creates a process and redirects its output to a pipe
+ * COPYRIGHT: Copyright 2015 Thomas Faber <thomas.faber(a)reactos.org>
+ */
+
+#include "precomp.h"
+
+/**
+ * Constructs a CPipedProcess object and starts the process with redirected output.
+ *
+ * @param CommandLine
+ * A std::wstring containing the command line to run.
+ *
+ * @param Pipe
+ * The CPipe instance to redirect the process's output to.
+ * Note that only the read pipe is usable after the pipe was passed to this object.
+ */
+CPipedProcess::CPipedProcess(const wstring& CommandLine, CPipe& Pipe)
+ : CProcess(CommandLine, InitStartupInfo(Pipe))
+{
+ Pipe.CloseWritePipe();
+}
+
+/**
+ * Initializes the STARTUPINFO structure for use in CreateProcessW.
+ *
+ * @param Pipe
+ * The CPipe instance to redirect the process's output to.
+ */
+LPSTARTUPINFOW
+CPipedProcess::InitStartupInfo(CPipe& Pipe)
+{
+ ZeroMemory(&m_StartupInfo, sizeof(m_StartupInfo));
+ m_StartupInfo.cb = sizeof(m_StartupInfo);
+ m_StartupInfo.dwFlags = STARTF_USESTDHANDLES;
+ m_StartupInfo.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
+ m_StartupInfo.hStdOutput = Pipe.m_hWritePipe;
+ m_StartupInfo.hStdError = Pipe.m_hWritePipe;
+ return &m_StartupInfo;
+}
Propchange: trunk/rostests/rosautotest/CPipedProcess.cpp
------------------------------------------------------------------------------
svn:eol-style = native
Added: trunk/rostests/rosautotest/CPipedProcess.h
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CPipedProcess…
==============================================================================
--- trunk/rostests/rosautotest/CPipedProcess.h (added)
+++ trunk/rostests/rosautotest/CPipedProcess.h [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -0,0 +1,17 @@
+/*
+ * PROJECT: ReactOS Automatic Testing Utility
+ * LICENSE: GNU GPLv2 or any later version as published by the Free Software Foundation
+ * PURPOSE: Class that creates a process and redirects its output to a pipe
+ * COPYRIGHT: Copyright 2015 Thomas Faber <thomas.faber(a)reactos.org>
+ */
+
+class CPipedProcess : public CProcess
+{
+private:
+ STARTUPINFOW m_StartupInfo;
+
+ LPSTARTUPINFOW InitStartupInfo(CPipe& Pipe);
+
+public:
+ CPipedProcess(const wstring& CommandLine, CPipe& Pipe);
+};
Propchange: trunk/rostests/rosautotest/CPipedProcess.h
------------------------------------------------------------------------------
svn:eol-style = native
Modified: trunk/rostests/rosautotest/CWineTest.cpp
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CWineTest.cpp…
==============================================================================
--- trunk/rostests/rosautotest/CWineTest.cpp [iso-8859-1] (original)
+++ trunk/rostests/rosautotest/CWineTest.cpp [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -18,10 +18,7 @@
/* Zero-initialize variables */
m_hFind = NULL;
- m_hReadPipe = NULL;
- m_hWritePipe = NULL;
m_ListBuffer = NULL;
- memset(&m_StartupInfo, 0, sizeof(m_StartupInfo));
/* Set up m_TestPath */
if(!GetWindowsDirectoryW(WindowsDirectory, MAX_PATH))
@@ -38,12 +35,6 @@
{
if(m_hFind)
FindClose(m_hFind);
-
- if(m_hReadPipe)
- CloseHandle(m_hReadPipe);
-
- if(m_hWritePipe)
- CloseHandle(m_hWritePipe);
if(m_ListBuffer)
delete m_ListBuffer;
@@ -111,6 +102,7 @@
DWORD BytesAvailable;
DWORD Temp;
wstring CommandLine;
+ CPipe Pipe;
/* Build the command line */
CommandLine = m_TestPath;
@@ -119,7 +111,7 @@
{
/* Start the process for getting all available tests */
- CProcess Process(CommandLine, &m_StartupInfo);
+ CPipedProcess Process(CommandLine, Pipe);
/* Wait till this process ended */
if(WaitForSingleObject(Process.GetProcessHandle(), ListTimeout) == WAIT_FAILED)
@@ -127,8 +119,8 @@
}
/* Read the output data into a buffer */
- if(!PeekNamedPipe(m_hReadPipe, NULL, 0, NULL, &BytesAvailable, NULL))
- FATAL("PeekNamedPipe failed for the test list\n");
+ if(!Pipe.Peek(NULL, 0, NULL, &BytesAvailable))
+ FATAL("CPipe::Peek failed for the test list\n");
/* Check if we got any */
if(!BytesAvailable)
@@ -142,8 +134,8 @@
/* Read the data */
m_ListBuffer = new char[BytesAvailable];
- if(!ReadFile(m_hReadPipe, m_ListBuffer, BytesAvailable, &Temp, NULL))
- FATAL("ReadPipe failed\n");
+ if(!Pipe.Read(m_ListBuffer, BytesAvailable, &Temp))
+ FATAL("CPipe::Read failed\n");
return BytesAvailable;
}
@@ -260,13 +252,13 @@
void
CWineTest::RunTest(CTestInfo* TestInfo)
{
- bool BreakLoop = false;
DWORD BytesAvailable;
- DWORD Temp;
stringstream ss, ssFinish;
DWORD StartTime = GetTickCount();
float TotalTime;
string tailString;
+ CPipe Pipe;
+ char Buffer[1024];
ss << "Running Wine Test, Module: " << TestInfo->Module << ", Test: " << TestInfo->Test << endl;
StringOut(ss.str());
@@ -275,40 +267,20 @@
{
/* Execute the test */
- CProcess Process(TestInfo->CommandLine, &m_StartupInfo);
+ CPipedProcess Process(TestInfo->CommandLine, Pipe);
/* Receive all the data from the pipe */
- do
+ while(Pipe.Read(Buffer, sizeof(Buffer) - 1, &BytesAvailable) && BytesAvailable)
{
- /* When the application finished, make sure that we peek the pipe one more time, so that we get all data.
- If the following condition would be the while() condition, we might hit a race condition:
- - We check for data with PeekNamedPipe -> no data available
- - The application outputs its data and finishes
- - WaitForSingleObject reports that the application has finished and we break the loop without receiving any data
- */
- if(WaitForSingleObject(Process.GetProcessHandle(), 0) != WAIT_TIMEOUT)
- BreakLoop = true;
-
- if(!PeekNamedPipe(m_hReadPipe, NULL, 0, NULL, &BytesAvailable, NULL))
- FATAL("PeekNamedPipe failed for the test run\n");
-
- if(BytesAvailable)
- {
- /* There is data, so get it and output it */
- auto_array_ptr<char> Buffer(new char[BytesAvailable + 1]);
-
- if(!ReadFile(m_hReadPipe, Buffer, BytesAvailable, &Temp, NULL))
- FATAL("ReadFile failed for the test run\n");
-
- /* Output text through StringOut, even while the test is still running */
- Buffer[BytesAvailable] = 0;
- tailString = StringOut(tailString.append(string(Buffer)), false);
-
- if(Configuration.DoSubmit())
- TestInfo->Log += Buffer;
- }
+ /* Output text through StringOut, even while the test is still running */
+ Buffer[BytesAvailable] = 0;
+ tailString = StringOut(tailString.append(string(Buffer)), false);
+
+ if(Configuration.DoSubmit())
+ TestInfo->Log += Buffer;
}
- while(!BreakLoop);
+ if(GetLastError() != ERROR_BROKEN_PIPE)
+ FATAL("CPipe::Read failed for the test run\n");
}
/* Print what's left */
@@ -330,21 +302,6 @@
auto_ptr<CTestList> TestList;
auto_ptr<CWebService> WebService;
CTestInfo* TestInfo;
- SECURITY_ATTRIBUTES SecurityAttributes;
-
- /* Create a pipe for getting the output of the tests */
- SecurityAttributes.nLength = sizeof(SecurityAttributes);
- SecurityAttributes.bInheritHandle = TRUE;
- SecurityAttributes.lpSecurityDescriptor = NULL;
-
- if(!CreatePipe(&m_hReadPipe, &m_hWritePipe, &SecurityAttributes, 0))
- FATAL("CreatePipe failed\n");
-
- m_StartupInfo.cb = sizeof(m_StartupInfo);
- m_StartupInfo.dwFlags = STARTF_USESTDHANDLES;
- m_StartupInfo.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
- m_StartupInfo.hStdOutput = m_hWritePipe;
- m_StartupInfo.hStdError = m_hWritePipe;
/* The virtual test list is of course faster, so it should be preferred over
the journaled one.
Modified: trunk/rostests/rosautotest/CWineTest.h
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/CWineTest.h?r…
==============================================================================
--- trunk/rostests/rosautotest/CWineTest.h [iso-8859-1] (original)
+++ trunk/rostests/rosautotest/CWineTest.h [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -9,10 +9,7 @@
{
private:
HANDLE m_hFind;
- HANDLE m_hReadPipe;
- HANDLE m_hWritePipe;
PCHAR m_ListBuffer;
- STARTUPINFOW m_StartupInfo;
string m_CurrentTest;
wstring m_CurrentFile;
wstring m_CurrentListCommand;
Modified: trunk/rostests/rosautotest/precomp.h
URL: http://svn.reactos.org/svn/reactos/trunk/rostests/rosautotest/precomp.h?rev…
==============================================================================
--- trunk/rostests/rosautotest/precomp.h [iso-8859-1] (original)
+++ trunk/rostests/rosautotest/precomp.h [iso-8859-1] Mon Feb 16 13:17:04 2015
@@ -30,7 +30,9 @@
#include "CConfiguration.h"
#include "CFatalException.h"
#include "CInvalidParameterException.h"
+#include "CPipe.h"
#include "CProcess.h"
+#include "CPipedProcess.h"
#include "CSimpleException.h"
#include "CTestInfo.h"
#include "CTest.h"
Author: jimtabor
Date: Mon Feb 16 03:16:01 2015
New Revision: 66309
URL: http://svn.reactos.org/svn/reactos?rev=66309&view=rev
Log:
[NtUser]
- This fixes use after free linking in the message system. See CORE-9173. Dedicated to Thomas Faber.
Modified:
trunk/reactos/win32ss/user/ntuser/msgqueue.c
Modified: trunk/reactos/win32ss/user/ntuser/msgqueue.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/win32ss/user/ntuser/msgque…
==============================================================================
--- trunk/reactos/win32ss/user/ntuser/msgqueue.c [iso-8859-1] (original)
+++ trunk/reactos/win32ss/user/ntuser/msgqueue.c [iso-8859-1] Mon Feb 16 03:16:01 2015
@@ -789,8 +789,7 @@
/* insert it to the list of messages that are currently dispatched by this
message queue */
- InsertTailList(&pti->LocalDispatchingMessagesHead,
- &Message->ListEntry);
+ InsertTailList(&pti->LocalDispatchingMessagesHead, &Message->ListEntry);
ClearMsgBitsMask(pti, Message->QS_Flags);
@@ -866,7 +865,7 @@
}
/* remove the message from the dispatching list if needed, so lock the sender's message queue */
- if (Message->ptiSender)
+ if (Message->ptiSender && !(Message->ptiSender->TIF_flags & TIF_INCLEANUP))
{
if (Message->DispatchingListEntry.Flink != NULL)
{
@@ -953,8 +952,8 @@
ListHead = &pti->SentMessagesListHead;
while (CurrentEntry != ListHead)
{
- SentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE,
- ListEntry);
+ SentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE, ListEntry);
+
if(SentMessage->Msg.hwnd == Window->head.h)
{
TRACE("Notify the sender and remove a message from the queue that had not been dispatched\n");
@@ -1187,6 +1186,7 @@
Message->CompletionEvent = NULL;
Message->Result = NULL;
RemoveEntryList(&Message->ListEntry);
+ RemoveEntryList(&Message->DispatchingListEntry);
ClearMsgBitsMask(ptirec, Message->QS_Flags);
ExFreePoolWithTag(Message, TAG_USRMSG);
break;
@@ -1194,30 +1194,8 @@
Entry = Entry->Flink;
}
- /* Remove from the local dispatching list so the other thread knows,
- it can't pass a result and it must not set the completion event anymore */
- Entry = pti->DispatchingMessagesHead.Flink;
- while (Entry != &pti->DispatchingMessagesHead)
- {
- if ((PUSER_SENT_MESSAGE) CONTAINING_RECORD(Entry, USER_SENT_MESSAGE, DispatchingListEntry)
- == Message)
- {
- /* We can access Message here, it's secure because the sender's message is locked
- and the message has definitely not yet been destroyed, otherwise it would
- have been removed from this list by the dispatching routine right after
- dispatching the message */
- Message->CompletionEvent = NULL;
- Message->Result = NULL;
- RemoveEntryList(&Message->DispatchingListEntry);
- Message->DispatchingListEntry.Flink = NULL;
- break;
- }
- Entry = Entry->Flink;
- }
-
TRACE("MsqSendMessage (blocked) timed out 1 Status %p\n",WaitStatus);
-
- }
+ }
// Receiving thread passed on and left us hanging with issues still pending.
if ( WaitStatus == STATUS_WAIT_1 )
{
@@ -1272,29 +1250,9 @@
Message->CompletionEvent = NULL;
Message->Result = NULL;
RemoveEntryList(&Message->ListEntry);
+ RemoveEntryList(&Message->DispatchingListEntry);
ClearMsgBitsMask(ptirec, Message->QS_Flags);
ExFreePoolWithTag(Message, TAG_USRMSG);
- break;
- }
- Entry = Entry->Flink;
- }
-
- /* Remove from the local dispatching list so the other thread knows,
- it can't pass a result and it must not set the completion event anymore */
- Entry = pti->DispatchingMessagesHead.Flink;
- while (Entry != &pti->DispatchingMessagesHead)
- {
- if ((PUSER_SENT_MESSAGE) CONTAINING_RECORD(Entry, USER_SENT_MESSAGE, DispatchingListEntry)
- == Message)
- {
- /* We can access Message here, it's secure because the sender's message is locked
- and the message has definitely not yet been destroyed, otherwise it would
- have been removed from this list by the dispatching routine right after
- dispatching the message */
- Message->CompletionEvent = NULL;
- Message->Result = NULL;
- RemoveEntryList(&Message->DispatchingListEntry);
- Message->DispatchingListEntry.Flink = NULL;
break;
}
Entry = Entry->Flink;
@@ -1375,12 +1333,7 @@
MessageQueue = pti->MessageQueue;
- if (dwQEvent)
- {
- ERR("Post Msg; System Qeued Event Message!\n");
- InsertHeadList(&pti->PostedMessagesListHead, &Message->ListEntry);
- }
- else if (!HardwareMessage)
+ if (!HardwareMessage)
{
InsertTailList(&pti->PostedMessagesListHead, &Message->ListEntry);
}
@@ -2122,8 +2075,7 @@
while (!IsListEmpty(&pti->PostedMessagesListHead))
{
CurrentEntry = RemoveHeadList(&pti->PostedMessagesListHead);
- CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE,
- ListEntry);
+ CurrentMessage = CONTAINING_RECORD(CurrentEntry, USER_MESSAGE, ListEntry);
MsqDestroyMessage(CurrentMessage);
}
@@ -2131,8 +2083,7 @@
while (!IsListEmpty(&pti->SentMessagesListHead))
{
CurrentEntry = RemoveHeadList(&pti->SentMessagesListHead);
- CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE,
- ListEntry);
+ CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE, ListEntry);
TRACE("Notify the sender and remove a message from the queue that had not been dispatched\n");
/* Only if the message has a sender was the message in the DispatchingList */
@@ -2163,8 +2114,7 @@
while (!IsListEmpty(&pti->LocalDispatchingMessagesHead))
{
CurrentEntry = RemoveHeadList(&pti->LocalDispatchingMessagesHead);
- CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE,
- ListEntry);
+ CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE, ListEntry);
/* remove the message from the dispatching list */
if(CurrentSentMessage->DispatchingListEntry.Flink != NULL)
@@ -2194,8 +2144,7 @@
while (! IsListEmpty(&pti->DispatchingMessagesHead))
{
CurrentEntry = RemoveHeadList(&pti->DispatchingMessagesHead);
- CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE,
- DispatchingListEntry);
+ CurrentSentMessage = CONTAINING_RECORD(CurrentEntry, USER_SENT_MESSAGE, DispatchingListEntry);
CurrentSentMessage->CompletionEvent = NULL;
CurrentSentMessage->Result = NULL;