eal: introduce macro for always inline
[dpdk.git] / lib / librte_eal / common / include / rte_common.h
index 0ea1b49..a9a7494 100644 (file)
@@ -38,7 +38,7 @@
  * @file
  *
  * Generic, commonly-used macro and inline function definitions
- * for Intel DPDK.
+ * for DPDK.
  */
 
 #ifdef __cplusplus
@@ -59,6 +59,36 @@ extern "C" {
 #define asm __asm__
 #endif
 
+/** C extension macro for environments lacking C11 features. */
+#if !defined(__STDC_VERSION__) || __STDC_VERSION__ < 201112L
+#define RTE_STD_C11 __extension__
+#else
+#define RTE_STD_C11
+#endif
+
+#ifdef RTE_ARCH_STRICT_ALIGN
+typedef uint64_t unaligned_uint64_t __attribute__ ((aligned(1)));
+typedef uint32_t unaligned_uint32_t __attribute__ ((aligned(1)));
+typedef uint16_t unaligned_uint16_t __attribute__ ((aligned(1)));
+#else
+typedef uint64_t unaligned_uint64_t;
+typedef uint32_t unaligned_uint32_t;
+typedef uint16_t unaligned_uint16_t;
+#endif
+
+/**
+ * Force alignment
+ */
+#define __rte_aligned(a) __attribute__((__aligned__(a)))
+
+/**
+ * Force a structure to be packed
+ */
+#define __rte_packed __attribute__((__packed__))
+
+/******* Macro to mark functions and fields scheduled for removal *****/
+#define __rte_deprecated       __attribute__((__deprecated__))
+
 /*********** Macros to eliminate unused variable warnings ********/
 
 /**
@@ -72,6 +102,11 @@ extern "C" {
  */
 #define RTE_SET_USED(x) (void)(x)
 
+/**
+ * Force a function to be inlined
+ */
+#define __rte_always_inline inline __attribute__((always_inline))
+
 /*********** Macros for pointer arithmetic ********/
 
 /**
@@ -245,7 +280,8 @@ rte_align64pow2(uint64_t v)
 /**
  * Macro to return the minimum of two numbers
  */
-#define RTE_MIN(a, b) ({ \
+#define RTE_MIN(a, b) \
+       __extension__ ({ \
                typeof (a) _a = (a); \
                typeof (b) _b = (b); \
                _a < _b ? _a : _b; \
@@ -254,7 +290,8 @@ rte_align64pow2(uint64_t v)
 /**
  * Macro to return the maximum of two numbers
  */
-#define RTE_MAX(a, b) ({ \
+#define RTE_MAX(a, b) \
+       __extension__ ({ \
                typeof (a) _a = (a); \
                typeof (b) _b = (b); \
                _a > _b ? _a : _b; \
@@ -299,10 +336,42 @@ rte_bsf32(uint32_t v)
 #define offsetof(TYPE, MEMBER)  __builtin_offsetof (TYPE, MEMBER)
 #endif
 
+/**
+ * Return pointer to the wrapping struct instance.
+ *
+ * Example:
+ *
+ *  struct wrapper {
+ *      ...
+ *      struct child c;
+ *      ...
+ *  };
+ *
+ *  struct child *x = obtain(...);
+ *  struct wrapper *w = container_of(x, struct wrapper, c);
+ */
+#ifndef container_of
+#define container_of(ptr, type, member)        __extension__ ({                \
+                       const typeof(((type *)0)->member) *_ptr = (ptr); \
+                       __attribute__((unused)) type *_target_ptr =     \
+                               (type *)(ptr);                          \
+                       (type *)(((uintptr_t)_ptr) - offsetof(type, member)); \
+               })
+#endif
+
 #define _RTE_STR(x) #x
 /** Take a macro value and get a string version of it */
 #define RTE_STR(x) _RTE_STR(x)
 
+/**
+ * ISO C helpers to modify format strings using variadic macros.
+ * This is a replacement for the ", ## __VA_ARGS__" GNU extension.
+ * An empty %s argument is appended to avoid a dangling comma.
+ */
+#define RTE_FMT(fmt, ...) fmt "%.0s", __VA_ARGS__ ""
+#define RTE_FMT_HEAD(fmt, ...) fmt
+#define RTE_FMT_TAIL(fmt, ...) __VA_ARGS__
+
 /** Mask value of type "tp" for the first "ln" bit set. */
 #define        RTE_LEN2MASK(ln, tp)    \
        ((tp)((uint64_t)-1 >> (sizeof(uint64_t) * CHAR_BIT - (ln))))