logic: fixed crash when calling message listeners that already have been destroyed

* prevented lambda created by MessageQueue::sendMessageAsTask to call functions on message listeners that already have been destroyed.
This commit is contained in:
malte_langkabel
2015-12-03 13:54:47 +01:00
parent 23909058c8
commit 151b4d8620
5 changed files with 40 additions and 2 deletions
+20 -2
View File
@@ -53,6 +53,19 @@ void MessageQueue::unregisterListener(MessageListenerBase* listener)
LOG_ERROR("Listener was not found");
}
MessageListenerBase* MessageQueue::getListenerById(const uint id) const
{
std::lock_guard<std::mutex> lock(m_listenersMutex);
for (size_t i = 0; i < m_listeners.size(); i++)
{
if (m_listeners[i]->getId() == id)
{
return m_listeners[i];
}
}
return nullptr;
}
void MessageQueue::pushMessage(std::shared_ptr<MessageBase> message)
{
std::lock_guard<std::mutex> lock(m_backMessageBufferMutex);
@@ -240,10 +253,15 @@ void MessageQueue::sendMessageAsTask(std::shared_ptr<MessageBase> message, bool
if (listener->getType() == message->getType())
{
uint listenerId = listener->getId();
taskGroup->addTask(std::make_shared<LambdaTask>(
[listener, message]()
[listenerId, message]()
{
listener->handleMessageBase(message.get());
MessageListenerBase* listener = MessageQueue::getInstance()->getListenerById(listenerId);
if (listener)
{
listener->handleMessageBase(message.get());
}
}
));
}