Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
c5bb5182
Commit
c5bb5182
authored
Feb 15, 2005
by
Robert Shearman
Committed by
Alexandre Julliard
Feb 15, 2005
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Fix RPC server thread race.
parent
1912e889
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
44 additions
and
7 deletions
+44
-7
rpc_server.c
dlls/rpcrt4/rpc_server.c
+44
-7
No files found.
dlls/rpcrt4/rpc_server.c
View file @
c5bb5182
...
...
@@ -93,7 +93,14 @@ static CRITICAL_SECTION listen_cs = { &listen_cs_debug, -1, 0, 0, 0, 0 };
static
BOOL
std_listen
;
static
LONG
listen_count
=
-
1
;
static
HANDLE
mgr_event
,
server_thread
;
/* set on change of configuration (e.g. listening on new protseq) */
static
HANDLE
mgr_event
;
/* mutex for ensuring only one thread can change state at a time */
static
HANDLE
mgr_mutex
;
/* set when server thread has finished opening connections */
static
HANDLE
server_ready_event
;
/* thread that waits for connections */
static
HANDLE
server_thread
;
static
CRITICAL_SECTION
spacket_cs
;
static
CRITICAL_SECTION_DEBUG
spacket_cs_debug
=
...
...
@@ -451,6 +458,7 @@ static DWORD CALLBACK RPCRT4_server_thread(LPVOID the_arg)
RpcServerProtseq
*
cps
;
RpcConnection
*
conn
;
RpcConnection
*
cconn
;
BOOL
set_ready_event
=
FALSE
;
TRACE
(
"(the_arg == ^%p)
\n
"
,
the_arg
);
...
...
@@ -487,11 +495,22 @@ static DWORD CALLBACK RPCRT4_server_thread(LPVOID the_arg)
}
LeaveCriticalSection
(
&
server_cs
);
if
(
set_ready_event
)
{
/* signal to function that changed state that we are now sync'ed */
SetEvent
(
server_ready_event
);
set_ready_event
=
FALSE
;
}
/* start waiting */
res
=
WaitForMultipleObjects
(
count
,
objs
,
FALSE
,
INFINITE
);
if
(
res
==
WAIT_OBJECT_0
)
{
ResetEvent
(
m_event
);
if
(
!
std_listen
)
break
;
if
(
!
std_listen
)
{
SetEvent
(
server_ready_event
);
break
;
}
set_ready_event
=
TRUE
;
}
else
if
(
res
==
WAIT_FAILED
)
{
ERR
(
"wait failed
\n
"
);
...
...
@@ -536,13 +555,31 @@ static DWORD CALLBACK RPCRT4_server_thread(LPVOID the_arg)
return
0
;
}
/* tells the server thread that the state has changed and waits for it to
* make the changes */
static
void
RPCRT4_sync_with_server_thread
(
void
)
{
/* make sure we are the only thread sync'ing the server state, otherwise
* there is a race with the server thread setting an older state and setting
* the server_ready_event when the new state hasn't yet been applied */
WaitForSingleObject
(
mgr_mutex
,
INFINITE
);
SetEvent
(
mgr_event
);
/* wait for server thread to make the requested changes before returning */
WaitForSingleObject
(
server_ready_event
,
INFINITE
);
ReleaseMutex
(
mgr_mutex
);
}
static
void
RPCRT4_start_listen
(
void
)
{
TRACE
(
"
\n
"
);
EnterCriticalSection
(
&
listen_cs
);
if
(
!
++
listen_count
)
{
if
(
!
mgr_event
)
mgr_event
=
CreateEventW
(
NULL
,
TRUE
,
FALSE
,
NULL
);
if
(
!
mgr_mutex
)
mgr_mutex
=
CreateMutexW
(
NULL
,
FALSE
,
NULL
);
if
(
!
mgr_event
)
mgr_event
=
CreateEventW
(
NULL
,
FALSE
,
FALSE
,
NULL
);
if
(
!
server_ready_event
)
server_ready_event
=
CreateEventW
(
NULL
,
FALSE
,
FALSE
,
NULL
);
if
(
!
server_sem
)
server_sem
=
CreateSemaphoreW
(
NULL
,
0
,
MAX_THREADS
,
NULL
);
if
(
!
worker_tls
)
worker_tls
=
TlsAlloc
();
std_listen
=
TRUE
;
...
...
@@ -550,7 +587,7 @@ static void RPCRT4_start_listen(void)
LeaveCriticalSection
(
&
listen_cs
);
}
else
{
LeaveCriticalSection
(
&
listen_cs
);
SetEvent
(
mgr_event
);
RPCRT4_sync_with_server_thread
(
);
}
}
...
...
@@ -562,7 +599,7 @@ static void RPCRT4_stop_listen(void)
else
if
(
--
listen_count
==
-
1
)
{
std_listen
=
FALSE
;
LeaveCriticalSection
(
&
listen_cs
);
SetEvent
(
mgr_event
);
RPCRT4_sync_with_server_thread
(
);
}
else
LeaveCriticalSection
(
&
listen_cs
);
assert
(
listen_count
>
-
2
);
...
...
@@ -577,7 +614,7 @@ static RPC_STATUS RPCRT4_use_protseq(RpcServerProtseq* ps)
protseqs
=
ps
;
LeaveCriticalSection
(
&
server_cs
);
if
(
std_listen
)
SetEvent
(
mgr_event
);
if
(
std_listen
)
RPCRT4_sync_with_server_thread
(
);
return
RPC_S_OK
;
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment