diff --git a/pykd/dbgext.cpp b/pykd/dbgext.cpp index 019be5f..a8484f1 100644 --- a/pykd/dbgext.cpp +++ b/pykd/dbgext.cpp @@ -98,9 +98,11 @@ BOOST_PYTHON_MODULE( pykd ) boost::python::def( "ptrSignQWord", &loadByPtr<__int64> ); boost::python::def( "ptrPtr", &loadPtrByPtr ); boost::python::def( "compareMemory", &compareMemory ); - boost::python::def( "getStack", &getStack ); + boost::python::def( "getCurrentStack", &getCurrentStack ); boost::python::def( "reloadSymbols", &reloadSymbols ); boost::python::def( "getPdbFile", &getPdbFile ); + boost::python::def( "getImplicitThread", &getImplicitThread ); + boost::python::def( "setImplicitThread", &setImplicitThread ); boost::python::class_( "typedVarClass" ) .def("getAddress", &typedVarClass::getAddress ); boost::python::class_( "dbgModuleClass" ) @@ -112,7 +114,13 @@ BOOST_PYTHON_MODULE( pykd ) "dbgExtensionClass", "dbgExtensionClass", boost::python::init( boost::python::args("path"), "__init__ dbgExtensionClass" ) ) - .def("call", &dbgExtensionClass::call ); + .def("call", &dbgExtensionClass::call ); + boost::python::class_( "dbgStackFrameClass", "dbgStackFrameClass" ) + .def_readonly( "instructionOffset", &dbgStackFrameClass::InstructionOffset ) + .def_readonly( "returnOffset", &dbgStackFrameClass::ReturnOffset ) + .def_readonly( "frameOffset", &dbgStackFrameClass::FrameOffset ) + .def_readonly( "stackOffset", &dbgStackFrameClass::StackOffset ) + .def_readonly( "frameNumber", &dbgStackFrameClass::FrameNumber ); } ///////////////////////////////////////////////////////////////////////////////// @@ -167,6 +175,8 @@ SetupDebugEngine( IDebugClient4 *client, DbgExt *dbgExt ) client->QueryInterface( __uuidof(IDebugDataSpaces), (void **)&dbgExt->dataSpaces ); client->QueryInterface( __uuidof(IDebugAdvanced2), (void **)&dbgExt->advanced2 ); + + client->QueryInterface( __uuidof(IDebugSystemObjects2), (void**)&dbgExt->system2 ); } ///////////////////////////////////////////////////////////////////////////////// diff --git a/pykd/dbgext.h b/pykd/dbgext.h index 16a6fdb..f3798a2 100644 --- a/pykd/dbgext.h +++ b/pykd/dbgext.h @@ -5,20 +5,22 @@ struct DbgExt { - IDebugClient *client; - IDebugClient4 *client4; + IDebugClient *client; + IDebugClient4 *client4; - IDebugControl *control; + IDebugControl *control; - IDebugRegisters *registers; + IDebugRegisters *registers; - IDebugSymbols *symbols; - IDebugSymbols2 *symbols2; - IDebugSymbols3 *symbols3; + IDebugSymbols *symbols; + IDebugSymbols2 *symbols2; + IDebugSymbols3 *symbols3; - IDebugDataSpaces *dataSpaces; + IDebugDataSpaces *dataSpaces; - IDebugAdvanced2 *advanced2; + IDebugAdvanced2 *advanced2; + + IDebugSystemObjects2 *system2; }; extern DbgExt *dbgExt; diff --git a/pykd/dbgstack.cpp b/pykd/dbgstack.cpp index 4b93562..496f574 100644 --- a/pykd/dbgstack.cpp +++ b/pykd/dbgstack.cpp @@ -6,8 +6,73 @@ ///////////////////////////////////////////////////////////////////////////////// +bool +setImplicitThread( + ULONG64 newThreadAddr, + PULONG64 oldThreadAddr ) +{ + HRESULT hres; + + try { + + *oldThreadAddr = getImplicitThread(); + if ( *oldThreadAddr == -1 ) + return false; + + hres = dbgExt->system2->SetImplicitThreadDataOffset( newThreadAddr ); + if ( FAILED( hres ) ) + throw DbgException( "IDebugSystemObjects2::SetImplicitThreadDataOffset failed" ); + + return true; + + } + catch( std::exception &e ) + { + dbgExt->control->Output( DEBUG_OUTPUT_ERROR, "pykd error: %s\n", e.what() ); + } + catch(...) + { + dbgExt->control->Output( DEBUG_OUTPUT_ERROR, "pykd unexpected error\n" ); + } + + return false; +} + + +///////////////////////////////////////////////////////////////////////////////// + +ULONG64 +getImplicitThread() +{ + HRESULT hres; + + try { + + ULONG64 threadOffset = -1; + + hres = dbgExt->system2->GetImplicitThreadDataOffset( &threadOffset ); + if ( FAILED( hres ) ) + throw DbgException( "IDebugSystemObjects2::GetImplicitThreadDataOffset failed" ); + + return threadOffset; + + } + catch( std::exception &e ) + { + dbgExt->control->Output( DEBUG_OUTPUT_ERROR, "pykd error: %s\n", e.what() ); + } + catch(...) + { + dbgExt->control->Output( DEBUG_OUTPUT_ERROR, "pykd unexpected error\n" ); + } + + return -1; +} + +///////////////////////////////////////////////////////////////////////////////// + boost::python::object -getStack( ULONG64 stackPtr ) +getCurrentStack() { HRESULT hres; PDEBUG_STACK_FRAME frames = NULL; @@ -17,14 +82,19 @@ getStack( ULONG64 stackPtr ) frames = new DEBUG_STACK_FRAME [ 1000 ]; ULONG filledFrames; - hres = dbgExt->control->GetStackTrace( stackPtr, stackPtr, stackPtr, frames, 1000, &filledFrames ); + hres = dbgExt->control->GetStackTrace( 0, 0, 0, frames, 1000, &filledFrames ); - dbgExt->control->OutputStackTrace( DEBUG_OUTCTL_THIS_CLIENT, frames, filledFrames, DEBUG_STACK_FUNCTION_INFO | DEBUG_STACK_FRAME_ADDRESSES ); + boost::python::list frameList; + + for ( ULONG i = 0; i < filledFrames; ++i ) + { + frameList.append( boost::python::object( dbgStackFrameClass( frames[i] ) ) ); + } if ( frames ) delete[] frames; - return boost::python::object(); + return frameList; } catch( std::exception &e ) @@ -39,7 +109,8 @@ getStack( ULONG64 stackPtr ) if ( frames ) delete[] frames; - return boost::python::object(); + return boost::python::object(); } + ///////////////////////////////////////////////////////////////////////////////// \ No newline at end of file diff --git a/pykd/dbgstack.h b/pykd/dbgstack.h index 05096b9..fc28ca4 100644 --- a/pykd/dbgstack.h +++ b/pykd/dbgstack.h @@ -5,7 +5,31 @@ ///////////////////////////////////////////////////////////////////////////////// +bool +setImplicitThread( + ULONG64 newThreadAddr, + PULONG64 oldThreadAddr ); + +ULONG64 +getImplicitThread(); + + boost::python::object -getStack( ULONG64 stackPtr ); +getCurrentStack(); + +class dbgStackFrameClass : public DEBUG_STACK_FRAME { + +public: + + dbgStackFrameClass() + { + memset( static_cast( this ), 0, sizeof(DEBUG_STACK_FRAME) ); + } + + dbgStackFrameClass( const DEBUG_STACK_FRAME &stackFrame ) + { + memcpy( static_cast( this ), &stackFrame, sizeof(DEBUG_STACK_FRAME) ); + } +}; ///////////////////////////////////////////////////////////////////////////////// \ No newline at end of file diff --git a/pykd/dbgsym.cpp b/pykd/dbgsym.cpp index 7d9b02d..f0c73d8 100644 --- a/pykd/dbgsym.cpp +++ b/pykd/dbgsym.cpp @@ -13,9 +13,6 @@ findSymbolForAddress( ULONG64 addr ) HRESULT hres; try { - - DEBUG_MODULE_AND_ID debugId; - ULONG64 displace = 0; if ( *( (ULONG*)&addr + 1 ) == 0 ) *( (ULONG*)&addr + 1 ) = 0xFFFFFFFF; @@ -36,11 +33,19 @@ findSymbolForAddress( ULONG64 addr ) if ( FAILED( hres ) ) throw DbgException( "IDebugSymbol2::GetModuleNameString failed" ); - ULONG entries = 0; - hres = dbgExt->symbols3->GetSymbolEntriesByOffset( addr, 0, &debugId, &displace, 1, &entries ); + char symbolName[0x100]; + ULONG64 displace = 0; + hres = dbgExt->symbols->GetNameByOffset( addr, symbolName, sizeof(symbolName), NULL, &displace ); if ( FAILED( hres ) ) - throw DbgException( "IDebugSymbol3::GetSymbolEntriesByOffset failed" ); - + throw DbgException( "IDebugSymbol::GetNameByOffset failed" ); + + std::stringstream ss; + displace == 0 ? ss << symbolName : ss << symbolName << '+' << std::hex << displace; + + return boost::python::object( ss.str() ); + + +/* std::stringstream ss; if ( entries == 0 ) @@ -55,7 +60,7 @@ findSymbolForAddress( ULONG64 addr ) throw DbgException( "IDebugSymbol3::GetSymbolEntryString failed" ); ss << moduleName << "!" << symbolName; - return boost::python::object( ss.str() ); + return boost::python::object( ss.str() ); */ } catch( std::exception &e )