зеркало из https://github.com/mozilla/gecko-dev.git
Bug 540886, part 1: Refactor "special message" dispatch in AsyncChannel. r=bent
--HG-- extra : transplant_source : %81%F6%01%EB%0CE%B0%04R%02%A8%0B%F8c%EF/%1D%CC%3Ep
This commit is contained in:
Родитель
40ab77cad5
Коммит
162bed2213
|
@ -54,6 +54,32 @@ struct RunnableMethodTraits<mozilla::ipc::AsyncChannel>
|
|||
static void ReleaseCallee(mozilla::ipc::AsyncChannel* obj) { }
|
||||
};
|
||||
|
||||
namespace {
|
||||
|
||||
// This is an async message
|
||||
class GoodbyeMessage : public IPC::Message
|
||||
{
|
||||
public:
|
||||
enum { ID = GOODBYE_MESSAGE_TYPE };
|
||||
GoodbyeMessage() :
|
||||
IPC::Message(MSG_ROUTING_NONE, ID, PRIORITY_NORMAL)
|
||||
{
|
||||
}
|
||||
// XXX not much point in implementing this; maybe could help with
|
||||
// debugging?
|
||||
static bool Read(const Message* msg)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
void Log(const std::string& aPrefix,
|
||||
FILE* aOutf) const
|
||||
{
|
||||
fputs("(special `Goodbye' message)", aOutf);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace <anon>
|
||||
|
||||
namespace mozilla {
|
||||
namespace ipc {
|
||||
|
||||
|
@ -150,7 +176,7 @@ AsyncChannel::Close()
|
|||
AssertWorkerThread();
|
||||
|
||||
// notify the other side that we're about to close our socket
|
||||
SendGoodbye();
|
||||
SendSpecialMessage(new GoodbyeMessage());
|
||||
|
||||
mChannelState = ChannelClosing;
|
||||
|
||||
|
@ -198,10 +224,12 @@ AsyncChannel::OnDispatchMessage(const Message& msg)
|
|||
NS_ASSERTION(!msg.is_reply(), "can't process replies here");
|
||||
NS_ASSERTION(!(msg.is_sync() || msg.is_rpc()), "async dispatch only");
|
||||
|
||||
if (MaybeInterceptGoodbye(msg))
|
||||
// there's a NotifyMaybeChannelError event waiting for us, or
|
||||
// will be soon
|
||||
if (MSG_ROUTING_NONE == msg.routing_id()) {
|
||||
if (!OnSpecialMessage(msg.type(), msg))
|
||||
// XXX real error handling
|
||||
NS_RUNTIMEABORT("unhandled special message!");
|
||||
return;
|
||||
}
|
||||
|
||||
// it's OK to dispatch messages if the channel is closed/error'd,
|
||||
// since we don't have a reply to send back
|
||||
|
@ -209,49 +237,31 @@ AsyncChannel::OnDispatchMessage(const Message& msg)
|
|||
(void)MaybeHandleError(mListener->OnMessageReceived(msg), "AsyncChannel");
|
||||
}
|
||||
|
||||
// This is an async message
|
||||
class GoodbyeMessage : public IPC::Message
|
||||
bool
|
||||
AsyncChannel::OnSpecialMessage(uint16 id, const Message& msg)
|
||||
{
|
||||
public:
|
||||
enum { ID = GOODBYE_MESSAGE_TYPE };
|
||||
GoodbyeMessage() :
|
||||
IPC::Message(MSG_ROUTING_NONE, ID, PRIORITY_NORMAL)
|
||||
{
|
||||
switch (id) {
|
||||
case GOODBYE_MESSAGE_TYPE:
|
||||
return ProcessGoodbyeMessage();
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
// XXX not much point in implementing this; maybe could help with
|
||||
// debugging?
|
||||
static bool Read(const Message* msg)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
void Log(const std::string& aPrefix,
|
||||
FILE* aOutf) const
|
||||
{
|
||||
fputs("(special `Goodbye' message)", aOutf);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
void
|
||||
AsyncChannel::SendGoodbye()
|
||||
AsyncChannel::SendSpecialMessage(Message* msg)
|
||||
{
|
||||
AssertWorkerThread();
|
||||
|
||||
mIOLoop->PostTask(
|
||||
FROM_HERE,
|
||||
NewRunnableMethod(this, &AsyncChannel::OnSend, new GoodbyeMessage()));
|
||||
NewRunnableMethod(this, &AsyncChannel::OnSend, msg));
|
||||
}
|
||||
|
||||
bool
|
||||
AsyncChannel::MaybeInterceptGoodbye(const Message& msg)
|
||||
AsyncChannel::ProcessGoodbyeMessage()
|
||||
{
|
||||
// IPDL code isn't allowed to send MSG_ROUTING_NONE messages, so
|
||||
// there's no chance of confusion here
|
||||
if (MSG_ROUTING_NONE != msg.routing_id())
|
||||
return false;
|
||||
|
||||
if (msg.is_sync() || msg.is_rpc() || GOODBYE_MESSAGE_TYPE != msg.type())
|
||||
NS_RUNTIMEABORT("received unknown MSG_ROUTING_NONE message when expecting `Goodbye'");
|
||||
|
||||
MutexAutoLock lock(mMutex);
|
||||
// TODO sort out Close() on this side racing with Close() on the
|
||||
// other side
|
||||
|
|
|
@ -143,6 +143,9 @@ protected:
|
|||
|
||||
// Run on the worker thread
|
||||
void OnDispatchMessage(const Message& aMsg);
|
||||
virtual bool OnSpecialMessage(uint16 id, const Message& msg);
|
||||
void SendSpecialMessage(Message* msg);
|
||||
|
||||
bool MaybeHandleError(Result code, const char* channelName);
|
||||
void ReportConnectionError(const char* channelName);
|
||||
|
||||
|
@ -154,8 +157,7 @@ protected:
|
|||
|
||||
// Run on the worker thread
|
||||
|
||||
void SendGoodbye();
|
||||
bool MaybeInterceptGoodbye(const Message& msg);
|
||||
bool ProcessGoodbyeMessage();
|
||||
|
||||
void NotifyChannelClosed();
|
||||
void NotifyMaybeChannelError();
|
||||
|
|
Загрузка…
Ссылка в новой задаче