[0.1.x] added : !pycmd implementation

git-svn-id: https://pykd.svn.codeplex.com/svn@70280 9b283d60-5439-405e-af05-b73fd8c4d996
This commit is contained in:
SND\kernelnet_cp 2011-10-10 11:19:12 +00:00 committed by Mikhail I. Izmestev
parent f33a030f84
commit 5ef445611c
8 changed files with 212 additions and 69 deletions

View File

@ -8,7 +8,7 @@ namespace pykd {
///////////////////////////////////////////////////////////////////////////////////
DebugClientPtr g_dbgClient( DebugClient::createDbgClient() );
DebugClientPtr g_dbgClient; //( DebugClient::createDbgClient() );
void loadDump( const std::wstring &fileName ) {
g_dbgClient->loadDump( fileName );
@ -37,43 +37,6 @@ DebugClientPtr DebugClient::setDbgClientCurrent( DebugClientPtr newDbgClient )
///////////////////////////////////////////////////////////////////////////////////
DebugClient::DebugClient()
{
HRESULT hres;
hres = DebugCreate( __uuidof(IDebugClient5), (void **)&m_client );
if ( FAILED( hres ) )
throw DbgException("DebugCreate failed");
hres = m_client->QueryInterface( __uuidof(IDebugControl4), (void**)&m_control );
if ( FAILED( hres ) )
throw DbgException("QueryInterface IDebugControl4 failed");
hres = m_client->QueryInterface( __uuidof(IDebugSymbols3), (void**)&m_symbols );
if ( FAILED( hres ) )
throw DbgException("QueryInterface IDebugSymbols3 failed");
}
///////////////////////////////////////////////////////////////////////////////////
DebugClient::DebugClient( IDebugClient4 *client )
{
HRESULT hres;
hres = client->QueryInterface( __uuidof(IDebugClient5), (void**)&m_client );
if ( FAILED( hres ) )
throw DbgException("QueryInterface IDebugControl4 failed");
hres = client->QueryInterface( __uuidof(IDebugControl4), (void**)&m_control );
if ( FAILED( hres ) )
throw DbgException("QueryInterface IDebugControl4 failed");
hres = client->QueryInterface( __uuidof(IDebugSymbols3), (void**)&m_symbols );
if ( FAILED( hres ) )
throw DbgException("QueryInterface IDebugSymbols3 failed");
}
///////////////////////////////////////////////////////////////////////////////////
void DebugClient::loadDump( const std::wstring &fileName )
{
HRESULT hres;
@ -133,7 +96,7 @@ void DebugClient::attachKernel( const std::wstring &param )
{
HRESULT hres;
hres = m_client->AttachKernelWide( DEBUG_ATTACH_KERNEL_CONNECTION, param.c_str() );
hres = m_client5->AttachKernelWide( DEBUG_ATTACH_KERNEL_CONNECTION, param.c_str() );
if ( FAILED( hres ) )
throw DbgException( "IDebugClient5::AttachKernelWide failed" );
}

View File

@ -6,6 +6,7 @@
#include <boost\smart_ptr\scoped_ptr.hpp>
#include "dbgobj.h"
#include "dbgexcept.h"
#include "module.h"
#include "dbgio.h"
@ -21,7 +22,7 @@ typedef boost::shared_ptr<DebugClient> DebugClientPtr;
/////////////////////////////////////////////////////////////////////////////////
class DebugClient {
class DebugClient : private DbgObject {
public:
@ -29,7 +30,15 @@ public:
static
DebugClientPtr createDbgClient() {
return DebugClientPtr( new DebugClient() );
HRESULT hres;
CComPtr<IDebugClient4> client = NULL;
hres = DebugCreate( __uuidof(IDebugClient4), (void **)&client );
if ( FAILED( hres ) )
throw DbgException("DebugCreate failed");
return createDbgClient( client );
}
static
@ -74,15 +83,26 @@ public:
return DbgIn( m_client );
}
public:
CComPtr<IDebugClient4>&
client() {
return m_client;
}
CComPtr<IDebugClient5>&
client5() {
return m_client5;
}
CComPtr<IDebugControl4>&
control() {
return m_control;
}
private:
DebugClient();
DebugClient( IDebugClient4 *client );
CComPtr<IDebugClient5> m_client;
CComPtr<IDebugControl4> m_control;
CComPtr<IDebugSymbols3> m_symbols;
DebugClient( IDebugClient4 *client ) : DbgObject( client ) {}
};
/////////////////////////////////////////////////////////////////////////////////

View File

@ -73,8 +73,8 @@ BOOST_PYTHON_MODULE( pykd )
.def( "dprintln", &pykd::DebugClient::dprintln,
"Print out string and insert end of line symbol. If dml = True string is printed with dml highlighting ( only for windbg )" );
// python::def( "createDbgClient", pykd::DebugClient::createDbgClient,
// "create a new instance of the dbgClient class" );
python::def( "createDbgClient", (DebugClientPtr(*)())&pykd::DebugClient::createDbgClient,
"create a new instance of the dbgClient class" );
python::def( "loadDump", &pykd::loadDump,
"Load crash dump (only for console)");
python::def( "startProcess", &pykd::startProcess,
@ -392,15 +392,13 @@ py( PDEBUG_CLIENT4 client, PCSTR args )
try {
// ïîëó÷àåì äîñòïó ê ãëîáàëüíîìó ìàïó ( íóæåí äëÿ âûçîâà exec_file )
boost::python::object main = python::import("__main__");
python::object main = python::import("__main__");
boost::python::object global(main.attr("__dict__"));
python::object global(main.attr("__dict__"));
boost::python::import( "pykd" );
// íàñòðàèâàåì ââîä/âûâîä ( ÷òîáû â ñêðèïòå ìîæíî áûëî ïèñàòü print )
boost::python::object sys = boost::python::import("sys");
python::object sys = python::import("sys");
sys.attr("stdout") = python::object( dbgClient->dout() );
sys.attr("stdin") = python::object( dbgClient->din() );
@ -514,7 +512,21 @@ pycmd( PDEBUG_CLIENT4 client, PCSTR args )
try {
// ïåðåíàïðàâëåíèå ñòàíäàðòíûõ ïîòîêîâ ÂÂ
python::object sys = python::import("sys");
sys.attr("stdout") = python::object( DbgOut( client ) );
sys.attr("stdin") = python::object( DbgIn( client ) );
client->SetOutputMask( DEBUG_OUTPUT_NORMAL );
//client->SetInputCallbacks( NULL );
PyRun_String(
"__import__('code').InteractiveConsole(__import__('__main__').__dict__).interact()",
Py_file_input,
WindbgGlobalSession::global().ptr(),
WindbgGlobalSession::global().ptr()
);
}
catch(...)
{

View File

@ -94,8 +94,9 @@ DbgOut::write( const std::wstring &str )
{
for ( size_t i = 0; i < str.size() / 100 + 1; ++i )
{
m_control->OutputWide(
DEBUG_OUTPUT_ERROR,
m_control->ControlledOutputWide(
DEBUG_OUTCTL_AMBIENT_TEXT,
DEBUG_OUTPUT_NORMAL,
L"%ws",
str.substr( i*100, min( str.size() - i*100, 100 ) ).c_str()
);
@ -112,7 +113,12 @@ DbgOut::write( const std::wstring &str )
std::string
DbgIn::readline()
{
return "";
char str[0x100];
ULONG inputSize = 0;
m_control->Input( str, sizeof(str), &inputSize );
return std::string( str ) + "\n";
}
///////////////////////////////////////////////////////////////////////////////////

View File

@ -1,6 +1,7 @@
#pragma once
#include "dbgobj.h"
#include <vector>
namespace pykd {
@ -20,7 +21,7 @@ class DbgOut : private DbgObject {
public:
DbgOut( IDebugClient5 *client ) : DbgObject( client )
DbgOut( IDebugClient4 *client ) : DbgObject( client )
{}
void
@ -33,7 +34,7 @@ class DbgIn : private DbgObject {
public:
DbgIn( IDebugClient5 *client ) : DbgObject( client )
DbgIn( IDebugClient4 *client ) : DbgObject( client )
{}
std::string
@ -42,4 +43,142 @@ public:
/////////////////////////////////////////////////////////////////////////////////
// êëàññ äëÿ ïåðåõâàòà âûâîäà â îòëàä÷èê
class OutputReader : private DbgObject, public IDebugOutputCallbacks, private boost::noncopyable {
public:
explicit OutputReader( IDebugClient4 *client ) : DbgObject( client )
{
HRESULT hres;
hres = m_client->GetOutputCallbacks( &m_previousCallback );
if ( FAILED( hres ) )
throw DbgException( "IDebugClient::GetOutputCallbacks failed" );
hres = m_client->SetOutputCallbacks( this );
if ( FAILED( hres ) )
throw DbgException( "IDebugClient::GetOutputCallbacks failed" );
}
~OutputReader()
{
if ( m_previousCallback )
m_client->SetOutputCallbacks( m_previousCallback );
}
const std::string&
Line() const {
return m_readLine;
}
private:
// IUnknown.
STDMETHOD(QueryInterface)(
__in REFIID InterfaceId,
__out PVOID* Interface ) {
return E_NOINTERFACE;
}
STDMETHOD_(ULONG, AddRef)() {
return 1L;
}
STDMETHOD_(ULONG, Release)() {
return 0L;
}
STDMETHOD(Output)(
__in ULONG Mask,
__in PCSTR Text )
{
if ( Mask == DEBUG_OUTPUT_NORMAL )
{
m_readLine += std::string( Text );
}
return S_OK;
}
private:
std::string m_readLine;
CComPtr<IDebugOutputCallbacks> m_previousCallback;
};
///////////////////////////////////////////////////////////////////////////////////
//
//class InputReader : public IDebugInputCallbacks, private DbgObject, private boost::noncopyable {
//
//public:
//
// explicit InputReader( IDebugClient4 *debugClient ) : DbgObject( debugClient )
// {
// HRESULT hres;
//
// hres = m_client->GetInputCallbacks( &m_previousCallback );
// if ( FAILED( hres ) )
// throw DbgException( "IDebugClient::GetInputCallbacks failed" );
//
// hres = m_client->SetInputCallbacks( this );
// if ( FAILED( hres ) )
// throw DbgException( "IDebugClient::SetInputCallbacks failed" );
// }
//
// ~InputReader()
// {
// if ( m_previousCallback )
// m_client->SetInputCallbacks( m_previousCallback );
// }
//
//
//private:
//
// // IUnknown.
// STDMETHOD(QueryInterface)(
// __in REFIID InterfaceId,
// __out PVOID* Interface ) {
// return E_NOINTERFACE;
// }
//
// STDMETHOD_(ULONG, AddRef)() {
// return 1L;
// }
//
//
// STDMETHOD_(ULONG, Release)() {
// return 0L;
// }
//
// STDMETHOD( EndInput )() {
// return S_OK;
// }
//
// STDMETHOD( StartInput )(
// IN ULONG BufferSize ) {
//
// std::vector<char> buf(BufferSize);
//
// ULONG inputSize;
//
// m_control->Input( &buf[0], BufferSize, &inputSize );
//
// m_control->ReturnInput( &buf[0] );
//
// return S_OK;
// }
//
//private:
//
// CComPtr<IDebugInputCallbacks> m_previousCallback;
//
//};
/////////////////////////////////////////////////////////////////////////////////
};

View File

@ -11,12 +11,14 @@ class DbgObject {
protected:
DbgObject( IDebugClient5 *client ) {
DbgObject( IDebugClient4 *client ) {
m_client = client;
HRESULT hres;
hres = client->QueryInterface( __uuidof(IDebugClient5), (void **)&m_client );
hres = client->QueryInterface( __uuidof(IDebugClient5), (void **)&m_client5 );
if ( FAILED( hres ) )
throw DbgException("DebugCreate failed");
throw DbgException("QueryInterface IDebugClient5 failed");
hres = client->QueryInterface( __uuidof(IDebugControl4), (void**)&m_control );
if ( FAILED( hres ) )
@ -33,7 +35,8 @@ protected:
virtual ~DbgObject() {};
CComPtr<IDebugClient5> m_client;
CComPtr<IDebugClient5> m_client5;
CComPtr<IDebugClient4> m_client;
CComPtr<IDebugControl4> m_control;
CComPtr<IDebugSymbols3> m_symbols;
CComPtr<IDebugAdvanced2> m_advanced;

View File

@ -20,7 +20,7 @@ Module findModule( ULONG64 offset ) {
///////////////////////////////////////////////////////////////////////////////////
Module::Module( IDebugClient5 *client, const std::string& moduleName ) : DbgObject( client )
Module::Module( IDebugClient4 *client, const std::string& moduleName ) : DbgObject( client )
{
HRESULT hres;
@ -55,7 +55,7 @@ Module::Module( IDebugClient5 *client, const std::string& moduleName ) : DbgObje
///////////////////////////////////////////////////////////////////////////////////
Module::Module( IDebugClient5 *client, ULONG64 offset ) : DbgObject( client )
Module::Module( IDebugClient4 *client, ULONG64 offset ) : DbgObject( client )
{
HRESULT hres;

View File

@ -14,9 +14,9 @@ class Module : private DbgObject {
public:
Module( IDebugClient5 *client, const std::string& moduleName );
Module( IDebugClient4 *client, const std::string& moduleName );
Module( IDebugClient5 *client, ULONG64 offset );
Module( IDebugClient4 *client, ULONG64 offset );
std::string getName() {
return m_name;