Details
Description
The deadlock I encountered was when one thread was calling iterate_all_connections and trying to call signalIfIdle on a connection. It runs through all of the threads by first locking the thread, then locking the global connection structure (to ensure that the connections won't go away) and inspects all connections and calls the callback if it is bound to the locked worker thread. If the callback calls signalIfIdle we try to update the event mask for the connection to make sure that it is scheduled again. This calls tries to lock the event base for the connection...
If that worker thread comes alive before the callback acquires the lock for the event base the worker thread will block trying to acquire the thread lock and we're in a deadlocked situation.
(This will also break even more if other worker threads try to accept / close other connections as the connection mutex is locked so they'll also wait on the deadlocked thread).
Suggestion: Refactor signalIfIdle to work the same way as notifyIoComplete (put it on the workerthreads list and tell the workerthread to process it).
Attachments
Issue Links
- backports to
-
MB-32687 BP [6.0.2]: Connection::signalIfIdle may cause a deadlock when used from a different thread
- Closed