{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF}
{$ASSERTIONS ON}
program TruncBug;
{$IFNDEF FPC}{$APPTYPE CONSOLE}{$ENDIF}
uses SysUtils;
var
A: Extended;
begin
A := 0.6659963050;
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.66599630 0.66599631 0.66599631
Win64: 0.66599631 0.66599631
Lnx64: 0.66599630
*)
Writeln(FloatToStrF(A, ffFixed, 20, 8));
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.66599630 0.66599631 0.66599631
Win64: 0.66599631 0.66599631
Lnx64: 0.66599630
*)
Writeln(Format('%.8n',[A]));
end.
{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF}
{$ASSERTIONS ON}
program TruncBug;
{$IFNDEF FPC}{$APPTYPE CONSOLE}{$ENDIF}
uses
SysUtils;
var
A,B: Extended;
begin
A := 0.3050;
B := 0.6659963050;
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.31; 0.66599630 0.31; 0.66599631 0.31; 0.66599631
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.31; 0.66599630
*)
Writeln(FloatToStrF(A, ffFixed, 20, 2) + '; '+ FloatToStrF(B, ffFixed, 20, 8));
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.31; 0.66599630 0.31; 0.66599631 0.31; 0.66599631
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.31; 0.66599630
*)
Writeln(Format('%.2n; %.8n',[A,B]));
end.
Can you explain this:??? :P ::) O:-) <grumpy >:D >:D>
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF}
{$IFDEF D+} is shorthand for {$IF DEFINED(DEBUG}} or even {$IFDEF DEBUG} so you just wasted a second of your life by writing this... ;D
{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF} // With this redundant line commented out, nothing will be written. :D
{$ASSERTIONS ON}
program Test;
{$IFNDEF FPC}{$APPTYPE CONSOLE}{$ENDIF}
uses
SysUtils;
begin
{$IFDEF DEBUG}
Writeln('Hello World');
{$ENDIF}
end.
Note you are using a quite old trunk and recently there have been some changes regarding this.
IF you use trunk, then ALWAYS use the CURRENT trunk, give or take one or two minor revisions.
Otherwise it is rather pointless. I used 39712.
It is strange that linux64 and win64 differ. Of course the extended type is not the most ideal type to test, specially if you include 64-bit
{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF}
{$ASSERTIONS ON}
program TruncBug;
{$IFNDEF FPC}{$APPTYPE CONSOLE}{$ENDIF}
uses
SysUtils;
var
A,B: Double;
begin
A := 0.3050;
B := 0.6659963050;
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.31; 0.66599631 0.30; 0.66599630 0.30; 0.66599630
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.31; 0.66599631
*)
Writeln(FloatToStrF(A, ffFixed, 20, 2) + '; '+ FloatToStrF(B, ffFixed, 20, 8));
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.30; 0.66599630 0.30; 0.66599630 0.30; 0.66599630
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.30; 0.66599630
*)
Writeln(Format('%.2n; %.8n',[A,B]));
end.
With that redundant line commented out, nothing will be written. :D{$IFOPT D+} is enough. That's the point. DEBUG is predefined for the compiler. E.g:
I can confirm comingnine's observation. Here there is no output (Win7/64 and FPC304 or FPC311). May be this is default for Lazarus?With that redundant line commented out, nothing will be written. :D{$IFOPT D+} is enough. That's the point. DEBUG is predefined for the compiler. E.g:
begin {$IFOPT D+} // is the same as {$IFDEF DEBUG} you dont't need to mix them like you did. Writeln('Hello World'); {$ENDIF} end.
It is strange that linux64 and win64 differ. Of course the extended type is not the most ideal type to test, specially if you include 64-bitNo, it's not. Win64 is the only x86_64 target where Extended is not available. The other targets have not deprecated the FPU and thus FPC is happily using it for calculations.
The code tries to output a rounded float, and the output are given in the block comment. As seen, FloatToStrF and Format are inconsistent within FPC, and inconsistent with Delphi under Win32 and Lnx64. Could you help to comment how to make FloatToStrF and Format consistent within FPC (and with Delphi) ?The difference between the FPC targets is that Extended is not available on x86_64-win64, while it is available for the other x86_64 targets as well as all i386 targets (plus i8086, but that's probably neither here nor there for you :P ). It's also not supported on any other platform we have (e.g. ARM, PowerPC, etc.).
You are not entirely correct. The D option or DebugInfo is only enabled (outside of using $D+ or $DebugInfo On) when the parameter -g is passed (see here (https://www.freepascal.org/docs-html/current/prog/progsu89.html#x97-960001.3.6)).With that redundant line commented out, nothing will be written. :D{$IFOPT D+} is enough. That's the point. DEBUG is predefined for the compiler. E.g:
begin {$IFOPT D+} // is the same as { $IFDEF DEBUG} you dont't need to mix them like you did. Writeln('Hello World'); {$ENDIF} end.
#IFDEF DEBUG
-gl
-Crtoi
#WRITE Compiling Debug Version
#ENDIF
So it's in fact like this: if you compile with -dDEBUG then -g will be set and thus the D option will be as well.
What do you get if you try:
{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
{$IFOPT D+} {$DEFINE DEBUG} {$ENDIF}
{$ASSERTIONS ON}
program TruncBug;
{$IFNDEF FPC}{$APPTYPE CONSOLE}{$ENDIF}
uses
SysUtils;
var
A,B: Double;
Ax: Cardinal absolute A;
Bx: Cardinal absolute B;
begin
A := 0.3050;
B := 0.6659963050;
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.31; 0.66599631 0.30; 0.66599630 0.30; 0.66599630
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.31; 0.66599631
*)
Writeln(FloatToStrF(A, ffFixed, 20, 2) + '; '+ FloatToStrF(B, ffFixed, 20, 8));
(* FPC 3.1.1-r39514 Delphi7 Delphi25Tokyo
Win32: 0.30; 0.66599630 0.30; 0.66599630 0.30; 0.66599630
Win64: 0.31; 0.66599631 0.31; 0.66599631
Lnx64: 0.30; 0.66599630
*)
Writeln(Format('%.2n; %.8n',[A,B]));
(* FPC Delphi7 Delphi25Tokyo
WIN32 $B851EB85, $7BA76B3E $B851EB85, $7BA76B3E $B851EB85, $7BA76B3E
WIN64 $B851EB85, $7BA76B3E $B851EB85, $7BA76B3E
LNX64 $B851EB85, $7BA76B3E
*)
WriteLn('$',IntToHex(Ax,8),', $',IntToHex(Bx,8))
end.
It seems the representation is the same.While most likely they are the same, but the previous code is wrong. We should use QWord instead of DWord. Double is 8 bytes.