diff --git a/pykd/dbgclient.cpp b/pykd/dbgclient.cpp index ebe09fe..281b28c 100644 --- a/pykd/dbgclient.cpp +++ b/pykd/dbgclient.cpp @@ -8,8 +8,8 @@ namespace pykd { /////////////////////////////////////////////////////////////////////////////////// -DebugClient primaryClient; -DebugClient *g_dbgClient = &primaryClient; +DebugClientPtr g_dbgClient( new DebugClient ); + void loadDump( const std::wstring &fileName ) { g_dbgClient->loadDump( fileName ); diff --git a/pykd/dbgclient.h b/pykd/dbgclient.h index 8e4c61d..3dc8c49 100644 --- a/pykd/dbgclient.h +++ b/pykd/dbgclient.h @@ -4,6 +4,8 @@ #include <dbgeng.h> #include <dbghelp.h> +#include <boost\smart_ptr\scoped_ptr.hpp> + #include "dbgexcept.h" #include "module.h" @@ -13,6 +15,11 @@ namespace pykd { ///////////////////////////////////////////////////////////////////////////////// +class DebugClient; +typedef boost::shared_ptr<DebugClient> DebugClientPtr; + +///////////////////////////////////////////////////////////////////////////////// + class DebugClient { public: @@ -21,6 +28,11 @@ public: virtual ~DebugClient() {} + static + DebugClientPtr createDbgClient() { + return DebugClientPtr( new DebugClient() ); + } + void loadDump( const std::wstring &fileName ); void startProcess( const std::wstring &processName ); @@ -46,9 +58,11 @@ private: CComPtr<IDebugSymbols3> m_symbols; }; + + ///////////////////////////////////////////////////////////////////////////////// -extern DebugClient *g_dbgClient; +extern DebugClientPtr g_dbgClient; void loadDump( const std::wstring &fileName ); diff --git a/pykd/dbgext.cpp b/pykd/dbgext.cpp index cc2d941..07aa472 100644 --- a/pykd/dbgext.cpp +++ b/pykd/dbgext.cpp @@ -88,7 +88,7 @@ static python::dict genDict(const pyDia::Symbol::ValueNameEntry srcValues[], siz BOOST_PYTHON_MODULE( pykd ) { - python::class_<pykd::DebugClient>("dbgClient", "Class representing a debugging session" ) + python::class_<pykd::DebugClient, pykd::DebugClientPtr>("dbgClient", "Class representing a debugging session", python::no_init ) .def( "loadDump", &pykd::DebugClient::loadDump, "Load crash dump" ) .def( "startProcess", &pykd::DebugClient::startProcess, @@ -102,6 +102,8 @@ BOOST_PYTHON_MODULE( pykd ) .def( "findModule", &pykd::DebugClient::findModule, "Return instance of the Module class which posseses specified address" ); + boost::python::def( "createDbgClient", pykd::DebugClient::createDbgClient, + "create a new instance of the dbgClient class" ); boost::python::def( "loadDump", &loadDump, "Load crash dump (only for console)"); boost::python::def( "startProcess", &startProcess, @@ -130,8 +132,15 @@ BOOST_PYTHON_MODULE( pykd ) "Return the full path to the module's pdb file ( symbol information )" ) .def("reload", &pykd::Module::reloadSymbols, "(Re)load symbols for the module" ) - .def("symbols", &pykd::Module::getSymbols, - "Return list of all symbols of the module" ); + .def("offset", &pykd::Module::getSymbol, + "Return offset of the symbol" ) + .def("rva", &pykd::Module::getSymbolRva, + "Return rva of the symbol" ) + .def("__getattr__", &pykd::Module::getSymbol, + "Return address of the symbol" ); + + //.def("symbols", &pykd::Module::getSymbols, + // "Return list of all symbols of the module" ); python::def( "diaLoadPdb", &pyDia::GlobalScope::loadPdb, @@ -255,7 +264,7 @@ BOOST_PYTHON_MODULE( pykd ) DEF_PY_CONST_ULONG(LocInMetaData); DEF_PY_CONST_ULONG(LocIsConstant); python::scope().attr("diaLocTypeName") = - genDict(pyDia::Symbol::symTagName, _countof(pyDia::Symbol::locTypeName)); + genDict(pyDia::Symbol::locTypeName, _countof(pyDia::Symbol::locTypeName)); DEF_PY_CONST_ULONG(btNoType); DEF_PY_CONST_ULONG(btVoid); diff --git a/pykd/module.h b/pykd/module.h index 514a231..0e5c3a0 100644 --- a/pykd/module.h +++ b/pykd/module.h @@ -42,15 +42,30 @@ public: void reloadSymbols(); + + ULONG64 + getSymbol( const std::string &symbolname ) { - python::list - getSymbols() { if ( !m_dia ) m_dia = pyDia::GlobalScope::loadPdb( getPdbName() ); - return m_dia->findChildrenEx( SymTagNull, "*", nsRegularExpression ); + pyDia::SymbolPtr sym = m_dia->getChildByName( symbolname ); + + return m_base + sym->getRva(); } + ULONG + getSymbolRva( const std::string &symbolname ) { + + if ( !m_dia ) + m_dia = pyDia::GlobalScope::loadPdb( getPdbName() ); + + pyDia::SymbolPtr sym = m_dia->getChildByName( symbolname ); + + return sym->getRva(); + } + + private: std::string m_name; diff --git a/pykd/pykd_2008.vcproj b/pykd/pykd_2008.vcproj index c936340..d72a7b8 100644 --- a/pykd/pykd_2008.vcproj +++ b/pykd/pykd_2008.vcproj @@ -1,7 +1,7 @@ <?xml version="1.0" encoding="windows-1251"?> <VisualStudioProject ProjectType="Visual C++" - Version="9.00" + Version="9,00" Name="pykd" ProjectGUID="{FE961905-666F-4908-A212-961465F46F13}" RootNamespace="pykd" diff --git a/test/scripts/moduletest.py b/test/scripts/moduletest.py index 79cc3d2..b88d15f 100644 --- a/test/scripts/moduletest.py +++ b/test/scripts/moduletest.py @@ -46,6 +46,6 @@ class ModuleTest( unittest.TestCase ): try: pykd.findModule( target.module.end() + 0x10) except pykd.BaseException: pass - def testSymbols( self ): - syms = target.module.symbols() - self.assertNotEqual( 0, len( syms ) ) + def testSymbol( self ): + self.assertEqual( target.module.rva("FuncWithName0"), target.module.offset("FuncWithName0") - target.module.begin() ) + self.assertEqual( target.module.rva("FuncWithName0"), target.module.FuncWithName0 - target.module.begin() )