mirror of
https://github.com/ivellioscolin/pykd.git
synced 2025-04-29 11:53:23 +08:00
[0.2.x] added : cpuReg class
git-svn-id: https://pykd.svn.codeplex.com/svn@78577 9b283d60-5439-405e-af05-b73fd8c4d996
This commit is contained in:
parent
c8d99b5565
commit
3a47a6574d
167
pykd/cpureg.cpp
167
pykd/cpureg.cpp
@ -1,195 +1,48 @@
|
||||
#include "stdafx.h"
|
||||
|
||||
#include <boost\algorithm\string\case_conv.hpp>
|
||||
//#include <boost\algorithm\string\case_conv.hpp>
|
||||
|
||||
#include "dbgengine.h"
|
||||
#include "cpureg.h"
|
||||
#include "dbgclient.h"
|
||||
#include "dbgexcept.h"
|
||||
|
||||
namespace pykd {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
CpuReg::CpuReg( IDebugClient4 *client, const std::string ®Name ) :
|
||||
DbgObject( client )
|
||||
CpuReg::CpuReg( const std::string ®Name )
|
||||
{
|
||||
HRESULT hres;
|
||||
|
||||
m_name = regName;
|
||||
|
||||
hres = m_registers->GetIndexByName( boost::to_lower_copy(m_name).c_str(), &m_index );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetIndexByName", hres );
|
||||
|
||||
DEBUG_REGISTER_DESCRIPTION desc = {};
|
||||
|
||||
hres =
|
||||
m_registers->GetDescription(
|
||||
m_index,
|
||||
NULL,
|
||||
0,
|
||||
NULL,
|
||||
&desc );
|
||||
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetDescription", hres );
|
||||
|
||||
switch ( desc.Type )
|
||||
{
|
||||
case DEBUG_VALUE_INT8:
|
||||
case DEBUG_VALUE_INT16:
|
||||
case DEBUG_VALUE_INT32:
|
||||
case DEBUG_VALUE_INT64:
|
||||
break;
|
||||
|
||||
default:
|
||||
throw DbgException( "Unsupported register type ( not integer )" );
|
||||
}
|
||||
m_index = getRegIndexByName( m_name );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
CpuReg::CpuReg( IDebugClient4 *client, ULONG index ) :
|
||||
DbgObject( client )
|
||||
CpuReg::CpuReg( ULONG index )
|
||||
{
|
||||
HRESULT hres;
|
||||
|
||||
m_index = index;
|
||||
|
||||
ULONG nameSize = 0;
|
||||
|
||||
hres =
|
||||
m_registers->GetDescription(
|
||||
m_index,
|
||||
NULL,
|
||||
0,
|
||||
&nameSize,
|
||||
NULL );
|
||||
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetDescription", hres );
|
||||
|
||||
std::vector<char> nameBuffer(nameSize);
|
||||
DEBUG_REGISTER_DESCRIPTION desc = {};
|
||||
|
||||
hres =
|
||||
m_registers->GetDescription(
|
||||
m_index,
|
||||
&nameBuffer[0],
|
||||
nameSize,
|
||||
NULL,
|
||||
&desc );
|
||||
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetDescription", hres );
|
||||
|
||||
switch ( desc.Type )
|
||||
{
|
||||
case DEBUG_VALUE_INT8:
|
||||
case DEBUG_VALUE_INT16:
|
||||
case DEBUG_VALUE_INT32:
|
||||
case DEBUG_VALUE_INT64:
|
||||
break;
|
||||
|
||||
default:
|
||||
throw DbgException( "Unsupported register type ( not integer )" );
|
||||
}
|
||||
|
||||
m_name = std::string( &nameBuffer[0] );
|
||||
|
||||
m_name = getRegNameByIndex( m_index );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
BaseTypeVariant CpuReg::getValue()
|
||||
{
|
||||
HRESULT hres;
|
||||
|
||||
DEBUG_VALUE debugValue;
|
||||
hres = m_registers->GetValue( m_index, &debugValue );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetValue", hres );
|
||||
|
||||
switch( debugValue.Type )
|
||||
{
|
||||
case DEBUG_VALUE_INT8:
|
||||
return BaseTypeVariant( (LONG)debugValue.I8 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT16:
|
||||
return BaseTypeVariant( (LONG)debugValue.I16 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT32:
|
||||
return BaseTypeVariant( debugValue.I32 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT64:
|
||||
return BaseTypeVariant( debugValue.I64 );
|
||||
break;
|
||||
}
|
||||
|
||||
throw DbgException( "Failed to convert register value" );
|
||||
return getRegVariantValue( m_index );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
CpuReg DebugClient::getRegByName( const std::string ®Name )
|
||||
{
|
||||
return CpuReg( m_client, regName );
|
||||
}
|
||||
|
||||
|
||||
CpuReg getRegByName( const std::string ®Name )
|
||||
{
|
||||
return g_dbgClient->getRegByName( regName );
|
||||
return CpuReg( regName );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
CpuReg DebugClient::getRegByIndex( ULONG index )
|
||||
{
|
||||
return CpuReg( m_client, index );
|
||||
}
|
||||
|
||||
|
||||
CpuReg getRegByIndex( ULONG index )
|
||||
{
|
||||
return g_dbgClient->getRegByIndex( index );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ULONG64 DebugClient::loadMSR( ULONG msr )
|
||||
{
|
||||
HRESULT hres;
|
||||
ULONG64 value;
|
||||
|
||||
hres = m_dataSpaces->ReadMsr( msr, &value );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugDataSpaces::ReadMsr", hres );
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
ULONG64 loadMSR( ULONG msr )
|
||||
{
|
||||
return g_dbgClient->loadMSR( msr );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void DebugClient::setMSR( ULONG msr, ULONG64 value)
|
||||
{
|
||||
HRESULT hres;
|
||||
|
||||
hres = m_dataSpaces->WriteMsr(msr, value);
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugDataSpaces::WriteMsr", hres );
|
||||
}
|
||||
|
||||
void setMSR( ULONG msr, ULONG64 value)
|
||||
{
|
||||
g_dbgClient->setMSR( msr, value );
|
||||
return CpuReg( index );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -1,19 +1,18 @@
|
||||
#pragma once
|
||||
|
||||
#include "intbase.h"
|
||||
#include "dbgobj.h"
|
||||
#include "variant.h"
|
||||
|
||||
namespace pykd {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
class CpuReg : public intBase, protected DbgObject {
|
||||
class CpuReg : public intBase {
|
||||
|
||||
public:
|
||||
|
||||
CpuReg( IDebugClient4 *client, const std::string ®Name );
|
||||
CpuReg( const std::string ®Name );
|
||||
|
||||
CpuReg( IDebugClient4 *client, ULONG index );
|
||||
CpuReg( ULONG index );
|
||||
|
||||
std::string
|
||||
name() const {
|
||||
|
@ -1,6 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "dbgmem.h"
|
||||
#include "variant.h"
|
||||
|
||||
namespace pykd {
|
||||
|
||||
@ -13,6 +14,7 @@ void debugGo();
|
||||
|
||||
// system properties
|
||||
ULONG ptrSize();
|
||||
bool is64bitSystem();
|
||||
|
||||
//manage debug module
|
||||
ULONG64 findModuleBase( const std::string &moduleName );
|
||||
@ -24,6 +26,11 @@ std::string getModuleSymbolFileName( ULONG64 baseOffset );
|
||||
ULONG getModuleTimeStamp( ULONG64 baseOffset );
|
||||
ULONG getModuleCheckSum( ULONG64 baseOffset );
|
||||
|
||||
// CPU registers
|
||||
ULONG getRegIndexByName( const std::string ®Name );
|
||||
std::string getRegNameByIndex( ULONG index );
|
||||
BaseTypeVariant getRegVariantValue( ULONG index );
|
||||
|
||||
// ýòî íóæíî ñäåëàòü ïî-äðóãîìó!
|
||||
std::string getSymbolByOffset( ULONG64 offset );
|
||||
|
||||
|
@ -328,11 +328,66 @@ ULONGLONG DiaSymbol::getVa()
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void DiaSymbol::getValue( VARIANT &vtValue)
|
||||
void DiaSymbol::getValue( BaseTypeVariant &btv )
|
||||
{
|
||||
CComVariant vtValue;
|
||||
HRESULT hres = m_symbol->get_value(&vtValue);
|
||||
if (S_OK != hres)
|
||||
throw DiaException("Call IDiaSymbol::get_value", hres);
|
||||
|
||||
switch (vtValue.vt)
|
||||
{
|
||||
case VT_I1:
|
||||
btv = (LONG)vtValue.bVal;
|
||||
break;
|
||||
|
||||
case VT_UI1:
|
||||
btv = (ULONG)vtValue.bVal;
|
||||
break;
|
||||
|
||||
case VT_BOOL:
|
||||
btv = !!vtValue.iVal;
|
||||
break;
|
||||
|
||||
case VT_I2:
|
||||
btv = (LONG)vtValue.iVal;
|
||||
break;
|
||||
|
||||
case VT_UI2:
|
||||
btv = (ULONG)vtValue.iVal;
|
||||
break;
|
||||
|
||||
case VT_I4:
|
||||
case VT_INT:
|
||||
btv = (LONG)vtValue.lVal;
|
||||
break;
|
||||
|
||||
case VT_UI4:
|
||||
case VT_UINT:
|
||||
case VT_ERROR:
|
||||
case VT_HRESULT:
|
||||
btv = (ULONG)vtValue.lVal;
|
||||
break;
|
||||
|
||||
case VT_I8:
|
||||
btv = (ULONG64)vtValue.llVal;
|
||||
break;
|
||||
|
||||
case VT_UI8:
|
||||
btv = (LONG64)vtValue.llVal;
|
||||
break;
|
||||
|
||||
//case VT_R4:
|
||||
// btv = vtValue.fltVal;
|
||||
// break;
|
||||
|
||||
//case VT_R8:
|
||||
// fillDataBuff(vtValue.dblVal);
|
||||
// break;
|
||||
|
||||
default:
|
||||
throw DbgException( "Unsupported const value" );
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -102,7 +102,7 @@ public:
|
||||
//static void getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue);
|
||||
//python::object getValue();
|
||||
|
||||
void getValue( VARIANT &vtValue);
|
||||
void getValue( BaseTypeVariant &vtValue );
|
||||
|
||||
//bool isBasicType();
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include "intbase.h"
|
||||
#include "variant.h"
|
||||
#include "symengine.h"
|
||||
#include "typeinfo.h"
|
||||
#include "typedvar.h"
|
||||
|
@ -349,6 +349,10 @@
|
||||
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
|
||||
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\cpureg.cpp"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\dbgexcept.cpp"
|
||||
>
|
||||
@ -431,6 +435,10 @@
|
||||
Filter="h;hpp;hxx;hm;inl;inc;xsd"
|
||||
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\cpureg.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\dbgengine.h"
|
||||
>
|
||||
@ -443,10 +451,6 @@
|
||||
RelativePath=".\dbgmem.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\intbase.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\module.h"
|
||||
>
|
||||
@ -483,6 +487,10 @@
|
||||
RelativePath=".\vardata.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\variant.h"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Resource Files"
|
||||
|
@ -10,11 +10,12 @@
|
||||
#include "symengine.h"
|
||||
|
||||
#include "module.h"
|
||||
#include "intbase.h"
|
||||
#include "variant.h"
|
||||
#include "dbgexcept.h"
|
||||
#include "dbgmem.h"
|
||||
#include "typeinfo.h"
|
||||
#include "typedvar.h"
|
||||
#include "cpureg.h"
|
||||
|
||||
using namespace pykd;
|
||||
|
||||
@ -61,6 +62,8 @@ BOOST_PYTHON_MODULE( pykd )
|
||||
// system properties
|
||||
python::def( "ptrSize", &ptrSize,
|
||||
"Return effective pointer size" );
|
||||
python::def( "is64bitSystem", &is64bitSystem,
|
||||
"Check if target system has 64 address space" );
|
||||
|
||||
// Manage target memory access
|
||||
|
||||
@ -143,6 +146,16 @@ BOOST_PYTHON_MODULE( pykd )
|
||||
"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" );
|
||||
|
||||
// CPU registers
|
||||
python::def( "reg", &getRegByName,
|
||||
"Return a CPU regsiter value by the register's name" );
|
||||
python::def( "reg", &getRegByIndex,
|
||||
"Return a CPU regsiter value by the register's value" );
|
||||
python::def ( "rdmsr", &loadMSR,
|
||||
"Return MSR value" );
|
||||
python::def( "wrmsr", &setMSR,
|
||||
"Set MSR value" );
|
||||
|
||||
python::class_<intBase>( "intBase", "intBase", python::no_init )
|
||||
.def( python::init<python::object&>() )
|
||||
.def( "__eq__", &intBase::eq )
|
||||
@ -275,6 +288,12 @@ BOOST_PYTHON_MODULE( pykd )
|
||||
.def("__getitem__", &TypedVar::getElementByIndex )
|
||||
.def("__getitem__", &TypedVar::getElementByIndexPtr );
|
||||
|
||||
|
||||
python::class_<CpuReg, python::bases<intBase> >(
|
||||
"cpuReg", "CPU regsiter class", boost::python::no_init )
|
||||
.def( "name", &CpuReg::name, "The name of the regsiter" )
|
||||
.def( "index", &CpuReg::index, "The index of thr register" );
|
||||
|
||||
// wrapper for standart python exceptions
|
||||
python::register_exception_translator<PyException>( &PyException::exceptionTranslate );
|
||||
|
||||
@ -301,6 +320,14 @@ BOOST_PYTHON_MODULE( pykd )
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
//#include <dia2.h>
|
||||
|
@ -1,5 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "variant.h"
|
||||
|
||||
namespace pykd {
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
@ -128,7 +130,7 @@ public:
|
||||
virtual ULONG getSymTag() = 0;
|
||||
virtual SymbolPtr getType() = 0;
|
||||
virtual ULONGLONG getVa() = 0;
|
||||
virtual void getValue( VARIANT &vtValue) = 0;
|
||||
virtual void getValue( BaseTypeVariant &vtValue) = 0;
|
||||
virtual ULONG getVirtualBaseDispIndex() = 0;
|
||||
virtual int getVirtualBasePointerOffset() = 0;
|
||||
virtual bool isVirtualBaseClass() = 0;
|
||||
|
@ -1,7 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "typeinfo.h"
|
||||
#include "intbase.h"
|
||||
#include "variant.h"
|
||||
#include "dbgexcept.h"
|
||||
#include "vardata.h"
|
||||
|
||||
|
@ -114,34 +114,7 @@ BaseTypeVariant TypeInfo::getValue()
|
||||
if ( !m_constant )
|
||||
throw TypeException( getName(), "this type is not a constant and has not a value" );
|
||||
|
||||
switch( m_constantValue.vt )
|
||||
{
|
||||
case VT_UI1:
|
||||
return (ULONG)m_constantValue.bVal;;
|
||||
|
||||
case VT_I1:
|
||||
return (LONG)m_constantValue.cVal;
|
||||
|
||||
case VT_UI2:
|
||||
return (ULONG)m_constantValue.uiVal;
|
||||
|
||||
case VT_I2:
|
||||
return (LONG)m_constantValue.iVal;
|
||||
|
||||
case VT_UI4:
|
||||
return (ULONG)m_constantValue.lVal;
|
||||
|
||||
case VT_I4:
|
||||
return (LONG)m_constantValue.ulVal;
|
||||
|
||||
case VT_UI8:
|
||||
return (ULONG64)m_constantValue.ullVal;
|
||||
|
||||
case VT_I8:
|
||||
return (LONG64)m_constantValue.llVal;
|
||||
}
|
||||
|
||||
throw TypeException( getName(), "Failed to convert constant type to any integer type" );
|
||||
return m_constantValue;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
@ -166,9 +139,8 @@ TypeInfoPtr TypeInfo::getTypeInfo( SymbolPtr &symScope, const std::string &symN
|
||||
|
||||
TypeInfoPtr TypeInfo::getTypeInfo( SymbolPtr &symScope, SymbolPtr &symChild )
|
||||
{
|
||||
CComVariant constVal;
|
||||
|
||||
SymbolPtr symType = symChild;
|
||||
|
||||
if ( symType->getSymTag() == SymTagData )
|
||||
{
|
||||
if ( symType->getLocType() == LocIsBitField )
|
||||
@ -178,18 +150,17 @@ TypeInfoPtr TypeInfo::getTypeInfo( SymbolPtr &symScope, SymbolPtr &symChild )
|
||||
|
||||
if ( symType->getDataKind() == DataIsConstant )
|
||||
{
|
||||
BaseTypeVariant constVal;
|
||||
symType->getValue( constVal );
|
||||
TypeInfoPtr ptr = getTypeInfo( symType->getType() );
|
||||
ptr->setConstant( constVal );
|
||||
return ptr;
|
||||
}
|
||||
|
||||
symType = symType->getType();
|
||||
}
|
||||
|
||||
TypeInfoPtr ptr = getTypeInfo( symType );
|
||||
|
||||
if ( constVal.vt != VT_EMPTY )
|
||||
ptr->setConstant( constVal );
|
||||
|
||||
return ptr;
|
||||
return getTypeInfo( symType );
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
@ -766,11 +737,11 @@ python::dict EnumTypeInfo::asMap()
|
||||
|
||||
for ( SymbolPtrList::iterator it = symbolsList.begin(); it != symbolsList.end(); it++ )
|
||||
{
|
||||
CComVariant val;
|
||||
BaseTypeVariant val;
|
||||
|
||||
(*it)->getValue( val );
|
||||
|
||||
dct[val.ulVal] = (*it)->getName();
|
||||
dct[ boost::apply_visitor( VariantToULong(), val ) ] = (*it)->getName();
|
||||
}
|
||||
|
||||
return dct;
|
||||
@ -788,11 +759,11 @@ std::string EnumTypeInfo::print()
|
||||
|
||||
for ( SymbolPtrList::iterator it = symbolsList.begin(); it != symbolsList.end(); it++ )
|
||||
{
|
||||
CComVariant val;
|
||||
BaseTypeVariant val;
|
||||
(*it)->getValue( val );
|
||||
|
||||
sstr << " " << (*it)->getName();
|
||||
sstr << " = " << std::hex << val.ulVal << " (" << std::dec << val.ulVal << ')';
|
||||
sstr << " = " << boost::apply_visitor( VariantToHex(), val ) << " (" << boost::apply_visitor( VariantToStr(), val )<< ')';
|
||||
sstr << std::endl;
|
||||
}
|
||||
|
||||
|
@ -5,7 +5,7 @@
|
||||
#include <boost\enable_shared_from_this.hpp>
|
||||
|
||||
#include "udtutils.h"
|
||||
#include "intbase.h"
|
||||
#include "variant.h"
|
||||
#include "symengine.h"
|
||||
#include "dbgexcept.h"
|
||||
|
||||
@ -56,9 +56,7 @@ public:
|
||||
m_virtualBasePtr( 0 ),
|
||||
m_virtualDispIndex( 0 ),
|
||||
m_virtualDispSize( 0 )
|
||||
{
|
||||
m_constantValue.vt = VT_EMPTY;
|
||||
}
|
||||
{}
|
||||
|
||||
virtual std::string print() {
|
||||
std::stringstream sstr;
|
||||
@ -156,7 +154,7 @@ public:
|
||||
throw PyException( PyExc_TypeError, "object is unsubscriptable");
|
||||
}
|
||||
|
||||
void setConstant( const VARIANT& var )
|
||||
void setConstant( const BaseTypeVariant& var )
|
||||
{
|
||||
m_constant = true;
|
||||
m_constantValue = var;
|
||||
@ -220,7 +218,7 @@ protected:
|
||||
|
||||
bool m_virtualMember;
|
||||
|
||||
VARIANT m_constantValue;
|
||||
BaseTypeVariant m_constantValue;
|
||||
|
||||
LONG m_virtualBasePtr;
|
||||
|
||||
|
128
pykd/vardata.cpp
128
pykd/vardata.cpp
@ -60,107 +60,103 @@ ULONG64 VarDataMemory::readPtr() const
|
||||
|
||||
VarDataConst::VarDataConst( SymbolPtr &symData) :
|
||||
m_fieldOffset(0)
|
||||
, m_dataBuff( new std::vector< UCHAR >((size_t)symData->getType()->getSize(), 0) )
|
||||
{
|
||||
VARIANT vtValue = {0};
|
||||
symData->getValue(vtValue);
|
||||
|
||||
switch (vtValue.vt)
|
||||
{
|
||||
case VT_I1:
|
||||
case VT_UI1:
|
||||
fillDataBuff(vtValue.bVal);
|
||||
break;
|
||||
|
||||
case VT_BOOL:
|
||||
fillDataBuff(!!vtValue.iVal);
|
||||
break;
|
||||
|
||||
case VT_I2:
|
||||
case VT_UI2:
|
||||
fillDataBuff(vtValue.iVal);
|
||||
break;
|
||||
|
||||
case VT_I4:
|
||||
case VT_UI4:
|
||||
case VT_INT:
|
||||
case VT_UINT:
|
||||
case VT_ERROR:
|
||||
case VT_HRESULT:
|
||||
fillDataBuff(vtValue.lVal);
|
||||
break;
|
||||
|
||||
case VT_I8:
|
||||
case VT_UI8:
|
||||
fillDataBuff(vtValue.llVal);
|
||||
break;
|
||||
|
||||
case VT_R4:
|
||||
fillDataBuff(vtValue.fltVal);
|
||||
break;
|
||||
|
||||
case VT_R8:
|
||||
fillDataBuff(vtValue.dblVal);
|
||||
break;
|
||||
|
||||
default:
|
||||
throw DbgException( "Unsupported const value" );
|
||||
}
|
||||
symData->getValue(m_value);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// VARIANT vtValue = {0};
|
||||
// symData->getValue(vtValue);
|
||||
//
|
||||
// switch (vtValue.vt)
|
||||
// {
|
||||
// case VT_I1:
|
||||
// case VT_UI1:
|
||||
// fillDataBuff(vtValue.bVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_BOOL:
|
||||
// fillDataBuff(!!vtValue.iVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_I2:
|
||||
// case VT_UI2:
|
||||
// fillDataBuff(vtValue.iVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_I4:
|
||||
// case VT_UI4:
|
||||
// case VT_INT:
|
||||
// case VT_UINT:
|
||||
// case VT_ERROR:
|
||||
// case VT_HRESULT:
|
||||
// fillDataBuff(vtValue.lVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_I8:
|
||||
// case VT_UI8:
|
||||
// fillDataBuff(vtValue.llVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_R4:
|
||||
// fillDataBuff(vtValue.fltVal);
|
||||
// break;
|
||||
//
|
||||
// case VT_R8:
|
||||
// fillDataBuff(vtValue.dblVal);
|
||||
// break;
|
||||
//
|
||||
// default:
|
||||
// throw DbgException( "Unsupported const value" );
|
||||
// }
|
||||
//}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::string VarDataConst::asString() const
|
||||
{
|
||||
return "<constant>";
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ULONG64 VarDataConst::getAddr() const
|
||||
{
|
||||
throw DbgException("Constant does not have address");
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
VarDataPtr VarDataConst::fork(ULONG offset) const
|
||||
{
|
||||
return VarDataPtr(new VarDataConst(*this, offset));
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void VarDataConst::read(PVOID buffer, ULONG length, ULONG offset /*= 0*/) const
|
||||
{
|
||||
if (offset + length > m_dataBuff->size())
|
||||
ULONG64 val = boost::apply_visitor( VariantToULong64(), m_value );
|
||||
if (offset + length > sizeof(val) )
|
||||
throw DbgException("Internal error in " __FUNCTION__);
|
||||
RtlCopyMemory(buffer, &m_dataBuff->at(offset), length);
|
||||
|
||||
RtlCopyMemory(buffer, (char*)&val + offset, length);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////'
|
||||
//////////////////////////////////////////////////////////////////////////////////'
|
||||
|
||||
ULONG64 VarDataConst::readPtr() const
|
||||
{
|
||||
ULONG64 val = 0;
|
||||
const ULONG length = ptrSize();
|
||||
if (length > m_dataBuff->size())
|
||||
throw DbgException("Internal error in " __FUNCTION__);
|
||||
RtlCopyMemory(&val, &m_dataBuff->at(0), length);
|
||||
return val;
|
||||
return boost::apply_visitor( VariantToULong64(), m_value );
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
VarDataConst::VarDataConst(const VarDataConst &from, ULONG fieldOffset) :
|
||||
m_fieldOffset(from.m_fieldOffset + fieldOffset)
|
||||
, m_dataBuff(from.m_dataBuff)
|
||||
m_fieldOffset(from.m_fieldOffset + fieldOffset),
|
||||
m_value(from.m_value)
|
||||
{
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
//////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
} // end pykd namespace
|
||||
|
@ -75,16 +75,21 @@ protected:
|
||||
VarDataConst(SymbolPtr &symData);
|
||||
VarDataConst(const VarDataConst &from, ULONG fieldOffset);
|
||||
|
||||
template<typename T>
|
||||
void fillDataBuff(const T &data)
|
||||
{
|
||||
RtlCopyMemory( &m_dataBuff->at(0), &data, min(sizeof(T), m_dataBuff->size()) );
|
||||
}
|
||||
//template<typename T>
|
||||
//void fillDataBuff(const T &data)
|
||||
//{
|
||||
// RtlCopyMemory( &m_dataBuff->at(0), &data, min(sizeof(T), m_dataBuff->size()) );
|
||||
//}
|
||||
|
||||
private:
|
||||
|
||||
BaseTypeVariant m_value;
|
||||
ULONG m_fieldOffset;
|
||||
boost::shared_ptr< std::vector<UCHAR> > m_dataBuff;
|
||||
|
||||
//ULONG m_fieldOffset;
|
||||
//boost::shared_ptr< std::vector<UCHAR> > m_dataBuff;
|
||||
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -1,5 +1,7 @@
|
||||
#include "stdafx.h"
|
||||
|
||||
#include <boost\algorithm\string\case_conv.hpp>
|
||||
|
||||
#include "win/dbgeng.h"
|
||||
#include "dbgexcept.h"
|
||||
|
||||
@ -318,6 +320,21 @@ ULONG ptrSize()
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
bool is64bitSystem()
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
|
||||
hres = g_dbgEng->control->IsPointer64Bit();
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugControl::IsPointer64Bit failed" );
|
||||
|
||||
return hres == S_OK;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::string getSymbolByOffset( ULONG64 offset )
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
@ -344,8 +361,127 @@ std::string getSymbolByOffset( ULONG64 offset )
|
||||
return symbolName;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
};
|
||||
ULONG64 loadMSR( ULONG msr )
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
ULONG64 value;
|
||||
|
||||
hres = g_dbgEng->dataspace->ReadMsr( msr, &value );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugDataSpaces::ReadMsr", hres );
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void setMSR( ULONG msr, ULONG64 value)
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
|
||||
hres = g_dbgEng->dataspace->WriteMsr(msr, value);
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugDataSpaces::WriteMsr", hres );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ULONG getRegIndexByName( const std::string ®Name )
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
ULONG index;
|
||||
|
||||
hres = g_dbgEng->registers->GetIndexByName( boost::to_lower_copy(regName).c_str(), &index );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetIndexByName", hres );
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::string getRegNameByIndex( ULONG index )
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
|
||||
ULONG nameSize = 0;
|
||||
|
||||
hres =
|
||||
g_dbgEng->registers->GetDescription(
|
||||
index,
|
||||
NULL,
|
||||
0,
|
||||
&nameSize,
|
||||
NULL );
|
||||
|
||||
if ( nameSize == 0 )
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetDescription", hres );
|
||||
|
||||
std::vector<char> nameBuffer(nameSize);
|
||||
DEBUG_REGISTER_DESCRIPTION desc = {};
|
||||
|
||||
hres =
|
||||
g_dbgEng->registers->GetDescription(
|
||||
index,
|
||||
&nameBuffer[0],
|
||||
nameSize,
|
||||
NULL,
|
||||
&desc );
|
||||
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetDescription", hres );
|
||||
|
||||
return std::string( &nameBuffer[0] );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
BaseTypeVariant getRegVariantValue( ULONG index )
|
||||
{
|
||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||
|
||||
HRESULT hres;
|
||||
|
||||
DEBUG_VALUE debugValue;
|
||||
hres = g_dbgEng->registers->GetValue( index, &debugValue );
|
||||
if ( FAILED( hres ) )
|
||||
throw DbgException( "IDebugRegister::GetValue", hres );
|
||||
|
||||
switch( debugValue.Type )
|
||||
{
|
||||
case DEBUG_VALUE_INT8:
|
||||
return BaseTypeVariant( (LONG)debugValue.I8 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT16:
|
||||
return BaseTypeVariant( (LONG)debugValue.I16 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT32:
|
||||
return BaseTypeVariant( debugValue.I32 );
|
||||
break;
|
||||
|
||||
case DEBUG_VALUE_INT64:
|
||||
return BaseTypeVariant( debugValue.I64 );
|
||||
break;
|
||||
}
|
||||
|
||||
throw DbgException( "Failed to convert register value" );
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
} // end pykd namespace
|
||||
|
||||
|
||||
|
@ -23,6 +23,7 @@ public:
|
||||
CComQIPtr<IDebugSymbols3> symbols;
|
||||
CComQIPtr<IDebugDataSpaces4> dataspace;
|
||||
CComQIPtr<IDebugAdvanced2> advanced;
|
||||
CComQIPtr<IDebugRegisters2> registers;
|
||||
|
||||
DbgEngBind( PDEBUG_CLIENT4 c )
|
||||
{
|
||||
@ -32,6 +33,7 @@ public:
|
||||
symbols = c;
|
||||
dataspace = c;
|
||||
advanced = c;
|
||||
registers = c;
|
||||
}
|
||||
|
||||
PyThreadStateSaver pystate;
|
||||
|
@ -18,6 +18,7 @@ import memtest
|
||||
import moduletest
|
||||
import typeinfo
|
||||
import typedvar
|
||||
import regtest
|
||||
|
||||
def getTestSuite( singleName = "" ):
|
||||
if singleName == "":
|
||||
@ -29,6 +30,7 @@ def getTestSuite( singleName = "" ):
|
||||
unittest.TestLoader().loadTestsFromTestCase( memtest.MemoryTest ),
|
||||
unittest.TestLoader().loadTestsFromTestCase( typeinfo.TypeInfoTest ),
|
||||
unittest.TestLoader().loadTestsFromTestCase( typedvar.TypedVarTest ),
|
||||
unittest.TestLoader().loadTestsFromTestCase( regtest.CpuRegTest ),
|
||||
] )
|
||||
else:
|
||||
return unittest.TestSuite( unittest.TestLoader().loadTestsFromName( singleName ) )
|
||||
|
Loading…
Reference in New Issue
Block a user