diff --git a/pykd/dbgext.cpp b/pykd/dbgext.cpp index 5f378e8..9a1385a 100644 --- a/pykd/dbgext.cpp +++ b/pykd/dbgext.cpp @@ -153,6 +153,8 @@ BOOST_PYTHON_MODULE( pykd ) "Retrieves the location type of a data symbol: LocIsXxx" ) .def( "offset", &pyDia::Symbol::getOffset, "Retrieves the offset of the symbol location" ) + .def( "count", &pyDia::Symbol::getCount, + "Retrieves the number of items in a list or array" ) .def( "value", &pyDia::Symbol::getValue, "Retrieves the value of a constant") .def( "isBasic", &pyDia::Symbol::isBasicType, diff --git a/pykd/diaprint.cpp b/pykd/diaprint.cpp index a815810..6c21ea8 100644 --- a/pykd/diaprint.cpp +++ b/pykd/diaprint.cpp @@ -193,12 +193,11 @@ std::string Symbol::printImpl( sstream << ", "; sstream << symTagName[dwValue].second; - if (SymTagUDT == symTagName[dwValue].first) - { - hres = _symbol->get_udtKind(&dwValue); - if ((S_OK == hres) && (dwValue < cntUdtKindName)) - sstream << ": " << udtKindName[dwValue].second; - } + if ((S_OK == _symbol->get_udtKind(&dwValue)) && (dwValue < cntUdtKindName)) + sstream << ": " << udtKindName[dwValue].second; + + if (S_OK == _symbol->get_count(&dwValue)) + sstream << ", Count: " << std::dec << dwValue; bFuncDebugRange = (SymTagFuncDebugStart == symTagName[dwValue].first) || diff --git a/pykd/diawrapper.cpp b/pykd/diawrapper.cpp index 101c3d9..1e7c780 100644 --- a/pykd/diawrapper.cpp +++ b/pykd/diawrapper.cpp @@ -142,6 +142,13 @@ LONG Symbol::getOffset() return callSymbol(get_offset); } +//////////////////////////////////////////////////////////////////////////////// + +ULONG Symbol::getCount() +{ + return callSymbol(get_count); +} + //////////////////////////////////////////////////////////////////////////////// void Symbol::getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue) { diff --git a/pykd/diawrapper.h b/pykd/diawrapper.h index 6a3d414..d4f2375 100644 --- a/pykd/diawrapper.h +++ b/pykd/diawrapper.h @@ -99,6 +99,8 @@ public: LONG getOffset(); + ULONG getCount(); + static void getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue); python::object getValue(); diff --git a/test/scripts/diatest.py b/test/scripts/diatest.py index 1b549d2..ce3a16d 100644 --- a/test/scripts/diatest.py +++ b/test/scripts/diatest.py @@ -7,118 +7,196 @@ import target import pykd class DiaTest( unittest.TestCase ): - def testFind(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertNotEqual(0, len(gScope)) - symFunction = gScope.find("FuncWithName0") - self.assertTrue(1 == len( symFunction )) - symFunction = gScope.findEx(pykd.SymTagNull, - "FuNc*Name?", - pykd.nsCaseInRegularExpression) - self.assertTrue(len(symFunction) > 1) + def testFind(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertNotEqual(0, len(gScope)) + symFunction = gScope.find("FuncWithName0") + self.assertTrue(1 == len( symFunction )) + symFunction = gScope.findEx(pykd.SymTagNull, + "FuNc*Name?", + pykd.nsCaseInRegularExpression) + self.assertTrue(len(symFunction) > 1) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testSize(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual(1, gScope["g_ucharValue"].type().size()) - self.assertEqual(2, gScope["g_ushortValue"].type().size()) - self.assertEqual(4, gScope["g_ulongValue"].type().size()) - self.assertEqual(8, gScope["g_ulonglongValue"].type().size()) + def testSize(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual(1, gScope["g_ucharValue"].type().size()) + self.assertEqual(2, gScope["g_ushortValue"].type().size()) + self.assertEqual(4, gScope["g_ulongValue"].type().size()) + self.assertEqual(8, gScope["g_ulonglongValue"].type().size()) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testValue(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual(0x5555, gScope["g_constNumValue"].value()) - self.assertEqual(True, gScope["g_constBoolValue"].value()) + def testValue(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual(0x5555, gScope["g_constNumValue"].value()) + self.assertEqual(True, gScope["g_constBoolValue"].value()) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testName(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual("g_constNumValue", gScope["g_constNumValue"].name()) - self.assertEqual("FuncWithName0", gScope["FuncWithName0"].name()) + def testName(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual( "g_constNumValue", + gScope["g_constNumValue"].name() ) + self.assertEqual( "FuncWithName0", + gScope["FuncWithName0"].name() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testRva(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - _rva = gScope["FuncWithName0"].rva() - self.assertNotEqual(0, _rva) - self.assertTrue( _rva < (target.module.end() - target.module.begin()) ) - _rva = gScope["g_string"].rva() - self.assertNotEqual(0, _rva) - self.assertTrue( _rva < (target.module.end() - target.module.begin()) ) + def testRva(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + _rva = gScope["FuncWithName0"].rva() + self.assertNotEqual(0, _rva) + modLen = target.module.end() - target.module.begin() + self.assertTrue( _rva < modLen ) + _rva = gScope["g_string"].rva() + self.assertNotEqual(0, _rva) + self.assertTrue( _rva < modLen ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testSymTag(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual(pykd.SymTagFunction, gScope["FuncWithName0"].symTag()) - self.assertEqual(pykd.SymTagData, gScope["g_string"].symTag()) + def testSymTag(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual( pykd.SymTagFunction, + gScope["FuncWithName0"].symTag() ) + self.assertEqual( pykd.SymTagData, + gScope["g_string"].symTag() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testLocType(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual(pykd.LocIsConstant, gScope["g_constNumValue"].locType()) - self.assertEqual(pykd.LocIsStatic, gScope["FuncWithName1"].locType()) + def testLocType(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual( pykd.LocIsConstant, + gScope["g_constNumValue"].locType() ) + self.assertEqual( pykd.LocIsStatic, + gScope["FuncWithName1"].locType() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testBasicType(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertFalse(gScope["g_string"].type().isBasic()) - self.assertEqual(pykd.btBool, gScope["g_constBoolValue"].type().baseType()) - self.assertEqual(pykd.btULong, gScope["g_ulongValue"].type().baseType()) + def testBasicType(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertFalse(gScope["g_string"].type().isBasic()) + self.assertEqual( pykd.btBool, + gScope["g_constBoolValue"].type().baseType() ) + self.assertEqual( pykd.btULong, + gScope["g_ulongValue"].type().baseType() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testBits(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - structWithBits = gScope["structWithBits"] - bitField = structWithBits["m_bit0_4"] - self.assertEqual(pykd.LocIsBitField, bitField.locType()) - self.assertEqual(0, bitField.bitPos()) - self.assertEqual(5, bitField.size()) - bitField = structWithBits["m_bit5"] - self.assertEqual(pykd.LocIsBitField, bitField.locType()) - self.assertEqual(5, bitField.bitPos()) - self.assertEqual(1, bitField.size()) - bitField = structWithBits["m_bit6_7"] - self.assertEqual(pykd.LocIsBitField, bitField.locType()) - self.assertEqual(6, bitField.bitPos()) - self.assertEqual(2, bitField.size()) + def testBits(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + structWithBits = gScope["structWithBits"] + bitField = structWithBits["m_bit0_4"] + self.assertEqual(pykd.LocIsBitField, bitField.locType()) + self.assertEqual(0, bitField.bitPos()) + self.assertEqual(5, bitField.size()) + bitField = structWithBits["m_bit5"] + self.assertEqual(pykd.LocIsBitField, bitField.locType()) + self.assertEqual(5, bitField.bitPos()) + self.assertEqual(1, bitField.size()) + bitField = structWithBits["m_bit6_7"] + self.assertEqual(pykd.LocIsBitField, bitField.locType()) + self.assertEqual(6, bitField.bitPos()) + self.assertEqual(2, bitField.size()) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testIndexId(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertNotEqual( gScope["classChild"].indexId(), - gScope["classBase"].indexId() ) - self.assertNotEqual( gScope["FuncWithName0"].indexId(), - gScope["FuncWithName1"].indexId() ) + def testIndexId(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertNotEqual( gScope["classChild"].indexId(), + gScope["classBase"].indexId() ) + self.assertNotEqual( gScope["FuncWithName0"].indexId(), + gScope["FuncWithName1"].indexId() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testUdtKind(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertEqual(pykd.UdtStruct, gScope["structWithBits"].udtKind()) - self.assertEqual(pykd.UdtUnion, gScope["unionTest"].udtKind()) - self.assertEqual(pykd.UdtClass, gScope["classBase"].udtKind()) + def testUdtKind(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + self.assertEqual(pykd.UdtStruct, gScope["structTest"].udtKind()) + self.assertEqual(pykd.UdtUnion, gScope["unionTest"].udtKind()) + self.assertEqual(pykd.UdtClass, gScope["classBase"].udtKind()) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testOffset(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - structTest = gScope["structTest"] - self.assertEqual( 0, structTest["m_field0"].offset() ) - self.assertTrue( structTest["m_field0"].offset() < - structTest["m_field1"].offset() ) - self.assertTrue( structTest["m_field1"].offset() < - structTest["m_field2"].offset() ) - self.assertTrue( structTest["m_field2"].offset() < - structTest["m_field3"].offset() ) - self.assertTrue(structTest["m_field3"].offset() < structTest.size()) + def testOffset(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + structTest = gScope["structTest"] + self.assertEqual( 0, structTest["m_field0"].offset() ) + self.assertTrue( structTest["m_field0"].offset() < + structTest["m_field1"].offset() ) + self.assertTrue( structTest["m_field1"].offset() < + structTest["m_field2"].offset() ) + self.assertTrue( structTest["m_field2"].offset() < + structTest["m_field3"].offset() ) + self.assertTrue( structTest["m_field3"].offset() < + structTest.size() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testMachine(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - self.assertTrue( (gScope.machineType() == pykd.IMAGE_FILE_MACHINE_I386) or - (gScope.machineType() == pykd.IMAGE_FILE_MACHINE_AMD64) ) + def testMachine(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + machine = gScope.machineType() + self.assertTrue( (machine == pykd.IMAGE_FILE_MACHINE_I386) or + (machine == pykd.IMAGE_FILE_MACHINE_AMD64) ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - def testFindByRva(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - func = gScope["FuncWithName0"] + def testFindByRva(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + func = gScope["FuncWithName0"] + tplSymOffset = gScope.findByRva(func.rva(), pykd.SymTagFunction) + self.assertEqual(tplSymOffset[0].indexId(), func.indexId()) + self.assertEqual(tplSymOffset[1], 0) + tplSymOffset = gScope.findByRva(func.rva()+2, pykd.SymTagFunction) + self.assertEqual(tplSymOffset[0].indexId(), func.indexId()) + self.assertEqual(tplSymOffset[1], 2) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - tplSymOffset = gScope.findByRva(func.rva(), pykd.SymTagFunction) - self.assertEqual(tplSymOffset[0].indexId(), func.indexId()) - self.assertEqual(tplSymOffset[1], 0) + def testSymbolById(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + func = gScope["FuncWithName0"] + self.assertEqual( gScope.symbolById(func.indexId()).indexId(), + func.indexId()) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) - tplSymOffset = gScope.findByRva(func.rva() + 2, pykd.SymTagFunction) - self.assertEqual(tplSymOffset[0].indexId(), func.indexId()) - self.assertEqual(tplSymOffset[1], 2) - - def testSymbolById(self): - gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) - func = gScope["FuncWithName0"] - self.assertEqual( gScope.symbolById(func.indexId()).indexId(), - func.indexId()) + def testCount(self): + try: + gScope = pykd.diaLoadPdb( str(target.module.pdb()) ) + var = gScope["FuncWithName1"]["_unionTest"] + self.assertEqual( 2, var.type().count() ) + except pykd.DiaException as diaExcept: + print diaExcept + self.assertTrue(False) diff --git a/test/targetapp/targetapp.cpp b/test/targetapp/targetapp.cpp index 0447dc1..bede5f3 100644 --- a/test/targetapp/targetapp.cpp +++ b/test/targetapp/targetapp.cpp @@ -69,8 +69,8 @@ void FuncWithName0() void FuncWithName1(int a) { - unionTest _unionTest; - _unionTest.m_value = 0; + unionTest _unionTest[2]; + _unionTest[1].m_value = 0; structTest _structTest; _structTest.m_field1 = a; struct2 _struct2;