Correct Clang feature detection Clang's __GNUC__ and __GNUC_MINOR__ definitions are not reliable and may not be defined at all when targeting the MSVC ABI. Use feature-checking macros when possible or check for __clang__. [guillem@hadrons.org: Update for __ protected keyword change. ] Signed-off-by: Guillem Jover <guillem@hadrons.org>
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126
diff --git a/include/bsd/sys/cdefs.h b/include/bsd/sys/cdefs.h
index c574fc2..999bda2 100644
--- a/include/bsd/sys/cdefs.h
+++ b/include/bsd/sys/cdefs.h
@@ -30,6 +30,13 @@
#ifndef __has_include_next
#define __has_include_next(x) 1
#endif
+#ifndef __has_attribute
+#define __has_attribute(x) 0
+#endif
+/* Clang expands this to 1 if an identifier is *not* reserved. */
+#ifndef __is_identifier
+#define __is_identifier(x) 1
+#endif
#ifdef LIBBSD_OVERLAY
/*
@@ -85,7 +92,7 @@
#define LIBBSD_GCC_VERSION 0
#endif
-#if LIBBSD_GCC_VERSION >= 0x0405
+#if LIBBSD_GCC_VERSION >= 0x0405 || __has_attribute(__deprecated__)
#define LIBBSD_DEPRECATED(x) __attribute__((__deprecated__(x)))
#elif LIBBSD_GCC_VERSION >= 0x0301
#define LIBBSD_DEPRECATED(x) __attribute__((__deprecated__))
@@ -93,14 +100,14 @@
#define LIBBSD_DEPRECATED(x)
#endif
-#if LIBBSD_GCC_VERSION >= 0x0200
+#if LIBBSD_GCC_VERSION >= 0x0200 || defined(__clang__)
#define LIBBSD_REDIRECT(name, proto, alias) name proto __asm__(LIBBSD_ASMNAME(#alias))
#endif
#define LIBBSD_ASMNAME(cname) LIBBSD_ASMNAME_PREFIX(__USER_LABEL_PREFIX__, cname)
#define LIBBSD_ASMNAME_PREFIX(prefix, cname) LIBBSD_STRING(prefix) cname
#ifndef __dead2
-# if LIBBSD_GCC_VERSION >= 0x0207
+# if LIBBSD_GCC_VERSION >= 0x0207 || __has_attribute(__noreturn__)
# define __dead2 __attribute__((__noreturn__))
# else
# define __dead2
@@ -108,7 +115,7 @@
#endif
#ifndef __pure2
-# if LIBBSD_GCC_VERSION >= 0x0207
+# if LIBBSD_GCC_VERSION >= 0x0207 || __has_attribute(__const__)
# define __pure2 __attribute__((__const__))
# else
# define __pure2
@@ -116,7 +123,7 @@
#endif
#ifndef __packed
-# if LIBBSD_GCC_VERSION >= 0x0207
+# if LIBBSD_GCC_VERSION >= 0x0207 || __has_attribute(__packed__)
# define __packed __attribute__((__packed__))
# else
# define __packed
@@ -124,7 +131,7 @@
#endif
#ifndef __aligned
-# if LIBBSD_GCC_VERSION >= 0x0207
+# if LIBBSD_GCC_VERSION >= 0x0207 || __has_attribute(__aligned__)
# define __aligned(x) __attribute__((__aligned__(x)))
# else
# define __aligned(x)
@@ -145,7 +152,7 @@
#endif
#ifndef __printflike
-# if LIBBSD_GCC_VERSION >= 0x0300
+# if LIBBSD_GCC_VERSION >= 0x0300 || __has_attribute(__format__)
# define __printflike(x, y) __attribute((__format__(__printf__, (x), (y))))
# else
# define __printflike(x, y)
@@ -153,7 +160,7 @@
#endif
#ifndef __nonnull
-# if LIBBSD_GCC_VERSION >= 0x0302
+# if LIBBSD_GCC_VERSION >= 0x0302 || __has_attribute(__nonnull__)
# define __nonnull(x) __attribute__((__nonnull__(x)))
# else
# define __nonnull(x)
@@ -175,7 +182,7 @@
* require it.
*/
#ifndef __offsetof
-# if LIBBSD_GCC_VERSION >= 0x0401
+# if LIBBSD_GCC_VERSION >= 0x0401 || !__is_identifier(__builtin_offsetof)
# define __offsetof(type, field) __builtin_offsetof(type, field)
# else
# ifndef __cplusplus
@@ -200,7 +207,7 @@
* compatible with member m.
*/
#ifndef __containerof
-# if LIBBSD_GCC_VERSION >= 0x0301
+# if LIBBSD_GCC_VERSION >= 0x0301 || !__is_identifier(__typeof__)
# define __containerof(x, s, m) ({ \
const volatile __typeof__(((s *)0)->m) *__x = (x); \
__DEQUALIFY(s *, (const volatile char *)__x - __offsetof(s, m)); \
diff --git a/src/arc4random.c b/src/arc4random.c
index c6f89c3..1a7b72f 100644
--- a/src/arc4random.c
+++ b/src/arc4random.c
@@ -39,11 +39,11 @@
#define minimum(a, b) ((a) < (b) ? (a) : (b))
-#if defined(__GNUC__) || defined(_MSC_VER)
+#if defined(__GNUC__) || defined(__clang__) || defined(_MSC_VER)
#define inline __inline
-#else /* __GNUC__ || _MSC_VER */
+#else /* __GNUC__ || __clang__ || _MSC_VER */
#define inline
-#endif /* !__GNUC__ && !_MSC_VER */
+#endif /* !__GNUC__ && !__clang__ && !_MSC_VER */
#define KEYSZ 32
#define IVSZ 8