[glib] gmacros: Don't define bogus __has_* macros



commit e2bd6a6a8f2b9f22e7092578f920e2b3057f4156
Author: Nirbheek Chauhan <nirbheek centricular com>
Date:   Fri Mar 23 23:10:57 2018 +0530

    gmacros: Don't define bogus __has_* macros
    
    This pollutes the reserved compiler namespace and breaks applications
    trying to do their own feature detection. For instance, this falsely
    detects that alloca is not a builtin on gcc:
    
        #include <glib.h>
        #if defined(__has_builtin)
        # if !__has_builtin(alloca)
        #  error "wtf glib?"
        # endif
        #else
        /* version-checking to determine alloca existence */
        #endif
    
    Instead, define our own g_macro__has_* versions that have the
    behaviour that we need.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=794635

 glib/gmacros.h       | 33 ++++++++++++++++++++++++---------
 glib/gnulib/verify.h | 10 ++++++----
 glib/gtypes.h        |  2 +-
 3 files changed, 31 insertions(+), 14 deletions(-)
---
diff --git a/glib/gmacros.h b/glib/gmacros.h
index 430a3fbb7..fcd49bdcd 100644
--- a/glib/gmacros.h
+++ b/glib/gmacros.h
@@ -108,21 +108,36 @@
 #define G_GNUC_NULL_TERMINATED
 #endif
 
-/* Clang feature detection: http://clang.llvm.org/docs/LanguageExtensions.html */
-#ifndef __has_attribute
-#define __has_attribute(x) 0
+/*
+ * Clang feature detection: http://clang.llvm.org/docs/LanguageExtensions.html
+ * These are not available on GCC, but since the pre-processor doesn't do
+ * operator short-circuiting, we can't use it in a statement or we'll get:
+ *
+ * error: missing binary operator before token "("
+ *
+ * So we define it to 0 to satisfy the pre-processor.
+ */
+
+#ifdef __has_attribute
+#define g_macro__has_attribute __has_attribute
+#else
+#define g_macro__has_attribute(x) 0
 #endif
 
-#ifndef __has_feature
-#define __has_feature(x) 0
+#ifdef __has_feature
+#define g_macro__has_feature __has_feature
+#else
+#define g_macro__has_feature(x) 0
 #endif
 
-#ifndef __has_builtin
-#define __has_builtin(x) 0
+#ifdef __has_builtin
+#define g_macro__has_builtin __has_builtin
+#else
+#define g_macro__has_builtin(x) 0
 #endif
 
 #if     (!defined(__clang__) && ((__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3))) || \
-        (defined(__clang__) && __has_attribute(__alloc_size__))
+        (defined(__clang__) && g_macro__has_attribute(__alloc_size__))
 #define G_GNUC_ALLOC_SIZE(x) __attribute__((__alloc_size__(x)))
 #define G_GNUC_ALLOC_SIZE2(x,y) __attribute__((__alloc_size__(x,y)))
 #else
@@ -223,7 +238,7 @@
 #endif  /* !__GNUC__ */
 #endif  /* !G_DISABLE_DEPRECATED */
 
-#if __has_feature(attribute_analyzer_noreturn) && defined(__clang_analyzer__)
+#if g_macro__has_feature(attribute_analyzer_noreturn) && defined(__clang_analyzer__)
 #define G_ANALYZER_ANALYZING 1
 #define G_ANALYZER_NORETURN __attribute__((analyzer_noreturn))
 #else
diff --git a/glib/gnulib/verify.h b/glib/gnulib/verify.h
index 267de2959..f5933b859 100644
--- a/glib/gnulib/verify.h
+++ b/glib/gnulib/verify.h
@@ -250,21 +250,23 @@ template <int w>
 
 #define verify(R) _GL_VERIFY (R, "verify (" #R ")")
 
-#ifndef __has_builtin
-# define __has_builtin(x) 0
+#ifdef __has_builtin
+# define _GL_MACRO__has_builtin __has_builtin
+#else
+# define _GL_MACRO__has_builtin(x) 0
 #endif
 
 /* Assume that R always holds.  This lets the compiler optimize
    accordingly.  R should not have side-effects; it may or may not be
    evaluated.  Behavior is undefined if R is false.  */
 
-#if (__has_builtin (__builtin_unreachable) \
+#if (_GL_MACRO__has_builtin (__builtin_unreachable) \
      || 4 < __GNUC__ + (5 <= __GNUC_MINOR__))
 # define assume(R) ((R) ? (void) 0 : __builtin_unreachable ())
 #elif 1200 <= _MSC_VER
 # define assume(R) __assume (R)
 #elif (defined lint \
-       && (__has_builtin (__builtin_trap) \
+       && (_GL_MACRO__has_builtin (__builtin_trap) \
            || 3 < __GNUC__ + (3 < __GNUC_MINOR__ + (4 <= __GNUC_PATCHLEVEL__))))
   /* Doing it this way helps various packages when configured with
      --enable-gcc-warnings, which compiles with -Dlint.  It's nicer
diff --git a/glib/gtypes.h b/glib/gtypes.h
index 047ac6227..09d9bd145 100644
--- a/glib/gtypes.h
+++ b/glib/gtypes.h
@@ -384,7 +384,7 @@ typedef const gchar *   (*GTranslateFunc)       (const gchar   *str,
 /* https://bugzilla.gnome.org/show_bug.cgi?id=769104 */
 #if __GNUC__ >= 5 && !defined(__INTEL_COMPILER)
 #define _GLIB_HAVE_BUILTIN_OVERFLOW_CHECKS
-#elif __has_builtin(__builtin_uadd_overflow)
+#elif g_macro__has_builtin(__builtin_uadd_overflow)
 #define _GLIB_HAVE_BUILTIN_OVERFLOW_CHECKS
 #endif
 #endif


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]