GME  13
CoreXmlFile.cpp
Go to the documentation of this file.
00001 #include "stdafx.h"
00002 #include <stdio.h>
00003 #include <io.h>
00004 #include <stdlib.h>
00005 #include "CoreXmlFile.h"
00006 #include "CommonCollection.h"
00007 
00008 using namespace XERCES_CPP_NAMESPACE;
00009 
00010 
00011 void bin2string( const unsigned char * bytes, int len, string& str )
00012 {
00013     char hex[3];
00014     str.clear();
00015     for( int i=0; i<len; ++i )
00016     {
00017         sprintf( hex, "%02x", bytes[i] );
00018         str += hex;
00019     }
00020 }
00021 
00022 void string2bin( const char * str, unsigned char * bytes )
00023 {
00024     int l = strlen(str) / 2;
00025     for( int i=0; i<l; ++i )
00026     {
00027         unsigned char c;
00028         sscanf( str + i*2, "%02x", &c );
00029         bytes[i] = c;
00030     }
00031 }
00032 
00033 void guid2str( GUID guid, string& str )
00034 {
00035     if( guid == GUID_NULL )
00036         str = "null";
00037     else
00038         bin2string( (unsigned char*)&guid, sizeof(GUID), str );
00039 }
00040 
00041 GUID str2guid( const char * str )
00042 {
00043     int len = strlen(str);
00044     if( len == 0 || strcmp( str, "null" ) == 0 )
00045         return GUID_NULL;
00046     else
00047     {
00048         GUID guid;
00049         string2bin( str, (unsigned char*)&guid );
00050         return guid;
00051     }
00052 }
00053 
00054 
00056 // XmlAttrBase class
00058 
00059 XmlAttrBase * XmlAttrBase::create(valtype_type valtype)
00060 {
00061     ASSERT( valtype != VALTYPE_NONE );
00062 
00063         XmlAttrBase * xmlattr = NULL;
00064 
00065         switch(valtype)
00066         {
00067     case VALTYPE_LONG:
00068                 xmlattr = new XmlAttrLong();
00069                 break;
00070 
00071         case VALTYPE_STRING:
00072                 xmlattr = new XmlAttrString();
00073                 break;
00074 
00075         case VALTYPE_BINARY:
00076                 xmlattr = new XmlAttrBinary();
00077                 break;
00078 
00079         case VALTYPE_LOCK:
00080                 xmlattr = new XmlAttrLock();
00081                 break;
00082 
00083         case VALTYPE_POINTER:
00084                 xmlattr = new XmlAttrPointer();
00085                 break;
00086 
00087         case VALTYPE_COLLECTION:
00088                 xmlattr = new XmlAttrCollection();
00089                 break;
00090 
00091         case VALTYPE_REAL:
00092                 xmlattr = new XmlAttrReal();
00093                 break;
00094 
00095         default:
00096                 HR_THROW(E_METAPROJECT);
00097         }
00098 
00099         if( xmlattr == NULL )
00100                 HR_THROW(E_OUTOFMEMORY);
00101 
00102         return xmlattr;
00103 }
00104 
00105 XmlAttrBase::XmlAttrBase()
00106 { 
00107 }
00108     
00109 XmlAttrBase::~XmlAttrBase() 
00110 { 
00111 }
00112 
00114 // XmlAttrLong class
00116 
00117 XmlAttrLong::XmlAttrLong()
00118 {
00119     m_value = 0;
00120 }
00121 
00122 valtype_type XmlAttrLong::getType() const
00123 {
00124     return VALTYPE_LONG;
00125 }
00126 
00127 void XmlAttrLong::fromVariant(VARIANT p)
00128 {
00129     CopyTo(p, m_value);
00130 }
00131 
00132 void XmlAttrLong::toVariant(VARIANT *p) const
00133 {
00134     CopyTo(m_value, p);
00135 }
00136 
00137 void XmlAttrLong::fromString(const char * str)
00138 {
00139     if( str == NULL || strlen(str)==0 )
00140         m_value = 0;
00141     else
00142         m_value = atoi( str );
00143 }
00144 
00145 void XmlAttrLong::toString(string& str) const
00146 {
00147     static char buf[100];
00148     sprintf( buf, "%d", m_value );
00149     str = buf;
00150 }
00151 
00153 // XmlAttrReal class
00155 
00156 XmlAttrReal::XmlAttrReal()
00157 {
00158     m_value = 0;
00159 }
00160 
00161 valtype_type XmlAttrReal::getType() const
00162 {
00163     return VALTYPE_REAL;
00164 }
00165 
00166 void XmlAttrReal::fromVariant(VARIANT p)
00167 {
00168     CopyTo(p, m_value);
00169 }
00170 
00171 void XmlAttrReal::toVariant(VARIANT *p) const
00172 {
00173     CopyTo(m_value, p);
00174 }
00175 
00176 void XmlAttrReal::fromString(const char * str)
00177 {
00178     if( str == NULL || strlen(str)==0 )
00179         m_value = 0;
00180     else
00181         m_value = atof( str );
00182 }
00183 
00184 void XmlAttrReal::toString(string& str) const
00185 {
00186     static char buf[100];
00187     sprintf( buf, "%.6f", m_value );
00188     str = buf;
00189 }
00190 
00192 // XmlAttrString class
00194 
00195 valtype_type XmlAttrString::getType() const
00196 {
00197     return VALTYPE_STRING;
00198 }
00199 
00200 void XmlAttrString::fromVariant(VARIANT p)
00201 {
00202     // TODO: test
00203     CopyTo(p, m_value);
00204 }
00205 
00206 void XmlAttrString::toVariant(VARIANT *p) const
00207 {
00208     // TODO: test
00209     CopyTo(m_value, p);
00210 }
00211 
00212 void XmlAttrString::fromString(const char * str)
00213 {
00214     if( str == NULL )
00215         m_value = "";
00216     else
00217         m_value = str;
00218 }
00219 
00220 void XmlAttrString::toString(string& str) const
00221 {
00222     str = m_value;
00223 }
00224 
00226 // XmlAttrBinary class
00228 
00229 valtype_type XmlAttrBinary::getType() const
00230 {
00231     return VALTYPE_BINARY;
00232 }
00233 
00234 void XmlAttrBinary::fromVariant(VARIANT p)
00235 {
00236     CopyTo(p, m_value);
00237 }
00238 
00239 void XmlAttrBinary::toVariant(VARIANT *p) const
00240 {
00241     CopyTo(m_value, p);
00242 }
00243 
00244 void XmlAttrBinary::fromString(const char * str)
00245 {   
00246     if( str == NULL || strlen(str) == 0 )
00247         m_value.clear();
00248     else
00249     {
00250         // TODO: optimize this code
00251         int             len  = strlen(str)/2;
00252         unsigned char * buff = new unsigned char[len];
00253         string2bin( str, buff );
00254         m_value.resize( len );
00255         for( int i=0; i<len; ++i )
00256             m_value [i] = buff[i];
00257         delete [] buff;
00258     }
00259 }
00260 
00261 void XmlAttrBinary::toString(string& str) const
00262 {
00263     bin2string( m_value.begin(), m_value.size(), str );
00264 }
00265 
00267 // XmlAttrLock class
00269 
00270 XmlAttrLock::XmlAttrLock()
00271 {
00272     m_value = LOCKING_NONE;
00273 }
00274 
00275 valtype_type XmlAttrLock::getType() const
00276 {
00277     return VALTYPE_LOCK;
00278 }
00279 
00280 void XmlAttrLock::fromVariant(VARIANT p)
00281 {
00282     CopyTo(p, m_value);
00283 }
00284 
00285 void XmlAttrLock::toVariant(VARIANT *p) const
00286 {
00287     CopyTo(m_value, p);
00288 }
00289 
00290 void XmlAttrLock::fromString(const char * str)
00291 {   
00292     if( str == NULL || strlen(str) == 0 )
00293         m_value = LOCKING_NONE;
00294     else
00295         m_value = atoi( str );
00296 }
00297 
00298 void XmlAttrLock::toString(string& str) const
00299 {
00300     static char buf[100];
00301     sprintf( buf, "%d", m_value );
00302     str = buf;
00303 }
00304 
00306 // XmlAttrPointer class
00308 
00309 XmlAttrPointer::XmlAttrPointer()
00310 {
00311     m_parent = NULL;
00312 }
00313 
00314 valtype_type XmlAttrPointer::getType() const
00315 {
00316     return VALTYPE_POINTER;
00317 }
00318 
00320 // XmlAttrCollection class
00322 
00323 valtype_type XmlAttrCollection::getType() const
00324 {
00325     return VALTYPE_COLLECTION;
00326 }
00327 
00329 // XmlObject class
00331 
00332 XmlObject::XmlObject(ICoreMetaObject *metaobject, bool createAllAttributes)
00333 {
00334     m_deleted         = false;
00335     m_modified        = false;
00336     m_loaded          = createAllAttributes;
00337 
00338     //m_readOnly        = false;
00339 
00340     createAttributes(metaobject,m_loaded);
00341     CoCreateGuid(&m_guid);
00342 }
00343 
00344 XmlObject::~XmlObject()
00345 {
00346     for( AttribMapIter it = m_attributes.begin(); it != m_attributes.end(); ++it )
00347         delete it->second;
00348 }
00349 
00350 void XmlObject::createAttributes(ICoreMetaObject *metaobject, bool all)
00351 {
00352     ASSERT( metaobject != NULL );
00353 
00354         CComObjPtr<ICoreMetaAttributes> metaattributes;
00355         COMTHROW( metaobject->get_Attributes(PutOut(metaattributes)) );
00356         ASSERT( metaattributes != NULL );
00357 
00358         typedef vector< CComObjPtr<ICoreMetaAttribute> > metaattributelist_type;
00359         metaattributelist_type metaattributelist;
00360         GetAll<ICoreMetaAttributes, ICoreMetaAttribute>(metaattributes, metaattributelist);
00361 
00362     for( metaattributelist_type::iterator i=metaattributelist.begin(); i!=metaattributelist.end(); ++i )
00363     {
00364                 valtype_type valtype;
00365                 COMTHROW( (*i)->get_ValueType(&valtype) );
00366         if( all || valtype==VALTYPE_POINTER || valtype==VALTYPE_COLLECTION || valtype==VALTYPE_LOCK)
00367         {
00368                     attrid_type attrId = ATTRID_NONE;
00369                     COMTHROW( (*i)->get_AttrID(&attrId) );
00370             ASSERT( attrId != ATTRID_NONE );
00371             if( m_attributes.find(attrId) == m_attributes.end() )
00372                 m_attributes.insert( AttribMap::value_type(attrId,XmlAttrBase::create(valtype)) );
00373         }
00374         }
00375 }
00376 
00377 void XmlObject::deleteSecondaryAttribs()
00378 {
00379     for( AttribMapIter it = m_attributes.begin(); it != m_attributes.end(); ++it )
00380     {
00381         valtype_type type =it->second->getType();
00382         if( type!=VALTYPE_LOCK && type!=VALTYPE_POINTER && type!=VALTYPE_COLLECTION )
00383         {
00384             delete it->second;
00385             m_attributes.erase(it);
00386         }
00387     }
00388 }
00389 
00390 
00392 // CCoreXmlFile class
00394 
00395 CCoreXmlFile::CCoreXmlFile()
00396 {
00397     m_opened               = false;
00398     m_inTransaction        = false;
00399     m_modified             = false;
00400     m_metaAttributeId      = ATTRID_NONE;
00401     m_metaAttributeValType = VALTYPE_NONE;
00402     m_openedObject         = NULL;
00403 
00404     fillParentMap();
00405 
00406     XMLPlatformUtils::Initialize();    
00407 }
00408 
00409 CCoreXmlFile::~CCoreXmlFile()
00410 {
00411     clearAll();
00412 }
00413 
00414 STDMETHODIMP CCoreXmlFile::get_MetaProject(ICoreMetaProject **p)
00415 {
00416     CHECK_OUT(p);
00417         CopyTo(m_metaProject, p);
00418         return S_OK;
00419 }
00420 
00421 STDMETHODIMP CCoreXmlFile::put_MetaProject(ICoreMetaProject *p)
00422 {
00423     COMTRY
00424         {
00425                 closeMetaProject();
00426                 m_metaProject = p;
00427         }
00428         COMCATCH( closeMetaProject() )
00429 }
00430 
00431 STDMETHODIMP CCoreXmlFile::get_MetaObject(ICoreMetaObject **p)
00432 {
00433     CHECK_OUT(p);
00434         CopyTo(m_metaObject, p);
00435         return S_OK;
00436 }
00437 
00438 STDMETHODIMP CCoreXmlFile::put_MetaObject(ICoreMetaObject *p)
00439 {
00440     if( m_metaProject == NULL )
00441                 COMRETURN(E_INVALID_USAGE);
00442 
00443         if( m_metaObject == p )
00444                 return S_OK;
00445 
00446         COMTRY
00447         {
00448                 if( p != NULL )
00449                 {
00450             // check the metaproject of the object, it must be the same as the metaproject
00451             // of the storage
00452                         CComObjPtr<ICoreMetaProject> t;
00453                         COMTHROW( p->get_Project(PutOut(t)) );
00454                         if( !IsEqualObject(m_metaProject, t) )
00455                                 HR_THROW(E_SAMEPROJECT);
00456                 }
00457 
00458                 closeMetaObject();
00459                 m_metaObject = p;
00460                 if( m_metaObject != NULL )
00461                         openMetaObject();
00462         }
00463         COMCATCH( closeMetaObject() )
00464 }
00465 
00466 STDMETHODIMP CCoreXmlFile::get_MetaID(metaid_type *p)
00467 {
00468     CHECK_OUT(p);
00469         *p = m_metaObjectId;
00470         return S_OK;
00471 }
00472 
00473 STDMETHODIMP CCoreXmlFile::put_MetaID(metaid_type metaid)
00474 {
00475     if( m_metaProject == NULL )
00476                 COMRETURN(E_INVALID_USAGE);
00477 
00478         COMTRY
00479         {
00480                 if( metaid != METAID_NONE )
00481                 {
00482                         CComObjPtr<ICoreMetaObject> p;
00483                         COMTHROW( m_metaProject->get_Object(metaid, PutOut(p)) );
00484                         ASSERT( p != NULL );
00485 
00486                         if( m_metaObject != p )
00487                         {
00488                                 closeMetaObject();
00489                                 MoveTo(p, m_metaObject);
00490                                 openMetaObject();
00491                         }
00492                 }
00493                 else
00494                         closeMetaObject();
00495         }
00496         COMCATCH( closeMetaObject() )
00497 }
00498 
00499 STDMETHODIMP CCoreXmlFile::get_MetaAttribute(ICoreMetaAttribute **p)
00500 {
00501         CHECK_OUT(p);
00502         CopyTo(m_metaAttribute, p);
00503         return S_OK;
00504 }
00505 
00506 STDMETHODIMP CCoreXmlFile::put_MetaAttribute(ICoreMetaAttribute *p)
00507 {
00508     if( m_metaObject == NULL )
00509                 COMRETURN(E_INVALID_USAGE);
00510         ASSERT( m_metaProject != NULL );
00511 
00512         if( m_metaAttribute == p )
00513                 return S_OK;
00514 
00515         COMTRY
00516         {
00517                 if( m_metaAttribute != NULL )
00518                 {
00519             // the metaobject of the given metaattribute must be the same as the metaobject of 
00520             // the storage
00521                         CComObjPtr<ICoreMetaObject> t;
00522                         COMTHROW( m_metaAttribute->get_Object(PutOut(t)) );
00523                         if( !IsEqualObject(m_metaObject, t) )
00524                         {
00525                                 m_metaAttribute = NULL;
00526                                 return E_INVALIDARG;
00527                         }
00528                 }
00529 
00530                 closeMetaAttribute();
00531                 m_metaAttribute = p;
00532                 if( m_metaAttribute != NULL )
00533                         openMetaAttribute();
00534         }
00535         COMCATCH( closeMetaAttribute() )
00536 }
00537 
00538 STDMETHODIMP CCoreXmlFile::get_AttrID(attrid_type *p)
00539 {
00540         CHECK_OUT(p);
00541         if( m_metaAttribute )
00542                 return m_metaAttribute->get_AttrID(p);
00543         *p = 0;
00544         return S_OK;
00545 }
00546 
00547 STDMETHODIMP CCoreXmlFile::put_AttrID(attrid_type attrid)
00548 {
00549     if( m_metaObject == NULL )
00550                 COMRETURN(E_INVALID_USAGE);
00551         ASSERT( m_metaProject != NULL );
00552 
00553         COMTRY
00554         {
00555                 if( attrid != ATTRID_NONE )
00556                 {
00557                         CComObjPtr<ICoreMetaAttribute> p;
00558                         COMTHROW( m_metaObject->get_Attribute(attrid, PutOut(p)) );
00559                         ASSERT( p != NULL );
00560 
00561                         if( m_metaAttribute != p )
00562                         {
00563                                 closeMetaAttribute();
00564                                 m_metaAttribute = p;
00565                                 openMetaAttribute();
00566                         }
00567                 }
00568                 else
00569                         closeMetaAttribute();
00570         }
00571         COMCATCH( closeMetaAttribute() )
00572 }
00573 
00574 STDMETHODIMP CCoreXmlFile::get_AttributeValue(VARIANT *p)
00575 {
00576     CHECK_OUT(p);
00577 
00578         if( m_openedObject == NULL || !m_inTransaction )
00579                 COMRETURN(E_INVALID_USAGE);
00580         
00581         COMTRY
00582         {
00583         AttribMapIter it = m_openedObject->m_attributes.find( m_metaAttributeId );
00584         if( m_metaAttributeValType == VALTYPE_POINTER )
00585         {
00586             getPointer( (XmlAttrPointer*)it->second, p );
00587         }
00588         else if( m_metaAttributeValType == VALTYPE_COLLECTION )
00589         {
00590             getCollection( (XmlAttrCollection*)it->second, p );
00591         }
00592         else if( m_metaAttributeValType == VALTYPE_LOCK )
00593         {
00594             it->second->toVariant(p);
00595         }
00596         else
00597         {
00598             if( !m_openedObject->m_loaded )
00599             {
00600                 // attributes are not in memory!!
00601             }
00602             else
00603             {
00604                 it->second->toVariant(p);
00605             }
00606         }
00607         }
00608         COMCATCH(;)
00609 }
00610 
00611 STDMETHODIMP CCoreXmlFile::put_AttributeValue(VARIANT p)
00612 {
00613     if( m_openedObject == NULL || !m_inTransaction )
00614                 COMRETURN(E_INVALID_USAGE);
00615 
00616     // TODO: return with specific error code
00617     //if( m_openedObject->m_readOnly )
00618       //  COMRETURN(E_INVALID_USAGE);
00619         
00620         COMTRY
00621         {
00622         AttribMapIter it = m_openedObject->m_attributes.find( m_metaAttributeId );
00623         if( m_metaAttributeValType == VALTYPE_POINTER )
00624         {
00625             setPointer( (XmlAttrPointer*)it->second, p );
00626         }
00627         else if( m_metaAttributeValType == VALTYPE_COLLECTION )
00628         {
00629             ASSERT( false );
00630         }
00631         else if( m_metaAttributeValType == VALTYPE_LOCK )
00632         {
00633             it->second->fromVariant(p);
00634         }
00635         else
00636         {
00637             if( !m_openedObject->m_loaded )
00638             {
00639                 // attributes are not in memory!!
00640             }
00641             else
00642             {
00643                 it->second->fromVariant(p);
00644             }
00645         }
00646 
00647         m_openedObject->m_modified = true;
00648         }
00649         COMCATCH(;)
00650 }
00651 
00652 STDMETHODIMP CCoreXmlFile::OpenObject(objid_type objid)
00653 {
00654     if( m_metaObject == NULL || !m_inTransaction )
00655                 COMRETURN(E_INVALID_USAGE);
00656            
00657     if( m_openedObject == (XmlObject*)objid )
00658                 return S_OK;
00659 
00660     metaobjidpair_type idpair;
00661         idpair.metaid = m_metaObjectId;
00662         idpair.objid  = objid;
00663 
00664         COMTRY
00665         {
00666         m_openedObject = objectFromObjId(idpair);
00667         }
00668         COMCATCH(;)
00669 }
00670 
00671 STDMETHODIMP CCoreXmlFile::CreateObject(objid_type *objid)
00672 {
00673     CHECK_OUT(objid);
00674 
00675         if( m_metaObject == NULL || !m_inTransaction )
00676                 COMRETURN(E_INVALID_USAGE);
00677 
00678     ASSERT( m_metaObjectId != METAID_ROOT );
00679 
00680         COMTRY
00681         {                               
00682         // create and add new object
00683         XmlObject * obj = new XmlObject(m_metaObject);
00684         obj->m_metaid   = m_metaObjectId;
00685         addObject( obj );
00686 
00687         m_modified = true;
00688         m_openedObject = obj;
00689                 *objid = (long)obj;
00690         }
00691         COMCATCH(;)
00692 }
00693 
00694 STDMETHODIMP CCoreXmlFile::CloseObject()
00695 {
00696     m_openedObject = NULL;
00697         return S_OK;
00698 }
00699 
00700 STDMETHODIMP CCoreXmlFile::LockObject()
00701 {
00702         return S_OK;
00703 }
00704 
00705 STDMETHODIMP CCoreXmlFile::DeleteObject()
00706 {
00707         return S_OK;
00708 }
00709 
00710 STDMETHODIMP CCoreXmlFile::OpenProject(BSTR connection, VARIANT_BOOL *ro_mode) 
00711 {
00712     if( m_opened || m_metaProject == NULL )
00713         COMRETURN(E_INVALID_USAGE);
00714 
00715     setFolderPathOnOpen( connection );
00716 
00717     readAll();
00718 
00719     m_opened   = true;
00720     m_modified = false;
00721 
00722     //readBinaryCache();
00723 
00724 
00725     //UnresolvedPointerVec pointers;
00726     //readXMLFile("c:\\temp\\gmetest\\xml3\\test1\\d6b6c42a6d4ea8409ef6cd583eefa54c.xml", pointers );
00727 
00728 
00729 
00730     return S_OK;
00731 }
00732 
00733 STDMETHODIMP CCoreXmlFile::CreateProject(BSTR connection)
00734 {
00735     if( m_opened || m_metaProject == NULL )
00736                 COMRETURN(E_INVALID_USAGE);
00737     
00738     // create project folder
00739     setFolderPathOnCreate(connection);
00740     if( CreateDirectory(m_folderPath.c_str(),NULL) == 0 )
00741         COMRETURN(E_FILEOPEN);
00742 
00743     // clear data structures
00744     clearAll();
00745 
00746     // query the metaobject for the root
00747     CComObjPtr<ICoreMetaObject> mo;
00748         COMTHROW( m_metaProject->get_Object(METAID_ROOT, PutOut(mo)) );
00749         ASSERT( mo != NULL );
00750 
00751     // create the root
00752     m_root = new XmlObject(mo);
00753     m_root->m_metaid = METAID_ROOT;
00754     addObject( m_root );
00755     
00756     m_opened   = true;
00757     m_modified = true;
00758     
00759     return S_OK;
00760 }
00761 
00762 STDMETHODIMP CCoreXmlFile::SaveProject(BSTR connection, VARIANT_BOOL keepoldname = VARIANT_TRUE) 
00763 {
00764     return S_OK;        
00765 }
00766 
00767 STDMETHODIMP CCoreXmlFile::CloseProject( VARIANT_BOOL abort)
00768 {
00769     if( !m_opened || m_metaProject == NULL )
00770                 COMRETURN(E_INVALID_USAGE);
00771 
00772         COMTRY
00773         {
00774                 /*if( abort == VARIANT_FALSE && modified && !(filename == ".")) 
00775                         SaveProject(NULL);*/
00776 
00777                 //CancelProject();
00778 
00779         //writeBinaryCache();
00780         //writeAll();
00781         clearAll();
00782 
00783         }
00784         COMCATCH(;)
00785 
00786         return S_OK;
00787 }
00788 
00789 STDMETHODIMP CCoreXmlFile::DeleteProject()
00790 { 
00791     return E_NOTIMPL;
00792 }
00793 
00794 STDMETHODIMP CCoreXmlFile::BeginTransaction()
00795 {       
00796     if( !m_opened || m_inTransaction )
00797                 COMRETURN(E_INVALID_USAGE);
00798         m_inTransaction = true;
00799         return S_OK;
00800 }
00801 
00802 STDMETHODIMP CCoreXmlFile::CommitTransaction()
00803 {
00804     if( !m_inTransaction )
00805                 COMRETURN(E_INVALID_USAGE);
00806 
00807         ASSERT( m_opened );
00808 
00809         CloseObject();  
00810         m_inTransaction = false;
00811 
00812 
00813         return S_OK;
00814 }
00815 
00816 STDMETHODIMP CCoreXmlFile::AbortTransaction()
00817 {
00818         if( !m_inTransaction )
00819                 COMRETURN(E_INVALID_USAGE);
00820 
00821         ASSERT( m_opened );
00822 
00823         CloseObject();  
00824         m_inTransaction = false;
00825         return S_OK;
00826 }
00827 
00828 STDMETHODIMP CCoreXmlFile::get_StorageType(long *p)
00829 {
00830     CHECK_OUT(p);
00831         *p = 0;
00832         return S_OK;
00833 }
00834 
00835 void CCoreXmlFile::fillParentMap()
00836 {
00837     m_parentMap.clear();
00838 
00839     m_parentMap.insert( ParentMap::value_type( DTID_CONSTRAINT , ATTRID_CONSTROWNER ) );
00840     m_parentMap.insert( ParentMap::value_type( DTID_REGNODE    , ATTRID_REGNOWNER   ) );
00841     m_parentMap.insert( ParentMap::value_type( DTID_FOLDER     , ATTRID_PARENT      ) );
00842     m_parentMap.insert( ParentMap::value_type( DTID_MODEL      , ATTRID_PARENT      ) );
00843     m_parentMap.insert( ParentMap::value_type( DTID_ATOM       , ATTRID_PARENT      ) );
00844     m_parentMap.insert( ParentMap::value_type( DTID_REFERENCE  , ATTRID_PARENT      ) );
00845     m_parentMap.insert( ParentMap::value_type( DTID_SET        , ATTRID_PARENT      ) );
00846     m_parentMap.insert( ParentMap::value_type( DTID_SETNODE    , ATTRID_SETMEMBER   ) );
00847     m_parentMap.insert( ParentMap::value_type( DTID_CONNECTION , ATTRID_PARENT      ) );
00848     m_parentMap.insert( ParentMap::value_type( DTID_CONNROLE   , ATTRID_CONNROLE    ) );
00849     m_parentMap.insert( ParentMap::value_type( DTID_CONNROLESEG, ATTRID_CONNSEG     ) );
00850     m_parentMap.insert( ParentMap::value_type( DTID_STRATTR    , ATTRID_ATTRPARENT  ) );
00851     m_parentMap.insert( ParentMap::value_type( DTID_INTATTR    , ATTRID_ATTRPARENT  ) );
00852     m_parentMap.insert( ParentMap::value_type( DTID_FLOATATTR  , ATTRID_ATTRPARENT  ) );
00853     m_parentMap.insert( ParentMap::value_type( DTID_BOOLATTR   , ATTRID_ATTRPARENT  ) );
00854     m_parentMap.insert( ParentMap::value_type( DTID_REFATTR    , ATTRID_ATTRPARENT  ) );
00855 }
00856 
00857 void CCoreXmlFile::closeMetaProject()
00858 {
00859     closeMetaObject();
00860     CloseProject();
00861         m_metaProject = NULL;
00862 }
00863 
00864 void CCoreXmlFile::openMetaObject()
00865 {
00866         ASSERT( m_metaObject != NULL );
00867         COMTHROW( m_metaObject->get_MetaID(&m_metaObjectId) );
00868 }
00869 
00870 void CCoreXmlFile::closeMetaObject()
00871 {
00872         CloseObject();
00873         closeMetaAttribute();
00874         m_metaObject   = NULL;
00875         m_metaObjectId = METAID_NONE;
00876 }
00877 
00878 void CCoreXmlFile::openMetaAttribute()
00879 {
00880         ASSERT( m_metaAttribute != NULL );
00881         COMTHROW( m_metaAttribute->get_AttrID(&m_metaAttributeId) );
00882     COMTHROW( m_metaAttribute->get_ValueType(&m_metaAttributeValType) );
00883 
00884         if( m_metaAttributeId == ATTRID_NONE )
00885                 HR_THROW(E_METAPROJECT);
00886 }
00887 
00888 void CCoreXmlFile::closeMetaAttribute()
00889 {
00890         m_metaAttribute        = NULL;
00891         m_metaAttributeId      = ATTRID_NONE;
00892     m_metaAttributeValType = VALTYPE_NONE;
00893 }
00894 
00895 void CCoreXmlFile::setFolderPathOnCreate(BSTR connection)
00896 {
00897     string conn;
00898 
00899     CopyTo(connection, conn);
00900 
00901     if( !(string(conn, 0, 4) == "MGX=") )
00902             HR_THROW(E_INVALID_USAGE);
00903 
00904     conn.erase(0, 4);
00905     m_folderPath = conn;
00906 
00907     char drive[_MAX_DRIVE];
00908     char dir[_MAX_DIR];
00909     char fname[_MAX_FNAME];
00910     char ext[_MAX_EXT];
00911 
00912     _splitpath( conn.c_str(), drive, dir, fname, ext );
00913 
00914     m_cacheFileName = m_folderPath;
00915     m_cacheFileName += "\\";
00916     m_cacheFileName += fname;
00917     m_cacheFileName += ".mgx";
00918 }
00919 
00920 void CCoreXmlFile::setFolderPathOnOpen(BSTR connection)
00921 {
00922     string conn;
00923 
00924     CopyTo(connection, conn);
00925 
00926     if( !(string(conn, 0, 4) == "MGX=") )
00927             HR_THROW(E_INVALID_USAGE);
00928 
00929     conn.erase(0, 4);
00930     
00931     char drive[_MAX_DRIVE];
00932     char dir[_MAX_DIR];
00933     char fname[_MAX_FNAME];
00934     char ext[_MAX_EXT];
00935 
00936     _splitpath( conn.c_str(), drive, dir, fname, ext );
00937 
00938     m_folderPath = drive;
00939     m_folderPath += "\\";
00940     m_folderPath += dir;
00941     m_folderPath.resize(m_folderPath.size()-1); // remove the ending "\"
00942 
00943     m_cacheFileName = m_folderPath;
00944     m_cacheFileName += "\\";
00945     m_cacheFileName += fname;
00946     m_cacheFileName += ".mgx";
00947 }
00948 
00949 
00950 
00951 
00952 
00953 
00954 
00955 
00956 
00957 
00958 
00959 void CCoreXmlFile::clearAll()
00960 {
00961     for( XmlObjVecIter i=m_objects.begin(); i!=m_objects.end(); ++i )       
00962         delete (*i);
00963     m_objects.clear();
00964     m_openedObject = NULL;
00965     m_root = NULL;
00966 }
00967 
00968 void CCoreXmlFile::addObject(XmlObject * obj)
00969 {
00970     obj->m_index = m_objects.size();
00971     m_objects.push_back( obj );
00972     m_objectsByGUID.insert( GUIDToXmlObjectMap::value_type( obj->m_guid, obj ) );
00973 }
00974     
00975 void CCoreXmlFile::removeObject(XmlObject * obj)
00976 {
00977     // remove pointers
00978     for(AttribMapIter it=obj->m_attributes.begin(); it!=obj->m_attributes.end(); ++it)
00979     {
00980         if( it->second->getType() == VALTYPE_POINTER )
00981         {
00982             // remove it from parent object's collection
00983             XmlAttrPointer * pointer = (XmlAttrPointer*)it->second;
00984             if( pointer->m_parent != NULL )
00985             {
00986                 AttribMapIter it2 = pointer->m_parent->m_attributes.find( it->first + ATTRID_COLLECTION );
00987                 ASSERT( it2 != pointer->m_parent->m_attributes.end() );
00988                 ASSERT( it2->second->getType() == VALTYPE_COLLECTION );
00989                 ((XmlAttrCollection*)it2->second)->m_children.erase(obj);
00990             }
00991         }
00992         else if( it->second->getType() == VALTYPE_COLLECTION )
00993         {
00994             XmlAttrCollection * collection = (XmlAttrCollection*)it->second;
00995             for( XmlObjSetIter it2=collection->m_children.begin(); it2!=collection->m_children.end(); ++it2 )
00996             {
00997                 // set parent of this child to NULL
00998                 XmlObject * obj2 = (*it2);
00999                 AttribMapIter it3 = obj2->m_attributes.find( it->first - ATTRID_COLLECTION );
01000                 ASSERT( it3 != obj2->m_attributes.end() );
01001                 ASSERT( it3->second->getType() == VALTYPE_POINTER );
01002                 ((XmlAttrPointer *)(it3->second))->m_parent = NULL;
01003             }
01004         }
01005     }
01006 
01007     obj->m_deleted = true;
01008 }
01009 
01010 void CCoreXmlFile::setPointer(XmlObject * obj, attrid_type attribId, XmlObject * parent)
01011 {
01012     ASSERT( obj!=NULL );
01013 
01014     AttribMapIter it = obj->m_attributes.find(attribId);
01015     ASSERT( it!=obj->m_attributes.end() );
01016     
01017     XmlAttrPointer * attr = (XmlAttrPointer*)it->second;
01018     
01019     // remove item from old parent's list
01020     if( attr->m_parent != NULL )
01021     {
01022         // find collection attribute of parent
01023         AttribMapIter it2 = attr->m_parent->m_attributes.find( attribId + ATTRID_COLLECTION );
01024         ASSERT( it2 != attr->m_parent->m_attributes.end() );
01025         ASSERT( it2->second->getType() == VALTYPE_COLLECTION );
01026         
01027         // remove this form the list
01028         ((XmlAttrCollection *)it2->second)->m_children.erase(obj);
01029     }
01030 
01031     // set pointer attribute
01032     attr->m_parent = parent;
01033 
01034     // add item to new parent's list
01035     if( parent != NULL )
01036     {
01037         AttribMapIter it3 = parent->m_attributes.find( attribId + ATTRID_COLLECTION );
01038         ASSERT( it3 != parent->m_attributes.end() );
01039         ASSERT( it3->second->getType() == VALTYPE_COLLECTION );
01040         ((XmlAttrCollection *)it3->second)->m_children.insert(obj);
01041     }
01042 }
01043 
01044 void CCoreXmlFile::setPointer(XmlAttrPointer * attr, VARIANT p)
01045 {   
01046     metaobjidpair_type idpair;
01047     CopyTo(p, idpair);
01048     XmlObject * parent = objectFromObjId(idpair);
01049     setPointer( m_openedObject, m_metaAttributeId, parent );
01050 }
01051     
01052 void CCoreXmlFile::updateCollections()
01053 {
01054     for( XmlObjVecIter it=m_objects.begin(); it!=m_objects.end(); ++it )
01055     {   
01056         XmlObject * obj = (*it);
01057         for( AttribMapIter j=obj->m_attributes.begin(); j!=obj->m_attributes.end(); ++j)
01058         {
01059             if( j->second->getType() == VALTYPE_POINTER )
01060             {
01061                 XmlAttrPointer * pointer = (XmlAttrPointer*)j->second;
01062                 if( pointer->m_parent != NULL )
01063                 {
01064                     AttribMapIter k = pointer->m_parent->m_attributes.find( j->first + ATTRID_COLLECTION );
01065                     ASSERT( k != pointer->m_parent->m_attributes.end() );
01066                     ((XmlAttrCollection*)k->second)->m_children.insert( obj );
01067                 }
01068             }
01069         }
01070     }
01071 }
01072 
01073 void CCoreXmlFile::resolvePointers(UnresolvedPointerVec& pointers)
01074 {
01075     for( UnresolvedPointerVecIt it=pointers.begin(); it!=pointers.end(); ++it )
01076     {
01077         if( it->m_pointedObjGuid == GUID_NULL )
01078         {
01079             setPointer( it->m_object, it->m_attrib, NULL );
01080         }
01081         else
01082         {
01083             GUIDToXmlObjectMapIter it2 = m_objectsByGUID.find( it->m_pointedObjGuid );
01084             if( it2 != m_objectsByGUID.end() )
01085             {
01086                 setPointer( it->m_object, it->m_attrib, it2->second );
01087             }
01088             else
01089             {
01090                 // TODO: invalid pointer, what to do?
01091             }
01092         }
01093     }
01094 }
01095 
01096 void CCoreXmlFile::getPointer(XmlAttrPointer * attr, VARIANT * p)
01097 {
01098     ASSERT( attr!= NULL );
01099     metaobjidpair_type id;
01100     objIdFromObject( attr->m_parent, id );
01101     CopyTo(id, p);
01102 }
01103 
01104 void CCoreXmlFile::getCollection(XmlAttrCollection * attr, VARIANT * p)
01105 {
01106     ASSERT( attr!= NULL );
01107     vector<metaobjidpair_type> idpairs;
01108     for( XmlObjSetIter it = attr->m_children.begin(); it != attr->m_children.end(); ++it )
01109     {
01110         metaobjidpair_type id;
01111         objIdFromObject( *it, id );
01112         idpairs.push_back( id );
01113     }
01114     CopyTo(idpairs, p);
01115 }
01116 
01117 XmlObject * CCoreXmlFile::objectFromObjId(metaobjidpair_type idpair)
01118 {
01119     if( idpair.metaid == METAID_NONE && idpair.objid == OBJID_NONE )
01120         return NULL;
01121 
01122     if( idpair.metaid == METAID_ROOT )
01123         return m_root;
01124     else
01125         return (XmlObject*)idpair.objid;
01126 }
01127 
01128 void CCoreXmlFile::objIdFromObject(XmlObject * obj, metaobjidpair_type& idpair)
01129 {
01130     if( obj == NULL )
01131     {
01132         idpair.metaid = METAID_NONE;
01133         idpair.objid  = OBJID_NONE;
01134     }
01135     else
01136     {
01137         idpair.metaid = obj->m_metaid;
01138         if( idpair.metaid == METAID_ROOT )
01139             idpair.objid = 1;
01140         else
01141             idpair.objid = (long)obj;
01142     }
01143 }
01144 
01145 void CCoreXmlFile::writeBinaryCache()
01146 {
01147     FILE * f = fopen( m_cacheFileName.c_str(), "wb" );
01148     if( f==NULL )
01149         HR_THROW(E_FILEOPEN);
01150 
01151     XmlObjVecIter i;
01152 
01153     // write out GUIDs and metaids
01154     int n = m_objects.size();
01155     fwrite( &n, sizeof(n), 1, f );
01156     for( i = m_objects.begin(); i != m_objects.end(); ++i )
01157     {
01158         fwrite( &((*i)->m_metaid), sizeof(long), 1, f );
01159         fwrite( &((*i)->m_guid), sizeof(GUID), 1, f );
01160     }
01161 
01162     // write out pointers
01163     int x;
01164     for( i=m_objects.begin(); i!=m_objects.end(); ++i )
01165     {   
01166         XmlObject * obj = (*i);
01167         for( AttribMapIter j=obj->m_attributes.begin(); j!=obj->m_attributes.end(); ++j)
01168         {
01169             if( j->second->getType() == VALTYPE_POINTER )
01170             {
01171                 XmlAttrPointer * pointer = (XmlAttrPointer*)j->second;
01172                 if( pointer->m_parent == NULL )
01173                     x = 0;
01174                 else
01175                     x = pointer->m_parent->m_index;
01176                 fwrite( &x, sizeof(x), 1, f );
01177             }
01178         }
01179     }
01180 
01181     fclose(f);
01182 }
01183 
01184 void CCoreXmlFile::readBinaryCache()
01185 {    
01186     FILE * f = fopen( m_cacheFileName.c_str(), "rb" );
01187     if( f==NULL )
01188         HR_THROW(E_FILEOPEN);
01189 
01190     clearAll();
01191 
01192     // read GUIDs and metaids and create objects
01193     int n,i;
01194     fread( &n, sizeof(n), 1, f );
01195     for( i=0; i<n; ++i )
01196     {
01197         long metaid;
01198         GUID guid;
01199 
01200         fread( &metaid, sizeof(metaid), 1, f );
01201         fread( &guid, sizeof(GUID), 1, f );
01202 
01203         CComObjPtr<ICoreMetaObject> metaobject;
01204         COMTHROW( m_metaProject->get_Object(metaid, PutOut(metaobject)) );
01205 
01206         XmlObject * obj = new XmlObject(metaobject);
01207         obj->m_metaid = metaid;
01208         obj->m_guid   = guid;
01209         addObject(obj);
01210     }
01211 
01212     // read and set pointers
01213     int x;
01214     for( XmlObjVecIter it=m_objects.begin(); it!=m_objects.end(); ++it )
01215     {   
01216         XmlObject * obj = (*it);
01217         for( AttribMapIter j=obj->m_attributes.begin(); j!=obj->m_attributes.end(); ++j)
01218         {
01219             if( j->second->getType() == VALTYPE_POINTER )
01220             {
01221                 XmlAttrPointer * pointer = (XmlAttrPointer*)j->second;
01222 
01223                 fread( &x, sizeof(x), 1, f );
01224                 if( x == 0 )
01225                     pointer->m_parent = NULL;
01226                 else
01227                     pointer->m_parent = m_objects[x];
01228             }
01229         }
01230     }
01231 
01232     fclose(f);
01233 
01234     updateCollections();
01235 }
01236 
01237 void CCoreXmlFile::writeAll()
01238 {
01239     for( XmlObjVecIter it=m_objects.begin(); it!=m_objects.end(); ++it )
01240     {
01241         XmlObject * obj = (*it);
01242 
01243         if( obj->m_metaid == DTID_MODEL || obj->m_metaid == DTID_FOLDER 
01244             || obj->m_metaid == METAID_ROOT )
01245         {
01246             writeXMLFile( obj );
01247         }
01248     }
01249 }
01250 
01251 void CCoreXmlFile::writeXMLFile(XmlObject * container)
01252 {
01253     // container must be model or folder or the root
01254     if( container->m_metaid != DTID_MODEL && container->m_metaid != DTID_FOLDER 
01255         && container->m_metaid != METAID_ROOT )
01256         HR_THROW(E_INVALID_USAGE);
01257 
01258     // set file name
01259     char fileName[MAX_PATH];
01260     string guidStr;
01261     guid2str(container->m_guid,guidStr);
01262     sprintf( fileName, "%s\\%s.xml", m_folderPath.c_str(), guidStr.c_str() );
01263 
01264     // open file
01265     FILE * file = fopen( fileName, "w" );
01266     if( file == NULL )
01267         HR_THROW(E_FILEOPEN);
01268 
01269     // write objects recursively
01270     writeObject( container, file, true, "" );
01271     
01272     fclose(file);
01273 }
01274 
01275 void CCoreXmlFile::writeObject(XmlObject * obj, FILE * file, bool container, const char * prefix)
01276 {        
01277     string                          str;
01278     CComObjPtr<ICoreMetaObject>     metaobject;
01279     CComBSTR                        metaToken;    
01280 
01281     COMTHROW( m_metaProject->get_Object( obj->m_metaid, PutOut(metaobject) ) );
01282     COMTHROW( metaobject->get_Token( &metaToken ) );
01283     guid2str( obj->m_guid, str );
01284 
01285     fprintf(file, "%s<%S MetaId=\"%d\" Id=\"%s\"", prefix, metaToken, obj->m_metaid, str.c_str() );
01286 
01287     // write pointers, attributes
01288     AttribMapIter it;
01289     for( it=obj->m_attributes.begin(); it!=obj->m_attributes.end(); ++it )
01290     {
01291         XmlAttrBase                    * attr = it->second;
01292         CComObjPtr<ICoreMetaAttribute>   metaAttrib;
01293         CComBSTR                         attribToken;
01294         string                           attrVal;
01295 
01296         COMTHROW( metaobject->get_Attribute( it->first, PutOut(metaAttrib) ) );
01297         metaAttrib->get_Token( &attribToken );
01298 
01299         if( attr->getType() == VALTYPE_POINTER  )
01300         {
01301             ParentMap::iterator it2 = m_parentMap.find( obj->m_metaid );
01302             if( it2==m_parentMap.end() || it2->second!=it->first || container )
01303             {
01304                 XmlAttrPointer * pointer = (XmlAttrPointer*)attr;
01305                 if( pointer->m_parent != NULL )
01306                     guid2str( pointer->m_parent->m_guid, attrVal );
01307             }
01308         }
01309         else if( attr->getType() != VALTYPE_COLLECTION && attr->getType() != VALTYPE_LOCK )
01310         {
01311             XmlAttrBase * attr = it->second;
01312             attr->toString(attrVal);
01313         }
01314 
01315         if( !attrVal.empty() )
01316             fprintf(file, " %S=\"%s\"", attribToken, attrVal.c_str() );
01317     }
01318     fprintf(file, ">\n" );
01319 
01320     // write out children
01321     // child is written if it is not the root, a model or a folder
01322     // and the parent of the child is a us according to m_parentMap
01323     string newPrefix = prefix;
01324     newPrefix += "\t";
01325     for( it=obj->m_attributes.begin(); it!=obj->m_attributes.end(); ++it )
01326     {
01327         XmlAttrBase * attr = it->second;
01328         if( attr->getType() == VALTYPE_COLLECTION )
01329         {
01330             XmlAttrCollection * coll = (XmlAttrCollection*)attr;
01331             for( XmlObjSetIter it2=coll->m_children.begin(); it2!=coll->m_children.end(); ++it2 )
01332             {
01333                 XmlObject * obj2 = (*it2);
01334                 if( obj2!=NULL && obj2->m_metaid!=DTID_MODEL && obj2->m_metaid!=DTID_FOLDER                  
01335                     && obj2->m_metaid != METAID_ROOT )
01336                 {                    
01337                     ParentMap::iterator it3 = m_parentMap.find( obj2->m_metaid );
01338                     ASSERT( it3 != m_parentMap.end() );
01339                     if( it3->second + ATTRID_COLLECTION == it->first )
01340                         writeObject( obj2, file, false, newPrefix.c_str() );
01341                 }
01342             }
01343         }
01344     }
01345     
01346     fprintf(file, "%s</%S>\n",prefix, metaToken);
01347 }
01348 
01349 void CCoreXmlFile::readXMLFile( const char * fileName, UnresolvedPointerVec& pointers )
01350 {
01351     DOMBuilder * parser = NULL;
01352 
01353     try
01354     {    
01355         DOMImplementationLS * domimpl = DOMImplementationRegistry::getDOMImplementation(NULL);
01356         ASSERT( domimpl != NULL );
01357 
01358         parser = domimpl->createDOMBuilder( DOMImplementationLS::MODE_SYNCHRONOUS, NULL );
01359         ASSERT( parser != NULL );
01360 
01361         DOMDocument * doc = parser->parseURI( fileName );
01362     
01363         readObject( doc->getDocumentElement(), pointers, NULL );
01364 
01365         delete parser;
01366     }
01367     catch(...)
01368     {
01369         if( parser != NULL )
01370             delete parser;
01371 
01372         HR_THROW(E_FILEOPEN);
01373     }
01374 }
01375 
01376 void CCoreXmlFile::readObject(DOMElement * e, UnresolvedPointerVec& pointers, XmlObject * parent)
01377 {    
01378     // get metaid, and id
01379     char * metaidStr  = XMLString::transcode(e->getAttribute(XMLString::transcode("MetaId")));
01380     char * objGUIDStr = XMLString::transcode(e->getAttribute(XMLString::transcode("Id" )));
01381     long   metaid     = atoi( metaidStr );
01382     GUID   guid       = str2guid( objGUIDStr );
01383     delete metaidStr;
01384     delete objGUIDStr;
01385 
01386     // get meta object
01387     CComObjPtr<ICoreMetaObject> metaobject;
01388     COMTHROW( m_metaProject->get_Object( metaid, PutOut(metaobject) ) );
01389 
01390     // find or create object
01391     XmlObject * obj = NULL;
01392     GUIDToXmlObjectMapIter it = m_objectsByGUID.find( guid );
01393     if( it != m_objectsByGUID.end() )
01394     {
01395         obj = it->second;
01396         if( !obj->m_loaded )
01397         {
01398             obj->createAttributes(metaobject,true);
01399             obj->m_loaded = true;
01400         }
01401     }
01402     else
01403     {
01404         obj = new XmlObject(metaobject,true);
01405         obj->m_metaid = metaid;
01406         obj->m_guid   = guid;
01407         addObject( obj );
01408         if( metaid == METAID_ROOT )
01409             m_root = obj;
01410     }
01411     
01412     // read attributes
01413     AttribMapIter it2;
01414     for( it2 = obj->m_attributes.begin(); it2 != obj->m_attributes.end(); ++it2 )
01415     {        
01416         CComObjPtr<ICoreMetaAttribute>  metaAttrib;
01417         CComBSTR                        attribToken;
01418 
01419         COMTHROW( metaobject->get_Attribute( it2->first, PutOut(metaAttrib) ) );
01420         COMTHROW( metaAttrib->get_Token( &attribToken ));        
01421 
01422         char * attrVal = XMLString::transcode(e->getAttribute(attribToken));
01423 
01424         XmlAttrBase * attr = it2->second;
01425         if( attr->getType() == VALTYPE_POINTER )
01426         {
01427             UnresolvedPointer p;
01428             p.m_object = obj;
01429             p.m_attrib = it2->first;          
01430             if( attrVal==NULL || strlen(attrVal)==0 )
01431                 p.m_pointedObjGuid = GUID_NULL;
01432             else
01433                 p.m_pointedObjGuid = str2guid( attrVal );
01434             pointers.push_back( p );
01435         }
01436         else if( attr->getType() != VALTYPE_LOCK && attr->getType() != VALTYPE_COLLECTION )
01437         {
01438             it2->second->fromString(attrVal);
01439         }
01440 
01441         delete attrVal;
01442     }
01443 
01444     // implicit parent pointer
01445     if( parent != NULL )
01446     {
01447         ParentMap::iterator it3 = m_parentMap.find( obj->m_metaid );
01448         UnresolvedPointer p;
01449         p.m_object = obj;
01450         p.m_attrib = it3->second;
01451         p.m_pointedObjGuid = parent->m_guid;
01452         pointers.push_back(p);
01453     }        
01454   
01455     // read children
01456     DOMNodeList * children = e->getChildNodes();
01457     for( int i=0; i<children->getLength(); ++i )
01458     {
01459         DOMNode * node = children->item(i);
01460         if( node->getNodeType() == DOMNode::ELEMENT_NODE )        
01461             readObject( (DOMElement*)node, pointers, obj );
01462     }
01463 }
01464 
01465 void CCoreXmlFile::readAll()
01466 {
01467     UnresolvedPointerVec pointers;
01468     char                 buf[_MAX_PATH];
01469     _finddata_t          fileInfo;
01470 
01471     clearAll();
01472     
01473     sprintf( buf, "%s\\*.xml", m_folderPath.c_str() );
01474     long searchHandle = _findfirst( buf, &fileInfo );
01475     long ret = searchHandle;
01476     while( ret != -1 )
01477     {
01478         sprintf( buf, "%s\\%s", m_folderPath.c_str(), fileInfo.name );
01479         readXMLFile( buf, pointers );
01480         ret = _findnext( searchHandle, &fileInfo );
01481     }
01482     _findclose( searchHandle );
01483 
01484     resolvePointers( pointers );
01485 }
01486 
01487 void CCoreXmlFile::incrementalUpdate()
01488 {
01489     // vegig kell menni a fileokon es megnezni az uj es a modosult fileokat
01490 
01491     // minden file-ra meghivjuk a readXMLFile ami beolvassa az objektumokat a filebol, 
01492     // torli a mar nem letezo objektumokat beolvassa az atributumokat
01493     // (lehet hogy csak a pointereket kene beolvasni!)
01494     // a feloldatlan pointereket egy listaba gyujtjuk
01495     // objektum torlesnel figyelni kell hogy a pointereket is update-eljuk
01496 
01497     // a felodatlan pointereket a vegen feloldjuk
01498     
01499 
01500 }
01501