Fennel: /home/pub/open/dev/fennel/calctest/CalcExtMathTest.cpp Source File (original) (raw)

00001 00002 00003 00004 00005 00006 00007 00008 00009 00010 00011 00012 00013 00014 00015 00016 00017 00018 00019 00020 00021 00022 00023 00024 #include "fennel/common/CommonPreamble.h" 00025 #include "fennel/test/TestBase.h" 00026 #include "fennel/common/TraceSource.h" 00027 00028 #include "fennel/tuple/TupleDataWithBuffer.h" 00029 #include "fennel/tuple/TuplePrinter.h" 00030 #include "fennel/calculator/CalcCommon.h" 00031 #include "fennel/common/FennelExcn.h" 00032 00033 #include <boost/test/test_tools.hpp> 00034 #include <boost/scoped_array.hpp> 00035 #include 00036 #include 00037 #include <math.h> 00038 00039 using namespace fennel; 00040 using namespace std; 00041 00042 00043 class CalcExtMathTest : virtual public TestBase, public TraceSource 00044 { 00045 void checkWarnings(Calculator& calc, string expected); 00046 00047 void testCalcExtMathLogarithms(); 00048 void testCalcExtMathLogarithmsFails(); 00049 void testCalcExtMathPow(); 00050 void testCalcExtMathPowFails(); 00051 void testCalcExtMathAbs(); 00052 00053 void printOutput( 00054 TupleData const & tup, 00055 Calculator const & calc); 00056 00057 string mProgramPower; 00058 public: 00059 explicit CalcExtMathTest() 00060 : TraceSource(shared_from_this(),"CalcExtMathTest") 00061 { 00062 srand(time(NULL)); 00063 CalcInit::instance(); 00064 FENNEL_UNIT_TEST_CASE(CalcExtMathTest, testCalcExtMathLogarithms); 00065 FENNEL_UNIT_TEST_CASE(CalcExtMathTest, testCalcExtMathLogarithmsFails); 00066 FENNEL_UNIT_TEST_CASE(CalcExtMathTest, testCalcExtMathAbs); 00067 FENNEL_UNIT_TEST_CASE(CalcExtMathTest, testCalcExtMathPow); 00068 FENNEL_UNIT_TEST_CASE(CalcExtMathTest, testCalcExtMathPowFails); 00069 00070 00071
00072 ostringstream pg; 00073 00074 pg << "O d;" << endl; 00075 pg << "L d;" << endl; 00076 pg << "C %s, %s;" << endl; 00077 pg << "V %s, %s;" << endl; 00078 pg << "T;" << endl; 00079 pg << "CALL 'POW(L0, C0, C1);" << endl; 00080 pg << "REF O0, L0;" << endl; 00081 00082 mProgramPower = pg.str(); 00083 } 00084 00085 virtual ~CalcExtMathTest() 00086 { 00087 } 00088 }; 00089 00090 00091 void 00092 CalcExtMathTest::printOutput( 00093 TupleData const & tup, 00094 Calculator const & calc) 00095 { 00096 #if 0 00097 TuplePrinter tuplePrinter; 00098 tuplePrinter.print(cout, calc.getOutputRegisterDescriptor(), tup); 00099 cout << endl; 00100 #endif 00101 } 00102 00103 00104 void 00105 CalcExtMathTest::checkWarnings(Calculator& calc, string expected) 00106 { 00107 try { 00108 calc.exec(); 00109 } catch (...) { 00110 BOOST_FAIL("An exception was thrown while running program"); 00111 } 00112 00113 int i = calc.warnings().find(expected); 00114 00115 if (i < 0) { 00116 string msg = "Unexpected or no warning found\n"; 00117 msg += "Expected: "; 00118 msg += expected; 00119 msg += "\nActual: "; 00120 msg += calc.warnings(); 00121 00122 BOOST_FAIL(msg); 00123 } 00124 } 00125 00126 void 00127 CalcExtMathTest::testCalcExtMathLogarithms() 00128 { 00129 ostringstream pg(""); 00130 00131 pg << "O d, d;" << endl; 00132 pg << "L d, d;" << endl; 00133 pg << "C d, d;" << endl; 00134 pg << "V 2.71828, 10.0;" << endl; 00135 pg << "T;" << endl; 00136 pg << "CALL 'LN(L0, C0);" << endl; 00137 pg << "CALL 'LOG10(L1, C1);" << endl; 00138 pg << "REF O0, L0;" << endl; 00139 pg << "REF O1, L1;" << endl; 00140 00141 Calculator calc(0); 00142 00143 try { 00144 calc.assemble(pg.str().c_str()); 00145 } catch (FennelExcn& ex) { 00146 BOOST_FAIL("Assemble exception " << ex.getMessage()<< pg.str()); 00147 } 00148 00149 TupleDataWithBuffer outTuple(calc.getOutputRegisterDescriptor()); 00150 TupleDataWithBuffer inTuple(calc.getInputRegisterDescriptor()); 00151 00152 calc.bind(&inTuple, &outTuple); 00153 calc.exec(); 00154 printOutput(outTuple, calc); 00155 00156 for (int i = 0; i < 2; i++) { 00157 BOOST_CHECK( 00158 fabs( 00159 *(reinterpret_cast<double*> 00160 (const_cast(outTuple[i].pData))) - 1.0) 00161 < 0.0001); 00162 } 00163 } 00164 00165 00166 void 00167 CalcExtMathTest::testCalcExtMathLogarithmsFails() 00168 { 00169 char buff[1024]; 00170 const char* pg = 00171 "O d;\n" 00172 "L d;\n" 00173 "C %s;\n" 00174 "V %s;\n" 00175 "T;\n" 00176 "CALL '%s(L0, C0);\n" 00177 "REF O0, L0;\n"; 00178 00179 const char* tests[][3] = { 00180 { "LN", "s8", "0" }, 00181 { "LN", "d", "0.0" }, 00182 { "LN", "s8", "-1" }, 00183 { "LN", "d", "-1.0" }, 00184 { "LOG10", "s8", "0" }, 00185 { "LOG10", "d", "0.0" }, 00186 { "LOG10", "s8", "-1" }, 00187 { "LOG10", "d", "-1.0" }, 00188 }; 00189 00190 int n = sizeof(tests) / sizeof(tests[0]); 00191 for (int i = 0; i < n; i++) { 00192 Calculator calc(0); 00193 sprintf(buff, pg, tests[i][1], tests[i][2], tests[i][0]); 00194 try { 00195 calc.assemble(buff); 00196 } catch (FennelExcn& ex) { 00197 BOOST_FAIL("Assemble exception " << ex.getMessage() << ex.what()); 00198 } 00199 00200 TupleDataWithBuffer outTuple(calc.getOutputRegisterDescriptor()); 00201 TupleDataWithBuffer inTuple(calc.getInputRegisterDescriptor()); 00202 00203 calc.bind(&inTuple, &outTuple); 00204 checkWarnings(calc,"22023"); 00205 if (!outTuple.containsNull()) { 00206 BOOST_FAIL("Result should be NULL"); 00207 } 00208 } 00209 } 00210 00211 void 00212 CalcExtMathTest::testCalcExtMathAbs() 00213 { 00214 ostringstream pg(""); 00215 00216 pg << "O d, d, d, s8, s8, s8;" << endl; 00217 pg << "L d, d, d, s8, s8, s8;" << endl; 00218 pg << "C d, d, d, s8, s8, s8;" << endl; 00219
00220 pg << "V 0.0, -1234567890123.0, 1234567890123.0,";; 00221 pg << "0, 9223372036854775807, -9223372036854775807;" << endl; 00222 pg << "T;" << endl; 00223 pg << "CALL 'ABS(L0, C0);" << endl; 00224 pg << "CALL 'ABS(L1, C1);" << endl; 00225 pg << "CALL 'ABS(L2, C2);" << endl; 00226 pg << "CALL 'ABS(L3, C3);" << endl; 00227 pg << "CALL 'ABS(L4, C4);" << endl; 00228 pg << "CALL 'ABS(L5, C5);" << endl; 00229 pg << "REF O0, L0;" << endl; 00230 pg << "REF O1, L1;" << endl; 00231 pg << "REF O2, L2;" << endl; 00232 pg << "REF O3, L3;" << endl; 00233 pg << "REF O4, L4;" << endl; 00234 pg << "REF O5, L5;" << endl; 00235 00236
00237 00238 Calculator calc(0); 00239 00240 try { 00241 calc.assemble(pg.str().c_str()); 00242 } catch (FennelExcn& ex) { 00243 BOOST_FAIL("Assemble exception " << ex.getMessage() << pg.str()); 00244 } 00245 00246 TupleDataWithBuffer outTuple(calc.getOutputRegisterDescriptor()); 00247 TupleDataWithBuffer inTuple(calc.getInputRegisterDescriptor()); 00248 00249 calc.bind(&inTuple, &outTuple); 00250 calc.exec(); 00251 printOutput(outTuple, calc); 00252 00253 00254 double epsilon = 0.000001; 00255 00256 BOOST_CHECK( 00257 fabs( 00258 *(reinterpret_cast<double*> 00259 (const_cast(outTuple[0].pData))) - 00260 0) 00261 < epsilon); 00262 00263 BOOST_CHECK( 00264 fabs( 00265 *(reinterpret_cast<double*> 00266 (const_cast(outTuple[1].pData))) - 00267 1234567890123.0) 00268 < epsilon); 00269 00270 BOOST_CHECK( 00271 fabs( 00272 *(reinterpret_cast<double*> 00273 (const_cast(outTuple[2].pData))) - 00274 1234567890123.0) 00275 < epsilon); 00276 00277 BOOST_CHECK_EQUAL( 00278 *(reinterpret_cast<uint64_t*> 00279 (const_cast(outTuple[3].pData))),0); 00280 00281 BOOST_CHECK_EQUAL( 00282 (reinterpret_cast<uint64_t*>( 00283 const_cast(outTuple[4].pData))), 00284 9223372036854775807LL); 00285 BOOST_CHECK_EQUAL( 00286 (reinterpret_cast<uint64_t*>( 00287 const_cast(outTuple[5].pData))), 00288 9223372036854775807LL); 00289 } 00290 00291 void 00292 CalcExtMathTest::testCalcExtMathPow() 00293 { 00294 char buff[1024]; 00295 00296 00297 const char tests[][4] = { 00298 { "d", "d", "2.0", "2.2" }, 00299 { "d", "d", "2.0", "-2.2" }, 00300 { "d", "d", "-2.0", "2.0" }, 00301 }; 00302 00303 double results[] = { 4.5947934, 0.21763764, 4}; 00304 int n = sizeof(results) / sizeof(results[0]); 00305 assert(n == (sizeof(tests) / sizeof(tests[0]))); 00306 for (int i = 0; i < n; i++) { 00307 sprintf( 00308 buff, mProgramPower.c_str(), 00309 tests[i][0], tests[i][1], tests[i][2], tests[i][3]); 00310 00311 Calculator calc(0); 00312 try { 00313 calc.assemble(buff); 00314 } catch (FennelExcn& ex) { 00315 BOOST_FAIL( 00316 "Assemble exception " << ex.getMessage() << ex.what() << buff); 00317 } 00318 00319 TupleDataWithBuffer outTuple(calc.getOutputRegisterDescriptor()); 00320 TupleDataWithBuffer inTuple(calc.getInputRegisterDescriptor()); 00321 00322 calc.bind(&inTuple, &outTuple); 00323 calc.exec(); 00324 printOutput(outTuple, calc); 00325 00326 BOOST_CHECK( 00327 fabs( 00328 *(reinterpret_cast<double*>( 00329 const_cast(outTuple[0].pData))) - results[i]) 00330 < 0.00001); 00331 } 00332 } 00333 00334 void 00335 CalcExtMathTest::testCalcExtMathPowFails() 00336 { 00337 char buff[1024]; 00338 00339 const char tests[][4] = { 00340 { "d", "d", "0.0", "-1.0" }, 00341 { "d", "d", "-2.0", "2.2" }, 00342 { "d", "d", "-2.0", "-2.2" }, 00343 }; 00344 00345 int n = sizeof(tests) / sizeof(tests[0]); 00346 for (int i = 0; i < n; i++) { 00347 Calculator calc(0); 00348 sprintf( 00349 buff, mProgramPower.c_str(), 00350 tests[i][0], tests[i][1], tests[i][2], tests[i][3]); 00351 00352 try { 00353 calc.assemble(buff); 00354 } catch (FennelExcn& ex) { 00355 BOOST_FAIL("Assemble exception " << ex.getMessage() << ex.what()); 00356 } 00357 00358 TupleDataWithBuffer outTuple(calc.getOutputRegisterDescriptor()); 00359 TupleDataWithBuffer inTuple(calc.getInputRegisterDescriptor()); 00360 00361 calc.bind(&inTuple, &outTuple); 00362 checkWarnings(calc,"22023"); 00363 if (!outTuple.containsNull()) { 00364 BOOST_FAIL("Result should be NULL"); 00365 } 00366 } 00367 } 00368 00369 00370 FENNEL_UNIT_TEST_SUITE(CalcExtMathTest); 00371 00372