[commit] r2299 - in trunk: GME/Core GME/Mga Tests/GPyUnit
GMESRC Repository Notifications
gme-commit at list.isis.vanderbilt.edu
Wed Aug 21 14:40:13 CDT 2013
Author: ksmyth
Date: Wed Aug 21 14:40:13 2013
New Revision: 2299
Log:
Detect dup GUIDs in mga open, and reassign them
Added:
trunk/Tests/GPyUnit/SFDemo_dup_guids.mga
trunk/Tests/GPyUnit/test_mga_open.py
Modified:
trunk/GME/Core/CoreBinFile.cpp
trunk/GME/Core/CoreBinFile.h
trunk/GME/Mga/MgaFCO.cpp
trunk/GME/Mga/MgaLibOps.cpp
trunk/GME/Mga/MgaLibRefr.h
trunk/Tests/GPyUnit/__init__.py
trunk/Tests/GPyUnit/test_copy.py
trunk/Tests/GPyUnit/test_parser.py
Modified: trunk/GME/Core/CoreBinFile.cpp
==============================================================================
--- trunk/GME/Core/CoreBinFile.cpp Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/GME/Core/CoreBinFile.cpp Wed Aug 21 14:40:13 2013 (r2299)
@@ -145,7 +145,7 @@
}
}
-bool BinObject::HasGuidAndStatAttributes( bool* p_guidFound, bool* p_statusFound, bool* p_oldRegFound)
+void BinObject::HasGuidAndStatAttributes(GUID& t_guid, bool* p_statusFound, bool* p_oldRegFound)
{
int a1( 0), a2( 0), a3( 0), a4( 0);
@@ -153,12 +153,30 @@
binattrs_iterator e = binattrs.end();
while( i != e)
{
- switch( (i)->attrid)
+ switch ((i)->attrid)
{
- case ATTRID_GUID1: ++a1;break;
- case ATTRID_GUID2: ++a2;break;
- case ATTRID_GUID3: ++a3;break;
- case ATTRID_GUID4: ++a4;break;
+ case ATTRID_GUID1:
+ t_guid.Data1 = reinterpret_cast<BinAttr<VALTYPE_LONG>*>(&(*i))->a;
+ break;
+ case ATTRID_GUID2:
+ t_guid.Data2 = (reinterpret_cast<BinAttr<VALTYPE_LONG>*>(&(*i))->a) >> 16;
+ t_guid.Data3 = (reinterpret_cast<BinAttr<VALTYPE_LONG>*>(&(*i))->a) & 0xFFFF;
+ break;
+
+ case ATTRID_GUID3: {
+ long v3 = reinterpret_cast<BinAttr<VALTYPE_LONG>*>(&(*i))->a;
+ t_guid.Data4[0] = (v3 >> 24);
+ t_guid.Data4[1] = (v3 >> 16) & 0xFF;
+ t_guid.Data4[2] = (v3 >> 8) & 0xFF;
+ t_guid.Data4[3] = v3 & 0xFF;
+ } break;
+ case ATTRID_GUID4: {
+ long v4 = reinterpret_cast<BinAttr<VALTYPE_LONG>*>(&(*i))->a;
+ t_guid.Data4[4] = (v4 >> 24);
+ t_guid.Data4[5] = (v4 >> 16) & 0xFF;
+ t_guid.Data4[6] = (v4 >> 8) & 0xFF;
+ t_guid.Data4[7] = v4 & 0xFF;
+ } break;
case ATTRID_FILESTATUS: *p_statusFound = true; break;
case ATTRID_REGNOWNER + ATTRID_COLLECTION:
*p_oldRegFound = true; break;
@@ -166,12 +184,6 @@
++i;
}
-
- // a1, a2, a3, a4 should be equal & have the 0 or 1 value
- ASSERT( (a1 == 0 || a1 == 1) && a1 == a2 && a1 == a3 && a1 == a4);
-
- *p_guidFound = a1 && a2 && a3 && a4;
- return *p_guidFound;
}
// this method will create Guid attributes for mga objects
@@ -1059,6 +1071,46 @@
cifs_eof = file_buffer.getEnd();
}
+// KMS: due to a bug in MgaFolder::CopyFCOs (ObjTreeCopyFoldersToo) fixed in r2297, some mga files may have duplicate GUIDs
+static void SetNewGuid(CCoreBinFile* p_bf, BinObject& o)
+{
+ CComVariant l1, l2, l3, l4;
+ l4.vt = l3.vt = l2.vt = l1.vt = VT_I4;
+ getMeAGuid( &l1.lVal, &l2.lVal, &l3.lVal, &l4.lVal);
+
+ binattrs_iterator i = o.binattrs.begin();
+ binattrs_iterator e = o.binattrs.end();
+ while( i != e)
+ {
+ switch (i->attrid)
+ {
+ case ATTRID_GUID1:
+ i->Set(p_bf, l1);
+ break;
+ case ATTRID_GUID2:
+ i->Set(p_bf, l2);
+ break;
+ case ATTRID_GUID3:
+ i->Set(p_bf, l3);
+ break;
+ case ATTRID_GUID4:
+ i->Set(p_bf, l4);
+ break;
+ default:
+ break;
+ }
+ i++;
+ }
+}
+
+struct GUID_hash {
+ size_t operator()(const GUID& guid) const
+ {
+ int* iGuid = (int*)(void*)&guid;
+ return iGuid[0] ^ iGuid[1] ^ iGuid[2] ^ iGuid[3];
+ }
+};
+
void CCoreBinFile::LoadProject()
{
InitMaxObjIDs();
@@ -1069,6 +1121,8 @@
cifs = file_buffer.getBegin();
cifs_eof = file_buffer.getEnd();
+ std::unordered_map<GUID, bool, GUID_hash> guids;
+
bindata guid;
read(guid);
@@ -1115,13 +1169,21 @@
// if the object read is folder or fco and it does NOT have guid attributes (old version mga file)
if( metaid >= DTID_MODEL && metaid <= DTID_FOLDER) // 101 .. 106
{
- bool stat_found( false), guid_found( false);
+ bool stat_found( false);
- opened_object->second.HasGuidAndStatAttributes( &guid_found, &stat_found, &oldReg_found);
+ GUID zero_guid = {0};
+ GUID guid = {0};
+ opened_object->second.HasGuidAndStatAttributes(guid, &stat_found, &oldReg_found);
- if( !guid_found) // we will create guid attributes for it
+ if(guid == zero_guid) // we will create guid attributes for it
opened_object->second.CreateGuidAttributes( this);
+ std::pair<std::hash_map<GUID, bool>::iterator, bool> guid_insert = guids.emplace(std::make_pair(guid, true));
+ if (guid_insert.second == true)
+ {
+ SetNewGuid(this, opened_object->second);
+ }
+
if( !stat_found && ( metaid == DTID_MODEL || metaid == DTID_FOLDER)) // we will create status attribute for M and F
opened_object->second.CreateStatusAttribute( this);
}
Modified: trunk/GME/Core/CoreBinFile.h
==============================================================================
--- trunk/GME/Core/CoreBinFile.h Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/GME/Core/CoreBinFile.h Wed Aug 21 14:40:13 2013 (r2299)
@@ -146,7 +146,7 @@
binattrs_type binattrs;
bool deleted;
- bool HasGuidAndStatAttributes( bool* p_guidFound, bool* p_statusFound, bool* p_oldRegFound);
+ void HasGuidAndStatAttributes(GUID& guid, bool* p_statusFound, bool* p_oldRegFound);
void CreateGuidAttributes( CCoreBinFile* p_bf);
void CreateStatusAttribute( CCoreBinFile* p_bf);
void UpgradeRegistryIfNecessary(CCoreBinFile* binFile);
Modified: trunk/GME/Mga/MgaFCO.cpp
==============================================================================
--- trunk/GME/Mga/MgaFCO.cpp Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/GME/Mga/MgaFCO.cpp Wed Aug 21 14:40:13 2013 (r2299)
@@ -1234,16 +1234,16 @@
GUID t_guid;
t_guid.Data1 = v1;
t_guid.Data2 = (v2 >> 16);
- t_guid.Data3 = (v2 << 16) >> 16;
+ t_guid.Data3 = v2 & 0xFFFF;
t_guid.Data4[0] = (v3 >> 24);
- t_guid.Data4[1] = (v3 << 8) >> 24;
- t_guid.Data4[2] = (v3 << 16) >> 24;
- t_guid.Data4[3] = (v3 << 24) >> 24;
+ t_guid.Data4[1] = (v3 >> 16) & 0xFF;
+ t_guid.Data4[2] = (v3 >> 8) & 0xFF;
+ t_guid.Data4[3] = v3 & 0xFF;
t_guid.Data4[4] = (v4 >> 24);
- t_guid.Data4[5] = (v4 << 8) >> 24;
- t_guid.Data4[6] = (v4 << 16) >> 24;
- t_guid.Data4[7] = (v4 << 24) >> 24;
+ t_guid.Data4[5] = (v4 >> 16) & 0xFF;
+ t_guid.Data4[6] = (v4 >> 8) & 0xFF;
+ t_guid.Data4[7] = v4 & 0xFF;
char buff[39];
sprintf( buff, "{%08lx-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
Modified: trunk/GME/Mga/MgaLibOps.cpp
==============================================================================
--- trunk/GME/Mga/MgaLibOps.cpp Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/GME/Mga/MgaLibOps.cpp Wed Aug 21 14:40:13 2013 (r2299)
@@ -1377,17 +1377,17 @@
GUID t_guid;
t_guid.Data1 = v1;
- t_guid.Data2 = (v2 >> 16);
- t_guid.Data3 = (v2 << 16) >> 16;
+ t_guid.Data2 = v2 >> 16;
+ t_guid.Data3 = v2 & 0xFFFF;
t_guid.Data4[0] = (v3 >> 24);
- t_guid.Data4[1] = (v3 << 8) >> 24;
- t_guid.Data4[2] = (v3 << 16) >> 24;
- t_guid.Data4[3] = (v3 << 24) >> 24;
+ t_guid.Data4[1] = (v3 >> 16) & 0xFF;
+ t_guid.Data4[2] = (v3 >> 8) & 0xFF;
+ t_guid.Data4[3] = v3 & 0xFF;
t_guid.Data4[4] = (v4 >> 24);
- t_guid.Data4[5] = (v4 << 8) >> 24;
- t_guid.Data4[6] = (v4 << 16) >> 24;
- t_guid.Data4[7] = (v4 << 24) >> 24;
+ t_guid.Data4[5] = (v4 >> 16) & 0xFF;
+ t_guid.Data4[6] = (v4 >> 8) & 0xFF;
+ t_guid.Data4[7] = v4 & 0xFF;
char buff[39];
sprintf( buff, "{%08lX-%04X-%04x-%02X%02X-%02X%02X%02X%02X%02X%02X}",
Modified: trunk/GME/Mga/MgaLibRefr.h
==============================================================================
--- trunk/GME/Mga/MgaLibRefr.h Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/GME/Mga/MgaLibRefr.h Wed Aug 21 14:40:13 2013 (r2299)
@@ -85,17 +85,17 @@
{
const BinGuid &m_guid = *this;
p_guid.Data1 = m_guid.v1;
- p_guid.Data2 = (m_guid.v2 >> 16);
- p_guid.Data3 = (m_guid.v2 << 16) >> 16;
+ p_guid.Data2 = m_guid.v2 >> 16;
+ p_guid.Data3 = m_guid.v2 & 0xFFFF;
p_guid.Data4[0] = (m_guid.v3 >> 24);
- p_guid.Data4[1] = (m_guid.v3 << 8) >> 24;
- p_guid.Data4[2] = (m_guid.v3 << 16) >> 24;
- p_guid.Data4[3] = (m_guid.v3 << 24) >> 24;
+ p_guid.Data4[1] = (m_guid.v3 >> 16) & 0xFF;
+ p_guid.Data4[2] = (m_guid.v3 >> 8) & 0xFF;
+ p_guid.Data4[3] = m_guid.v3 & 0xFF;
p_guid.Data4[4] = (m_guid.v4 >> 24);
- p_guid.Data4[5] = (m_guid.v4 << 8) >> 24;
- p_guid.Data4[6] = (m_guid.v4 << 16) >> 24;
- p_guid.Data4[7] = (m_guid.v4 << 24) >> 24;
+ p_guid.Data4[5] = (m_guid.v4 >> 16) & 0xFF;
+ p_guid.Data4[6] = (m_guid.v4 >> 8) & 0xFF;
+ p_guid.Data4[7] = m_guid.v4 & 0xFF;
}
};
Added: trunk/Tests/GPyUnit/SFDemo_dup_guids.mga
==============================================================================
Binary files /dev/null 00:00:00 1970 (empty, because file is newly added) and trunk/Tests/GPyUnit/SFDemo_dup_guids.mga Wed Aug 21 14:40:13 2013 (r2299) differ
Modified: trunk/Tests/GPyUnit/__init__.py
==============================================================================
--- trunk/Tests/GPyUnit/__init__.py Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/Tests/GPyUnit/__init__.py Wed Aug 21 14:40:13 2013 (r2299)
@@ -26,6 +26,7 @@
'test_gmeoleapp',
'test_parser',
'test_copy',
+ 'test_mga_open',
'test_registry',
'test_instances',
'GME_297.suite',
Modified: trunk/Tests/GPyUnit/test_copy.py
==============================================================================
--- trunk/Tests/GPyUnit/test_copy.py Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/Tests/GPyUnit/test_copy.py Wed Aug 21 14:40:13 2013 (r2299)
@@ -7,7 +7,7 @@
import os.path
return os.path.join(os.path.dirname(os.path.abspath(__file__)), file)
-class TestParser(unittest.TestCase):
+class TestCopy(unittest.TestCase):
def test_CopyFCODupGUID(self):
mga = GPyUnit.util.parse_xme(self.connstr, _adjacent_file(r'..\..\Paradigms\SF\SFDemo.xme'))
mga.Save()
@@ -29,7 +29,7 @@
def connstr(self):
return "MGA=" + _adjacent_file("copytest.mga")
-GPyUnit.util.MUGenerator(globals(), TestParser)
+GPyUnit.util.MUGenerator(globals(), TestCopy)
if __name__ == "__main__":
unittest.main()
Added: trunk/Tests/GPyUnit/test_mga_open.py
==============================================================================
--- /dev/null 00:00:00 1970 (empty, because file is newly added)
+++ trunk/Tests/GPyUnit/test_mga_open.py Wed Aug 21 14:40:13 2013 (r2299)
@@ -0,0 +1,45 @@
+from __future__ import with_statement
+
+import sys
+import os.path
+import unittest
+import GPyUnit.util
+import GPyUnit.util.gme
+from GPyUnit.util import DispatchEx
+
+def _adjacent_file(file):
+ import os.path
+ return os.path.join(os.path.dirname(os.path.abspath(__file__)), file)
+
+class TestMgaOpen(unittest.TestCase):
+ def __init__(self, name, **kwds):
+ super(TestMgaOpen, self).__init__(name, **kwds)
+ self.output_file = "test_mga_open-output.mga"
+ self.project = None
+
+ def tearDown(self):
+ if not self.project is None:
+ self.project.Close(True)
+
+ def test(self):
+ from GPyUnit import util
+ util.register_xmp('SF')
+ with util.disable_early_binding():
+ self.project = DispatchEx("Mga.MgaProject")
+ self.project.Open("MGA=" + _adjacent_file('SFDemo_dup_guids.mga'))
+
+ self.project.BeginTransactionInNewTerr(0)
+ mga = self.project
+ self.assertEqual(mga.ObjectByPath('/@Folder1').GetGuidDisp(), '{8ce2ca06-2729-4e4c-955f-fc88194782cc}')
+ self.assertEqual(mga.ObjectByPath('/@Folder1/@System').GetGuidDisp(), '{a57ca6b2-d95e-485c-a768-98c16fd30588}')
+ self.assertEqual(mga.ObjectByPath('/@Folder1/@System/@DBSetup1').GetGuidDisp(), '{009ef956-cfe9-4b2a-9bed-3d486dfc71ce}')
+ self.assertNotEqual(mga.ObjectByPath('/@Folder1').GetGuidDisp(), mga.ObjectByPath('/@Folder2').GetGuidDisp())
+ self.assertNotEqual(mga.ObjectByPath('/@Folder1/@System').GetGuidDisp(), mga.ObjectByPath('/@Folder2/@System').GetGuidDisp())
+ self.assertNotEqual(mga.ObjectByPath('/@Folder1/@System/@DBSetup1').GetGuidDisp(), mga.ObjectByPath('/@Folder2/@System/@DBSetup1').GetGuidDisp())
+ self.project.AbortTransaction()
+ self.project.Save("MGA=" + _adjacent_file(self.output_file), False)
+ self.project.Close(True)
+
+
+if __name__ == "__main__":
+ unittest.main()
Modified: trunk/Tests/GPyUnit/test_parser.py
==============================================================================
--- trunk/Tests/GPyUnit/test_parser.py Wed Aug 21 12:40:02 2013 (r2298)
+++ trunk/Tests/GPyUnit/test_parser.py Wed Aug 21 14:40:13 2013 (r2299)
@@ -29,8 +29,10 @@
try:
mga.BeginTransactionInNewTerr()
try:
+ self.assertEqual(mga.ObjectByPath('/@Folder1').GetGuidDisp(), '{8ce2ca06-2729-4e4c-955f-fc88194782cc}')
self.assertEqual(mga.ObjectByPath('/@Folder1/@System').GetGuidDisp(), '{a57ca6b2-d95e-485c-a768-98c16fd30588}')
self.assertEqual(mga.ObjectByPath('/@Folder1/@System/@DBSetup1').GetGuidDisp(), '{009ef956-cfe9-4b2a-9bed-3d486dfc71ce}')
+ self.assertNotEqual(mga.ObjectByPath('/@Folder1').GetGuidDisp(), mga.ObjectByPath('/@Folder2').GetGuidDisp())
self.assertNotEqual(mga.ObjectByPath('/@Folder1/@System').GetGuidDisp(), mga.ObjectByPath('/@Folder2/@System').GetGuidDisp())
self.assertNotEqual(mga.ObjectByPath('/@Folder1/@System/@DBSetup1').GetGuidDisp(), mga.ObjectByPath('/@Folder2/@System/@DBSetup1').GetGuidDisp())
finally:
More information about the gme-commit
mailing list