xref: /dpdk/lib/ring/rte_ring.h (revision 700989f512bbc2ee9758a8a9cb6973cfdeda6f27)
1 /* SPDX-License-Identifier: BSD-3-Clause
2  *
3  * Copyright (c) 2010-2020 Intel Corporation
4  * Copyright (c) 2007-2009 Kip Macy kmacy@freebsd.org
5  * All rights reserved.
6  * Derived from FreeBSD's bufring.h
7  * Used as BSD-3 Licensed with permission from Kip Macy.
8  */
9 
10 #ifndef _RTE_RING_H_
11 #define _RTE_RING_H_
12 
13 /**
14  * @file
15  * RTE Ring
16  *
17  * The Ring Manager is a fixed-size queue, implemented as a table of
18  * pointers. Head and tail pointers are modified atomically, allowing
19  * concurrent access to it. It has the following features:
20  *
21  * - FIFO (First In First Out)
22  * - Maximum size is fixed; the pointers are stored in a table.
23  * - Lockless implementation.
24  * - Multi- or single-consumer dequeue.
25  * - Multi- or single-producer enqueue.
26  * - Bulk dequeue.
27  * - Bulk enqueue.
28  * - Ability to select different sync modes for producer/consumer.
29  * - Dequeue start/finish (depending on consumer sync modes).
30  * - Enqueue start/finish (depending on producer sync mode).
31  *
32  * Note: the ring implementation is not preemptible. Refer to Programmer's
33  * guide/Environment Abstraction Layer/Multiple pthread/Known Issues/rte_ring
34  * for more information.
35  */
36 
37 #include <rte_ring_core.h>
38 #include <rte_ring_elem.h>
39 
40 #ifdef __cplusplus
41 extern "C" {
42 #endif
43 
44 /**
45  * Calculate the memory size needed for a ring
46  *
47  * This function returns the number of bytes needed for a ring, given
48  * the number of elements in it. This value is the sum of the size of
49  * the structure rte_ring and the size of the memory needed by the
50  * objects pointers. The value is aligned to a cache line size.
51  *
52  * @param count
53  *   The number of elements in the ring (must be a power of 2).
54  * @return
55  *   - The memory size needed for the ring on success.
56  *   - -EINVAL if count is not a power of 2.
57  */
58 ssize_t rte_ring_get_memsize(unsigned int count);
59 
60 /**
61  * Initialize a ring structure.
62  *
63  * Initialize a ring structure in memory pointed by "r". The size of the
64  * memory area must be large enough to store the ring structure and the
65  * object table. It is advised to use rte_ring_get_memsize() to get the
66  * appropriate size.
67  *
68  * The ring size is set to *count*, which must be a power of two.
69  * The real usable ring size is *count-1* instead of *count* to
70  * differentiate a full ring from an empty ring.
71  *
72  * The ring is not added in RTE_TAILQ_RING global list. Indeed, the
73  * memory given by the caller may not be shareable among dpdk
74  * processes.
75  *
76  * @param r
77  *   The pointer to the ring structure followed by the objects table.
78  * @param name
79  *   The name of the ring.
80  * @param count
81  *   The number of elements in the ring (must be a power of 2,
82  *   unless RING_F_EXACT_SZ is set in flags).
83  * @param flags
84  *   An OR of the following:
85  *   - One of mutually exclusive flags that define producer behavior:
86  *      - RING_F_SP_ENQ: If this flag is set, the default behavior when
87  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
88  *        is "single-producer".
89  *      - RING_F_MP_RTS_ENQ: If this flag is set, the default behavior when
90  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
91  *        is "multi-producer RTS mode".
92  *      - RING_F_MP_HTS_ENQ: If this flag is set, the default behavior when
93  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
94  *        is "multi-producer HTS mode".
95  *     If none of these flags is set, then default "multi-producer"
96  *     behavior is selected.
97  *   - One of mutually exclusive flags that define consumer behavior:
98  *      - RING_F_SC_DEQ: If this flag is set, the default behavior when
99  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
100  *        is "single-consumer". Otherwise, it is "multi-consumers".
101  *      - RING_F_MC_RTS_DEQ: If this flag is set, the default behavior when
102  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
103  *        is "multi-consumer RTS mode".
104  *      - RING_F_MC_HTS_DEQ: If this flag is set, the default behavior when
105  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
106  *        is "multi-consumer HTS mode".
107  *     If none of these flags is set, then default "multi-consumer"
108  *     behavior is selected.
109  *   - RING_F_EXACT_SZ: If this flag is set, the ring will hold exactly the
110  *     requested number of entries, and the requested size will be rounded up
111  *     to the next power of two, but the usable space will be exactly that
112  *     requested. Worst case, if a power-of-2 size is requested, half the
113  *     ring space will be wasted.
114  *     Without this flag set, the ring size requested must be a power of 2,
115  *     and the usable space will be that size - 1.
116  * @return
117  *   0 on success, or a negative value on error.
118  */
119 int rte_ring_init(struct rte_ring *r, const char *name, unsigned int count,
120 	unsigned int flags);
121 
122 /**
123  * Create a new ring named *name* in memory.
124  *
125  * This function uses ``memzone_reserve()`` to allocate memory. Then it
126  * calls rte_ring_init() to initialize an empty ring.
127  *
128  * The new ring size is set to *count*, which must be a power of two.
129  * The real usable ring size is *count-1* instead of *count* to
130  * differentiate a full ring from an empty ring.
131  *
132  * The ring is added in RTE_TAILQ_RING list.
133  *
134  * @param name
135  *   The name of the ring.
136  * @param count
137  *   The size of the ring (must be a power of 2,
138  *   unless RING_F_EXACT_SZ is set in flags).
139  * @param socket_id
140  *   The *socket_id* argument is the socket identifier in case of
141  *   NUMA. The value can be *SOCKET_ID_ANY* if there is no NUMA
142  *   constraint for the reserved zone.
143  * @param flags
144  *   An OR of the following:
145  *   - One of mutually exclusive flags that define producer behavior:
146  *      - RING_F_SP_ENQ: If this flag is set, the default behavior when
147  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
148  *        is "single-producer".
149  *      - RING_F_MP_RTS_ENQ: If this flag is set, the default behavior when
150  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
151  *        is "multi-producer RTS mode".
152  *      - RING_F_MP_HTS_ENQ: If this flag is set, the default behavior when
153  *        using ``rte_ring_enqueue()`` or ``rte_ring_enqueue_bulk()``
154  *        is "multi-producer HTS mode".
155  *     If none of these flags is set, then default "multi-producer"
156  *     behavior is selected.
157  *   - One of mutually exclusive flags that define consumer behavior:
158  *      - RING_F_SC_DEQ: If this flag is set, the default behavior when
159  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
160  *        is "single-consumer". Otherwise, it is "multi-consumers".
161  *      - RING_F_MC_RTS_DEQ: If this flag is set, the default behavior when
162  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
163  *        is "multi-consumer RTS mode".
164  *      - RING_F_MC_HTS_DEQ: If this flag is set, the default behavior when
165  *        using ``rte_ring_dequeue()`` or ``rte_ring_dequeue_bulk()``
166  *        is "multi-consumer HTS mode".
167  *     If none of these flags is set, then default "multi-consumer"
168  *     behavior is selected.
169  *   - RING_F_EXACT_SZ: If this flag is set, the ring will hold exactly the
170  *     requested number of entries, and the requested size will be rounded up
171  *     to the next power of two, but the usable space will be exactly that
172  *     requested. Worst case, if a power-of-2 size is requested, half the
173  *     ring space will be wasted.
174  *     Without this flag set, the ring size requested must be a power of 2,
175  *     and the usable space will be that size - 1.
176  * @return
177  *   On success, the pointer to the new allocated ring. NULL on error with
178  *    rte_errno set appropriately. Possible errno values include:
179  *    - E_RTE_NO_CONFIG - function could not get pointer to rte_config structure
180  *    - EINVAL - count provided is not a power of 2
181  *    - ENOSPC - the maximum number of memzones has already been allocated
182  *    - EEXIST - a memzone with the same name already exists
183  *    - ENOMEM - no appropriate memory area found in which to create memzone
184  */
185 struct rte_ring *rte_ring_create(const char *name, unsigned int count,
186 				 int socket_id, unsigned int flags);
187 
188 /**
189  * De-allocate all memory used by the ring.
190  *
191  * @param r
192  *   Ring to free.
193  *   If NULL then, the function does nothing.
194  */
195 void rte_ring_free(struct rte_ring *r);
196 
197 /**
198  * Dump the status of the ring to a file.
199  *
200  * @param f
201  *   A pointer to a file for output
202  * @param r
203  *   A pointer to the ring structure.
204  */
205 void rte_ring_dump(FILE *f, const struct rte_ring *r);
206 
207 /**
208  * @warning
209  * @b EXPERIMENTAL: this API may change without prior notice.
210  *
211  * Dump the status of a headtail to a file.
212  *
213  * @param f
214  *   A pointer to a file for output
215  * @param prefix
216  *   A string to prefix each output line with
217  * @param r
218  *   A pointer to a ring headtail structure.
219  */
220 __rte_experimental
221 void
222 rte_ring_headtail_dump(FILE *f, const char *prefix,
223 		const struct rte_ring_headtail *r);
224 
225 /**
226  * Enqueue several objects on the ring (multi-producers safe).
227  *
228  * This function uses a "compare and set" instruction to move the
229  * producer index atomically.
230  *
231  * @param r
232  *   A pointer to the ring structure.
233  * @param obj_table
234  *   A pointer to a table of void * pointers (objects).
235  * @param n
236  *   The number of objects to add in the ring from the obj_table.
237  * @param free_space
238  *   if non-NULL, returns the amount of space in the ring after the
239  *   enqueue operation has finished.
240  * @return
241  *   The number of objects enqueued, either 0 or n
242  */
243 static __rte_always_inline unsigned int
244 rte_ring_mp_enqueue_bulk(struct rte_ring *r, void * const *obj_table,
245 			 unsigned int n, unsigned int *free_space)
246 {
247 	return rte_ring_mp_enqueue_bulk_elem(r, obj_table, sizeof(void *),
248 			n, free_space);
249 }
250 
251 /**
252  * Enqueue several objects on a ring (NOT multi-producers safe).
253  *
254  * @param r
255  *   A pointer to the ring structure.
256  * @param obj_table
257  *   A pointer to a table of void * pointers (objects).
258  * @param n
259  *   The number of objects to add in the ring from the obj_table.
260  * @param free_space
261  *   if non-NULL, returns the amount of space in the ring after the
262  *   enqueue operation has finished.
263  * @return
264  *   The number of objects enqueued, either 0 or n
265  */
266 static __rte_always_inline unsigned int
267 rte_ring_sp_enqueue_bulk(struct rte_ring *r, void * const *obj_table,
268 			 unsigned int n, unsigned int *free_space)
269 {
270 	return rte_ring_sp_enqueue_bulk_elem(r, obj_table, sizeof(void *),
271 			n, free_space);
272 }
273 
274 /**
275  * Enqueue several objects on a ring.
276  *
277  * This function calls the multi-producer or the single-producer
278  * version depending on the default behavior that was specified at
279  * ring creation time (see flags).
280  *
281  * @param r
282  *   A pointer to the ring structure.
283  * @param obj_table
284  *   A pointer to a table of void * pointers (objects).
285  * @param n
286  *   The number of objects to add in the ring from the obj_table.
287  * @param free_space
288  *   if non-NULL, returns the amount of space in the ring after the
289  *   enqueue operation has finished.
290  * @return
291  *   The number of objects enqueued, either 0 or n
292  */
293 static __rte_always_inline unsigned int
294 rte_ring_enqueue_bulk(struct rte_ring *r, void * const *obj_table,
295 		      unsigned int n, unsigned int *free_space)
296 {
297 	return rte_ring_enqueue_bulk_elem(r, obj_table, sizeof(void *),
298 			n, free_space);
299 }
300 
301 /**
302  * Enqueue one object on a ring (multi-producers safe).
303  *
304  * This function uses a "compare and set" instruction to move the
305  * producer index atomically.
306  *
307  * @param r
308  *   A pointer to the ring structure.
309  * @param obj
310  *   A pointer to the object to be added.
311  * @return
312  *   - 0: Success; objects enqueued.
313  *   - -ENOBUFS: Not enough room in the ring to enqueue; no object is enqueued.
314  */
315 static __rte_always_inline int
316 rte_ring_mp_enqueue(struct rte_ring *r, void *obj)
317 {
318 	return rte_ring_mp_enqueue_elem(r, &obj, sizeof(void *));
319 }
320 
321 /**
322  * Enqueue one object on a ring (NOT multi-producers safe).
323  *
324  * @param r
325  *   A pointer to the ring structure.
326  * @param obj
327  *   A pointer to the object to be added.
328  * @return
329  *   - 0: Success; objects enqueued.
330  *   - -ENOBUFS: Not enough room in the ring to enqueue; no object is enqueued.
331  */
332 static __rte_always_inline int
333 rte_ring_sp_enqueue(struct rte_ring *r, void *obj)
334 {
335 	return rte_ring_sp_enqueue_elem(r, &obj, sizeof(void *));
336 }
337 
338 /**
339  * Enqueue one object on a ring.
340  *
341  * This function calls the multi-producer or the single-producer
342  * version, depending on the default behaviour that was specified at
343  * ring creation time (see flags).
344  *
345  * @param r
346  *   A pointer to the ring structure.
347  * @param obj
348  *   A pointer to the object to be added.
349  * @return
350  *   - 0: Success; objects enqueued.
351  *   - -ENOBUFS: Not enough room in the ring to enqueue; no object is enqueued.
352  */
353 static __rte_always_inline int
354 rte_ring_enqueue(struct rte_ring *r, void *obj)
355 {
356 	return rte_ring_enqueue_elem(r, &obj, sizeof(void *));
357 }
358 
359 /**
360  * Dequeue several objects from a ring (multi-consumers safe).
361  *
362  * This function uses a "compare and set" instruction to move the
363  * consumer index atomically.
364  *
365  * @param r
366  *   A pointer to the ring structure.
367  * @param obj_table
368  *   A pointer to a table of void * pointers (objects) that will be filled.
369  * @param n
370  *   The number of objects to dequeue from the ring to the obj_table.
371  * @param available
372  *   If non-NULL, returns the number of remaining ring entries after the
373  *   dequeue has finished.
374  * @return
375  *   The number of objects dequeued, either 0 or n
376  */
377 static __rte_always_inline unsigned int
378 rte_ring_mc_dequeue_bulk(struct rte_ring *r, void **obj_table,
379 		unsigned int n, unsigned int *available)
380 {
381 	return rte_ring_mc_dequeue_bulk_elem(r, obj_table, sizeof(void *),
382 			n, available);
383 }
384 
385 /**
386  * Dequeue several objects from a ring (NOT multi-consumers safe).
387  *
388  * @param r
389  *   A pointer to the ring structure.
390  * @param obj_table
391  *   A pointer to a table of void * pointers (objects) that will be filled.
392  * @param n
393  *   The number of objects to dequeue from the ring to the obj_table,
394  *   must be strictly positive.
395  * @param available
396  *   If non-NULL, returns the number of remaining ring entries after the
397  *   dequeue has finished.
398  * @return
399  *   The number of objects dequeued, either 0 or n
400  */
401 static __rte_always_inline unsigned int
402 rte_ring_sc_dequeue_bulk(struct rte_ring *r, void **obj_table,
403 		unsigned int n, unsigned int *available)
404 {
405 	return rte_ring_sc_dequeue_bulk_elem(r, obj_table, sizeof(void *),
406 			n, available);
407 }
408 
409 /**
410  * Dequeue several objects from a ring.
411  *
412  * This function calls the multi-consumers or the single-consumer
413  * version, depending on the default behaviour that was specified at
414  * ring creation time (see flags).
415  *
416  * @param r
417  *   A pointer to the ring structure.
418  * @param obj_table
419  *   A pointer to a table of void * pointers (objects) that will be filled.
420  * @param n
421  *   The number of objects to dequeue from the ring to the obj_table.
422  * @param available
423  *   If non-NULL, returns the number of remaining ring entries after the
424  *   dequeue has finished.
425  * @return
426  *   The number of objects dequeued, either 0 or n
427  */
428 static __rte_always_inline unsigned int
429 rte_ring_dequeue_bulk(struct rte_ring *r, void **obj_table, unsigned int n,
430 		unsigned int *available)
431 {
432 	return rte_ring_dequeue_bulk_elem(r, obj_table, sizeof(void *),
433 			n, available);
434 }
435 
436 /**
437  * Dequeue one object from a ring (multi-consumers safe).
438  *
439  * This function uses a "compare and set" instruction to move the
440  * consumer index atomically.
441  *
442  * @param r
443  *   A pointer to the ring structure.
444  * @param obj_p
445  *   A pointer to a void * pointer (object) that will be filled.
446  * @return
447  *   - 0: Success; objects dequeued.
448  *   - -ENOENT: Not enough entries in the ring to dequeue; no object is
449  *     dequeued.
450  */
451 static __rte_always_inline int
452 rte_ring_mc_dequeue(struct rte_ring *r, void **obj_p)
453 {
454 	return rte_ring_mc_dequeue_elem(r, obj_p, sizeof(void *));
455 }
456 
457 /**
458  * Dequeue one object from a ring (NOT multi-consumers safe).
459  *
460  * @param r
461  *   A pointer to the ring structure.
462  * @param obj_p
463  *   A pointer to a void * pointer (object) that will be filled.
464  * @return
465  *   - 0: Success; objects dequeued.
466  *   - -ENOENT: Not enough entries in the ring to dequeue, no object is
467  *     dequeued.
468  */
469 static __rte_always_inline int
470 rte_ring_sc_dequeue(struct rte_ring *r, void **obj_p)
471 {
472 	return rte_ring_sc_dequeue_elem(r, obj_p, sizeof(void *));
473 }
474 
475 /**
476  * Dequeue one object from a ring.
477  *
478  * This function calls the multi-consumers or the single-consumer
479  * version depending on the default behaviour that was specified at
480  * ring creation time (see flags).
481  *
482  * @param r
483  *   A pointer to the ring structure.
484  * @param obj_p
485  *   A pointer to a void * pointer (object) that will be filled.
486  * @return
487  *   - 0: Success, objects dequeued.
488  *   - -ENOENT: Not enough entries in the ring to dequeue, no object is
489  *     dequeued.
490  */
491 static __rte_always_inline int
492 rte_ring_dequeue(struct rte_ring *r, void **obj_p)
493 {
494 	return rte_ring_dequeue_elem(r, obj_p, sizeof(void *));
495 }
496 
497 /**
498  * Flush a ring.
499  *
500  * This function flush all the elements in a ring
501  *
502  * @warning
503  * Make sure the ring is not in use while calling this function.
504  *
505  * @param r
506  *   A pointer to the ring structure.
507  */
508 void
509 rte_ring_reset(struct rte_ring *r);
510 
511 /**
512  * Return the number of entries in a ring.
513  *
514  * @param r
515  *   A pointer to the ring structure.
516  * @return
517  *   The number of entries in the ring.
518  */
519 static inline unsigned int
520 rte_ring_count(const struct rte_ring *r)
521 {
522 	uint32_t prod_tail = r->prod.tail;
523 	uint32_t cons_tail = r->cons.tail;
524 	uint32_t count = (prod_tail - cons_tail) & r->mask;
525 	return (count > r->capacity) ? r->capacity : count;
526 }
527 
528 /**
529  * Return the number of free entries in a ring.
530  *
531  * @param r
532  *   A pointer to the ring structure.
533  * @return
534  *   The number of free entries in the ring.
535  */
536 static inline unsigned int
537 rte_ring_free_count(const struct rte_ring *r)
538 {
539 	return r->capacity - rte_ring_count(r);
540 }
541 
542 /**
543  * Test if a ring is full.
544  *
545  * @param r
546  *   A pointer to the ring structure.
547  * @return
548  *   - 1: The ring is full.
549  *   - 0: The ring is not full.
550  */
551 static inline int
552 rte_ring_full(const struct rte_ring *r)
553 {
554 	return rte_ring_free_count(r) == 0;
555 }
556 
557 /**
558  * Test if a ring is empty.
559  *
560  * @param r
561  *   A pointer to the ring structure.
562  * @return
563  *   - 1: The ring is empty.
564  *   - 0: The ring is not empty.
565  */
566 static inline int
567 rte_ring_empty(const struct rte_ring *r)
568 {
569 	uint32_t prod_tail = r->prod.tail;
570 	uint32_t cons_tail = r->cons.tail;
571 	return cons_tail == prod_tail;
572 }
573 
574 /**
575  * Return the size of the ring.
576  *
577  * @param r
578  *   A pointer to the ring structure.
579  * @return
580  *   The size of the data store used by the ring.
581  *   NOTE: this is not the same as the usable space in the ring. To query that
582  *   use ``rte_ring_get_capacity()``.
583  */
584 static inline unsigned int
585 rte_ring_get_size(const struct rte_ring *r)
586 {
587 	return r->size;
588 }
589 
590 /**
591  * Return the number of elements which can be stored in the ring.
592  *
593  * @param r
594  *   A pointer to the ring structure.
595  * @return
596  *   The usable size of the ring.
597  */
598 static inline unsigned int
599 rte_ring_get_capacity(const struct rte_ring *r)
600 {
601 	return r->capacity;
602 }
603 
604 /**
605  * Return sync type used by producer in the ring.
606  *
607  * @param r
608  *   A pointer to the ring structure.
609  * @return
610  *   Producer sync type value.
611  */
612 static inline enum rte_ring_sync_type
613 rte_ring_get_prod_sync_type(const struct rte_ring *r)
614 {
615 	return r->prod.sync_type;
616 }
617 
618 /**
619  * Check is the ring for single producer.
620  *
621  * @param r
622  *   A pointer to the ring structure.
623  * @return
624  *   true if ring is SP, zero otherwise.
625  */
626 static inline int
627 rte_ring_is_prod_single(const struct rte_ring *r)
628 {
629 	return (rte_ring_get_prod_sync_type(r) == RTE_RING_SYNC_ST);
630 }
631 
632 /**
633  * Return sync type used by consumer in the ring.
634  *
635  * @param r
636  *   A pointer to the ring structure.
637  * @return
638  *   Consumer sync type value.
639  */
640 static inline enum rte_ring_sync_type
641 rte_ring_get_cons_sync_type(const struct rte_ring *r)
642 {
643 	return r->cons.sync_type;
644 }
645 
646 /**
647  * Check is the ring for single consumer.
648  *
649  * @param r
650  *   A pointer to the ring structure.
651  * @return
652  *   true if ring is SC, zero otherwise.
653  */
654 static inline int
655 rte_ring_is_cons_single(const struct rte_ring *r)
656 {
657 	return (rte_ring_get_cons_sync_type(r) == RTE_RING_SYNC_ST);
658 }
659 
660 /**
661  * Dump the status of all rings on the console
662  *
663  * @param f
664  *   A pointer to a file for output
665  */
666 void rte_ring_list_dump(FILE *f);
667 
668 /**
669  * Search a ring from its name
670  *
671  * @param name
672  *   The name of the ring.
673  * @return
674  *   The pointer to the ring matching the name, or NULL if not found,
675  *   with rte_errno set appropriately. Possible rte_errno values include:
676  *    - ENOENT - required entry not available to return.
677  */
678 struct rte_ring *rte_ring_lookup(const char *name);
679 
680 /**
681  * Enqueue several objects on the ring (multi-producers safe).
682  *
683  * This function uses a "compare and set" instruction to move the
684  * producer index atomically.
685  *
686  * @param r
687  *   A pointer to the ring structure.
688  * @param obj_table
689  *   A pointer to a table of void * pointers (objects).
690  * @param n
691  *   The number of objects to add in the ring from the obj_table.
692  * @param free_space
693  *   if non-NULL, returns the amount of space in the ring after the
694  *   enqueue operation has finished.
695  * @return
696  *   - n: Actual number of objects enqueued.
697  */
698 static __rte_always_inline unsigned int
699 rte_ring_mp_enqueue_burst(struct rte_ring *r, void * const *obj_table,
700 			 unsigned int n, unsigned int *free_space)
701 {
702 	return rte_ring_mp_enqueue_burst_elem(r, obj_table, sizeof(void *),
703 			n, free_space);
704 }
705 
706 /**
707  * Enqueue several objects on a ring (NOT multi-producers safe).
708  *
709  * @param r
710  *   A pointer to the ring structure.
711  * @param obj_table
712  *   A pointer to a table of void * pointers (objects).
713  * @param n
714  *   The number of objects to add in the ring from the obj_table.
715  * @param free_space
716  *   if non-NULL, returns the amount of space in the ring after the
717  *   enqueue operation has finished.
718  * @return
719  *   - n: Actual number of objects enqueued.
720  */
721 static __rte_always_inline unsigned int
722 rte_ring_sp_enqueue_burst(struct rte_ring *r, void * const *obj_table,
723 			 unsigned int n, unsigned int *free_space)
724 {
725 	return rte_ring_sp_enqueue_burst_elem(r, obj_table, sizeof(void *),
726 			n, free_space);
727 }
728 
729 /**
730  * Enqueue several objects on a ring.
731  *
732  * This function calls the multi-producer or the single-producer
733  * version depending on the default behavior that was specified at
734  * ring creation time (see flags).
735  *
736  * @param r
737  *   A pointer to the ring structure.
738  * @param obj_table
739  *   A pointer to a table of void * pointers (objects).
740  * @param n
741  *   The number of objects to add in the ring from the obj_table.
742  * @param free_space
743  *   if non-NULL, returns the amount of space in the ring after the
744  *   enqueue operation has finished.
745  * @return
746  *   - n: Actual number of objects enqueued.
747  */
748 static __rte_always_inline unsigned int
749 rte_ring_enqueue_burst(struct rte_ring *r, void * const *obj_table,
750 		      unsigned int n, unsigned int *free_space)
751 {
752 	return rte_ring_enqueue_burst_elem(r, obj_table, sizeof(void *),
753 			n, free_space);
754 }
755 
756 /**
757  * Dequeue several objects from a ring (multi-consumers safe). When the request
758  * objects are more than the available objects, only dequeue the actual number
759  * of objects
760  *
761  * This function uses a "compare and set" instruction to move the
762  * consumer index atomically.
763  *
764  * @param r
765  *   A pointer to the ring structure.
766  * @param obj_table
767  *   A pointer to a table of void * pointers (objects) that will be filled.
768  * @param n
769  *   The number of objects to dequeue from the ring to the obj_table.
770  * @param available
771  *   If non-NULL, returns the number of remaining ring entries after the
772  *   dequeue has finished.
773  * @return
774  *   - n: Actual number of objects dequeued, 0 if ring is empty
775  */
776 static __rte_always_inline unsigned int
777 rte_ring_mc_dequeue_burst(struct rte_ring *r, void **obj_table,
778 		unsigned int n, unsigned int *available)
779 {
780 	return rte_ring_mc_dequeue_burst_elem(r, obj_table, sizeof(void *),
781 			n, available);
782 }
783 
784 /**
785  * Dequeue several objects from a ring (NOT multi-consumers safe).When the
786  * request objects are more than the available objects, only dequeue the
787  * actual number of objects
788  *
789  * @param r
790  *   A pointer to the ring structure.
791  * @param obj_table
792  *   A pointer to a table of void * pointers (objects) that will be filled.
793  * @param n
794  *   The number of objects to dequeue from the ring to the obj_table.
795  * @param available
796  *   If non-NULL, returns the number of remaining ring entries after the
797  *   dequeue has finished.
798  * @return
799  *   - n: Actual number of objects dequeued, 0 if ring is empty
800  */
801 static __rte_always_inline unsigned int
802 rte_ring_sc_dequeue_burst(struct rte_ring *r, void **obj_table,
803 		unsigned int n, unsigned int *available)
804 {
805 	return rte_ring_sc_dequeue_burst_elem(r, obj_table, sizeof(void *),
806 			n, available);
807 }
808 
809 /**
810  * Dequeue multiple objects from a ring up to a maximum number.
811  *
812  * This function calls the multi-consumers or the single-consumer
813  * version, depending on the default behaviour that was specified at
814  * ring creation time (see flags).
815  *
816  * @param r
817  *   A pointer to the ring structure.
818  * @param obj_table
819  *   A pointer to a table of void * pointers (objects) that will be filled.
820  * @param n
821  *   The number of objects to dequeue from the ring to the obj_table.
822  * @param available
823  *   If non-NULL, returns the number of remaining ring entries after the
824  *   dequeue has finished.
825  * @return
826  *   - Number of objects dequeued
827  */
828 static __rte_always_inline unsigned int
829 rte_ring_dequeue_burst(struct rte_ring *r, void **obj_table,
830 		unsigned int n, unsigned int *available)
831 {
832 	return rte_ring_dequeue_burst_elem(r, obj_table, sizeof(void *),
833 			n, available);
834 }
835 
836 #ifdef __cplusplus
837 }
838 #endif
839 
840 #endif /* _RTE_RING_H_ */
841