Use stdbool.h if suitable
authorPeter Eisentraut <peter_e@gmx.net>
Fri, 23 Mar 2018 00:42:25 +0000 (20:42 -0400)
committerPeter Eisentraut <peter_e@gmx.net>
Fri, 23 Mar 2018 00:42:25 +0000 (20:42 -0400)
Using the standard bool type provided by C allows some recent compilers
and debuggers to give better diagnostics.  Also, some extension code and
third-party headers are increasingly pulling in stdbool.h, so it's
probably saner if everyone uses the same definition.

But PostgreSQL code is not prepared to handle bool of a size other than
1, so we keep our own old definition if we encounter a stdbool.h with a
bool of a different size.  (Among current build farm members, this only
applies to old macOS versions on PowerPC.)

To check that the used bool is of the right size, add a static
assertions about size of GinTernaryValue vs bool.  This is currently the
only place that assumes that bool and char are of the same size.

Discussion: https://www.postgresql.org/message-id/flat/3a0fe7e1-5ed1-414b-9230-53bbc0ed1f49@2ndquadrant.com

src/backend/utils/adt/tsginidx.c
src/include/access/gin.h
src/include/c.h
src/include/pg_config.h.win32
src/pl/plperl/plperl.h

index de59e6417ebb71e348219e93f75e9d5cfa26c606..00e32b2570e027655e21ea694cb251273cc12d39 100644 (file)
@@ -309,7 +309,9 @@ gin_tsquery_consistent(PG_FUNCTION_ARGS)
         * query.
         */
        gcv.first_item = GETQUERY(query);
-       gcv.check = check;
+       StaticAssertStmt(sizeof(GinTernaryValue) == sizeof(bool),
+                        "sizes of GinTernaryValue and bool are not equal");
+       gcv.check = (GinTernaryValue *) check;
        gcv.map_item_operand = (int *) (extra_data[0]);
        gcv.need_recheck = recheck;
 
index 0acdb88241e68196b66fbc6d9dcc27a204431520..3d8a130b69bef093c19f473dc25fc61464c449f4 100644 (file)
@@ -51,8 +51,8 @@ typedef struct GinStatsData
 /*
  * A ternary value used by tri-consistent functions.
  *
- * For convenience, this is compatible with booleans. A boolean can be
- * safely cast to a GinTernaryValue.
+ * This must be of the same size as a bool because some code will cast a
+ * pointer to a bool to a pointer to a GinTernaryValue.
  */
 typedef char GinTernaryValue;
 
index 37c0c3919902a48a542a05a8452fdd8ce4abbb82..107f4f6bcd72829e5ca2b75d168ae5e54b6c0508 100644 (file)
  * bool
  *     Boolean value, either true or false.
  *
- * XXX for C++ compilers, we assume the compiler has a compatible
- * built-in definition of bool.
+ * Use stdbool.h if available and its bool has size 1.  That's useful for
+ * better compiler and debugger output and for compatibility with third-party
+ * libraries.  But PostgreSQL currently cannot deal with bool of other sizes;
+ * there are static assertions around the code to prevent that.
+ *
+ * For C++ compilers, we assume the compiler has a compatible built-in
+ * definition of bool.
  */
 
 #ifndef __cplusplus
 
+#if defined(HAVE_STDBOOL_H) && SIZEOF_BOOL == 1
+#include <stdbool.h>
+#else
+
 #ifndef bool
 typedef char bool;
 #endif
@@ -273,6 +282,7 @@ typedef char bool;
 #define false  ((bool) 0)
 #endif
 
+#endif
 #endif                         /* not C++ */
 
 
index e934cf87bd2c4a0f4abac02c9d21418715077cf8..b0477f02311508fa965526a357d97aa7e4ec02d5 100644 (file)
 /* Define to 1 if you have the `SSL_get_current_compression' function. */
 #define HAVE_SSL_GET_CURRENT_COMPRESSION 1
 
+/* Define to 1 if stdbool.h conforms to C99. */
+/* #undef HAVE_STDBOOL_H */
+
 /* Define to 1 if you have the <stdint.h> header file. */
 /* #undef HAVE_STDINT_H */
 
 /* Define to 1 if you have the <winldap.h> header file. */
 /* #undef HAVE_WINLDAP_H */
 
+/* Define to 1 if the system has the type `_Bool'. */
+/* #undef HAVE__BOOL */
+
 /* Define to 1 if your compiler understands __builtin_bswap16. */
 /* #undef HAVE__BUILTIN_BSWAP16 */
 
 /* A string containing the version number, platform, and C compiler */
 #define PG_VERSION_STR "Uninitialized version string (win32)"
 
+/* The size of `bool', as computed by sizeof. */
+#define SIZEOF_BOOL 0
+
 /* The size of `long', as computed by sizeof. */
 #define SIZEOF_LONG 4
 
index 6fe7803088e7d5ce1d40db4604c74a34537a51be..a85aefea6c11fda23e7bafb50378747b3c288c21 100644 (file)
 #define __inline__ inline
 #endif
 
+/*
+ * Prevent perl from redefining "bool".
+ */
+#define HAS_BOOL 1
+
 
 /*
  * Get the basic Perl API.  We use PERL_NO_GET_CONTEXT mode so that our code
 #define NEED_sv_2pv_flags
 #include "ppport.h"
 
-/* perl may have a different width of "bool", don't buy it */
-#ifdef bool
-#undef bool
-#endif
-
 /* supply HeUTF8 if it's missing - ppport.h doesn't supply it, unfortunately */
 #ifndef HeUTF8
 #define HeUTF8(he)            ((HeKLEN(he) == HEf_SVKEY) ?            \