chiark / gitweb /
util: generalize code that checks whether PIDs are alive or unwaited for
[elogind.git] / src / shared / macro.h
index 54b641be2361593e9d2b57625e5450aea626817f..dfbc20142f753172ee8708f5e5aa94eca27fa66b 100644 (file)
@@ -30,7 +30,6 @@
 #define _printf_(a,b) __attribute__ ((format (printf, a, b)))
 #define _alloc_(...) __attribute__ ((alloc_size(__VA_ARGS__)))
 #define _sentinel_ __attribute__ ((sentinel))
-#define _noreturn_ __attribute__((noreturn))
 #define _unused_ __attribute__ ((unused))
 #define _destructor_ __attribute__ ((destructor))
 #define _pure_ __attribute__ ((pure))
@@ -118,6 +117,13 @@ static inline size_t ALIGN_TO(size_t l, size_t ali) {
                         _a < _b ? _a : _b;      \
                 })
 
+#define LESS_BY(A,B)                            \
+        __extension__ ({                        \
+                        typeof(A) _A = (A);     \
+                        typeof(B) _B = (B);     \
+                        _A > _B ? _A - _B : 0;  \
+                })
+
 #ifndef CLAMP
 #define CLAMP(x, low, high)                                             \
         __extension__ ({                                                \
@@ -153,10 +159,12 @@ static inline size_t ALIGN_TO(size_t l, size_t ali) {
 #define assert_cc(expr) struct UNIQUE(_assert_struct_) { char x[(expr) ? 0 : -1]; };
 #endif
 
-#define assert_return(expr, r)                    \
-        do {                                      \
-                if (_unlikely_(!(expr)))          \
-                        return (r);               \
+#define assert_return(expr, r)                                          \
+        do {                                                            \
+                if (_unlikely_(!(expr))) {                              \
+                        log_assert_failed_return(#expr, __FILE__, __LINE__, __PRETTY_FUNCTION__); \
+                        return (r);                                     \
+                }                                                       \
         } while (false)
 
 #define PTR_TO_INT(p) ((int) ((intptr_t) (p)))
@@ -285,17 +293,41 @@ do {                                                                    \
 #define SET_FLAG(v, flag, b) \
         (v) = (b) ? ((v) | (flag)) : ((v) & ~(flag))
 
-#define IN_SET(x, ...) ({                                               \
-        typeof(x) _x = (x);                                             \
-        unsigned _i;                                                    \
-        bool _found = false;                                            \
-        for (_i = 0; _i < sizeof((typeof(_x)[]) { __VA_ARGS__ })/sizeof(typeof(_x)); _i++) \
-                if (((typeof(_x)[]) { __VA_ARGS__ })[_i] == _x) {       \
-                        _found = true;                                  \
-                        break;                                          \
-                }                                                       \
-        _found;                                                         \
+#define IN_SET(x, ...)                                                  \
+        ({                                                              \
+                const typeof(x) _x = (x);                               \
+                unsigned _i;                                            \
+                bool _found = false;                                    \
+                for (_i = 0; _i < sizeof((const typeof(_x)[]) { __VA_ARGS__ })/sizeof(const typeof(_x)); _i++) \
+                        if (((const typeof(_x)[]) { __VA_ARGS__ })[_i] == _x) { \
+                                _found = true;                          \
+                                break;                                  \
+                        }                                               \
+                _found;                                                 \
         })
 
+/* Define C11 thread_local attribute even on older gcc compiler
+ * version */
+#ifndef thread_local
+/*
+ * Don't break on glibc < 2.16 that doesn't define __STDC_NO_THREADS__
+ * see http://gcc.gnu.org/bugzilla/show_bug.cgi?id=53769
+ */
+#if __STDC_VERSION__ >= 201112L && !(defined(__STDC_NO_THREADS__) || (defined(__GNU_LIBRARY__) && __GLIBC__ == 2 && __GLIBC_MINOR__ < 16))
+#define thread_local _Thread_local
+#else
+#define thread_local __thread
+#endif
+#endif
+
+/* Define C11 noreturn without <stdnoreturn.h> and even on older gcc
+ * compiler versions */
+#ifndef noreturn
+#if __STDC_VERSION__ >= 201112L
+#define noreturn _Noreturn
+#else
+#define noreturn __attribute__((noreturn))
+#endif
+#endif
 
 #include "log.h"