mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
401 lines
8.8 KiB
401 lines
8.8 KiB
#include <stdio.h>
|
|
#include <float.h>
|
|
#include <math.h>
|
|
#include <errno.h>
|
|
|
|
// All global, this is just a test program
|
|
double TwoTo63,MinusTwoTo63;
|
|
double d;
|
|
|
|
double dd;
|
|
double yy;
|
|
|
|
void TestSin()
|
|
{
|
|
printf("TestSin\n");
|
|
// According to man, sin(2^63) returns non-finite
|
|
d = sin(TwoTo63);
|
|
if (_finite(d))
|
|
printf("sin(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
// According to man, sin(-2^63) returns non-finite
|
|
d = sin(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("sin(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
|
|
}
|
|
|
|
void TestSinh()
|
|
{
|
|
printf("TestSinh\n");
|
|
// According to man, sinh(2^63) returns non-finite
|
|
d = sinh(TwoTo63);
|
|
if (_finite(d))
|
|
printf("sinh(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
// According to man, sinh(-2^63) returns non-finite
|
|
d = sinh(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("sinh(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestaSin()
|
|
{
|
|
printf("TestaSin\n");
|
|
// According to man, asin(2^63) returns non-finite
|
|
d = asin(TwoTo63);
|
|
if (_finite(d))
|
|
printf("asin(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
// According to man, asin(-2^63) returns non-finite
|
|
d = asin(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("asin(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestCos()
|
|
{
|
|
printf("TestCos\n");
|
|
// According to man, cos(2^63) returns non-finite
|
|
d = cos(TwoTo63);
|
|
if (_finite(d))
|
|
printf("cos(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
// According to man, cos(-2^63) returns non-finite
|
|
d = cos(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("cos(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestCosh()
|
|
{
|
|
printf("TestCosh\n");
|
|
// According to man, cosh(2^63) returns non-finite
|
|
d = cosh(TwoTo63);
|
|
if (_finite(d))
|
|
printf("cosh(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
// According to man, cos(-2^63) returns non-finite
|
|
d = cosh(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("cosh(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestaCos()
|
|
{
|
|
printf("TestaCos\n");
|
|
// According to man, acos(2^63) returns non-finite
|
|
d = acos(TwoTo63);
|
|
if (_finite(d))
|
|
printf("acos(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
// According to man, acos(-2^63) returns non-finite
|
|
d = acos(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("acos(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestTan()
|
|
{
|
|
printf("TestTan\n");
|
|
// According to man, tan(2^63) returns non-finite
|
|
d = tan(TwoTo63);
|
|
if (_finite(d))
|
|
printf("tan(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
// According to man, tan(-2^63) returns non-finite
|
|
d = tan(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("tan(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
printf("\n");
|
|
}
|
|
|
|
void TestLog()
|
|
{
|
|
printf("TestLog\n");
|
|
// According to man, log(2^63) returns non-finite
|
|
d = log(TwoTo63);
|
|
if (_finite(d))
|
|
printf("log(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
// According to man, log(-2^63) returns non-finite
|
|
d = log(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("log(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
for (dd = -2.0; dd <= 5.0; dd += 1.0) {
|
|
yy = log( dd ); /* log of a negative number should return NaN */
|
|
printf ("log (%e) = %e\n",dd,yy);
|
|
}
|
|
|
|
printf("\n");
|
|
}
|
|
|
|
void TestLog10()
|
|
{
|
|
printf("TestLog10\n");
|
|
// According to man, log10(2^63) returns non-finite
|
|
d = log10(TwoTo63);
|
|
if (_finite(d))
|
|
printf("log10(2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
// According to man, log10(-2^63) returns non-finite
|
|
d = log10(MinusTwoTo63);
|
|
if (_finite(d))
|
|
printf("log10(-2^63) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
|
|
printf("\n");
|
|
}
|
|
|
|
void TestFmod()
|
|
{
|
|
printf("TestFmod\n");
|
|
d = fmod(1.0,0.0);
|
|
if (_finite(d))
|
|
printf("fmod(x,0.0) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
void TestSqrt()
|
|
{
|
|
printf("TestSqrt\n");
|
|
d = sqrt(-1);
|
|
if (_finite(d))
|
|
printf("sqrt(-1) returned finite number %e\n",d);
|
|
else
|
|
printf("Returned infinite number %e\n",d);
|
|
printf("\n");
|
|
}
|
|
|
|
char pdAcc[8];
|
|
|
|
#define dAcc (*(double *)pdAcc)
|
|
|
|
void DoubleSin()
|
|
{
|
|
|
|
__unaligned double pi;
|
|
|
|
char numPiHalf[8] = {0x18, 0x2D, 0x44, 0x54, 0xFB, 0x21, 0xF9, 0x3F};
|
|
|
|
printf("DoubleSin\n");
|
|
|
|
pi = (*(double *)numPiHalf)*2.0;
|
|
dAcc = pi * 10000000;
|
|
|
|
|
|
dAcc = sin(dAcc);
|
|
|
|
printf("Using EXCEL's PI %e\n",dAcc);
|
|
|
|
pi =3.14159265358979323846;
|
|
dAcc = pi * 10000000;
|
|
|
|
dAcc = sin(dAcc);
|
|
printf("Using LINUX's PI %e\n",dAcc);
|
|
|
|
pi =3.14159265358979;
|
|
dAcc = pi * 10000000;
|
|
|
|
dAcc = sin(dAcc);
|
|
printf("Using my rounded PI %e\n",dAcc);
|
|
|
|
pi =3.1415926535897932385;
|
|
dAcc = pi * 10000000;
|
|
|
|
dAcc = sin(dAcc);
|
|
printf("Using my rounded PI2 %e\n",dAcc);
|
|
|
|
printf("\n");
|
|
}
|
|
|
|
void PowProb()
|
|
{
|
|
double x, y;
|
|
double z;
|
|
int ii;
|
|
|
|
printf("PowProb\n");
|
|
|
|
x = 0;
|
|
|
|
for (z = -2.0, ii=0 ; z < 5.0; z++, ii++) {
|
|
errno = 0;
|
|
y = pow(x,z);
|
|
printf("pow(%e,%e) = %e and errno is %d\n",
|
|
x,z,y,errno);
|
|
}
|
|
|
|
for (z = -1.0, ii=0 ; z > -11.0; z--, ii++) {
|
|
errno = 0;
|
|
y = pow(10.0,z);
|
|
printf("pow(%e,%e) = %e and errno is %d\n",
|
|
10.0,z,y,errno);
|
|
}
|
|
printf("\n");
|
|
}
|
|
|
|
|
|
void SinPi()
|
|
{
|
|
|
|
double pi = 3.1415926535;
|
|
|
|
printf("SinPi\n");
|
|
|
|
printf("sin(pi) = %e\n",sin(pi));
|
|
printf("sin(pi * 100000000 = %e\n",
|
|
sin(pi * 100000000));
|
|
|
|
printf("\n");
|
|
}
|
|
|
|
void TanPi()
|
|
{
|
|
|
|
double pi = 3.1415926535;
|
|
double x, y;
|
|
|
|
printf("TanPi\n");
|
|
|
|
x = tan( pi / 4 );
|
|
y = tanh( x );
|
|
printf( "tan( %f ) = %e\n", x, y );
|
|
printf( "tanh( %f ) = %e\n", y, x );
|
|
printf("tan(pi / 2) = %e\n",tan(pi / 2));
|
|
printf("\n");
|
|
}
|
|
|
|
main()
|
|
{
|
|
|
|
|
|
TwoTo63 = pow(2,63);
|
|
MinusTwoTo63 = pow(-2,63);
|
|
printf("TwoTo63 = pow(2,63) = %e\n",TwoTo63);
|
|
printf("MinusTwoTo63 = pow(-2,63) = %e\n\n",MinusTwoTo63);
|
|
|
|
TestSin();
|
|
TestSinh(); // is okay
|
|
TestaSin(); // is okay
|
|
TestCos();
|
|
TestCosh(); // is okay
|
|
TestaCos(); // is okay
|
|
TestTan();
|
|
TestLog();
|
|
TestLog10();
|
|
TestFmod();
|
|
TestSqrt(); // is okay
|
|
DoubleSin();
|
|
PowProb();
|
|
SinPi();
|
|
TanPi();
|
|
}
|
|
|
|
/*
|
|
d1@ = 922337203685447.5807@
|
|
|
|
e1@ = -0.8
|
|
' do multipication first
|
|
C@ = d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2)
|
|
' than add this expression
|
|
If e1@ < 0@ Then
|
|
C@ = -C@ - ((e1@ * 10 Mod 10) * -15.19@) ^ 2
|
|
Else
|
|
C@ = C@ + ((e1@ * 10 Mod 10) * -15.19@) ^ 2
|
|
End If
|
|
|
|
If Abs(d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2) + ((e1@ * 10 Mod
|
|
10) * -15.19@) ^ 2) <> C@ Then
|
|
Debug.Print "Expression: Loop interation -> " + Str$(e1@), "", "", "OB 1
|
|
931"
|
|
End If
|
|
|
|
|
|
|
|
The sub expression
|
|
|
|
d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2)
|
|
|
|
is a double expression (not currency) and is imprecise. On intel,
|
|
the intermediate results are kept on the chip in 80-bit format
|
|
(64-bit mantissa). On MIPS, they're in 64-bit format and, thus, have
|
|
less precision and will likely generate different values.
|
|
|
|
In the case where we spill this value to a currency, this imprecise
|
|
double value gets rounded to currency representation (64-bit integer).
|
|
|
|
C@ = d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2)
|
|
If e1@ < 0@ Then
|
|
C@ = -C@ - ((e1@ * 10 Mod 10) * -15.19@) ^ 2
|
|
Else
|
|
C@ = C@ + ((e1@ * 10 Mod 10) * -15.19@) ^ 2
|
|
End If
|
|
|
|
In the case where the expression is *not* spilled to currency, the
|
|
intermediate result is kept as a double and the rest of the expression
|
|
is calculated. That is, the intermediate result may be different because
|
|
it was never rounded to currency representation. With intel's 80-bit
|
|
intermediate calculations, the answer will be more precise and, thus,
|
|
the difference is not apparant.
|
|
|
|
If Abs(d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2) +
|
|
((e1@ * 10 Mod 10) * -15.19@) ^ 2) <> C@
|
|
Then
|
|
Debug.Print "Fail"
|
|
End If
|
|
|
|
The correct way to write this test would be to subtract the two values
|
|
and make sure the difference was no greater than .0001 or something
|
|
like that (currency provides 4 decimal digits).
|
|
|
|
In order to semantically provide identical results, you would want to
|
|
convert the intermediate result to currency as follows (see the explicit
|
|
CCur call in the expression):
|
|
|
|
If Abs(CCur(d1@ * (e1@ ^ 4) * (e1@ ^ 3) * (e1@ ^ 2) * (e1@ ^ 2)) +
|
|
((e1@ * 10 Mod 10) * -15.19@) ^ 2) <> C@ Then
|
|
Debug.Print "Fail"
|
|
End If
|
|
|
|
*/
|