Dieter B?r?ner wrote:Dann, thanks for elaboborating on this.
I fear, this is drifting very offtopic for this forum now, and it is certainly my fault. Allow few more comment.
> For bit shift, the direction is important with signed values as to whether the behavior may be implementation defined or undefined.
They way, you say this, is a bit confusing for me, now. You refer to signed values. Isn't the undefined behaviour independent of the signedness? As I understand it, undefined behaviour can only be the result of shift count "out of bounds".
> The behavior with integer overflow might be implementation defined, or
> it may result in undefined behavior, depending on whether the
> hardware uses modular arithmetic:
I am confused a bit, here as well. Isn't "might be implementation defined" superflouos to mention here? When an overflow can result in undefined behaviour, unless specific conditions are given, where it won't result in undefined behaviour, I cannot see, how the undefined behaviour can be weakened to implementation defined behaviour.
Even, if it was the case, why should it depend on modular arithmetic. If I built a C-Compiler, and I write in the manual: "every signed integer overflow will evaluate to 0xffffffffffffffffLLU casted to the appropriate result type". That would clearly not be modular arithmetic. Still a rather implementation defined result, not?
I thought the annexes do not really belong to the Standard (in the sense, that a conforming C implementation can ignore the annexes).
Can you find fast, where in the main text of the Standard integer overflows are shown to be undefined behaviour?
Regards,
Dieter
This is from the body of the standard:
"3.4.3
1 undefined behavior
behavior, upon use of a nonportable or erroneous program construct or of erroneous data,
for which this International Standard imposes no requirements
2 NOTE Possible undefined behavior ranges from ignoring the situation completely with unpredictable
results, to behaving during translation or program execution in a documented manner characteristic of the
environment (with or without the issuance of a diagnostic message), to terminating a translation or
execution (with the issuance of a diagnostic message).
3 EXAMPLE An example of undefined behavior is the behavior on integer overflow."
But it is just an example.
From section "J.2 Undefined behavior" we do have this:
"? The value of the result of an integer arithmetic or conversion function cannot be represented (7.8.2.1, 7.8.2.2, 7.8.2.3, 7.8.2.4, 7.20.6.1, 7.20.6.2, 7.20.1)."
But the annex H (apparently) softens the result if the hardware platform defined the results of signed integer operations to be modular arithmetic (see the informative Annex H). At least that is how I read it.
As for the sifts... left shift of signed is undefined if negative:
"4 The result of E1 << E2 is E1 left-shifted E2 bit positions; vacated bits are filled with zeros. If E1 has an unsigned type, the value of the result is E1 ? 2E2, reduced modulo one more than the maximum value representable in the result type. If E1 has a signed type and nonnegative value, and E1 ? 2E2 is representable in the result type, then that is the resulting value; otherwise, the behavior is undefined."
but the right shift of negative numbers is implementation defined:
"5 The result of E1 >> E2 is E1 right-shifted E2 bit positions. If E1 has an unsigned type or if E1 has a signed type and a nonnegative value, the value of the result is the integral part of the quotient of E1 / 2E2. If E1 has a signed type and a negative value, the resulting value is implementation-defined."
Or so I would interpret it.