Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

  In fact, prior to Java 8, you could not even declare unsigned integers.
In Java 8 you still can't declare unsigned integers. It just that API have been extended to provide operations that treat an int or a long as having unsigned value.

  This seems to imply that Java leaves the behaviour of signed integer overflow
  up to the underlying hardware, but guarantees a two's complement
  representation even if the architecture does not.  It seems reasonable to
  expect that it would simply wrap to 0 (I wasn't able to find a more
  conclusive reference for this).
In fact Java Specification does specify what happens in case of overflow very precisely. For example for multiplication (section 15.17.1):

  If an integer multiplication overflows, then the result is the low-order bits
  of the mathematical product as represented in some sufficiently large
  two's-complement format.
And for addition (section 15.18.2):

  If an integer addition overflows, then the result is the low-order bits of the
  mathematical sum as represented in some sufficiently large two's-complement
  format.

Java approach without undefined behaviour would seem to be quite convenient for a programmer, but it does not seem to be the case in practice. Of course you gain ability to check for overflow after performing the operation, which is nice, but at the same time loose the straightforward way to detect bugs provided by undefined behaviour (UB).

If an application executes UB, then it is obviously wrong, thus a simple instrumentation of arithmetic operation followed by a check for overflow gives a way to detect such problems without false positives (see for example -fsanitize=undefined and similar options available in modern C/C++ compilers).

IMHO only very small fraction of overflow bugs would have been fixed by just wrapping result around.



Of course you gain ability to check for overflow after performing the operation,

Using exceptions?

IMHO only very small fraction of overflow bugs would have been fixed by just wrapping result around.

Yes, switching to wrapping integers is not the solution to overflow. Rather check the operation beforehand. I still think using unsigned integers is always preferred if you don't need negative values.


What I had in mind, is the fact that with defined overflow you could unconditionally perform the operation, and then observe the result to decide if overflow have in fact happened. For example, following pattern to check if adding 100 to an integer 'a' overflows would be valid:

  int a = ...;
  if (a + 100 < a) overflow
So this is one of cases where wrapping behaviour could potentially fix bugs in existing applications. Obviously, rewriting this to work with overflow is trivial if you are already aware of undefined behaviour that could occur.


How would that fix existing code without modifying it?


Suppose somebody have written above code. Then under current C++ standard it would invoke UB on overflow. But, if standard were to change and require wrapping behaviour for int, then it would be "fixed", i.e, do what programmer intended it to do. Similarly if you use some compiler specific option to ensure wrapping behaviour for signed integers like GCC -fwrapv.


Oh, you are assuming someone actually wrote that code. That is circular reasoning.

It would be much better to write proper checks or just call functions that do so.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: