> > Overall, it seems much simpler and safer to just correct overflows in the compiled code.
> Simpler: yes. Safer: yes. Unfortunately, it's also much slower.
In my experience with something similar - compiling LLVM to JavaScript in Emscripten, which also needs to properly implement integer math in JavaScript - it actually isn't a lot slower. On the Emscripten benchmark suite enabling overflow correction everywhere makes it only 5% slower. We might be running very different benchmarks I guess.
(However, overflow correction does increase code size a lot, which is why we have tools that let you get rid of it where it isn't needed.)
This is something we're aware of and we know we need to be extra clear and loud about it.
> Also, integer overflow is not the only case where this problem arises.
As far as I know, bigints are the only place where the VM and the generated JS intentionally differ in behavior. We are trying very hard to keep the two in sync.
> It also happens with say division of an integer. Will Dart compiled code in JS add proper rounding correction to all divisions of integers?
Dart has two division operators (~/ and /) to handle this. The former rounds (truncates? I'm not sure) and the latter does floating point division. So it's always the operation that determines the type of the result, and not the type of the operands.
> Overall, it seems much simpler and safer to just correct overflows in the compiled code.
Simpler: yes. Safer: yes. Unfortunately, it's also much slower.
Rolling your own numeric type in JS means slower behavior when you have overflowed and slow behavior even when you haven't. If you're generating code for "a + b", you can't compile that to "a + b" in JS because you need to check for overflow and handle the fact that a or b could be bignums.
We really want the compiled JS to behave the same as native code, but if it's significantly slower, people just won't use it at all. It's an unfortunate trade-off.