Path: utzoo!utgpu!jarvis.csri.toronto.edu!mailrus!wuarchive!wugate!uunet!zephyr.ens.tek.com!tekcrl!tekfdi!videovax!bart From: bart@videovax.tv.Tek.com (Bart Massey) Newsgroups: comp.lang.c++ Subject: Re: Time to standardize "true" and "false" Message-ID: <5571@videovax.tv.Tek.com> Date: 3 Oct 89 22:44:54 GMT References: <12070@cit-vax.Caltech.Edu> <8862@etana.tut.fi> <27541@amdcad.AMD.COM> <45fe2dd3.1199f@apollo.HP.COM> Reply-To: bart@videovax.tv.tek.com (Bart Massey) Organization: Tektronix TV Measurement Systems, Beaverton OR Lines: 79 In article <45fe2dd3.1199f@apollo.HP.COM> lsmith@apollo.HP.COM (Lawrence C. Smith) writes: > In article <27541@amdcad.AMD.COM> tim@amd.com (Tim Olson) writes: > >In article <8862@etana.tut.fi> pl@etana.tut.fi (Lehtinen Pertti) writes: > >| Then suddenly just behind the corner cames C-compiler from > >| ACME-corporation and realizes '!!a' -> negation of negation is > >| same as original -> we can optimize it away. > >| > >| Nice, isn't it. And too real too. > > > >And wrong, too. Do you know of a compiler that does this in the > >general case? > > Yes, all of them. Aiigh! I'm sure I'm about the millionth response to this, but I just can't stand it anymore! "The result of the logical negation operator ! is 1 if the value of its operand is 0, 0 if the value of its operand is non-zero. The type of the result is int. It is applicable to any arithmetic type or to pointers" -- K&R A:7.2, Stroustrup r.7.2 "The result of the logical negation operator ! is 0 if the value of its operand compares unequal to 0, 1 if the value of its operand compares equal to 0. The result has type int. The expression !E is equivalent to (0==E)." -- ANSI X3J11/88-158 3.3.3.3 19 So anything that is supposed to be a standard C or C++ compiler is *required* to do the right thing! As a test, I tried 4 C compilers we have around: Stanford's V6.0 68k (an ancient PCC based compiler) Greenhills 68k (a modern commercial compiler) BSD 4.3Tahoe VAX (a modern PCC based compiler) GNU GCC1.34 VAX (a cool highly optimizing retargetable compiler) The test code I used was simply: /* test.c */ main( argc, argv ) int argc; char **argv; { printf( "%d\n", (!!(atoi(argv[1]))) ); } All compilers, when invoked with "$(CC) $(MISCFLAGS) -O -o test test.c", produced a binary for which the invocation "./test 2" printed "1". Examination of the assembly code revealed various levels of optimization, but no obvious incorrect code. > This is an example of a "cheap" optimization, one that > is relatively easy and safe, most of the time. The fact that it does not > do what we would expect does not mean it is wrong, either. No, the fact that it does not conform to any accepted C language definition means that it is wrong. Note that your optimization *is* legal if the compiler can somehow tell that it is completely invisible -- the "as-if" rule. I.e., one can legally optimize if( !!a ) printf( "hello\n" ); to if( a ) printf( "hello\n" ); because the second statement behaves as if it were the first in all cases... Enough said. Please try writing some C code before making strong statements about the foibles of existing C compilers. I know of no compiler which will compile my test program above into incorrect code because of a bug involving the optimization of the "booleanizing operator" (sic :-) "!!". If anyone could give me an example of any such compiler that I could independently verify, I'd be truly interested. Bart Massey ..tektronix!videovax.tv.tek.com!bart ..tektronix!reed.bitnet!bart