Bug 552294: *Channel::OnError must run atomically. r=bent

This commit is contained in:
Chris Jones 2010-03-18 17:52:28 -05:00
parent 43b6710a53
commit cfe012af2f
4 changed files with 23 additions and 23 deletions

View File

@ -444,11 +444,18 @@ AsyncChannel::OnChannelError()
MutexAutoLock lock(mMutex);
// NB: this can race with the `Goodbye' event being processed by
// the worker thread
if (ChannelClosing != mChannelState)
mChannelState = ChannelError;
PostErrorNotifyTask();
}
void
AsyncChannel::PostErrorNotifyTask()
{
AssertIOThread();
mMutex.AssertCurrentThreadOwns();
NS_ASSERTION(!mChannelErrorTask, "OnChannelError called twice?");
// This must be the last code that runs on this thread!

View File

@ -175,6 +175,7 @@ protected:
void OnChannelOpened();
void OnSend(Message* aMsg);
void OnCloseChannel();
void PostErrorNotifyTask();
// Return true if |msg| is a special message targeted at the IO
// thread, in which case it shouldn't be delivered to the worker.

View File

@ -654,20 +654,16 @@ RPCChannel::OnChannelError()
{
AssertIOThread();
{
MutexAutoLock lock(mMutex);
MutexAutoLock lock(mMutex);
// NB: this can race with the `Goodbye' event being processed by
// the worker thread
if (ChannelClosing != mChannelState)
mChannelState = ChannelError;
if (ChannelClosing != mChannelState)
mChannelState = ChannelError;
// skip SyncChannel::OnError(); we subsume its duties
if (AwaitingSyncReply() || 0 < StackDepth())
NotifyWorkerThread();
}
// skip SyncChannel::OnError(); we subsume its duties
if (AwaitingSyncReply() || 0 < StackDepth())
NotifyWorkerThread();
AsyncChannel::OnChannelError();
PostErrorNotifyTask();
}
} // namespace ipc

View File

@ -213,19 +213,15 @@ SyncChannel::OnChannelError()
{
AssertIOThread();
{
MutexAutoLock lock(mMutex);
MutexAutoLock lock(mMutex);
// NB: this can race with the `Goodbye' event being processed by
// the worker thread
if (ChannelClosing != mChannelState)
mChannelState = ChannelError;
if (ChannelClosing != mChannelState)
mChannelState = ChannelError;
if (AwaitingSyncReply())
NotifyWorkerThread();
}
if (AwaitingSyncReply())
NotifyWorkerThread();
AsyncChannel::OnChannelError();
PostErrorNotifyTask();
}
//