2 * CFLAGS=-lpthread make pthread_msgqueue
13 typedef struct pthread_mq_t
{
15 pthread_cond_t cond_readable
;
16 pthread_cond_t cond_writable
;
25 bool pthread_mq_readable(pthread_mq_t
*mq
) { return (mq
->msg_count
> 0); }
26 bool pthread_mq_writable(pthread_mq_t
*mq
) { return (mq
->msg_count
< mq
->msg_count_max
); }
28 bool pthread_mq_init(pthread_mq_t
*mq
, size_t msg_size
, size_t msg_count_max
) {
29 pthread_mutex_init(&mq
->lock
, NULL
);
30 pthread_cond_init(&mq
->cond_readable
, NULL
);
31 pthread_cond_init(&mq
->cond_writable
, NULL
);
32 mq
->data
= malloc(msg_size
*msg_count_max
);
33 mq
->msg_size
= msg_size
;
34 mq
->msg_count_max
= msg_count_max
;
39 if(((msg_size
*msg_count_max
) > 0) && mq
->data
== NULL
) return false;
43 void pthread_mq_free(pthread_mq_t
*mq
) {
47 void pthread_mq_cond(pthread_mq_t
*mq
) {
48 if(pthread_mq_readable(mq
)) pthread_cond_broadcast(&mq
->cond_readable
);
49 if(pthread_mq_writable(mq
)) pthread_cond_broadcast(&mq
->cond_writable
);
52 bool pthread_mq_reset(pthread_mq_t
*mq
) {
53 if(pthread_mutex_lock(&mq
->lock
)) return false;
57 pthread_mutex_unlock(&mq
->lock
);
61 bool pthread_mq_send_generic(pthread_mq_t
*mq
, void * data
, bool to_front
, bool block
, const struct timespec
*restrict abs_timeout
) {
63 if(pthread_mutex_timedlock(&mq
->lock
, abs_timeout
)) return false;
65 //Wait for queue to be in writable condition
66 while(!pthread_mq_writable(mq
)) {
67 if(pthread_cond_timedwait(&mq
->cond_writable
, &mq
->lock
, abs_timeout
)) {
68 pthread_mutex_unlock(&mq
->lock
);
74 size_t idx
= ( ( mq
->msg_count_max
+ mq
->head_idx
+ (to_front
?-1:mq
->msg_count
) ) % mq
->msg_count_max
);
75 void *ptr
= mq
->data
+ (idx
* mq
->msg_size
);
77 if(to_front
) mq
->head_idx
= (mq
->msg_count_max
+ mq
->head_idx
- 1) % mq
->msg_count_max
;
78 memcpy(ptr
, data
, mq
->msg_size
);
80 //Signal conditions and unlock
82 pthread_mutex_unlock(&mq
->lock
);