Module: wine Branch: master Commit: 09e98be24350a7a8306cc6cd7302f94eae770afc URL: http://source.winehq.org/git/wine.git/?a=commit;h=09e98be24350a7a8306cc6cd73...
Author: Jacek Caban jacek@codeweavers.com Date: Wed May 31 17:30:52 2017 +0200
rpcrt4: Wait for server threads to finish in RpcMgmtWaitServerListen.
This fixes races when stopping manual listen RPC servers. It should fix races in Office applications as well as our services.exe (visible as CS error on prefix shutdown).
Signed-off-by: Jacek Caban jacek@codeweavers.com Signed-off-by: Alexandre Julliard julliard@winehq.org
---
dlls/rpcrt4/rpc_server.c | 25 ++++++++++++++++++++++++- 1 file changed, 24 insertions(+), 1 deletion(-)
diff --git a/dlls/rpcrt4/rpc_server.c b/dlls/rpcrt4/rpc_server.c index bd47de6..c350c59 100644 --- a/dlls/rpcrt4/rpc_server.c +++ b/dlls/rpcrt4/rpc_server.c @@ -1542,7 +1542,8 @@ RPC_STATUS WINAPI RpcServerListen( UINT MinimumCallThreads, UINT MaxCalls, UINT */ RPC_STATUS WINAPI RpcMgmtWaitServerListen( void ) { - HANDLE event; + RpcServerProtseq *protseq; + HANDLE event, wait_thread;
TRACE("()\n");
@@ -1558,6 +1559,28 @@ RPC_STATUS WINAPI RpcMgmtWaitServerListen( void ) TRACE( "done waiting\n" );
EnterCriticalSection(&listen_cs); + /* wait for server threads to finish */ + while(1) + { + if (listen_count) + break; + + wait_thread = NULL; + EnterCriticalSection(&server_cs); + LIST_FOR_EACH_ENTRY(protseq, &protseqs, RpcServerProtseq, entry) + { + if ((wait_thread = protseq->server_thread)) + break; + } + LeaveCriticalSection(&server_cs); + if (!wait_thread) + break; + + TRACE("waiting for thread %u\n", GetThreadId(wait_thread)); + LeaveCriticalSection(&listen_cs); + WaitForSingleObject(wait_thread, INFINITE); + EnterCriticalSection(&listen_cs); + } if (listen_done_event == event) { listen_done_event = NULL;