From: Anton Baskanov baskanov@gmail.com
--- dlls/dpwsockx/dpwsockx_dll.h | 2 ++ dlls/dpwsockx/dpwsockx_main.c | 46 +++++++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+)
diff --git a/dlls/dpwsockx/dpwsockx_dll.h b/dlls/dpwsockx/dpwsockx_dll.h index 477adb86fcd..db0445a845b 100644 --- a/dlls/dpwsockx/dpwsockx_dll.h +++ b/dlls/dpwsockx/dpwsockx_dll.h @@ -43,6 +43,8 @@ typedef struct tagDPWS_DATA SOCKADDR_IN tcpAddr;
BOOL started; + HANDLE thread; + WSAEVENT stopEvent; } DPWS_DATA, *LPDPWS_DATA;
#include "pshpack1.h" diff --git a/dlls/dpwsockx/dpwsockx_main.c b/dlls/dpwsockx/dpwsockx_main.c index 4a969b1711e..1a3e3257569 100644 --- a/dlls/dpwsockx/dpwsockx_main.c +++ b/dlls/dpwsockx/dpwsockx_main.c @@ -60,6 +60,30 @@ static HRESULT DPWS_BindToFreePort( SOCKET sock, SOCKADDR_IN *addr, int startPor return DPERR_UNAVAILABLE; }
+static DWORD WINAPI DPWS_ThreadProc( void *param ) +{ + DPWS_DATA *dpwsData = (DPWS_DATA *)param; + + SetThreadDescription( GetCurrentThread(), L"dpwsockx" ); + + for ( ;; ) + { + DWORD waitResult; + waitResult = WSAWaitForMultipleEvents( 1, &dpwsData->stopEvent, FALSE, WSA_INFINITE, TRUE ); + if ( waitResult == WSA_WAIT_FAILED ) + { + ERR( "WSAWaitForMultipleEvents() failed\n" ); + break; + } + if ( waitResult == WSA_WAIT_IO_COMPLETION ) + continue; + if ( waitResult == WSA_WAIT_EVENT_0 ) + break; + } + + return 0; +} + static HRESULT DPWS_Start( DPWS_DATA *dpwsData ) { HRESULT hr; @@ -89,6 +113,23 @@ static HRESULT DPWS_Start( DPWS_DATA *dpwsData ) return DPERR_UNAVAILABLE; }
+ dpwsData->stopEvent = WSACreateEvent(); + if ( !dpwsData->stopEvent ) + { + ERR( "WSACreateEvent() failed\n" ); + closesocket( dpwsData->tcpSock ); + return DPERR_UNAVAILABLE; + } + + dpwsData->thread = CreateThread( NULL, 0, DPWS_ThreadProc, dpwsData, 0, NULL ); + if ( !dpwsData->thread ) + { + ERR( "CreateThread() failed\n" ); + WSACloseEvent( dpwsData->stopEvent ); + closesocket( dpwsData->tcpSock ); + return DPERR_UNAVAILABLE; + } + dpwsData->started = TRUE;
return S_OK; @@ -101,6 +142,11 @@ static void DPWS_Stop( DPWS_DATA *dpwsData )
dpwsData->started = FALSE;
+ WSASetEvent( dpwsData->stopEvent ); + WaitForSingleObject( dpwsData->thread, INFINITE ); + CloseHandle( dpwsData->thread ); + + WSACloseEvent( dpwsData->stopEvent ); closesocket( dpwsData->tcpSock ); }