This is the mail archive of the gcc-bugs@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: gcc's <stdbool.h> is broken


On Mon, Feb 05, 2001 at 08:45:51PM +0000, Neil Booth wrote:
> Zack Weinberg wrote:-
> 
> > There is a real bug in this area, though: in C++, after including
> > stdbool.h, you still can't use 'true' and 'false' in #if.  They are
> > defined to themselves, and the preprocessor doesn't know the
> > keywords.
> 
> Hi Zack,
> 
> I'm a little confused.  What exactly does the C++ standard say
> w.r.t. true and false, and is your patch different?

I should have explained more clearly.

In C++98, there is a built-in boolean type, whose name is 'bool'.  The
keywords 'true' and 'false' are integer literals of type bool.  There
is no <stdbool.h>.  'true' and 'false' are not keywords during
preprocessing, so they do not work in #if expressions.

In C99, there is a built-in boolean type, whose name is '_Bool'.
'true', 'false', and 'bool' are not keywords, and there is no such
thing as an integer literal of type _Bool.  The standard header
<stdbool.h> contains these macros:

	#define bool _Bool
	#define true 1
	#define false 0
	#define __bool_true_false_are_defined 1

Therefore, after including <stdbool.h>, 'true' and 'false' are (macros
defined to) integer literals of type int, which work in #if
expressions.

The semantics of C++98 bool and C99 _Bool appear to be identical,
other than the above.  (But I Am Not A Language Lawyer.)

---

GCC's <stdbool.h> has been extended so that it works if included
from C++ code.  Instead of the above definitions, it does

	#define _Bool bool
	#define bool bool
	#define true true
	#define false false
	#define __bool_true_false_are_defined 1

Thus, _Bool can be used; bool, true, and false are macros; and true
and false are still integer literals of type bool.  It is essential
that true and false remain of type bool, otherwise

	#include <stdbool.h>

	extern void func(bool);
	extern void func(int);

	...

	func(true);

would call the wrong version of func.

However, with these definitions, true and false do not work in #if
expressions in C++ even after including stdbool.h.  It is desirable
that they do work, for maximum compatibility between C99 and C++, and
there's no reason why they shouldn't be known to the C++ preprocessor
at all times.

My patch makes them known to the C++ preprocessor at all times.  Using
them in #if is considered an extension (hence pedwarned) if you have
not already included <stdbool.h>.  The theory is that if you have
included stdbool.h, then (per C99), true and false are now the integer
constants 1 and 0, so the preprocessor should accept them in #if
without complaint.  They happen to keep their C++ish type, but that's
just quality-of-implementation.

Incidentally, it would probably be better (closer to C99 semantics) if
_Bool were a keyword of the C++ parser, with the same meaning as bool.
_Bool can be used in C99 code without including stdbool.h.

I don't envy the subcommittee charged with merging C99's changes into
C++0x.

zw

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]