CkptContainer.cc

Go to the documentation of this file.
00001 #include "CkptContainer.h"
00002 
00003 CkptContainer::CkptContainer(std::string containerName,
00004                 unsigned long maxObjects,
00005                 unsigned long maxObjectSize,
00006                 CkptRetentionPolicy rPolicy)
00007 {
00008     // Do some parm validation first
00009     if (maxObjects <= 1) maxObjects = 2;       // Always have at least 2 sections
00010     if (maxObjectSize <= 0) maxObjectSize = 4; // Minimum object size of 4 bytes
00011 
00012     _maxObjectSize = maxObjectSize;
00013     _containerName = containerName;
00014     _checkpointName.length = _containerName.length();
00015     memcpy(_checkpointName.value, _containerName.data(), _checkpointName.length);
00016     SaCkptCallbacksT callbacks = { NULL, NULL };
00017     SaVersionT version = { 'B', 1, 1 };
00018 
00019     SaAisErrorT error = saCkptInitialize (&_serviceHandle, &callbacks, &version);
00020 
00021     SaCkptCheckpointCreationAttributesT ckptAttributes;
00022     ckptAttributes.creationFlags = (SA_CKPT_WR_ALL_REPLICAS | SA_CKPT_CHECKPOINT_COLLOCATED);
00023     ckptAttributes.checkpointSize = maxObjects*maxObjectSize;
00024     if (rPolicy == CKPT_RETAIN) ckptAttributes.retentionDuration = SA_TIME_END;
00025     else ckptAttributes.retentionDuration = 0;
00026     ckptAttributes.maxSections = maxObjects;
00027     ckptAttributes.maxSectionSize = maxObjectSize;
00028     ckptAttributes.maxSectionIdSize = 64;
00029 
00030     error = saCkptCheckpointOpen (_serviceHandle,
00031                    &_checkpointName,
00032                    &ckptAttributes,
00033                    SA_CKPT_CHECKPOINT_WRITE | SA_CKPT_CHECKPOINT_READ | SA_CKPT_CHECKPOINT_CREATE,
00034                    SA_TIME_END,
00035                    &_checkpointHandle);
00036 
00037     if (error == SA_AIS_OK) _valid=true;
00038     else _valid = false;
00039     
00040     _daoFactory = new RawDAOFactory();
00041 }
00042 
00043 CkptContainer::~CkptContainer() {
00044     SaAisErrorT error;
00045     if (_valid) {
00046       error = saCkptCheckpointClose(_checkpointHandle);
00047     }
00048     error = saCkptFinalize(_serviceHandle);
00049     delete _daoFactory;
00050 }
00051 
00052 unsigned long CkptContainer::size() {
00053     SaAisErrorT error;
00054     SaCkptCheckpointDescriptorT status;
00055 
00056     error = saCkptCheckpointStatusGet( _checkpointHandle, &status );
00057     if (error != SA_AIS_OK) return 0;
00058 
00059     return (unsigned long)status.numberOfSections;
00060 }
00061 
00062 CkptObject* CkptContainer::get(CkptObjectKey* key) {
00063     if (!_valid) return NULL;
00064 
00065   // Create a ioVectorElement to retrieve the data from CKPT
00066   SaCkptIOVectorElementT ioElement;
00067   ioElement.sectionId  = *(key->sectionIdValue());
00068   // We SHOULDN'T need a local buffer for this. CKPT is supposed to provide it if
00069   // one isn't supplied by the caller. This is a hack, but later I'll pass in a
00070   // pointer into the CkptByteArray's data buffer for speed. That WILL violate
00071   // encapsulation. [TODO]
00072   ioElement.dataBuffer = (char*)malloc(_maxObjectSize);
00073   ioElement.dataSize   = _maxObjectSize; // Read up to our max
00074   ioElement.dataOffset = 0;              // No offset
00075 
00076   // Read data from section [key] into a byte array
00077   SaAisErrorT error = saCkptCheckpointRead(_checkpointHandle, &ioElement, 1, NULL);
00078 
00079   if ((error != SA_AIS_OK) || (ioElement.readSize==0)) {
00080     free(ioElement.dataBuffer);
00081     return NULL;
00082   }
00083 
00084   // Convert the buffer to a byte array
00085   CkptByteArray* bArray = new CkptByteArray((char*)ioElement.dataBuffer,
00086                           (unsigned int)ioElement.readSize);
00087   // Free our local buffer
00088   free(ioElement.dataBuffer);
00089 
00090   CkptObject* obj_ptr;
00091   DAOInterface* input = ((RawDAOFactory*)_daoFactory)->createInputDAO(bArray);
00092   *input & obj_ptr;
00093   delete input;
00094   delete bArray;
00095 
00096   // Set the object internals to reference this container/key
00097   obj_ptr->setContainer(this);
00098   obj_ptr->setKey(key);
00099   return obj_ptr;
00100 }
00101 
00102 CkptObject* CkptContainer::get(CkptObjectKey &key) {
00103     CkptObjectKey *ownedKey = new CkptObjectKey(key);
00104     return this->get(ownedKey);
00105 }
00106 
00107 CkptRC CkptContainer::persist(CkptObject* obj, bool overwriteExisting) {
00108   // This associates obj with the container and creates a section for
00109   // it in the underlying checkpoint.
00110 
00111   if (!_valid) return CkptFailure;
00112 
00113   // Associate this object with this container
00114   obj->setContainer(this);
00115 
00116   // Create the attribute structure for the underlying section
00117   SaCkptSectionCreationAttributesT cAttrs;
00118   cAttrs.sectionId = obj->getKey()->sectionIdValue();
00119   cAttrs.expirationTime = SA_TIME_END;
00120 
00121   // Serialize the data in the object
00122   //std::auto_ptr<CkptByteArray> bArray(obj->serialize());
00123   DAOInterface* output = _daoFactory->createOutputDAO();
00124   *output & obj;
00125   byte_array* bArray = output->getOutputData();
00126 
00127   // Create a section for the object in the checkpoint and
00128   // commit the data to the section
00129   SaAisErrorT error = saCkptSectionCreate(_checkpointHandle,
00130                       &cAttrs,
00131                       bArray->getDataPtr(),
00132                       bArray->getDataSize());
00133 
00134   if ( (error == SA_AIS_ERR_EXIST) && (overwriteExisting) ) {
00135     // There's already an object with this key in the container
00136     // Overwrite it if the overwriteExisting flag is set.
00137     error = saCkptSectionOverwrite(_checkpointHandle,
00138               obj->getKey()->sectionIdValue(),
00139               bArray->getDataPtr(),
00140               bArray->getDataSize());
00141   }
00142 
00143   delete output;
00144   return (error == SA_AIS_OK) ? CkptSuccess : CkptFailure;
00145 }
00146 
00147 CkptRC CkptContainer::remove(CkptObject* obj) {
00148   if (!_valid) return CkptFailure;
00149 
00150   // Disassociate this object with this container
00151   obj->setContainer(NULL);
00152 
00153   // Delete the section for the object in the checkpoint
00154   saCkptSectionDelete(_checkpointHandle,
00155                       obj->getKey()->sectionIdValue());
00156   return CkptSuccess;
00157 }
00158 
00159 CkptRC CkptContainer::commit(CkptObject* obj) {
00160   // Make sure this is a persisted object, fail if not.
00161   if (!_valid || (obj == NULL) || (obj->getState() != CKPT_OBJ_MANAGED)) {
00162     return CkptFailure;
00163   }
00164 
00165   DAOInterface* output = _daoFactory->createOutputDAO();
00166   *output & obj;
00167   byte_array* bArray = output->getOutputData();
00168 
00169   // Overwrite the data from the byte array into the section
00170   // corresponding to the object.
00171   SaAisErrorT error = saCkptSectionOverwrite(_checkpointHandle,
00172                         obj->getKey()->sectionIdValue(),
00173                         bArray->getDataPtr(),
00174                         bArray->getDataSize());
00175 
00176   delete output;
00177   return (error == SA_AIS_OK) ? CkptSuccess : CkptFailure;
00178 }
00179 
00180 CkptRC CkptContainer::setRetentionPolicy(CkptRetentionPolicy rPolicy)
00181 {
00182     if (!_valid) return CkptFailure;
00183     SaTimeT rTime = (rPolicy==CKPT_RETAIN) ? SA_TIME_END : 0;
00184     SaAisErrorT err = saCkptCheckpointRetentionDurationSet (_checkpointHandle, rTime);
00185     if (err != SA_AIS_OK) {
00186         return CkptFailure;
00187     }
00188     return CkptSuccess;
00189 }
00190 

Generated on Fri Apr 27 17:20:01 2007 for aiscoal by  doxygen 1.5.2