![]() |
The FreeRADIUS server $Id: a4e7f8c94e8038b7627bcf52356b7ed15955c1d7 $
|
Thread-safe queues. More...
#include <freeradius-devel/util/stdatomic.h>#include <freeradius-devel/util/talloc.h>
Include dependency graph for atomic_queue.h:Go to the source code of this file.
Typedefs | |
| typedef struct fr_atomic_queue_s | fr_atomic_queue_t |
| typedef struct fr_atomic_ring_s | fr_atomic_ring_t |
| Unbounded segmented single-producer / single-consumer queue. | |
Functions | |
| void | fr_atomic_queue_debug (FILE *fp, fr_atomic_queue_t *aq) |
| Dump an atomic queue. | |
| void | fr_atomic_queue_free (fr_atomic_queue_t **aq) |
| Free an atomic queue if it's not freed by ctx. | |
| fr_atomic_queue_t * | fr_atomic_queue_malloc (TALLOC_CTX *ctx, size_t size) |
| Create fixed-size atomic queue outside the talloc hierarchy, owned by a talloc context. | |
| bool | fr_atomic_queue_pop (fr_atomic_queue_t *aq, void **p_data) |
| Pop a pointer from the atomic queue. | |
| bool | fr_atomic_queue_push (fr_atomic_queue_t *aq, void *data) |
| Push a pointer into the atomic queue. | |
| size_t | fr_atomic_queue_size (fr_atomic_queue_t *aq) |
| fr_atomic_queue_t * | fr_atomic_queue_talloc (TALLOC_CTX *ctx, size_t size) |
| Create fixed-size atomic queue. | |
| fr_atomic_ring_t * | fr_atomic_ring_alloc (TALLOC_CTX *ctx, size_t seg_size) |
| Allocate an empty SPSC ring. | |
| void | fr_atomic_ring_free (fr_atomic_ring_t **ring) |
| Free the ring and all remaining segments. | |
| bool | fr_atomic_ring_pop (fr_atomic_ring_t *ring, void **p_data) |
| Pop a pointer from the ring, advancing past drained segments. | |
| bool | fr_atomic_ring_push (fr_atomic_ring_t *ring, void *data) |
| Push a pointer into the ring; allocate a new segment on overflow. | |
Thread-safe queues.
Definition in file atomic_queue.h.
| typedef struct fr_atomic_queue_s fr_atomic_queue_t |
Definition at line 40 of file atomic_queue.h.
| typedef struct fr_atomic_ring_s fr_atomic_ring_t |
Unbounded segmented single-producer / single-consumer queue.
Internally a linked list of fixed-size fr_atomic_queue_t segments. When the producer's current segment fills, a new segment is malloc'd and linked in; the consumer drains segments in order and frees them as it advances. Allocation on the producer side uses raw malloc (not talloc), so the producer thread is free to be one that cannot safely use talloc (e.g. a library-owned callback thread).
Exactly one producer and one consumer. Not safe for MPMC use.
Definition at line 60 of file atomic_queue.h.
| void fr_atomic_queue_debug | ( | FILE * | fp, |
| fr_atomic_queue_t * | aq | ||
| ) |
Dump an atomic queue.
Absolutely NOT thread-safe.
| [in] | aq | The atomic queue to debug. |
| [in] | fp | where the debugging information will be printed. |
Definition at line 841 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| void fr_atomic_queue_free | ( | fr_atomic_queue_t ** | aq | ) |
Free an atomic queue if it's not freed by ctx.
The queue memory must be cache line aligned, so it lives in one of three places: a talloc aligned array (chunk is the array), a raw allocation owned by a talloc handle (chunk is the handle, whose destructor frees the queue), or a raw allocation with no owner (chunk is NULL).
Definition at line 388 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| fr_atomic_queue_t * fr_atomic_queue_malloc | ( | TALLOC_CTX * | ctx, |
| size_t | size | ||
| ) |
Create fixed-size atomic queue outside the talloc hierarchy, owned by a talloc context.
The queue itself is a raw posix_memalign allocation, so it can be pushed to and popped from by threads where talloc is not safe, and can later be placed in memory talloc does not manage. A small owner handle allocated in ctx frees the queue when ctx is freed, or when the caller calls fr_atomic_queue_free.
| [in] | ctx | The talloc ctx which owns the queue. |
| [in] | size | The number of entries in the queue. |
Definition at line 360 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| bool fr_atomic_queue_pop | ( | fr_atomic_queue_t * | aq, |
| void ** | p_data | ||
| ) |
Pop a pointer from the atomic queue.
| [in] | aq | the atomic queue to retrieve data from. |
| [out] | p_data | where to write the data. |
Definition at line 531 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| bool fr_atomic_queue_push | ( | fr_atomic_queue_t * | aq, |
| void * | data | ||
| ) |
Push a pointer into the atomic queue.
| [in] | aq | The atomic queue to add data to. |
| [in] | data | to push. |
Definition at line 408 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| size_t fr_atomic_queue_size | ( | fr_atomic_queue_t * | aq | ) |
| fr_atomic_queue_t * fr_atomic_queue_talloc | ( | TALLOC_CTX * | ctx, |
| size_t | size | ||
| ) |
Create fixed-size atomic queue.
| [in] | ctx | The talloc ctx to allocate the queue in. |
| [in] | size | The number of entries in the queue. |
Definition at line 270 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| fr_atomic_ring_t * fr_atomic_ring_alloc | ( | TALLOC_CTX * | ctx, |
| size_t | seg_size | ||
| ) |
Allocate an empty SPSC ring.
| [in] | ctx | talloc ctx that owns the ring handle (segments live outside talloc; they are freed by the ring's destructor). |
| [in] | seg_size | Per-segment capacity. Rounded up to a power of 2. |
Definition at line 680 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| void fr_atomic_ring_free | ( | fr_atomic_ring_t ** | ring_p | ) |
Free the ring and all remaining segments.
Equivalent to talloc_free() on the ring, but nulls the caller's handle in the style of fr_atomic_queue_free.
Definition at line 709 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| bool fr_atomic_ring_pop | ( | fr_atomic_ring_t * | ring, |
| void ** | p_data | ||
| ) |
Pop a pointer from the ring, advancing past drained segments.
Single-consumer only. Must not be called concurrently with itself.
| [in] | ring | Ring to pop from. |
| [out] | p_data | Where to write the popped value on success. |
Definition at line 775 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:| bool fr_atomic_ring_push | ( | fr_atomic_ring_t * | ring, |
| void * | data | ||
| ) |
Push a pointer into the ring; allocate a new segment on overflow.
Single-producer only. Must not be called concurrently with itself.
| [in] | ring | Ring to push into. |
| [in] | data | Value to push (must be non-NULL). |
Definition at line 748 of file atomic_queue.c.
Here is the call graph for this function:
Here is the caller graph for this function:
1.9.8