Fix possibly fatal race condition when calling OnDelete()
This function could be called on an already deleted object, which could result in a crash, and always resulted in a TSAN error. Fix this by calling it before releasing the internal lock, which prevents this from happening, but will result in a deadlock if this function is overridden to do something requiring any lock held by the thread. This is not ideal, but still seems to be like a lesser evil.
This commit is contained in:
parent
345b8ff505
commit
59312f5ba0
2 changed files with 12 additions and 4 deletions
|
|
@ -486,8 +486,10 @@ public:
|
|||
will be executed in the context of the thread that called Delete() and
|
||||
<b>not</b> in this thread's context.
|
||||
|
||||
TestDestroy() will be true for the thread before OnDelete() gets
|
||||
executed.
|
||||
Note that TestDestroy() will block until OnDelete() returns, so this
|
||||
function should return as quickly as possible and definitely shouldn't
|
||||
perform any GUI actions nor try acquiring any locks, as this could
|
||||
easily result in a deadlock.
|
||||
|
||||
@since 2.9.2
|
||||
|
||||
|
|
|
|||
|
|
@ -1575,10 +1575,16 @@ wxThreadError wxThread::Delete(ExitCode *rc, wxThreadWait WXUNUSED(waitMode))
|
|||
// ask the thread to stop
|
||||
m_internal->SetCancelFlag();
|
||||
|
||||
m_critsect.Leave();
|
||||
|
||||
// Normally we should never call out while holding the lock (on m_critsect
|
||||
// in this case), but we can't do it later because as soon as we unlock it,
|
||||
// this object may be destroyed as the thread executing its Entry() may
|
||||
// call TestDestroy() and decide to exit at any moment, so we have to do it
|
||||
// now and hope that OnDelete() doesn't do anything stupid (or, preferably,
|
||||
// anything at all).
|
||||
OnDelete();
|
||||
|
||||
m_critsect.Leave();
|
||||
|
||||
switch ( state )
|
||||
{
|
||||
case STATE_NEW:
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue