FEI Version of the Day
test_FEI_Implementation.cpp
00001 /*--------------------------------------------------------------------*/
00002 /*    Copyright 2005 Sandia Corporation.                              */
00003 /*    Under the terms of Contract DE-AC04-94AL85000, there is a       */
00004 /*    non-exclusive license for use of this work by or on behalf      */
00005 /*    of the U.S. Government.  Export of this program may require     */
00006 /*    a license from the United States Government.                    */
00007 /*--------------------------------------------------------------------*/
00008 
00009 #include <string.h>
00010 
00011 #include <fei_macros.hpp>
00012 #include <fei_sstream.hpp>
00013 
00014 #include <test_utils/test_FEI_Implementation.hpp>
00015 
00016 #include <FEI_Implementation.hpp>
00017 #ifdef HAVE_FEI_AZTECOO
00018 #include <fei_Aztec_LinSysCore.hpp>
00019 #endif
00020 #include <test_utils/FEData.hpp>
00021 #include <fei_LibraryWrapper.hpp>
00022 
00023 #include <test_utils/testData.hpp>
00024 
00025 #include <fei_Filter.hpp>
00026 
00027 #undef fei_file
00028 #define fei_file "test_FEI_Implementation.cpp"
00029 #include <fei_ErrMacros.hpp>
00030 
00031 test_FEI_Implementation::test_FEI_Implementation(MPI_Comm comm)
00032  : tester(comm)
00033 {
00034 }
00035 
00036 test_FEI_Implementation::~test_FEI_Implementation()
00037 {
00038 }
00039 
00040 int test_FEI_Implementation::runtests()
00041 {
00042   if (numProcs_<2) {
00043     CHK_ERR( serialtest1() );
00044   }
00045 
00046   CHK_ERR( test1() );
00047   CHK_ERR( test2() );
00048   CHK_ERR( test3() );
00049   CHK_ERR( test4() );
00050   return(0);
00051 }
00052 
00053 int test_FEI_Implementation::serialtest1()
00054 {
00055   int i, j, n = 3;
00056   double** coefs = new double*[n];
00057   double** copy = new double*[n];
00058   double** correct = new double*[n];
00059 
00060   for(i=0; i<n; ++i) {
00061     coefs[i] = new double[n];
00062     copy[i] = new double[n];
00063     correct[i] = new double[n];
00064     for(j=0; j<n; ++j) {
00065       coefs[i][j] = (double)(i+j);
00066       correct[i][j] = (double)(i+j);
00067     }
00068   }
00069 
00070   Filter::copyStiffness(coefs, n, FEI_DENSE_ROW, copy);
00071   CHK_ERR( compareCoefs(n, correct, copy) );
00072 
00073   for(i=0; i<n; ++i) {
00074     for(j=0; j<n; ++j) coefs[i][j] = 0.0;
00075     for(j=i; j<n; ++j) {
00076       coefs[i][j-i] = (double)(i+j);
00077     }
00078   }
00079 
00080   Filter::copyStiffness(coefs, n, FEI_UPPER_SYMM_ROW, copy);
00081   CHK_ERR( compareCoefs(n, correct, copy) );
00082 
00083   for(i=0; i<n; ++i) {
00084     for(j=0; j<n; ++j) coefs[i][j] = 0.0;
00085     for(j=0; j<n; ++j) {
00086       if (j>i) continue;
00087       coefs[i][j] = (double)(i+j);
00088     }
00089   }
00090 
00091   Filter::copyStiffness(coefs, n, FEI_LOWER_SYMM_ROW, copy);
00092   CHK_ERR( compareCoefs(n, correct, copy) );
00093 
00094   for(i=0; i<n; ++i) {
00095     delete [] coefs[i];
00096     delete [] copy[i];
00097     delete [] correct[i];
00098   }
00099 
00100   delete [] coefs;
00101   delete [] copy;
00102   delete [] correct;
00103 
00104   return(0);
00105 }
00106 
00107 int test_FEI_Implementation::compareCoefs(int n,
00108             const double*const* coefs1,
00109             const double*const* coefs2)
00110 {
00111   for(int i=0; i<n; ++i) {
00112     for(int j=0; j<n; ++j) {
00113       double diff = coefs1[i][j] - coefs2[i][j];
00114       if (diff > 1.e-20 || diff < -1.e-20) {
00115   return(-1);
00116       }
00117     }
00118   }
00119 
00120   return(0);
00121 }
00122 
00123 int test_FEI_Implementation::test1()
00124 {
00125 #ifdef HAVE_FEI_AZTECOO
00126   fei::SharedPtr<testData> testdata(new testData(localProc_, numProcs_));
00127 
00128   fei::SharedPtr<LinearSystemCore> linSys(new fei_trilinos::Aztec_LinSysCore(comm_));
00129   fei::SharedPtr<LibraryWrapper> wrapper(new LibraryWrapper(linSys));
00130 
00131   fei::SharedPtr<FEI_Implementation>
00132     fei(new FEI_Implementation(wrapper, comm_, 0));
00133 
00134   int numParams = 2;
00135   char** params = new char*[numParams];
00136   params[0] = new char[128];
00137   strcpy(params[0], "name test1");
00138   if (path_.empty()) {
00139     params[1] = new char[32];
00140     strcpy(params[1], "debugOutput .");
00141   }
00142   else {
00143     FEI_OSTRINGSTREAM osstr;
00144     osstr << "debugOutput " << path_;
00145     std::string str = osstr.str();
00146     
00147     params[1] = new char[str.size()+1];
00148     strcpy(params[1], str.c_str());
00149   }
00150 
00151   //call the parameters function a couple of times to test the fei's internal
00152   //method for merging string lists when parameters is called more than once.
00153   CHK_ERR( fei->parameters(1, &params[0]) );
00154   CHK_ERR( fei->parameters(1, &params[1]) );
00155   CHK_ERR( fei->parameters(2, params) );
00156 
00157   delete [] params[0];
00158   delete [] params[1];
00159   delete [] params;
00160 
00161   CHK_ERR( fei->setIDLists(1, &(testdata->ids[0]),
00162          1, &(testdata->ids[0])) );
00163 
00164   CHK_ERR( fei->initFields(testdata->fieldIDs.size(),
00165         &(testdata->fieldSizes[0]),
00166         &(testdata->fieldIDs[0])) );
00167 
00168   unsigned numNodesPerElem = testdata->ids.size();
00169   std::vector<int> numFieldsPerNode(numNodesPerElem, 1);
00170   std::vector<int*>nodalFieldIDs(numNodesPerElem, &(testdata->fieldIDs[0]));
00171 
00172   CHK_ERR( fei->initElemBlock(0, //blockID
00173            1, //numElements
00174            numNodesPerElem,
00175            &numFieldsPerNode[0],
00176            &nodalFieldIDs[0],
00177            0, //numElemDofFieldsPerElement
00178            NULL, //elemDofFieldIDs
00179            0)); //interleaveStrategy
00180 
00181   CHK_ERR( fei->initElem(0, //blockID
00182             0, //elemID
00183             &(testdata->ids[0])) );
00184 
00185   std::vector<int*> sharingProcs2D(testdata->sharedIDs.size());
00186   int offset = 0;
00187   for(unsigned i=0; i<testdata->numSharingProcsPerID.size(); ++i) {
00188     sharingProcs2D[i] = &(testdata->sharingProcs[offset]);
00189     offset += testdata->numSharingProcsPerID[i];
00190   }
00191 
00192   if (testdata->sharedIDs.size() > 0) {
00193     CHK_ERR( fei->initSharedNodes(testdata->sharedIDs.size(),
00194       testdata->sharedIDs.size() ? &(testdata->sharedIDs[0]) : 0,
00195       testdata->numSharingProcsPerID.size() ? &(testdata->numSharingProcsPerID[0]) : 0,
00196       &sharingProcs2D[0]) );
00197   }
00198 
00199   CHK_ERR( fei->initComplete() );
00200 
00201   std::vector<double> rhsData(testdata->ids.size(), 1.0);
00202 
00203   double one = 1.0;
00204   CHK_ERR( fei->setMatScalars(1, &(testdata->ids[0]), &one) );
00205   CHK_ERR( fei->setRHSScalars(1, &(testdata->ids[0]), &one) );
00206 
00207   CHK_ERR( fei->setCurrentMatrix(testdata->ids[0]) );
00208   CHK_ERR( fei->setCurrentRHS(testdata->ids[0]) );
00209 
00210   CHK_ERR( fei->putIntoRHS(FEI_NODE, testdata->fieldIDs[0],
00211          testdata->ids.size(),
00212          &(testdata->ids[0]),
00213          &(rhsData[0])) );
00214 
00215   int numBCNodes = 2;
00216   GlobalID* BCNodeIDs = &(testdata->ids[0]);
00217   int BCFieldID = testdata->fieldIDs[0];
00218   double* values = new double[numBCNodes];
00219   int* offsetsIntoField = new int[numBCNodes];
00220   for(int ii=0; ii<numBCNodes; ++ii) {
00221     values[ii] = 1.0;
00222     offsetsIntoField[ii] = 0;
00223   }
00224 
00225   CHK_ERR( fei->loadNodeBCs(numBCNodes, BCNodeIDs, BCFieldID,
00226           offsetsIntoField, values) );
00227 
00228   delete [] offsetsIntoField;
00229   delete [] values;
00230 
00231   CHK_ERR( fei->loadComplete() );
00232 
00233   int numActiveNodes = 0;
00234   CHK_ERR( fei->getNumLocalNodes(numActiveNodes) );
00235   if (numActiveNodes != (int)testdata->ids.size()) {
00236     ERReturn(-1);
00237   }
00238 
00239   GlobalID* localNodes = new GlobalID[numActiveNodes];
00240   CHK_ERR( fei->getLocalNodeIDList(numActiveNodes, localNodes, numActiveNodes) );
00241 
00242   int totalFieldSize = 0;
00243   for(int ii=0; ii<(int)testdata->fieldSizes.size(); ++ii) {
00244     totalFieldSize += testdata->fieldSizes[ii];
00245   }
00246 
00247   double* soln = new double[numActiveNodes*totalFieldSize];
00248   int* offsets = new int[numActiveNodes+1];
00249 
00250   CHK_ERR( fei->getNodalSolution(numActiveNodes, localNodes,
00251          offsets, soln) );
00252   delete [] offsets;
00253   delete [] soln;
00254   delete [] localNodes;
00255 
00256   CHK_ERR( fei->resetInitialGuess() );
00257 
00258   int fieldSize = 0;
00259   CHK_ERR( fei->getFieldSize(testdata->fieldIDs[0], fieldSize) );
00260 
00261   double initTime, loadTime, solveTime, solnReturnTime;
00262   CHK_ERR( fei->cumulative_cpu_times(initTime, loadTime, solveTime,
00263               solnReturnTime) );
00264 #endif
00265   return(0);
00266 }
00267 
00268 int test_FEI_Implementation::test2()
00269 {
00270   fei::SharedPtr<testData> testdata(new testData(localProc_, numProcs_));
00271 
00272   fei::SharedPtr<FiniteElementData> fedata(new FEData(comm_));
00273   fei::SharedPtr<LibraryWrapper> wrapper(new LibraryWrapper(fedata));
00274   fei::SharedPtr<FEI_Implementation>
00275     fei(new FEI_Implementation(wrapper, comm_, 0));
00276 
00277   int numParams = 2;
00278   char** params = new char*[numParams];
00279   params[0] = new char[128];
00280   strcpy(params[0], "name test1");
00281   if (path_.empty()) {
00282     params[1] = new char[32];
00283     strcpy(params[1], "debugOutput .");
00284   }
00285   else {
00286     FEI_OSTRINGSTREAM osstr;
00287     osstr << "debugOutput " << path_;
00288     std::string str = osstr.str();
00289     
00290     params[1] = new char[str.size()+1];
00291     strcpy(params[1], str.c_str());
00292   }
00293 
00294 
00295   //call the parameters function a couple of times to test the fei's internal
00296   //method for merging string lists when parameters is called more than once.
00297   CHK_ERR( fei->parameters(1, &params[0]) );
00298   CHK_ERR( fei->parameters(1, &params[1]) );
00299   CHK_ERR( fei->parameters(2, params) );
00300 
00301   delete [] params[0];
00302   delete [] params[1];
00303   delete [] params;
00304 
00305   CHK_ERR( fei->setIDLists(1, &(testdata->ids[0]),
00306          1, &(testdata->ids[0])) );
00307 
00308   CHK_ERR( fei->initFields(testdata->fieldIDs.size(),
00309         &(testdata->fieldSizes[0]),
00310         &(testdata->fieldIDs[0])) );
00311 
00312   unsigned numNodesPerElem = testdata->ids.size();
00313   std::vector<int> numFieldsPerNode(numNodesPerElem, 1);
00314   std::vector<int*>nodalFieldIDs(numNodesPerElem, &(testdata->fieldIDs[0]));
00315 
00316   CHK_ERR( fei->initElemBlock(0, //blockID
00317             1, //numElements
00318             numNodesPerElem,
00319             &numFieldsPerNode[0],
00320             &nodalFieldIDs[0],
00321             0, //numElemDofFieldsPerElement
00322             NULL, //elemDofFieldIDs
00323             0)); //interleaveStrategy
00324 
00325   CHK_ERR( fei->initElem(0, //blockID
00326             0, //elemID
00327             &(testdata->ids[0])) );
00328 
00329   std::vector<int*> sharingProcs2D(testdata->sharedIDs.size());
00330   int offset = 0;
00331   for(unsigned i=0; i<testdata->numSharingProcsPerID.size(); ++i) {
00332     sharingProcs2D[i] = &(testdata->sharingProcs[offset]);
00333     offset += testdata->numSharingProcsPerID[i];
00334   }
00335 
00336   if (testdata->sharedIDs.size() > 0) {
00337     CHK_ERR( fei->initSharedNodes(testdata->sharedIDs.size(),
00338       testdata->sharedIDs.size() ? &(testdata->sharedIDs[0]) : 0,
00339       testdata->numSharingProcsPerID.size() ? &(testdata->numSharingProcsPerID[0]) : 0,
00340       &sharingProcs2D[0]) );
00341   }
00342 
00343   CHK_ERR( fei->initComplete() );
00344 
00345   int numBlkActNodes = 0;
00346   CHK_ERR( fei->getNumBlockActNodes(0, numBlkActNodes) );
00347 
00348   std::vector<double> rhsData(testdata->ids.size(), 1.0);
00349 
00350   double one = 1.0;
00351   CHK_ERR( fei->setMatScalars(1, &(testdata->ids[0]), &one) );
00352   CHK_ERR( fei->setRHSScalars(1, &(testdata->ids[0]), &one) );
00353 
00354   CHK_ERR( fei->setCurrentMatrix(testdata->ids[0]) );
00355   CHK_ERR( fei->setCurrentRHS(testdata->ids[0]) );
00356 
00357   CHK_ERR( fei->putIntoRHS(FEI_NODE, testdata->fieldIDs[0],
00358          testdata->ids.size(),
00359          &(testdata->ids[0]),
00360          &(rhsData[0])) );
00361 
00362   int numBCNodes = 2;
00363   GlobalID* BCNodeIDs = &(testdata->ids[0]);
00364   int BCFieldID = testdata->fieldIDs[0];
00365   double* values = new double[numBCNodes];
00366   int* offsetsIntoField = new int[numBCNodes];
00367   for(int ii=0; ii<numBCNodes; ++ii) {
00368     values[ii] = 1.0;
00369     offsetsIntoField[ii] = 0;
00370   }
00371 
00372   CHK_ERR( fei->loadNodeBCs(numBCNodes, BCNodeIDs, BCFieldID,
00373           offsetsIntoField, values) );
00374 
00375   delete [] offsetsIntoField;
00376   delete [] values;
00377 
00378   CHK_ERR( fei->loadComplete() );
00379 
00380   int numActiveNodes = 0;
00381   CHK_ERR( fei->getNumLocalNodes(numActiveNodes) );
00382   if (numActiveNodes != (int)testdata->ids.size()) {
00383     ERReturn(-1);
00384   }
00385 
00386   GlobalID* localNodes = new GlobalID[numActiveNodes];
00387   CHK_ERR( fei->getLocalNodeIDList(numActiveNodes, localNodes, numActiveNodes) );
00388 
00389   int totalFieldSize = 0;
00390   for(int ii=0; ii<(int)testdata->fieldSizes.size(); ++ii) {
00391     totalFieldSize += testdata->fieldSizes[ii];
00392   }
00393 
00394   double* soln = new double[numActiveNodes*totalFieldSize];
00395   int* offsets = new int[numActiveNodes+1];
00396 
00397   CHK_ERR( fei->getNodalSolution(numActiveNodes, localNodes,
00398          offsets, soln) );
00399   delete [] offsets;
00400   delete [] soln;
00401   delete [] localNodes;
00402 
00403   CHK_ERR( fei->resetInitialGuess() );
00404 
00405   int fieldSize = 0;
00406   CHK_ERR( fei->getFieldSize(testdata->fieldIDs[0], fieldSize) );
00407 
00408   double initTime, loadTime, solveTime, solnReturnTime;
00409   CHK_ERR( fei->cumulative_cpu_times(initTime, loadTime, solveTime,
00410               solnReturnTime) );
00411 
00412   return(0);
00413 }
00414 
00415 int test_FEI_Implementation::test3()
00416 {
00417   return(0);
00418 }
00419 
00420 int test_FEI_Implementation::test4()
00421 {
00422   return(0);
00423 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends