CppUnit project page
FAQ
Main Page
Related Pages
Modules
Namespaces
Classes
Files
File List
File Members
include
cppunit
portability
FloatingPoint.h
Go to the documentation of this file.
1
#ifndef CPPUNIT_PORTABILITY_FLOATINGPOINT_H_INCLUDED
2
#define CPPUNIT_PORTABILITY_FLOATINGPOINT_H_INCLUDED
3
4
#include <
cppunit/Portability.h
>
5
#include <math.h>
6
7
#if defined(__sun) && !defined(CPPUNIT_HAVE_ISFINITE) && defined(CPPUNIT_HAVE_FINITE)
8
#include <ieeefp.h>
9
// <math.h> is still needed for usage of fabs in TestAssert.cpp
10
#endif
11
12
CPPUNIT_NS_BEGIN
13
15
// According to IEEE-754 floating point standard,
16
// (see e.g. page 8 of
17
// http://www.cs.berkeley.edu/~wkahan/ieee754status/ieee754.ps)
18
// all comparisons with NaN are false except "x != x", which is true.
19
//
20
// At least Microsoft Visual Studio 6 is known not to implement this test correctly.
21
// It emits the following code to test equality:
22
// fcomp qword ptr [nan]
23
// fnstsw ax // copie fp (floating-point) status register to ax
24
// test ah,40h // test bit 14 of ax (0x4000) => C3 of fp status register
25
// According to the following documentation on the x86 floating point status register,
26
// the C2 bit should be tested to test for NaN value.
27
// http://webster.cs.ucr.edu/AoA/Windows/HTML/RealArithmetic.html#1000117
28
// In Microsoft Visual Studio 2003 & 2005, the test is implemented with:
29
// test ah,44h // Visual Studio 2005 test both C2 & C3...
30
//
31
// To work around this, a NaN is assumed to be detected if no strict ordering is found.
32
inline
bool
floatingPointIsUnordered
(
double
x )
33
{
34
// x != x will detect a NaN on conformant platform
35
// (2.0 < x && x < 1.0) will detect a NaN on non conformant platform:
36
// => no ordering can be found for x.
37
return
(x != x) || (2.0 < x && x < 1.0);
38
}
39
40
43
inline
int
floatingPointIsFinite
(
double
x )
44
{
45
#if defined(CPPUNIT_HAVE_ISFINITE)
46
return
isfinite( x );
47
#elif defined(CPPUNIT_HAVE_FINITE)
48
return
finite( x );
49
#elif defined(CPPUNIT_HAVE__FINITE)
50
return
_finite(x);
51
#else
52
double
testInf = x * 0.0;
// Produce 0.0 if x is finite, a NaN otherwise.
53
return
testInf == 0.0 && !
floatingPointIsUnordered
(testInf);
54
#endif
55
}
56
57
CPPUNIT_NS_END
58
59
#endif // CPPUNIT_PORTABILITY_FLOATINGPOINT_H_INCLUDED
Send comments to:
CppUnit Developers