[fpc-pascal] Division by Zero - not raised exception
Florian Klaempfl
florian at freepascal.org
Sun Apr 16 18:42:36 CEST 2006
Sasa Zeman wrote:
>> People will complain, if FPC isn't delphi compatible.
>
> FP actually is not 100% Delphi compatible by default mode and it is not
That's true.
> intention to be (regarding available informations on internet) it is
> actually intented to be compatible with Turbo/Borland Pascal, I suppose.
No. It depends on the mode.
> Delphi simulation mode (-Sd, or directive {$mode delphi} ) is not 100%
> compatible as well.
It tries to be ;)
>
>> Delphi in this case. And I see nothing wrong with it: the compiler can't
>> know the fpu exception mask at execution time when compiling the program
>> so throwing an error might be as wrong as returning Inf. So the only
>> real solution would be to carry out the 1/0 at run time, however, this
>> leads also to inconsistent code regarding const inf = 1/0; while
>> writeln(1/0); could throw an exception, writeln(Inf); wouldn't. So imo
>> any possible solution is wrong in some way.
>
> As I understood you (obviously not correct), you wrote that const block is
> not checked during compiling on division by Zero (as mentioned, infinity
> const can be set simply by bits setting)...
Well, doing this by hand is several work: you need to distinguish
between different endianesses, different data sizes and take care of non
standard formats like the arm fpa uses.
>From the compiler sources:
{$if defined(CPUARM) and defined(FPUFPA)}
MathQNaN : tdoublerec = (bytes : (0,0,252,255,0,0,0,0));
MathInf : tdoublerec = (bytes : (0,0,240,127,0,0,0,0));
MathNegInf : tdoublerec = (bytes : (0,0,240,255,0,0,0,0));
MathPi : tdoublerec = (bytes : (251,33,9,64,24,45,68,84));
{$else}
{$ifdef FPC_LITTLE_ENDIAN}
MathQNaN : tdoublerec = (bytes : (0,0,0,0,0,0,252,255));
MathInf : tdoublerec = (bytes : (0,0,0,0,0,0,240,127));
MathNegInf : tdoublerec = (bytes : (0,0,0,0,0,0,240,255));
MathPi : tdoublerec = (bytes : (24,45,68,84,251,33,9,64));
MathPiExtended : textendedrec = (bytes :
(53,194,104,33,162,218,15,201,0,64));
{$else FPC_LITTLE_ENDIAN}
MathQNaN : tdoublerec = (bytes : (255,252,0,0,0,0,0,0));
MathInf : tdoublerec = (bytes : (127,240,0,0,0,0,0,0));
MathNegInf : tdoublerec = (bytes : (255,240,0,0,0,0,0,0));
MathPi : tdoublerec = (bytes : (64,9,33,251,84,68,45,24));
MathPiExtended : textendedrec = (bytes :
(64,0,201,15,218,162,33,104,194,53));
{$endif FPC_LITTLE_ENDIAN}
{$endif}
>
> In any event, to be clear with suggestion: current solution is quiet
> problematic during testing quite complex calculations functionality, where
> dividing with zero constant is simple mistake.
> I have several quite complex
> statistical applications where simple mischanged constants division by 00
> instead of 100 (for example) create quite serious poblem, implying time to
> find the bug. Long compilation time for checking only (with -Cr ) and then
> without it just double already enormous compiling time (Lazarus project).
> That issued problem was consist with Delphi, however ut since fast
> compilation error was located and fixed very fast...
>
> Perhaps new {$AllowedDivisionByZero+-}compiler directive would be an
> convenient compromise.
Well, I consider the problem as minor so I don't know if it's worth to
introduce a new switch. I guess the best solution is to throw always a
hint. Since 1/0=Inf is IEEE compliant, it's no real error. If people
really want an error, they can create their own error msg file making
the hint an error.
More information about the fpc-pascal
mailing list