OT (partially): about promotion of integers

David Piepgrass qwertie256 at gmail.com
Wed Dec 12 16:17:46 PST 2012


On Wednesday, 12 December 2012 at 06:19:14 UTC, Walter Bright 
wrote:
> You're not going to get performance with overflow checking even 
> with the best compiler support. For example, much arithmetic 
> code is generated for the x86 using addressing mode 
> instructions, like:
>
>     LEA EAX,16[8*EBX][ECX]  for 16+8*b+c
>
> The LEA instruction does no overflow checking. If you wanted 
> it, the best code would be:
>
>     MOV EAX,16
>     IMUL EBX,8
>     JO overflow
>     ADD EAX,EBX
>     JO overflow
>     ADD EAX,ECX
>     JO overflow
>
> Which is considerably less efficient. (The LEA is designed to 
> run in one cycle). Plus, often more registers are modified 
> which impedes good register allocation.

Thanks for the tip. Of course, I don't need and wouldn't use 
overflow checking all the time--in fact, since I've written a big 
system in a language that can't do overflow checking, you might 
say I "never need" overflow checking, in the same way that C 
programmers "never need" constructors, destructors, generics or 
exceptions as demonstrated by the fact that they can and do build 
large systems without them.

Still, the cost of overflow checking is a lot bigger, and 
requires a lot more cleverness, without compiler support. Hence I 
work harder to avoid the need for it.

> If you desire overflows to be programming errors, then you want 
> an abort, not a thrown exception. I am perplexed by your desire 
> to continue execution when overflows happen regularly.

I explicitly say I want to handle overflows quickly, and you 
conclude that I want an unrecoverable abort? WTF! No, I think 
overflows should be handled efficiently, and should be nonfatal.

Maybe it would be better to think in terms of the carry flag: it 
seems to me that a developer needs access to the carry flag in 
order to do 128+bit arithmetic efficiently. I have written code 
to "make do" without the carry flag, it's just more efficient if 
it can be used. So imagine an intrinsic that gets the value of 
the carry flag*--obviously it wouldn't throw an exception. I just 
think overflow should be handled the same way. If the developer 
wants to react to overflow with an exception/abort, fine, but it 
should not be mandatory as it is in .NET.

* Yes, I know you'd usually just ADC instead of retrieving the 
actual value of the flag, but sometimes you do want to just get 
the flag.

Usually when there is an overflow I just want to discard one data 
point and move on, or set the result to the maximum/minimum 
integer, possibly make a note in a log, but only occasionally do 
I want the debugger to break.


More information about the Digitalmars-d mailing list