A priority message queue. We will use it to handle system notifications faster than client requests.
git-svn-id: file:///srv/svn/repos/haiku/trunk/current@2642 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
parent
9f7559815d
commit
fadf867232
130
src/servers/registrar/PriorityMessageQueue.cpp
Normal file
130
src/servers/registrar/PriorityMessageQueue.cpp
Normal file
@ -0,0 +1,130 @@
|
|||||||
|
//----------------------------------------------------------------------
|
||||||
|
// This software is part of the OpenBeOS distribution and is covered
|
||||||
|
// by the OpenBeOS license.
|
||||||
|
//---------------------------------------------------------------------
|
||||||
|
|
||||||
|
#include <Message.h>
|
||||||
|
|
||||||
|
#include "PriorityMessageQueue.h"
|
||||||
|
|
||||||
|
// MessageInfo
|
||||||
|
class PriorityMessageQueue::MessageInfo {
|
||||||
|
public:
|
||||||
|
MessageInfo(BMessage *message, int32 priority)
|
||||||
|
: fMessage(message),
|
||||||
|
fPriority(priority)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
BMessage *Message() const { return fMessage; }
|
||||||
|
int32 Priority() const { return fPriority; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
BMessage *fMessage;
|
||||||
|
int32 fPriority;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// constructor
|
||||||
|
PriorityMessageQueue::PriorityMessageQueue()
|
||||||
|
: fLock(),
|
||||||
|
fMessages(20, true)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// destructor
|
||||||
|
PriorityMessageQueue::~PriorityMessageQueue()
|
||||||
|
{
|
||||||
|
// delete the messages
|
||||||
|
for (int32 i = 0; MessageInfo *info = fMessages.ItemAt(i); i++)
|
||||||
|
delete info->Message();
|
||||||
|
// the infos are deleted automatically
|
||||||
|
}
|
||||||
|
|
||||||
|
// Lock
|
||||||
|
bool
|
||||||
|
PriorityMessageQueue::Lock()
|
||||||
|
{
|
||||||
|
return fLock.Lock();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Unlock
|
||||||
|
void
|
||||||
|
PriorityMessageQueue::Unlock()
|
||||||
|
{
|
||||||
|
fLock.Unlock();
|
||||||
|
}
|
||||||
|
|
||||||
|
// PushMessage
|
||||||
|
bool
|
||||||
|
PriorityMessageQueue::PushMessage(BMessage *message, int32 priority)
|
||||||
|
{
|
||||||
|
bool result = (message);
|
||||||
|
if (result)
|
||||||
|
result = Lock();
|
||||||
|
if (result) {
|
||||||
|
if (MessageInfo *info = new MessageInfo(message, priority)) {
|
||||||
|
// find the insertion index
|
||||||
|
int32 index = _FindInsertionIndex(priority);
|
||||||
|
if (!fMessages.AddItem(info, index)) {
|
||||||
|
result = false;
|
||||||
|
delete info;
|
||||||
|
}
|
||||||
|
} else // no memory
|
||||||
|
result = false;
|
||||||
|
Unlock();
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// PopMessage
|
||||||
|
BMessage *
|
||||||
|
PriorityMessageQueue::PopMessage()
|
||||||
|
{
|
||||||
|
BMessage *result = NULL;
|
||||||
|
if (Lock()) {
|
||||||
|
if (MessageInfo *info = fMessages.RemoveItemAt(0)) {
|
||||||
|
result = info->Message();
|
||||||
|
delete info;
|
||||||
|
}
|
||||||
|
Unlock();
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// CountMessages
|
||||||
|
int32
|
||||||
|
PriorityMessageQueue::CountMessages() const
|
||||||
|
{
|
||||||
|
int32 result = 0;
|
||||||
|
if (fLock.Lock()) {
|
||||||
|
result = fMessages.CountItems();
|
||||||
|
fLock.Unlock();
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// IsEmpty
|
||||||
|
bool
|
||||||
|
PriorityMessageQueue::IsEmpty() const
|
||||||
|
{
|
||||||
|
return (CountMessages() == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// _FindInsertionIndex
|
||||||
|
int32
|
||||||
|
PriorityMessageQueue::_FindInsertionIndex(int32 priority)
|
||||||
|
{
|
||||||
|
int32 lower = 0;
|
||||||
|
int32 upper = fMessages.CountItems();
|
||||||
|
while (lower < upper) {
|
||||||
|
int32 mid = (lower + upper) / 2;
|
||||||
|
MessageInfo *info = fMessages.ItemAt(mid);
|
||||||
|
if (info->Priority() >= priority)
|
||||||
|
lower = mid + 1;
|
||||||
|
else
|
||||||
|
upper = mid;
|
||||||
|
}
|
||||||
|
return lower;
|
||||||
|
}
|
||||||
|
|
39
src/servers/registrar/PriorityMessageQueue.h
Normal file
39
src/servers/registrar/PriorityMessageQueue.h
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
//----------------------------------------------------------------------
|
||||||
|
// This software is part of the OpenBeOS distribution and is covered
|
||||||
|
// by the OpenBeOS license.
|
||||||
|
//---------------------------------------------------------------------
|
||||||
|
|
||||||
|
#ifndef PRIORITY_MESSAGE_QUEUE_H
|
||||||
|
#define PRIORITY_MESSAGE_QUEUE_H
|
||||||
|
|
||||||
|
#include <Locker.h>
|
||||||
|
#include <ObjectList.h>
|
||||||
|
|
||||||
|
class BMessage;
|
||||||
|
|
||||||
|
class PriorityMessageQueue {
|
||||||
|
public:
|
||||||
|
PriorityMessageQueue();
|
||||||
|
~PriorityMessageQueue();
|
||||||
|
|
||||||
|
bool Lock();
|
||||||
|
void Unlock();
|
||||||
|
|
||||||
|
bool PushMessage(BMessage *message, int32 priority = 0);
|
||||||
|
BMessage *PopMessage();
|
||||||
|
|
||||||
|
int32 CountMessages() const;
|
||||||
|
bool IsEmpty() const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
int32 _FindInsertionIndex(int32 priority);
|
||||||
|
|
||||||
|
private:
|
||||||
|
class MessageInfo;
|
||||||
|
|
||||||
|
private:
|
||||||
|
mutable BLocker fLock;
|
||||||
|
BObjectList<MessageInfo> fMessages;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PRIORITY_MESSAGE_QUEUE_H
|
Loading…
Reference in New Issue
Block a user