Reference Manual

Main Page | Namespace List | Class Hierarchy | Alphabetical List | Compound List | File List | Namespace Members | Compound Members | File Members

# Inti::G::AsyncQueue Class Reference

A GAsyncQueue C++ wrapper interface. More...

`#include <inti/glib/asyncqueue.h>`

Inheritance diagram for Inti::G::AsyncQueue:

List of all members.

## Public Member Functions

Constructors

- AsyncQueue ()
    Constructs a new asynchronous queue.
- virtual ~AsyncQueue ()
    Destructor.

Accessors

- int length () const
    Gets the length of the queue.

Methods

- virtual void ref ()
    Increases the reference count of the asynchronous queue by one.
- virtual void unref ()
    Decreases the reference count of the asynchronous queue by one.
- void lock ()
    Acquires the queue's lock.
- void unlock ()
    Releases the queue's lock.
- void push (void *data)
    Pushes the data into the queue (data must not be null).
- void * pop ()
    Pop data from the async queue.
- void * try_pop ()
    Try to pop data.
- void * timed_pop (TimeVal *end_time)
    Pops data from the queue.

## Detailed Description

A GAsyncQueue C++ wrapper interface.

Often you need to communicate between different threads. In general it's safer not to do this by shared memory, but by explicit message passing. These messages only make sense asynchronously for multi-threaded applications though, as a synchronous operation could as well be done in the same thread.

Asynchronous queues are an exception from most other GLib data structures, as they can be used simultaneously from multiple threads without explicit locking and they bring their own builtin reference counting. This is because the nature of an asynchronous queue is that it will always be used by at least 2 concurrent threads.

For using an asynchronous queue you first have to construct one, either dynamically or on the stack. A newly-created queue will get the reference count 1. Whenever another thread is creating a new reference to a queue, it has to increase the reference count (using ref()). Also, before removing this reference, the reference count has to be decreased (using unref()). After that the queue might no longer exist so you must not access it after that point.

A thread which wants to send a message to a queue simply calls push() to push the message to the queue. A thread which is expecting messages from an asynchronous queue simply calls pop() for that queue. If no message is available in the queue at that point, the thread is now put to sleep until a message arrives. The message will be removed from the queue and returned. The methods try_pop() and timed_pop() can be used to only check for the presence of messages or to only wait a certain time for messages respectively.

In GLib, for almost every g_async_queue_* function there exist two variants, one that locks the queue and one that doesn't. That way you can hold the queue lock (acquire it with g_async_queue_lock() and release it with g_async_queue_unlock()) over multiple queue accessing instructions. This can be necessary to ensure the integrity of the queue, but should only be used when really necessary, as it can make your life harder if used unwisely. Normally you should only use the locking function variants (those without the suffix _unlocked).

AsyncQueue hides the these two function variants behind a single API. When you call lock() the bool flag 'locked_' is set, and the API calls the *_unlocked functions. When you call unlock() the 'locked_' flag is cleared, and the functions without the suffix _unlocked are called. For saftey reasons, and ensure the AsyncQueue locked_ flag can't be broken, there is no g_async_queue() method or conversion operator.

Note, you must call unref() whether you create the queue dynamically or on the stack. If you create an AsyncQueue dynamically with operatror new the easiest way to handle unref() is to use a smart pointer. If you create an AsyncQueue on the stack you will have to unref() it yourself, as you would with any object derived from ReferencedBase, including G::Objects.

## Member Function Documentation

int Inti::G::AsyncQueue::length | ( |  | ) | const

Gets the length of the queue.

Returns:
  The queue length.

Negative values mean that threads are waiting, positive values mean that there are entries in the queue. Actually this method returns the length of the queue minus the number of waiting threads, length == 0 could also mean 'n' entries in the queue and 'n' thread waiting. Such can happen due to locking of the queue or due to scheduling.

void Inti::G::AsyncQueue::lock | ( |  | ) |

| Acquires the queue's lock. All methods lock/unlock the queue for themselves, but in certain cirumstances you want to hold the lock longer, thus you lock the queue, and unlock when your finished.

void* Inti::G::AsyncQueue::pop | ( |  | ) |

Pop data from the async queue.

Returns:
  The data from the queue.

When no data is there, the thread is blocked until data arrives.

void Inti::G::AsyncQueue::push | ( | void * | data | ) |

Pushes the data into the queue (data must not be null).

Parameters:

  data | The data to push into the queue.

void* Inti::G::AsyncQueue::timed_pop | ( | TimeVal * | end_time | ) |

Pops data from the queue.

Parameters:

  end_time | A G::TimeVal, determining the final time.

Returns:
  The data from the queue, or null when no data is received before end_time.

To easily calculate end_time a combination of G::get_current_time() and G::TimeVal::add() can be used.

void* Inti::G::AsyncQueue::try_pop | ( |  | ) |

Try to pop data.

Returns:
  The data from the queue, or null if the queue is empty.

void Inti::G::AsyncQueue::unlock | ( |  | ) |

| Releases the queue's lock. All methods lock/unlock the queue for themselves, but in certain cirumstances you want to hold the lock longer, thus you lock the queue, and unlock when your finished.

virtual void Inti::G::AsyncQueue::unref | ( |  | ) | `[virtual]`

| Decreases the reference count of the asynchronous queue by one. After this call if the reference is zero and the queue will be destroyed. Reimplemented from Inti::ReferencedBase.

The documentation for this class was generated from the following file:

- asyncqueue.h

Main Page - Footer