https://github.com/netwide-assembler/nasm/commit/44e89ba9b650b5e1533bca43682e167f51a3511f From: "H. Peter Anvin (Intel)" Date: Sun, 12 Oct 2025 12:48:32 -0700 Subject: [PATCH] compiler.h: drop the stupid C++-style cast-to-bool hack The C++-style cast-to-bool hack was broken in concept that it doesn't help the fundamental problem -- implicit conversions are broken for the backwards compatibility enum definition -- as well as in implementation, as it misspelled __STDC_VERSION__ as __STDC_VERSION. The #ifdef bool test *should* have prevented this problem, but apparently several compilers do define "bool" in even when it is a keyword, in violation of the C23 spec. Signed-off-by: H. Peter Anvin (Intel) --- a/include/compiler.h +++ b/include/compiler.h @@ -181,19 +181,10 @@ size_t strlcpy(char *, const char *, size_t); char * pure_func strrchrnul(const char *, int); #endif -#if !defined(__cplusplus) || (__STDC_VERSION >= 202311L) /* C++ and C23 have bool, false, and true as proper keywords */ +#if !defined(__cplusplus) || (__STDC_VERSION__ >= 202311L) # ifdef HAVE_STDBOOL_H -/* If exists, include it explicitly to prevent it from - begin included later, causing the "bool" macro to be defined. */ # include -# ifdef bool -/* Force bool to be a typedef instead of a macro. What a "clever" hack - this is... */ - typedef bool /* The macro definition of bool */ -# undef bool - bool; /* No longer the macro definition */ -# endif # elif defined(HAVE___BOOL) typedef _Bool bool; # define false 0 @@ -201,14 +192,10 @@ char * pure_func strrchrnul(const char *, int); # else /* This is a bit dangerous, because casting to this ersatz bool will not produce the same result as the standard (bool) cast. - Instead, use the bool() constructor-style macro defined below. */ + Instead, use the explicit construct !!x instead of relying on + implicit conversions or casts. */ typedef enum bool { false, true } bool; # endif -/* This amounts to a C++-style conversion cast to bool. This works - because C ignores an argument-taking macro when used without an - argument and because bool was redefined as a typedef if it previously - was defined as a macro (see above.) */ -# define bool(x) ((bool)!!(x)) #endif /* Create a NULL pointer of the same type as the address of @@ -321,11 +308,11 @@ static inline void *mempset(void *dst, int c, size_t n) * less likely to be taken. */ #ifdef HAVE___BUILTIN_EXPECT -# define likely(x) __builtin_expect(bool(x), true) -# define unlikely(x) __builtin_expect(bool(x), false) +# define likely(x) __builtin_expect(!!(x), true) +# define unlikely(x) __builtin_expect(!!(x), false) #else -# define likely(x) bool(x) -# define unlikely(x) bool(x) +# define likely(x) (!!(x)) +# define unlikely(x) (!!(x)) #endif #ifdef HAVE___BUILTIN_PREFETCH https://github.com/netwide-assembler/nasm/commit/746e7c9efa37cec9a44d84a1e96b8c38f385cc1f From: "H. Peter Anvin (Intel)" Date: Sun, 12 Oct 2025 13:05:55 -0700 Subject: [PATCH] compiler.h: the test for "neither C++ nor C23" still wrong The test needs to test for neither nor; as it was it tested "(not C++) or C23" which was not at all what was intended... Signed-off-by: H. Peter Anvin (Intel) --- a/include/compiler.h +++ b/include/compiler.h @@ -182,7 +182,7 @@ char * pure_func strrchrnul(const char *, int); #endif /* C++ and C23 have bool, false, and true as proper keywords */ -#if !defined(__cplusplus) || (__STDC_VERSION__ >= 202311L) +#if !defined(__cplusplus) && (__STDC_VERSION__ < 202311L) # ifdef HAVE_STDBOOL_H # include # elif defined(HAVE___BOOL)