0

To state things plainly, 2 billion plus 2 billion addition performed with both numbers of the int data-type yields the result -294967296 in C. I understand why the value is negative. The leftmost bit of the 32 bits representing the integer is used to denote if the number is either positive or negative. So once the highest possible value is reached with the remaining 31 bits, the leftmost bit is activated and hence, the value is negative. But why does C render the value as negative 294967296..? I'd imagine that the calculation will lead to a 32 bit binary representation of the number 4 billion, but since the 32nd bit is read as a negative sign, the value of the 32nd bit, i.e. 2^31 is not read by C and hence the value can be removed from the 4 billion, This gives us the value 1852516352, which because of the activated 32nd bit, the value ought to be returned as -1852516352.

-294967296 isn't a random value, either. I tried to add 2 billion with 1 billion, and again the calculation yielded a negative value, but this time -1294967296, which is 1 billion lesser than the previous result. This clearly indicates a pattern, where the more we add to it, the number directly increases in value.

I worked out some simple calculations and by trial and error I noticed that the calculation happens in this way... as if step by step the value of number 1 from the second number is being transferred to the first number. When the second number loses enough value to cause the first number to exceed that max value it can represent with 31 bits, the 32nd bit is activated. Hence, at this point the second number equals 1852516352 while the first numbers value is 2^31, i.e. 2147483648. But in binary terms, this number is 1 followed by 31 0's.

This is where things get a bit confusing for me. If that leading 1 is considered as the negative sign, the addition at this point must follow as:

-0 + 1852516352

Without that 1, the entire string of bits must equal to 0 in value. However, what is happening in practice is this:

-2147483648 + 1852516352

Which on addition returns -294967296, the same value returned in C. Apparently somehow the 32nd bit is both a negative sign and also a bit with value of weight 2^31.

Can someone please explain to me how this fits into how addition of integers happens in C at a lower level..? In general, but also especially in the context of integer overflow.

Amos P
  • 35
  • 6
  • *"The leftmost bit of the 32 bits representing the integer is used to denote if the number is either positive or negative."* That's not the whole story, given a [two's complement](https://en.wikipedia.org/wiki/Two%27s_complement) representation. – Bob__ Jun 20 '22 at 10:56
  • You might want to read https://en.wikipedia.org/wiki/Signed_number_representations, specifically also https://en.wikipedia.org/wiki/Two%27s_complement. Note however that signed overflow _in C_ specifically causes undefined behavior. – user17732522 Jun 20 '22 at 10:57
  • 1
    Overflows aren't well-defined in C so anything can happen, including the compiler generating incorrect/unexpected machine code. It's undefined behavior. In practice though, the vast majority of C programs run on instruction sets based on two's complement and this is well-defined behavior on the assembler level. So you can study how your particular instruction set does things and chances are your C program on top of it will behave the same. – Lundin Jun 20 '22 at 10:58
  • Thank you all for your response. I am able to gather from the suggested answer and from your comments that signed integer overflow is undefined because it is dependent on the CPU that runs the program and hence the behavior is inconsistent, and therefore undefined. Also while I'm not yet able to understand a lot about addition and overflow [I hoped for a simpler explanation :'D], I am able to understand that 2^31 in binary terms will indeed be read as -2147483648 because of a concept "two's complement", which I will abstract away for now. Thank you, again. – Amos P Jun 20 '22 at 11:21

0 Answers0