cgma
CubitFileMetaData.cpp
Go to the documentation of this file.
00001 /*******************************************************************************
00002     COPYRIGHT 2002 CATERPILLAR INC.  ALL RIGHTS RESERVED
00003 
00004     This program is the property of Caterpillar Inc., includes Caterpillar's
00005     confidential and trade secret information, and is maintained as an
00006     unpublished copyrighted work.  It is not to be copied or used by others
00007     except under license from Caterpillar.  This program is also protected as an
00008     unpublished work in accordance with the copyright act of 1976.  In the event
00009     of either inadvertent or deliberate publication, Caterpillar Inc. intends to
00010     maintain copyright protection for this work under the relevant copyright
00011     laws pertaining to published works.  The inclusion of a copyright notice
00012     hereon is precautionary only, and does not imply publication or disclosure.
00013 
00014  
00015  Filename      : CubitFileMetaData.cpp
00016 
00017  Purpose       : Implements meta-data (descriptions) in the Cubit file.
00018            
00019  Special Notes :
00020 
00021  Creator       : Will A. Helden
00022 
00023  Creation Date : 02/15/02
00024 
00025  Owner         : Will A. Helden
00026 
00027 *******************************************************************************/
00028 
00029 #include "CubitFileMetaData.hpp"
00030 #include "CubitFileIOWrapper.hpp"
00031 #include <cstring>
00032 
00033 using namespace NCubitFile;
00034 
00036 // CMetaData -
00038 
00039 CMetaData::CMetaData(UnsignedInt32 xintGrowSizeBy)
00040 {
00041     mHeader.mintMetaDataSchema = 0;
00042     mHeader.mintMetaDataCompress = 0;
00043     mHeader.mintMetaDataCount = 0;
00044 
00045     mintGrowSizeBy = xintGrowSizeBy ? xintGrowSizeBy : 64;
00046     mintBufferSize = 0;
00047     mpaEntries = NULL;
00048 
00049     // Initialize the return buffer - allocated structures needed to return
00050     // the results of meta data queries will be owned and freed by this object.
00051     mSearchBuff.mintNumOwners = mSearchBuff.mintNumNames =
00052         mSearchBuff.mintNumMetaData = 0;
00053     mSearchBuff.mpaintOwners = NULL;
00054     mSearchBuff.mpapachrNames = NULL;
00055     mSearchBuff.mintMetaDataType = eUnsignedInt32;
00056     mSearchBuff.mpaValues = NULL;
00057     mSearchBuff.mpaintNumValues = NULL;
00058 }
00059 
00060 CMetaData::~CMetaData()
00061 {
00062     // Free the meta data.
00063     FreeAll();
00064 
00065     // Free the search return buffer.
00066     if(mSearchBuff.mpaintOwners)
00067         delete [] mSearchBuff.mpaintOwners;
00068     if(mSearchBuff.mpapachrNames)
00069         delete [] mSearchBuff.mpapachrNames;
00070     if(mSearchBuff.mpaValues) {
00071         switch(mSearchBuff.mintMetaDataType) {
00072         case eUnsignedInt32:
00073             delete [] (UnsignedInt32*)mSearchBuff.mpaValues;
00074             break;
00075         case eString:
00076             delete [] (ConstCharPtr*)mSearchBuff.mpaValues;
00077             break;
00078         case eDouble:
00079             delete [] (double*)mSearchBuff.mpaValues;
00080             break;
00081         case eUnsignedInt32Array:
00082             delete [] (ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues;
00083             break;
00084         case eDoubleArray:
00085             delete [] (ConstDoublePtr*)mSearchBuff.mpaValues;
00086             break;
00087         }
00088     }
00089     if(mSearchBuff.mpaintNumValues)
00090         delete [] mSearchBuff.mpaintNumValues;
00091 }
00092 
00093 void CMetaData::GrowSize()
00094 // Grows the meta-data storage structure by the predetermined growth size.
00095 {
00096     // Try to allocate a new storage structure.
00097     UnsignedInt32 lintNewBufferSize = mintBufferSize + mintGrowSizeBy;
00098     SCubitFileMetaDataEntry* lpaNewEntries =
00099         new SCubitFileMetaDataEntry[lintNewBufferSize];
00100     if(!lpaNewEntries)
00101         throw CCubitFile::eMemoryError;
00102 
00103     // Copy the existing data into the front new structure.
00104     if(mpaEntries) {
00105         memcpy(lpaNewEntries, mpaEntries,
00106             mintBufferSize * sizeof(SCubitFileMetaDataEntry));
00107     }
00108     // Initialize the remaining part of the new structure.
00109     for(UnsignedInt32 lintEntry = mintBufferSize; lintEntry <
00110         lintNewBufferSize; lintEntry++) {
00111         lpaNewEntries[lintEntry].mintMetaDataOwner = 0;
00112         lpaNewEntries[lintEntry].mintMetaDataType = eUnsignedInt32;
00113         lpaNewEntries[lintEntry].mpachrName = NULL;
00114         lpaNewEntries[lintEntry].muValue.mint = 0;
00115         lpaNewEntries[lintEntry].mintNumValues = 0;
00116     }
00117     // Replace the old structure with the new one and free the old one.
00118     if(mpaEntries)
00119         delete [] mpaEntries;
00120     mintBufferSize = lintNewBufferSize;
00121     mpaEntries = lpaNewEntries;
00122 }
00123 
00124 UnsignedInt32 CMetaData::AddEntry(UnsignedInt32 xintOwner,
00125                                   ConstCharPtr xpachrName)
00126 // Creates a valueless meta-data entry for the passed id and name.
00127 // Private function, returns the index of the new entry, throws exceptions.
00128 {
00129     if(mHeader.mintMetaDataCount == mintBufferSize)
00130         GrowSize();
00131     mpaEntries[mHeader.mintMetaDataCount].mintMetaDataOwner = xintOwner;
00132     UnsignedInt32 lintNameLength = std::strlen(xpachrName);
00133     mpaEntries[mHeader.mintMetaDataCount].mpachrName =
00134         new char[lintNameLength + 1];
00135     if(!mpaEntries[mHeader.mintMetaDataCount].mpachrName)
00136         throw CCubitFile::eMemoryError;
00137     std::strcpy(mpaEntries[mHeader.mintMetaDataCount].mpachrName, xpachrName);
00138     return mHeader.mintMetaDataCount++;
00139 }
00140 
00141 UnsignedInt32 CMetaData::Find(UnsignedInt32 xintOwner,
00142                               ConstCharPtr xpachrName,
00143                               UnsignedInt32& xintIndex)
00144 // Search for the index of a piece of data with the declared owner and name.
00145 // Private function, returns true/false, no exceptions thrown.
00146 {
00147     if(!mHeader.mintMetaDataCount)  return 0;  // false, not found
00148     for(UnsignedInt32 lintEntry = 0; lintEntry <
00149         mHeader.mintMetaDataCount; lintEntry++) {
00150         if(mpaEntries[lintEntry].mintMetaDataOwner == xintOwner) {
00151             if(!std::strcmp(xpachrName, mpaEntries[lintEntry].mpachrName)) {
00152                 xintIndex = lintEntry;
00153                 return 1;  // true, found
00154             }
00155         }
00156     }
00157     return 0;  // false, not found
00158 }
00159 
00160 
00162 // Get/Set Value Methods
00164 
00165 UnsignedInt32 CMetaData::GetValue(UnsignedInt32 xintOwner,
00166                                   ConstCharPtr xpachrName,
00167                                   UnsignedInt32& xintValue)
00168 // Retrieve integer valued meta-data by id and name.
00169 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00170 {
00171     UnsignedInt32 lintEntry;
00172     if(Find(xintOwner, xpachrName, lintEntry)) {
00173         if(mpaEntries[lintEntry].mintMetaDataType == eUnsignedInt32) {
00174             xintValue = mpaEntries[lintEntry].muValue.mint;
00175             return CCubitFile::eSuccess;
00176         }
00177     }
00178     xintValue = 0;
00179     return CCubitFile::eNotFound;
00180 }
00181 
00182 UnsignedInt32 CMetaData::GetValue(UnsignedInt32 xintOwner,
00183                                   ConstCharPtr xpachrName,
00184                                   ConstCharPtr& xpachrValue)
00185 // Retrieve string valued meta-data by id and name.
00186 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00187 {
00188     UnsignedInt32 lintEntry;
00189     if(Find(xintOwner, xpachrName, lintEntry)) {
00190         if(mpaEntries[lintEntry].mintMetaDataType == eString) {
00191             xpachrValue = mpaEntries[lintEntry].muValue.mpachr;
00192             return CCubitFile::eSuccess;
00193         }
00194     }
00195     xpachrValue = NULL;
00196     return CCubitFile::eNotFound;
00197 }
00198 
00199 UnsignedInt32 CMetaData::GetValue(UnsignedInt32 xintOwner,
00200                                   ConstCharPtr xpachrName,
00201                                   double& xdblValue)
00202 // Retrieve double valued meta-data by id and name.
00203 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00204 {
00205     UnsignedInt32 lintEntry;
00206     if(Find(xintOwner, xpachrName, lintEntry)) {
00207         if(mpaEntries[lintEntry].mintMetaDataType == eDouble) {
00208             xdblValue = mpaEntries[lintEntry].muValue.mdbl;
00209             return CCubitFile::eSuccess;
00210         }
00211     }
00212     xdblValue = 0.0;
00213     return CCubitFile::eNotFound;
00214 }
00215 
00216 UnsignedInt32 CMetaData::GetValue(UnsignedInt32 xintOwner,
00217                                   ConstCharPtr xpachrName,
00218                                   const UnsignedInt32*& xpaintValue,
00219                                   UnsignedInt32& xintNumValues)
00220 // Retrieve integer array valued meta-data by id and name.
00221 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00222 {
00223     UnsignedInt32 lintEntry;
00224     if(Find(xintOwner, xpachrName, lintEntry)) {
00225         if(mpaEntries[lintEntry].mintMetaDataType == eUnsignedInt32Array) {
00226             xpaintValue = mpaEntries[lintEntry].muValue.mpaint;
00227             xintNumValues = mpaEntries[lintEntry].mintNumValues;
00228             return CCubitFile::eSuccess;
00229         }
00230     }
00231     xpaintValue = NULL;
00232     xintNumValues = 0;
00233     return CCubitFile::eNotFound;
00234 }
00235 
00236 UnsignedInt32 CMetaData::GetValue(UnsignedInt32 xintOwner,
00237                                   ConstCharPtr xpachrName,
00238                                   const double*& xpadblValue,
00239                                   UnsignedInt32& xintNumValues)
00240 // Retrieve double array valued meta-data by id and name.
00241 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00242 {
00243     UnsignedInt32 lintEntry;
00244     if(Find(xintOwner, xpachrName, lintEntry)) {
00245         if(mpaEntries[lintEntry].mintMetaDataType == eDoubleArray) {
00246             xpadblValue = mpaEntries[lintEntry].muValue.mpadbl;
00247             xintNumValues = mpaEntries[lintEntry].mintNumValues;
00248             return CCubitFile::eSuccess;
00249         }
00250     }
00251     xpadblValue = NULL;
00252     xintNumValues = 0;
00253     return CCubitFile::eNotFound;
00254 }
00255 
00256 //-----------------------------------------------------------------------------
00257 
00258 UnsignedInt32 CMetaData::SetValue(UnsignedInt32 xintOwner,
00259                                   ConstCharPtr xpachrName,
00260                                   UnsignedInt32 xintValue)
00261 // Assign integer valued meta-data to an id and name.
00262 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00263 {
00264     if(!xpachrName)
00265         return CCubitFile::ePassedNullPointer;
00266 
00267     try {
00268         UnsignedInt32 lintEntry;
00269         if(Find(xintOwner, xpachrName, lintEntry))
00270             FreeValueAt(lintEntry);
00271         else
00272             lintEntry = AddEntry(xintOwner, xpachrName);
00273         mpaEntries[lintEntry].mintMetaDataType = eUnsignedInt32;
00274         mpaEntries[lintEntry].muValue.mint = xintValue;
00275         return CCubitFile::eSuccess;
00276     }
00277     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00278     catch(...)  {  return CCubitFile::eUnknownError;  }
00279 }
00280 
00281 UnsignedInt32 CMetaData::SetValue(UnsignedInt32 xintOwner,
00282                                   ConstCharPtr xpachrName,
00283                                   ConstCharPtr xpachrValue)
00284 // Assign string valued meta-data to an id and name.
00285 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00286 {
00287     if(!xpachrName)
00288         throw CCubitFile::ePassedNullPointer;
00289 
00290     try {
00291         UnsignedInt32 lintEntry, lintLength;
00292         if(Find(xintOwner, xpachrName, lintEntry))
00293             FreeValueAt(lintEntry);
00294         else
00295             lintEntry = AddEntry(xintOwner, xpachrName);
00296 
00297         mpaEntries[lintEntry].mintMetaDataType = eString;
00298         lintLength = xpachrValue ? std::strlen(xpachrValue) : 0;
00299         if(lintLength) {
00300             mpaEntries[lintEntry].muValue.mpachr = new char[lintLength + 1];
00301             if(!mpaEntries[lintEntry].muValue.mpachr)
00302                 throw CCubitFile::eMemoryError;
00303             std::strcpy(mpaEntries[lintEntry].muValue.mpachr, xpachrValue);
00304         }
00305         else
00306             mpaEntries[lintEntry].muValue.mpachr = NULL;
00307 
00308         return CCubitFile::eSuccess;
00309     }
00310     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00311     catch(...)  {  return CCubitFile::eUnknownError;  }
00312 }
00313 
00314 UnsignedInt32 CMetaData::SetValue(UnsignedInt32 xintOwner,
00315                                   ConstCharPtr xpachrName, double xdblValue)
00316 // Assign double valued meta-data to an id and name.
00317 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00318 {
00319     if(!xpachrName)
00320         throw CCubitFile::ePassedNullPointer;
00321 
00322     try {
00323         UnsignedInt32 lintEntry;
00324         if(Find(xintOwner, xpachrName, lintEntry))
00325             FreeValueAt(lintEntry);
00326         else
00327             lintEntry = AddEntry(xintOwner, xpachrName);
00328         mpaEntries[lintEntry].mintMetaDataType = eDouble;
00329         mpaEntries[lintEntry].muValue.mdbl = xdblValue;
00330         return CCubitFile::eSuccess;
00331     }
00332     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00333     catch(...)  {  return CCubitFile::eUnknownError;  }
00334 }
00335 
00336 UnsignedInt32 CMetaData::SetValue(UnsignedInt32 xintOwner,
00337                                   ConstCharPtr xpachrName,
00338                                   const UnsignedInt32* xpaintValue,
00339                                   UnsignedInt32 xintNumValues)
00340 // Assign integer array valued meta-data to an id and name.
00341 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00342 {
00343     if(!xpachrName)
00344         throw CCubitFile::ePassedNullPointer;
00345 
00346     try {
00347         UnsignedInt32 lintEntry;
00348         if(Find(xintOwner, xpachrName, lintEntry))
00349             FreeValueAt(lintEntry);
00350         else
00351             lintEntry = AddEntry(xintOwner, xpachrName);
00352 
00353         mpaEntries[lintEntry].mintMetaDataType = eUnsignedInt32Array;
00354         if(xpaintValue && xintNumValues) {
00355             mpaEntries[lintEntry].muValue.mpaint =
00356                 new UnsignedInt32[xintNumValues];
00357             if(!mpaEntries[lintEntry].muValue.mpaint)
00358                 throw CCubitFile::eMemoryError;
00359             memcpy(mpaEntries[lintEntry].muValue.mpaint, xpaintValue,
00360                 xintNumValues * sizeof(UnsignedInt32));
00361             mpaEntries[lintEntry].mintNumValues = xintNumValues;
00362         }
00363         else {
00364             mpaEntries[lintEntry].muValue.mpaint = NULL;
00365             mpaEntries[lintEntry].mintNumValues = 0;
00366         }
00367 
00368         return CCubitFile::eSuccess;
00369     }
00370     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00371     catch(...)  {  return CCubitFile::eUnknownError;  }
00372 }
00373 
00374 UnsignedInt32 CMetaData::SetValue(UnsignedInt32 xintOwner,
00375                                   ConstCharPtr xpachrName,
00376                                   const double* xpadblValue,
00377                                   UnsignedInt32 xintNumValues)
00378 // Assign double array valued meta-data to an id and name.
00379 // Public function, returns CCubitFile::EErrorCode, no exceptions thrown.
00380 {
00381     if(!xpachrName)
00382         throw CCubitFile::ePassedNullPointer;
00383 
00384     try {
00385         UnsignedInt32 lintEntry;
00386         if(Find(xintOwner, xpachrName, lintEntry))
00387             FreeValueAt(lintEntry);
00388         else
00389             lintEntry = AddEntry(xintOwner, xpachrName);
00390 
00391         mpaEntries[lintEntry].mintMetaDataType = eDoubleArray;
00392         if(xpadblValue && xintNumValues) {
00393             mpaEntries[lintEntry].muValue.mpadbl =
00394                 new double[xintNumValues];
00395             if(!mpaEntries[lintEntry].muValue.mpadbl)
00396                 throw CCubitFile::eMemoryError;
00397             memcpy(mpaEntries[lintEntry].muValue.mpadbl, xpadblValue,
00398                 xintNumValues * sizeof(double));
00399             mpaEntries[lintEntry].mintNumValues = xintNumValues;
00400         }
00401         else {
00402             mpaEntries[lintEntry].muValue.mpadbl = NULL;
00403             mpaEntries[lintEntry].mintNumValues = 0;
00404         }
00405 
00406         return CCubitFile::eSuccess;
00407     }
00408     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00409     catch(...)  {  return CCubitFile::eUnknownError;  }
00410 }
00411 
00412 
00413 
00415 // Search Methods
00417 
00418 
00419 //-----------------------------------------------------------------------------
00420 
00421 //-----------------------------------------------------------------------------
00422 
00423 UnsignedInt32 CMetaData::GetMetaDataAll(UnsignedInt32& xintNumFound,
00424                                         const ConstCharPtr*& xpapachrName,
00425                                         const UnsignedInt32*& xpaintOwner,
00426                                         const UnsignedInt32*& xpaintValue)
00427 // Search the meta-data for all entries of type integer.
00428 {
00429     xintNumFound = 0;
00430     xpapachrName = NULL;
00431     xpaintOwner = NULL;
00432     xpaintValue = NULL;
00433     try {  RebuildSearchBuff(eUnsignedInt32);  }
00434     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00435     catch(...)  {  return CCubitFile::eUnknownError;  }
00436 
00437     if((xintNumFound = SearchAll(eUnsignedInt32)) > 0) {
00438         xpapachrName = mSearchBuff.mpapachrNames;
00439         xpaintOwner = mSearchBuff.mpaintOwners;
00440         xpaintValue = (UnsignedInt32*)mSearchBuff.mpaValues;
00441     }
00442     return CCubitFile::eSuccess;
00443 }
00444 
00445 UnsignedInt32 CMetaData::GetMetaDataAll(UnsignedInt32& xintNumFound,
00446                                         const ConstCharPtr*& xpapachrName,
00447                                         const UnsignedInt32*& xpaintOwner,
00448                                         const ConstCharPtr*& xpapachrValue)
00449 // Search the meta-data for all entries of type string.
00450 {
00451     xintNumFound = 0;
00452     xpapachrName = NULL;
00453     xpaintOwner = NULL;
00454     xpapachrValue = NULL;
00455     try {  RebuildSearchBuff(eString);  }
00456     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00457     catch(...)  {  return CCubitFile::eUnknownError;  }
00458 
00459     if((xintNumFound = SearchAll(eString)) > 0) {
00460         xpapachrName = mSearchBuff.mpapachrNames;
00461         xpaintOwner = mSearchBuff.mpaintOwners;
00462         xpapachrValue = (ConstCharPtr*)mSearchBuff.mpaValues;
00463     }
00464     return CCubitFile::eSuccess;
00465 }
00466 
00467 UnsignedInt32 CMetaData::GetMetaDataAll(UnsignedInt32& xintNumFound,
00468                                         const ConstCharPtr*& xpapachrName,
00469                                         const UnsignedInt32*& xpaintOwner,
00470                                         const double*& xpadblValue)
00471 // Search the meta-data for all entries of type double.
00472 {
00473     xintNumFound = 0;
00474     xpapachrName = NULL;
00475     xpaintOwner = NULL;
00476     xpadblValue = NULL;
00477     try {  RebuildSearchBuff(eDouble);  }
00478     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00479     catch(...)  {  return CCubitFile::eUnknownError;  }
00480 
00481     if((xintNumFound = SearchAll(eDouble)) > 0) {
00482         xpapachrName = mSearchBuff.mpapachrNames;
00483         xpaintOwner = mSearchBuff.mpaintOwners;
00484         xpadblValue = (double*)mSearchBuff.mpaValues;
00485     }
00486     return CCubitFile::eSuccess;
00487 }
00488 
00489 UnsignedInt32 CMetaData::GetMetaDataAll(UnsignedInt32& xintNumFound,
00490                                         const ConstCharPtr*& xpapachrName,
00491                                         const UnsignedInt32*& xpaintOwner,
00492                                         const ConstUnsignedInt32Ptr*& xpapaintValue,
00493                                         const UnsignedInt32*& xpaintNumValues)
00494 // Search the meta-data for all entries of type integer array.
00495 {
00496     xintNumFound = 0;
00497     xpapachrName = NULL;
00498     xpaintOwner = NULL;
00499     xpapaintValue = NULL;
00500     xpaintNumValues = NULL;
00501     try {  RebuildSearchBuff(eUnsignedInt32Array);  }
00502     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00503     catch(...)  {  return CCubitFile::eUnknownError;  }
00504 
00505     if((xintNumFound = SearchAll(eUnsignedInt32Array)) > 0) {
00506         xpapachrName = mSearchBuff.mpapachrNames;
00507         xpaintOwner = mSearchBuff.mpaintOwners;
00508         xpapaintValue = (ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues;
00509         xpaintNumValues = mSearchBuff.mpaintNumValues;
00510     }
00511     return CCubitFile::eSuccess;
00512 }
00513 
00514 UnsignedInt32 CMetaData::GetMetaDataAll(UnsignedInt32& xintNumFound,
00515                                         const ConstCharPtr*& xpapachrName,
00516                                         const UnsignedInt32*& xpaintOwner,
00517                                         const ConstDoublePtr*& xpapadblValue,
00518                                         const UnsignedInt32*& xpaintNumValues)
00519 // Search the meta-data for all entries of type double array.
00520 {
00521     xintNumFound = 0;
00522     xpapachrName = NULL;
00523     xpaintOwner = NULL;
00524     xpapadblValue = NULL;
00525     xpaintNumValues = NULL;
00526     try {  RebuildSearchBuff(eDoubleArray);  }
00527     catch(CCubitFile::EErrorCode xeErrorCode)  {  return xeErrorCode;  }
00528     catch(...)  {  return CCubitFile::eUnknownError;  }
00529 
00530     if((xintNumFound = SearchAll(eDoubleArray)) > 0) {
00531         xpapachrName = mSearchBuff.mpapachrNames;
00532         xpaintOwner = mSearchBuff.mpaintOwners;
00533         xpapadblValue = (ConstDoublePtr*)mSearchBuff.mpaValues;
00534         xpaintNumValues = mSearchBuff.mpaintNumValues;
00535     }
00536     return CCubitFile::eSuccess;
00537 }
00538 
00539 
00540 //-----------------------------------------------------------------------------
00541 
00542 void CMetaData::RebuildSearchBuff(UnsignedInt32 xintSearchType)
00543 // Grow the search return buffer of the class to match the current storage
00544 // buffer size and fit it for the passed return type.
00545 {
00546     if(!mintBufferSize)  return;
00547 
00548     if(mSearchBuff.mintNumOwners < mintBufferSize) {
00549         if(mSearchBuff.mpaintOwners)
00550             delete [] mSearchBuff.mpaintOwners;
00551         mSearchBuff.mpaintOwners = new UnsignedInt32[mintBufferSize];
00552         mSearchBuff.mintNumOwners = mintBufferSize;
00553         if(!mSearchBuff.mpaintOwners) {
00554             mSearchBuff.mintNumOwners = 0;
00555             throw CCubitFile::eMemoryError;
00556         }
00557     }
00558     if(mSearchBuff.mintNumNames < mintBufferSize) {
00559         if(mSearchBuff.mpapachrNames)
00560             delete [] mSearchBuff.mpapachrNames;
00561         mSearchBuff.mpapachrNames = new ConstCharPtr[mintBufferSize];
00562         mSearchBuff.mintNumNames = mintBufferSize;
00563         if(!mSearchBuff.mpapachrNames) {
00564             mSearchBuff.mintNumNames = 0;
00565             throw CCubitFile::eMemoryError;
00566         }
00567     }
00568     if((mSearchBuff.mintNumMetaData < mintBufferSize) ||
00569         (mSearchBuff.mintMetaDataType != xintSearchType)) {
00570         if(mSearchBuff.mpaValues) {
00571             switch(mSearchBuff.mintMetaDataType) {
00572             case eUnsignedInt32:
00573                 delete [] (UnsignedInt32*)mSearchBuff.mpaValues;  break;
00574             case eString:
00575                 delete [] (ConstCharPtr*)mSearchBuff.mpaValues;  break;
00576             case eDouble:
00577                 delete [] (double*)mSearchBuff.mpaValues;  break;
00578             case eUnsignedInt32Array:
00579                 delete [] (ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues;  break;
00580             case eDoubleArray:
00581                 delete [] (ConstDoublePtr*)mSearchBuff.mpaValues;  break;
00582             }
00583         }
00584         if(mSearchBuff.mpaintNumValues)
00585             delete [] mSearchBuff.mpaintNumValues;
00586         mSearchBuff.mintMetaDataType = xintSearchType;
00587         mSearchBuff.mintNumMetaData = mintBufferSize;
00588 
00589         switch(mSearchBuff.mintMetaDataType) {
00590         case eUnsignedInt32:
00591             mSearchBuff.mpaValues = new UnsignedInt32[mintBufferSize];
00592             break;
00593         case eString:
00594             mSearchBuff.mpaValues = new ConstCharPtr[mintBufferSize];
00595             break;
00596         case eDouble:
00597             mSearchBuff.mpaValues = new double[mintBufferSize];
00598             break;
00599         case eUnsignedInt32Array:
00600             mSearchBuff.mpaValues = new ConstUnsignedInt32Ptr[mintBufferSize];
00601             break;
00602         case eDoubleArray:
00603             mSearchBuff.mpaValues = new ConstDoublePtr[mintBufferSize];
00604             break;
00605         }
00606         if(!mSearchBuff.mpaValues) {
00607             mSearchBuff.mintNumMetaData = 0;
00608             throw CCubitFile::eMemoryError;
00609         }
00610 
00611         switch(mSearchBuff.mintMetaDataType) {
00612         case eUnsignedInt32Array:
00613         case eDoubleArray:
00614             mSearchBuff.mpaintNumValues = new UnsignedInt32[mintBufferSize];
00615             if(!mSearchBuff.mpaintNumValues) {
00616                 mSearchBuff.mintMetaDataType = 0;
00617                 switch(mSearchBuff.mintMetaDataType) {
00618                 case eUnsignedInt32:
00619                     delete [] (UnsignedInt32*)mSearchBuff.mpaValues;  break;
00620                 case eString:
00621                     delete [] (ConstCharPtr*)mSearchBuff.mpaValues;  break;
00622                 case eDouble:
00623                     delete [] (double*)mSearchBuff.mpaValues;  break;
00624                 case eUnsignedInt32Array:
00625                     delete [] (ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues;  break;
00626                 case eDoubleArray:
00627                     delete [] (ConstDoublePtr*)mSearchBuff.mpaValues;  break;
00628                 }
00629                 mSearchBuff.mpaValues = NULL;
00630                 throw CCubitFile::eMemoryError;
00631             }
00632             break;
00633         default:
00634             mSearchBuff.mpaintNumValues = NULL;
00635         }
00636     }
00637 }
00638 
00639 UnsignedInt32 CMetaData::SearchByID(UnsignedInt32 xintSearchType,
00640                                     UnsignedInt32 xintOwner)
00641 // Traverses the meta-data entries to find entries with an owner id matching
00642 // the passed one and copies the values and names of those entries to the
00643 // search buffer.
00644 // Private function, returns the number of entries meeting the search criteria,
00645 // no exceptions thrown.
00646 {
00647     if(!mHeader.mintMetaDataCount)  return 0;  // none found
00648 
00649     UnsignedInt32 lintNumFound = 0;
00650     for(UnsignedInt32 lintEntry = 0; lintEntry <
00651         mHeader.mintMetaDataCount; lintEntry++) {
00652         if(mpaEntries[lintEntry].mintMetaDataOwner == xintOwner) {
00653             if(mpaEntries[lintEntry].mintMetaDataType == xintSearchType) {
00654                 mSearchBuff.mpapachrNames[lintNumFound] =
00655                     mpaEntries[lintEntry].mpachrName;
00656                 switch(xintSearchType) {
00657                 case eUnsignedInt32:
00658                     ((UnsignedInt32*)mSearchBuff.mpaValues)[lintNumFound] =
00659                         mpaEntries[lintEntry].muValue.mint;
00660                     break;
00661                 case eString:
00662                     ((ConstCharPtr*)mSearchBuff.mpaValues)[lintNumFound] =
00663                         mpaEntries[lintEntry].muValue.mpachr;
00664                     break;
00665                 case eDouble:
00666                     ((double*)mSearchBuff.mpaValues)[lintNumFound] =
00667                         mpaEntries[lintEntry].muValue.mdbl;
00668                     break;
00669                 case eUnsignedInt32Array:
00670                     ((ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues)[lintNumFound] =
00671                         mpaEntries[lintEntry].muValue.mpaint;
00672                     mSearchBuff.mpaintNumValues[lintNumFound] =
00673                         mpaEntries[lintEntry].mintNumValues;
00674                     break;
00675                 case eDoubleArray:
00676                     ((ConstDoublePtr*)mSearchBuff.mpaValues)[lintNumFound] =
00677                         mpaEntries[lintEntry].muValue.mpadbl;
00678                     mSearchBuff.mpaintNumValues[lintNumFound] =
00679                         mpaEntries[lintEntry].mintNumValues;
00680                     break;
00681                 }
00682                 lintNumFound++;
00683             }
00684         }
00685     }
00686     return lintNumFound;  // return number found
00687 }
00688 
00689 UnsignedInt32 CMetaData::SearchByName(UnsignedInt32 xintSearchType,
00690                                       const char* xpachrName)
00691 // Traverses the meta-data entries to find entries with an name matching
00692 // the passed one and copies the owner id's and names of those entries to the
00693 // search buffer.
00694 // Private function, returns the number of entries meeting the search criteria,
00695 // no exceptions thrown.
00696 {
00697     if(!mHeader.mintMetaDataCount)  return 0;  // none found
00698 
00699     UnsignedInt32 lintNumFound = 0;
00700     for(UnsignedInt32 lintEntry = 0; lintEntry <
00701         mHeader.mintMetaDataCount; lintEntry++) {
00702         if(!std::strcmp(xpachrName, mpaEntries[lintEntry].mpachrName)) {
00703             if(mpaEntries[lintEntry].mintMetaDataType == xintSearchType) {
00704                 mSearchBuff.mpaintOwners[lintNumFound] =
00705                     mpaEntries[lintEntry].mintMetaDataOwner;
00706                 switch(xintSearchType) {
00707                 case eUnsignedInt32:
00708                     ((UnsignedInt32*)mSearchBuff.mpaValues)[lintNumFound] =
00709                         mpaEntries[lintEntry].muValue.mint;
00710                     break;
00711                 case eString:
00712                     ((ConstCharPtr*)mSearchBuff.mpaValues)[lintNumFound] =
00713                         mpaEntries[lintEntry].muValue.mpachr;
00714                     break;
00715                 case eDouble:
00716                     ((double*)mSearchBuff.mpaValues)[lintNumFound] =
00717                         mpaEntries[lintEntry].muValue.mdbl;
00718                     break;
00719                 case eUnsignedInt32Array:
00720                     ((ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues)[lintNumFound] =
00721                         mpaEntries[lintEntry].muValue.mpaint;
00722                     mSearchBuff.mpaintNumValues[lintNumFound] =
00723                         mpaEntries[lintEntry].mintNumValues;
00724                     break;
00725                 case eDoubleArray:
00726                     ((ConstDoublePtr*)mSearchBuff.mpaValues)[lintNumFound] =
00727                         mpaEntries[lintEntry].muValue.mpadbl;
00728                     mSearchBuff.mpaintNumValues[lintNumFound] =
00729                         mpaEntries[lintEntry].mintNumValues;
00730                     break;
00731                 }
00732                 lintNumFound++;
00733             }
00734         }
00735     }
00736     return lintNumFound;  // return number found
00737 }
00738 
00739 UnsignedInt32 CMetaData::SearchAll(UnsignedInt32 xintSearchType)
00740 // Traverses the meta-data entries to find all entries of the passed type.
00741 // Private function, returns the number of entries meeting the search criteria,
00742 // no exceptions thrown.
00743 {
00744     if(!mHeader.mintMetaDataCount)  return 0;  // none found
00745 
00746     UnsignedInt32 lintNumFound = 0;
00747     for(UnsignedInt32 lintEntry = 0; lintEntry <
00748         mHeader.mintMetaDataCount; lintEntry++) {
00749         if(mpaEntries[lintEntry].mintMetaDataType == xintSearchType) {
00750             mSearchBuff.mpapachrNames[lintNumFound] =
00751                 mpaEntries[lintEntry].mpachrName;
00752             mSearchBuff.mpaintOwners[lintNumFound] =
00753                 mpaEntries[lintEntry].mintMetaDataOwner;
00754             switch(xintSearchType) {
00755             case eUnsignedInt32:
00756                 ((UnsignedInt32*)mSearchBuff.mpaValues)[lintNumFound] =
00757                     mpaEntries[lintEntry].muValue.mint;
00758                 break;
00759             case eString:
00760                 ((ConstCharPtr*)mSearchBuff.mpaValues)[lintNumFound] =
00761                     mpaEntries[lintEntry].muValue.mpachr;
00762                 break;
00763             case eDouble:
00764                 ((double*)mSearchBuff.mpaValues)[lintNumFound] =
00765                     mpaEntries[lintEntry].muValue.mdbl;
00766                 break;
00767             case eUnsignedInt32Array:
00768                 ((ConstUnsignedInt32Ptr*)mSearchBuff.mpaValues)[lintNumFound] =
00769                     mpaEntries[lintEntry].muValue.mpaint;
00770                 mSearchBuff.mpaintNumValues[lintNumFound] =
00771                     mpaEntries[lintEntry].mintNumValues;
00772                 break;
00773             case eDoubleArray:
00774                 ((ConstDoublePtr*)mSearchBuff.mpaValues)[lintNumFound] =
00775                     mpaEntries[lintEntry].muValue.mpadbl;
00776                 mSearchBuff.mpaintNumValues[lintNumFound] =
00777                     mpaEntries[lintEntry].mintNumValues;
00778                 break;
00779             }
00780             lintNumFound++;
00781         }
00782     }
00783     return lintNumFound;  // return number found
00784 }
00785 
00786 
00787 
00789 // Deletion functions
00791 
00792 UnsignedInt32 CMetaData::ClearMetaDataForID(UnsignedInt32 xintOwner)
00793 // Delete all meta-data entries with the same owner.
00794 {
00795     if(mHeader.mintMetaDataCount) {
00796         for(UnsignedInt32 lintEntry = 0; lintEntry <
00797             mHeader.mintMetaDataCount; lintEntry++) {
00798             if(mpaEntries[lintEntry].mintMetaDataOwner == xintOwner)
00799                 FreeAt(lintEntry);
00800         }
00801     }
00802     return CCubitFile::eSuccess;
00803 }
00804 
00805 void CMetaData::FreeValueAt(UnsignedInt32 xintEntry)
00806 // Frees any allocated memory associated with the value of the meta-data stored
00807 // at the passed index.  Private function, no exceptions thrown.
00808 {
00809     switch(mpaEntries[xintEntry].mintMetaDataType) {
00810     case eString:
00811         if(mpaEntries[xintEntry].muValue.mpachr)
00812             delete [] mpaEntries[xintEntry].muValue.mpachr;
00813         mpaEntries[xintEntry].muValue.mpachr = NULL;
00814         break;
00815     case eUnsignedInt32Array:
00816         if(mpaEntries[xintEntry].muValue.mpaint)
00817             delete [] mpaEntries[xintEntry].muValue.mpaint;
00818         mpaEntries[xintEntry].muValue.mpaint = NULL;
00819         break;
00820     case eDoubleArray:
00821         if(mpaEntries[xintEntry].muValue.mpadbl)
00822             delete [] mpaEntries[xintEntry].muValue.mpadbl;
00823         mpaEntries[xintEntry].muValue.mpadbl = NULL;
00824         break;
00825     }
00826 }
00827 
00828 void CMetaData::FreeAt(UnsignedInt32 xintEntry)
00829 // Frees the meta-data at the passed index and moves all data at higher indices
00830 // down to close the gap.  Private function, no exceptions thrown.
00831 {
00832     // Free the allocated memory for an entry.
00833     delete [] mpaEntries[xintEntry].mpachrName;
00834     FreeValueAt(xintEntry);
00835     mHeader.mintMetaDataCount--;
00836 
00837     // Move all entries in the meta-data table ahead of the deleted one down
00838     // to fill in the gap.
00839     if(xintEntry < mHeader.mintMetaDataCount) {
00840         for(UnsignedInt32 lintCopyTo = xintEntry; lintCopyTo <
00841             mHeader.mintMetaDataCount; lintCopyTo++) {
00842             memcpy(&mpaEntries[lintCopyTo], &mpaEntries[lintCopyTo + 1],
00843                 sizeof(SCubitFileMetaDataEntry));
00844         }
00845     }
00846 }
00847 
00848 void CMetaData::FreeAll()
00849 // Frees all memory used to store meta-data data and resets the object back
00850 // to its constructed state.  (Has no effect on the return buffers.)
00851 // Private function, no exceptions thrown.
00852 {
00853     if(mHeader.mintMetaDataCount) {
00854         for(UnsignedInt32 lintEntry = 0; lintEntry < mintBufferSize; lintEntry++) {
00855             if(mpaEntries[lintEntry].mpachrName)
00856                 delete [] mpaEntries[lintEntry].mpachrName;
00857             FreeValueAt(lintEntry);
00858         }
00859         delete [] mpaEntries;
00860         mHeader.mintMetaDataCount = 0;
00861         mintBufferSize = 0;
00862         mpaEntries = NULL;
00863     }
00864     mHeader.mintMetaDataSchema = 0;
00865     mHeader.mintMetaDataCompress = 0;
00866 }
00867 
00868 
00870 // Read / Write File Methods
00872 
00873 void CMetaData::WriteMetaData(FILE* xpFile,
00874                               UnsignedInt32& xintWroteAtOffset,
00875                               UnsignedInt32& xintLength,
00876                               UnsignedInt32 xintOffsetFrom)
00877 // Write the meta-data stored in this object to the passed file.  The file
00878 // position, offset from an optional passed value, and length are returned.
00879 {
00880     if(!xpFile)  throw CCubitFile::eFileWriteError;
00881 
00882     CIOWrapper* lpIO = new CIOWrapper(xpFile);
00883     xintWroteAtOffset = lpIO->BeginWriteBlock(xintOffsetFrom);
00884 
00885     // Write a description header.
00886     lpIO->Write(&mHeader.mintMetaDataSchema, 1);
00887     lpIO->Write(&mHeader.mintMetaDataCompress, 1);
00888     lpIO->Write(&mHeader.mintMetaDataCount, 1);
00889 
00890     // Write the actual meta-data entries.
00891     UnsignedInt32 lintEntry, lintNumEntries = mHeader.mintMetaDataCount;
00892     if(lintNumEntries) {
00893         for(lintEntry = 0; lintEntry < lintNumEntries; lintEntry++) {
00894             lpIO->Write(&mpaEntries[lintEntry].mintMetaDataOwner, 1);
00895             lpIO->Write(&mpaEntries[lintEntry].mintMetaDataType, 1);
00896             lpIO->Write(mpaEntries[lintEntry].mpachrName);
00897             switch(mpaEntries[lintEntry].mintMetaDataType) {
00898             case eUnsignedInt32:
00899                 lpIO->Write(&mpaEntries[lintEntry].muValue.mint, 1);
00900                 break;
00901             case eString:
00902                 lpIO->Write(mpaEntries[lintEntry].muValue.mpachr);
00903                 break;
00904             case eDouble:
00905                 lpIO->Write(&mpaEntries[lintEntry].muValue.mdbl, 1);
00906                 break;
00907             case eUnsignedInt32Array:
00908                 lpIO->Write(&mpaEntries[lintEntry].mintNumValues, 1);
00909                 if(mpaEntries[lintEntry].mintNumValues) {
00910                     lpIO->Write(mpaEntries[lintEntry].muValue.mpaint,
00911                         mpaEntries[lintEntry].mintNumValues);
00912                 }
00913                 break;
00914             case eDoubleArray:
00915                 lpIO->Write(&mpaEntries[lintEntry].mintNumValues, 1);
00916                 if(mpaEntries[lintEntry].mintNumValues) {
00917                     lpIO->Write(mpaEntries[lintEntry].muValue.mpadbl,
00918                         mpaEntries[lintEntry].mintNumValues);
00919                 }
00920                 break;
00921             }
00922         }
00923     }
00924     xintLength = lpIO->EndWriteBlock();
00925     delete lpIO;
00926 }
00927 
00928 void CMetaData::ReadMetaData(FILE* xpFile,
00929                              UnsignedInt32 xintAbsoluteOffset,
00930                              UnsignedInt32 xintRelativeOffset,
00931                              UnsignedInt32 xintSourceEndian)
00932 // Reset the meta-data object and then fill it with data read from a passed
00933 // file at the passed location.  The data will be in the passed endian format
00934 // which is not stored with the meta-data itself as the meta-data is never
00935 // fully independent.
00936 {
00937     // Delete all stored data
00938     FreeAll();
00939 
00940     if(!xpFile)  throw CCubitFile::eFileReadError;
00941 
00942     CIOWrapper* lpIO = new CIOWrapper(xpFile, xintSourceEndian);
00943     lpIO->BeginReadBlock(xintAbsoluteOffset, xintRelativeOffset);
00944 
00945     // Read the description header.
00946     lpIO->Read(&mHeader.mintMetaDataSchema, 1);
00947     lpIO->Read(&mHeader.mintMetaDataCompress, 1);
00948     lpIO->Read(&mHeader.mintMetaDataCount, 1);
00949 
00950     UnsignedInt32 lintEntry, lintNumEntries = mHeader.mintMetaDataCount;
00951     if(lintNumEntries) {
00952         // Grow the storage capacity of the meta-data object to match that of
00953         // the stored data.
00954         UnsignedInt32 lintGrowSizeBy = mintGrowSizeBy;
00955         mintGrowSizeBy = lintNumEntries;
00956         GrowSize();
00957         mintGrowSizeBy = lintGrowSizeBy;
00958 
00959         // Read the stored meta-data entries.
00960         for(lintEntry = 0; lintEntry < lintNumEntries; lintEntry++) {
00961             lpIO->Read(&mpaEntries[lintEntry].mintMetaDataOwner, 1);
00962             lpIO->Read(&mpaEntries[lintEntry].mintMetaDataType, 1);
00963             mpaEntries[lintEntry].mpachrName = lpIO->Read();
00964             switch(mpaEntries[lintEntry].mintMetaDataType) {
00965             case eUnsignedInt32:
00966                 lpIO->Read(&mpaEntries[lintEntry].muValue.mint, 1);
00967                 break;
00968             case eString:
00969                 mpaEntries[lintEntry].muValue.mpachr = lpIO->Read();
00970                 break;
00971             case eDouble:
00972                 lpIO->Read(&mpaEntries[lintEntry].muValue.mdbl, 1);
00973                 break;
00974             case eUnsignedInt32Array:
00975                 lpIO->Read(&mpaEntries[lintEntry].mintNumValues, 1);
00976                 if(mpaEntries[lintEntry].mintNumValues) {
00977                     mpaEntries[lintEntry].muValue.mpaint =
00978                         new UnsignedInt32[mpaEntries[lintEntry].mintNumValues];
00979                     if(!mpaEntries[lintEntry].muValue.mpaint)
00980                         throw CCubitFile::eMemoryError;
00981                     lpIO->Read(mpaEntries[lintEntry].muValue.mpaint,
00982                         mpaEntries[lintEntry].mintNumValues);
00983                 }
00984                 break;
00985             case eDoubleArray:
00986                 lpIO->Read(&mpaEntries[lintEntry].mintNumValues, 1);
00987                 if(mpaEntries[lintEntry].mintNumValues) {
00988                     mpaEntries[lintEntry].muValue.mpadbl =
00989                         new double[mpaEntries[lintEntry].mintNumValues];
00990                     if(!mpaEntries[lintEntry].muValue.mpadbl)
00991                         throw CCubitFile::eMemoryError;
00992                     lpIO->Read(mpaEntries[lintEntry].muValue.mpadbl,
00993                         mpaEntries[lintEntry].mintNumValues);
00994                 }
00995                 break;
00996             }
00997         }
00998     }
00999     delete lpIO;
01000 }
01001 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines