#include #include #include #include "wintype.h" #include "time_func.h" #include "msg_queue.h" PMSG_QUEUE Mq_alloc(UINT32 nentries) { int sz = sizeof(MSG_QUEUE) + (nentries * sizeof(MSG)); PMSG_QUEUE rc; rc = (PMSG_QUEUE)malloc(sz); if (!rc) return NULL; memset(rc, 0, sz); rc->startbound = &(rc->messagestore[0]); rc->endbound = rc->startbound + nentries; rc->head = rc->tail = rc->startbound; rc->nentries = nentries; pthread_mutex_init(&(rc->mutex), NULL); return rc; } void Mq_destroy(PMSG_QUEUE queue) { pthread_mutex_destroy(&(queue->mutex)); free(queue); } static void post_internal(PMSG_QUEUE queue, PMSG msg) { PMSG nexttail; pthread_mutex_lock(&(queue->mutex)); nexttail = queue->tail + 1; if (nexttail == queue->endbound) nexttail = queue->startbound; if (nexttail != queue->head) { memcpy(queue->tail, msg, sizeof(MSG)); queue->tail = nexttail; } /* else drop the message silently */ pthread_mutex_unlock(&(queue->mutex)); } void Mq_post(PMSG_QUEUE queue, HANDLE target, UINT32 message, const UINT_PTR *attrs, int nattrs) { MSG tmpmsg; memset(&tmpmsg, 0, sizeof(MSG)); tmpmsg.target = target; tmpmsg.message = message; if (nattrs > MSG_ATTRCOUNT) nattrs = MSG_ATTRCOUNT; if (nattrs > 0) memcpy(&(tmpmsg.attrs), attrs, sizeof(UINT_PTR) * nattrs); tmpmsg.timestamp = Time_since_start(); post_internal(queue, &tmpmsg); } void Mq_post2(PMSG_QUEUE queue, HANDLE target, UINT32 message, UINT_PTR attr1, UINT_PTR attr2) { MSG tmpmsg; memset(&tmpmsg, 0, sizeof(MSG)); tmpmsg.target = target; tmpmsg.message = message; tmpmsg.attrs[0] = attr1; tmpmsg.attrs[1] = attr2; tmpmsg.timestamp = Time_since_start(); post_internal(queue, &tmpmsg); } BOOL Mq_peek(PMSG_QUEUE queue, PMSG msg, UINT32 flags) { BOOL rc = FALSE; PMSG nexthead; pthread_mutex_lock(&(queue->mutex)); if (queue->head != queue->tail) { nexthead = queue->head + 1; if (nexthead == queue->endbound) nexthead = queue->startbound; memcpy(msg, queue->head, sizeof(MSG)); if (flags & PEEK_REMOVE) queue->head = nexthead; rc = TRUE; } pthread_mutex_unlock(&(queue->mutex)); return rc; }