Implement tryadd, adding itmes with a timeout

This commit is contained in:
Nils O. Selåsdal
2013-01-02 16:54:20 +01:00
parent dbe91d2d13
commit 3e7fd8a34b
3 changed files with 99 additions and 6 deletions
+27 -4
View File
@@ -57,21 +57,44 @@ int uc_thread_queue_init(struct uc_threadqueue *queue, long max_elements)
return rc;
}
int uc_thread_queue_add(struct uc_threadqueue *queue, struct uc_threadmsg *msg)
int uc_thread_queue_tryadd(struct uc_threadqueue *queue, const struct timespec *timeout, struct uc_threadmsg *msg)
{
int rc = 0;
struct timespec abstimeout;
if (queue == NULL || msg == NULL) {
return EINVAL;
}
if (timeout) {
uc_get_absolute_time(&abstimeout, timeout);
}
pthread_mutex_lock(&queue->mutex);
//Wait if the queue is full
while(queue->num_elements >= queue->max_elements) {
while(queue->num_elements >= queue->max_elements && rc != ETIMEDOUT) {
queue->num_write_waiters++;
pthread_cond_wait(&queue->write_cond, &queue->mutex);
if(timeout) {
//fastpath, check for a poll
if(timeout->tv_sec == 0 && timeout->tv_nsec == 0) {
rc = ETIMEDOUT;
} else {
rc = pthread_cond_timedwait(&queue->write_cond, &queue->mutex, &abstimeout);
}
} else {
pthread_cond_wait(&queue->write_cond, &queue->mutex);
}
queue->num_write_waiters--;
}
if (rc == ETIMEDOUT) {
pthread_mutex_unlock(&queue->mutex);
return rc;
}
//insert the new element
msg->next = NULL;
if (msg->msgtype >= 0) { //add at the tail