On Sun 20/04/08 3:43 PM , Christian Böhme monodhs@xxxxxx sent: > Tom St Denis wrote: > > But it isn't. > That's no news. I am interested in _why_ it is not. I have yet to > see a plausible explanation for the original algebraic statement why > a does not contain a _negative_ value although a's type allows it and > the compiler is given enough freedom to allocate a temporary large > enough and actually technically available (which is both the case) > to hold such a result. Because there is no such thing as a negative unsigned number. And the promotion applies to the operator, you do get that = is an operator just like + and / right? The promotions occur (in time) with respect to the order of precedence. If they occur out of order you end up with nastyness (like the float example I sent earlier). > > Numerically, that's what it does. > This is what is done _technically_. In pure algebraic terms and > > given the original expression, a = 4294967280UL is a colossal > screw-up which I actually expected the compiler to warn me about. Why? You negated an unsigned expression. Then assigned that unsigned value to a larger integer type. an unsigned promotion to a signed type [regardless of size] does NOT include a sign extension. Never has, never will. If you think about that, it makes sense. For example, unsigned char b = 255; int a = 4; a += b; Should the result be 3? Even though 255 is technically a -1 mod 256? How is that any different than your example? If we followed your logic, the above statement would read 1. promote b to a signed int (-1) 2. add to a and store > > I ask again. Why would that be sign extended? > > You are missing the point. The result of b * 2u is to be multiplied > by -1 and stored in a. How such a simple algebraic statement can > possibly be interpreted as some sick type conversion operation was > the point of the original post. Bottom line: If I wanted to use > modulo arithmetic I'd be _explicit_ about it. Bottom line is, if you want to work with signed data, don't use unsigned types. This sort of bug is probably hidden most of the time from you since if you use a 32-bit int, you'll get the negative value you want (but just by mere coincidence since they're both two's complement). > > You're right that a conversion is applied before being > stored, but the conversion > > rule applies to the = operator, nothing else. > > Interesting. Can you point me to the section(s) in the standard(s) > where temporary expressions are explicitly left out from integral > conversions ? They are converted, but to the type of the expression (multiple promotions may occur). For example: signed char a; short b; int c; long long d; d = d + (c + (b + a)); a is an expression of type signed char. b+a is of type short, c + ... is type int, and so on. The result of the expressions are promoted (converted) to the appropriate type. So if you had b = c = d = 0, and a = -1, then the result would be d = -1. Now change a to unsigned char and see what happens. All of a sudden d is equal to 255. Amazing! Apparently if you add 255 to a larger data type it doesn't get interpreted as negative! > > I have no idea what you're talking about. > > You will in a couple of years. All those having problem understanding the C [and C++] standards raise your hand (hint: this is embarrassing, but please raise your hand!!!). > That's a completely different problem dealing with _floating point_ > conversions (C++ 4.8) and irrelevant to the one I was describing. Actually, it's the exact same thing. The rules for promoting/converting regarding the = operator don't change just because you're using a float or heck even a structure!!! > It appears that you did not read the original post thoroughly as > that contained explicit references to the C++ standard. C++ and C are similar in regards to promoting data types for expressions. > > This is also totally off-topic for this list, as you're > not > > discussing a GCC bug. > > This is gcc-help and not gcc-bugs. And this has nothing specifically to do with GCC. Any conforming C or C++ compiler will generate the same damn output. And just because you're resilient to new information doesn't mean your complaints or observations are any more correct then when you first started posting. If you used the language properly in the first place, you wouldn't be in this mess. And while I'm on a rant, I should point out that type promotions is a very BASIC element of both the C and C++ languages, and any competent software developer should be familiar with them like they're 2nd nature. It'd be like the pianist having to look up where the middle C is every time they played... can't work that way. Tom