mirror of
https://github.com/ivellioscolin/pykd.git
synced 2025-04-20 03:23:23 +08:00
[0.1.x] added : containingRecord method of the module class
git-svn-id: https://pykd.svn.codeplex.com/svn@72131 9b283d60-5439-405e-af05-b73fd8c4d996
This commit is contained in:
parent
1609c0cac6
commit
3058af91a7
@ -388,46 +388,49 @@ BOOST_PYTHON_MODULE( pykd )
|
|||||||
.def("__len__", &TypedVar::getElementCount )
|
.def("__len__", &TypedVar::getElementCount )
|
||||||
.def("__getitem__", &TypedVar::getElementByIndex );
|
.def("__getitem__", &TypedVar::getElementByIndex );
|
||||||
|
|
||||||
python::class_<pykd::Module>("module", "Class representing executable module", python::no_init )
|
python::class_<Module>("module", "Class representing executable module", python::no_init )
|
||||||
.def("begin", &pykd::Module::getBase,
|
.def("begin", &Module::getBase,
|
||||||
"Return start address of the module" )
|
"Return start address of the module" )
|
||||||
.def("end", &pykd::Module::getEnd,
|
.def("end", &Module::getEnd,
|
||||||
"Return end address of the module" )
|
"Return end address of the module" )
|
||||||
.def("size", &pykd::Module::getSize,
|
.def("size", &Module::getSize,
|
||||||
"Return size of the module" )
|
"Return size of the module" )
|
||||||
.def("name", &pykd::Module::getName,
|
.def("name", &Module::getName,
|
||||||
"Return name of the module" )
|
"Return name of the module" )
|
||||||
.def("image", &pykd::Module::getImageName,
|
.def("image", &Module::getImageName,
|
||||||
"Return name of the image of the module" )
|
"Return name of the image of the module" )
|
||||||
.def("pdb", &pykd::Module::getPdbName,
|
.def("pdb", &Module::getPdbName,
|
||||||
"Return the full path to the module's pdb file ( symbol information )" )
|
"Return the full path to the module's pdb file ( symbol information )" )
|
||||||
.def("reload", &pykd::Module::reloadSymbols,
|
.def("reload", &Module::reloadSymbols,
|
||||||
"(Re)load symbols for the module" )
|
"(Re)load symbols for the module" )
|
||||||
.def("offset", &pykd::Module::getSymbol,
|
.def("offset", &Module::getSymbol,
|
||||||
"Return offset of the symbol" )
|
"Return offset of the symbol" )
|
||||||
.def("rva", &pykd::Module::getSymbolRva,
|
.def("rva", &Module::getSymbolRva,
|
||||||
"Return rva of the symbol" )
|
"Return rva of the symbol" )
|
||||||
.def("type", &pykd::Module::getTypeByName,
|
.def("type", &Module::getTypeByName,
|
||||||
"Return typeInfo class by type name" )
|
"Return typeInfo class by type name" )
|
||||||
.def("typedVar", &pykd::Module::getTypedVarByAddr,
|
.def("typedVar", &Module::getTypedVarByAddr,
|
||||||
"Return a typedVar class instance" )
|
"Return a typedVar class instance" )
|
||||||
.def("typedVar",&pykd::Module::getTypedVarByName,
|
.def("typedVar",&Module::getTypedVarByName,
|
||||||
"Return a typedVar class instance" )
|
"Return a typedVar class instance" )
|
||||||
.def("typedVar",&pykd::Module::getTypedVarByType,
|
.def("typedVar",&Module::getTypedVarByType,
|
||||||
"Return a typedVar class instance" )
|
"Return a typedVar class instance" )
|
||||||
.def("typedVar",&pykd::Module::getTypedVarByTypeName,
|
.def("typedVar",&Module::getTypedVarByTypeName,
|
||||||
"Return a typedVar class instance" )
|
"Return a typedVar class instance" )
|
||||||
.def("__getattr__", &pykd::Module::getSymbol,
|
.def("containingRecord", &Module::contaningRecord,
|
||||||
|
"Return instance of the typedVar class. It's value are loaded from the target memory."
|
||||||
|
"The start address is calculated by the same method as the standard macro CONTAINING_RECORD does" )
|
||||||
|
.def("__getattr__", &Module::getSymbol,
|
||||||
"Return address of the symbol" );
|
"Return address of the symbol" );
|
||||||
|
|
||||||
python::class_<DbgOut>( "dout", "dout", python::no_init )
|
python::class_<DbgOut>( "dout", "dout", python::no_init )
|
||||||
.def( "write", &pykd::DbgOut::write );
|
.def( "write", &DbgOut::write );
|
||||||
|
|
||||||
python::class_<DbgIn>( "din", "din", python::no_init )
|
python::class_<DbgIn>( "din", "din", python::no_init )
|
||||||
.def( "readline", &pykd::DbgIn::readline );
|
.def( "readline", &DbgIn::readline );
|
||||||
|
|
||||||
python::class_<DbgExtension, pykd::DbgExtensionPtr>("ext", python::no_init )
|
python::class_<DbgExtension, DbgExtensionPtr>("ext", python::no_init )
|
||||||
.def( "call", &pykd::DbgExtension::call,
|
.def( "call", &DbgExtension::call,
|
||||||
"Call debug extension command end return it's result as a string" );
|
"Call debug extension command end return it's result as a string" );
|
||||||
|
|
||||||
python::class_<EventHandlerWrap, boost::noncopyable>(
|
python::class_<EventHandlerWrap, boost::noncopyable>(
|
||||||
|
@ -219,5 +219,41 @@ ULONG Module::getRvaByName(const std::string &symName)
|
|||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
TypedVarPtr Module::contaningRecord( ULONG64 address, const std::string &typeName, const std::string &fieldName )
|
||||||
|
{
|
||||||
|
address = addr64(address);
|
||||||
|
|
||||||
|
TypeInfoPtr typeInfo = getTypeByName( typeName );
|
||||||
|
|
||||||
|
TypeInfoPtr fieldTypeInfo = typeInfo->getField( fieldName );
|
||||||
|
|
||||||
|
return TypedVar::getTypedVar( m_client, typeInfo, address - fieldTypeInfo->getOffset() );
|
||||||
|
|
||||||
|
|
||||||
|
//HRESULT hres;
|
||||||
|
//ULONG64 moduleBase;
|
||||||
|
|
||||||
|
//hres = dbgExt->symbols->GetModuleByModuleName( moduleName.c_str(), 0, NULL, &moduleBase );
|
||||||
|
//if ( FAILED( hres ) )
|
||||||
|
// throw TypeException();
|
||||||
|
|
||||||
|
//ULONG typeId;
|
||||||
|
//hres = dbgExt->symbols->GetTypeId( moduleBase, typeName.c_str(), &typeId );
|
||||||
|
//if ( FAILED( hres ) )
|
||||||
|
// throw TypeException();
|
||||||
|
|
||||||
|
//ULONG fieldTypeId;
|
||||||
|
//ULONG fieldOffset;
|
||||||
|
//hres = dbgExt->symbols3->GetFieldTypeAndOffset( moduleBase, typeId, fieldName.c_str(), &fieldTypeId, &fieldOffset );
|
||||||
|
//if ( FAILED( hres ) )
|
||||||
|
// throw TypeException();
|
||||||
|
//
|
||||||
|
//TypedVar var( moduleName, typeName, address - fieldOffset );
|
||||||
|
//
|
||||||
|
//return boost::python::object( var );
|
||||||
|
}
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
}; // end of namespace pykd
|
}; // end of namespace pykd
|
||||||
|
|
||||||
|
@ -68,6 +68,8 @@ public:
|
|||||||
|
|
||||||
TypedVarPtr getTypedVarByName( const std::string &symName );
|
TypedVarPtr getTypedVarByName( const std::string &symName );
|
||||||
|
|
||||||
|
TypedVarPtr contaningRecord( ULONG64 addr, const std::string &typeName, const std::string &fieldName );
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
ULONG getRvaByName(const std::string &symName);
|
ULONG getRvaByName(const std::string &symName);
|
||||||
|
@ -17,7 +17,6 @@ class BaseTest( unittest.TestCase ):
|
|||||||
self.assertTrue( hasattr(pykd, 'addr64') )
|
self.assertTrue( hasattr(pykd, 'addr64') )
|
||||||
self.assertTrue( hasattr(pykd, 'breakin') )
|
self.assertTrue( hasattr(pykd, 'breakin') )
|
||||||
self.assertTrue( hasattr(pykd, 'compareMemory') )
|
self.assertTrue( hasattr(pykd, 'compareMemory') )
|
||||||
self.assertTrue( hasattr(pykd, 'containingRecord') )
|
|
||||||
self.assertTrue( hasattr(pykd, 'dbgCommand') )
|
self.assertTrue( hasattr(pykd, 'dbgCommand') )
|
||||||
self.assertTrue( hasattr(pykd, 'dprint') )
|
self.assertTrue( hasattr(pykd, 'dprint') )
|
||||||
self.assertTrue( hasattr(pykd, 'dprintln') )
|
self.assertTrue( hasattr(pykd, 'dprintln') )
|
||||||
@ -104,6 +103,7 @@ class BaseTest( unittest.TestCase ):
|
|||||||
|
|
||||||
def testOldRemovedApi( self ):
|
def testOldRemovedApi( self ):
|
||||||
""" Branch test: old API 0.0.x what should be removed """
|
""" Branch test: old API 0.0.x what should be removed """
|
||||||
|
self.assertFalse( hasattr(pykd, 'containingRecord') )
|
||||||
self.assertFalse( hasattr(pykd, 'cpuReg') )
|
self.assertFalse( hasattr(pykd, 'cpuReg') )
|
||||||
self.assertFalse( hasattr(pykd, 'dbgModuleClass') )
|
self.assertFalse( hasattr(pykd, 'dbgModuleClass') )
|
||||||
self.assertFalse( hasattr(pykd, 'debugEvent') )
|
self.assertFalse( hasattr(pykd, 'debugEvent') )
|
||||||
|
@ -59,9 +59,7 @@ if __name__ == "__main__":
|
|||||||
|
|
||||||
suite = getTestSuite()
|
suite = getTestSuite()
|
||||||
#suite = getTestSuite( "typeinfo.TypeInfoTest.testCreateBySymbol" )
|
#suite = getTestSuite( "typeinfo.TypeInfoTest.testCreateBySymbol" )
|
||||||
#suite = getTestSuite( "intbase.IntBaseTest.testLongConvert" )
|
|
||||||
#suite = getTestSuite( "typedvar.TypedVarTest.testStruct" )
|
|
||||||
|
|
||||||
unittest.TextTestRunner(stream=sys.stdout, verbosity=2).run( suite )
|
unittest.TextTestRunner(stream=sys.stdout, verbosity=2).run( suite )
|
||||||
|
|
||||||
a = raw_input("\npress return\n")
|
#a = raw_input("\npress return\n")
|
||||||
|
@ -62,4 +62,9 @@ class TypedVarTest( unittest.TestCase ):
|
|||||||
self.assertEqual( -100000, target.module.typedVar( "longArray" )[3])
|
self.assertEqual( -100000, target.module.typedVar( "longArray" )[3])
|
||||||
self.assertEqual( -10000000000, target.module.typedVar( "longlongArray" )[4])
|
self.assertEqual( -10000000000, target.module.typedVar( "longlongArray" )[4])
|
||||||
self.assertEqual( target.module.g_structTest, target.module.typedVar( "g_structTestPtr" ) )
|
self.assertEqual( target.module.g_structTest, target.module.typedVar( "g_structTestPtr" ) )
|
||||||
|
|
||||||
|
def testContainingRecord(self):
|
||||||
|
off1 = target.module.type( "structTest" ).m_field2.offset()
|
||||||
|
off2 = target.module.offset( "g_structTest" )
|
||||||
|
tv = target.module.containingRecord( off2 + off1, "structTest", "m_field2" )
|
||||||
|
self.assertEqual( True, tv.m_field2 )
|
||||||
|
@ -19,6 +19,7 @@ class TypeInfoTest( unittest.TestCase ):
|
|||||||
self.assertEqual( "structTest**", target.module.type( "structTest**" ).name() )
|
self.assertEqual( "structTest**", target.module.type( "structTest**" ).name() )
|
||||||
self.assertEqual( "Int4B[2][3]", target.module.type("Int4B[2][3]").name() )
|
self.assertEqual( "Int4B[2][3]", target.module.type("Int4B[2][3]").name() )
|
||||||
self.assertEqual( "Int4B(*[4])[2][3]", target.module.type("Int4B(*[4])[2][3]").name() )
|
self.assertEqual( "Int4B(*[4])[2][3]", target.module.type("Int4B(*[4])[2][3]").name() )
|
||||||
|
self.assertEqual( "Int4B(*)[2][3]", target.module.type("Int4B((*))[2][3]").name() )
|
||||||
|
|
||||||
def testCreateBySymbol(self):
|
def testCreateBySymbol(self):
|
||||||
""" creating typeInfo by the symbol name """
|
""" creating typeInfo by the symbol name """
|
||||||
@ -29,6 +30,8 @@ class TypeInfoTest( unittest.TestCase ):
|
|||||||
self.assertEqual( "Char*[2]", target.module.type("strArray").name() )
|
self.assertEqual( "Char*[2]", target.module.type("strArray").name() )
|
||||||
self.assertEqual( "Char*(*)[2]", target.module.type("ptrStrArray").name() )
|
self.assertEqual( "Char*(*)[2]", target.module.type("ptrStrArray").name() )
|
||||||
self.assertEqual( "Int4B(*[4])[2][3]", target.module.type("arrIntMatrixPtrs").name() )
|
self.assertEqual( "Int4B(*[4])[2][3]", target.module.type("arrIntMatrixPtrs").name() )
|
||||||
|
self.assertEqual( "Int4B(*)[2][3]", target.module.type("ptrIntMatrix1").name() )
|
||||||
|
|
||||||
|
|
||||||
def testGetField( self ):
|
def testGetField( self ):
|
||||||
""" get field of the complex type """
|
""" get field of the complex type """
|
||||||
|
@ -79,6 +79,8 @@ int (* arrIntMatrixPtrs[4])[2][3] = {
|
|||||||
&intMatrix, &intMatrix2, &intMatrix3, &intMatrix4
|
&intMatrix, &intMatrix2, &intMatrix3, &intMatrix4
|
||||||
};
|
};
|
||||||
|
|
||||||
|
int ((*ptrIntMatrix1))[2][3] = &intMatrix;
|
||||||
|
|
||||||
char *(*ptrStrArray)[2] = &strArray;
|
char *(*ptrStrArray)[2] = &strArray;
|
||||||
|
|
||||||
class classChild : public classBase {
|
class classChild : public classBase {
|
||||||
|
Loading…
Reference in New Issue
Block a user