[yunqa.de] Re: FPU exceptions, Vista, and DISQLite3

  • From: "Michael J. Leaver" <MJLeaver@xxxxxxxxxxxxxxxxx>
  • To: <yunqa@xxxxxxxxxxxxx>
  • Date: Fri, 18 Jan 2008 14:28:08 +0800

Hi Ralf,

> I searched the web but all I could find was some vague mention of the
problem you describe, with no cause or > explanations given, not at
Microsoft's either. Which posting are you refering to exactly?

The post is titled "Vista and  Set8087CW" and is in the
"borland.public.delphi.language.delphi.win32" newsgroup. Here's a link:

http://dev.newswhat.com/amsg/borland.public.delphi.language.delphi.win32/478
e313a$1@xxxxxxxxxxxxxxxxxxxxxxxxxxx 

Thanks,
Michael J. Leaver
2BrightSparks Pte Ltd
http://www.2BrightSparks.com/
 
-----Original Message-----
From: yunqa-bounce@xxxxxxxxxxxxx [mailto:yunqa-bounce@xxxxxxxxxxxxx] On
Behalf Of Delphi Inspiration
Sent: Thursday, January 17, 2008 8:44 PM
To: yunqa@xxxxxxxxxxxxx
Subject: [yunqa.de] Re: FPU exceptions, Vista, and DISQLite3

Michael J. Leaver wrote:

>Hi, I saw on a CodeGear newsgroup that calling Set8087CW($133F) would fail
>on Vista unless the process was run with elevated privileges.


However, SQLiteSpy calls Set8087CW($133F); first thing after startup. If the
claim was true, it should certainly cause problems with Vista, but none have
yet been reported to me.

>The suggestion was to use the following code instead:
>
>procedure DisableFPUExceptions;
>var
>  FPUControlWord: Word;
>asm
>  FSTCW   FPUControlWord;
>  OR      FPUControlWord, $4 + $1;          // Divide by zero + invalid
>operation
>  FLDCW   FPUControlWord;
>end;

The above does not work with DISQLite3 as it only disables invalid operation
($1) and zerodivide ($4) FPU exceptions.

For DISQLite3, you also need to disable at least

 * zerodivide -  $4 
 * overflow   -  $8
 * underflow  - $16

My tests indicate that it is not necessary to suppress invalid operation
($1) as well, but it but it should not hurt either.

So here is the corrected versioni for DISQLite3:

procedure DisableFPUExceptions;
var
  FPUControlWord: Word;
asm
  FSTCW   FPUControlWord;
  { Disable the following FPU exceptions:
     $1 - invalid operation
     $2 - zero divide
     $8 - overflow
    $16 - underflow }
  OR      FPUControlWord, $10 + $8 + $4 + $1;
  FLDCW   FPUControlWord;
end;

To enable the FPU exceptions, call this:

procedure EnableFPUExceptions;
var
  FPUControlWord: Word;
asm
  FSTCW   FPUControlWord;
  { Enable the following FPU exceptions:
     $1 - invalid operation
     $2 - zero divide
     $8 - overflow
    $16 - underflow }
  AND     FPUControlWord, $FFFF - $1 - $4 - $8 - $10;
  FLDCW   FPUControlWord;
end;

I have not tested if these run fine on Vista in non-admin mode.

>Just to be sure, is there a requirement/reason to disable FPU exceptions
>when using DISQLite3?

Yes. You should disable FPU exceptions if your database handles floating
point numbers. Here is why:

The SQLite code is generally not prepared to recognize exceptions (FPU or
others) and does not respond to them as required. If an exception is raised,
the stack rolls back to the first point the exception is handled. For
Delphi, this is usually the build-in exception handler.

What is important to SQLite is that, as the stack rolls back, it skips all
code in SQLite which follows the instruction which raised the exception.
This code is usually contains commands to free allocated memory and report
errors. Applications will therefore end up with memory leaks and potentially
invalid error messages.

In addition, SQLite assumes the FPU to overflow or underflow for certain
floating point operations. Take these examples, which cause the FPU to store
INF and -INF to the result:

  SELECT  1e300*1e300;
  SELECT -1e300*1e300;

If FPU exceptions are disabled, the SQL will correctly return INF and -INF,
because the result is outside the range of a 8-bit floating point number.

With FPU exceptions enabled, the two SQL commands will raise an exception
when the floating point overflows or underflows. The stack will roll back,
SQLite can not clean up after itself, and your application will lack memory.

Ralf 

_______________________________________________
Delphi Inspiration mailing list
yunqa@xxxxxxxxxxxxx
//www.freelists.org/list/yunqa



_______________________________________________
Delphi Inspiration mailing list
yunqa@xxxxxxxxxxxxx
//www.freelists.org/list/yunqa



Other related posts: