mirror of
https://github.com/ivellioscolin/pykd.git
synced 2025-04-20 03:23:23 +08:00
[0.2.x] updated: getting local vars by index
git-svn-id: https://pykd.svn.codeplex.com/svn@82027 9b283d60-5439-405e-af05-b73fd8c4d996
This commit is contained in:
parent
4021a60d2d
commit
a718ec6716
@ -69,8 +69,8 @@ struct STACK_FRAME_DESC {
|
|||||||
ULONG64 stackOffset;
|
ULONG64 stackOffset;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
void getCurrentFrame(STACK_FRAME_DESC &frame );
|
||||||
void getStackTrace(std::vector<STACK_FRAME_DESC> &frames);
|
void getStackTrace(std::vector<STACK_FRAME_DESC> &frames);
|
||||||
|
|
||||||
void getStackTraceWow64(std::vector<STACK_FRAME_DESC> &frames);
|
void getStackTraceWow64(std::vector<STACK_FRAME_DESC> &frames);
|
||||||
|
|
||||||
// callback events
|
// callback events
|
||||||
|
@ -347,6 +347,167 @@ ULONG StackFrame::getParamCount()
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
python::object StackFrame::getLocalByIndex( ULONG index )
|
||||||
|
{
|
||||||
|
ModulePtr mod = Module::loadModuleByOffset( m_instructionOffset);
|
||||||
|
|
||||||
|
LONG displacemnt;
|
||||||
|
SymbolPtr func = mod->getSymbolByVa( m_instructionOffset, SymTagFunction, &displacemnt );
|
||||||
|
|
||||||
|
#ifdef _DEBUG
|
||||||
|
std::string funcName;
|
||||||
|
funcName = func->getName();
|
||||||
|
#endif // _DEBUG
|
||||||
|
|
||||||
|
if (!IsInDebugRange(func, static_cast<ULONG>( m_instructionOffset - mod->getBase())))
|
||||||
|
{
|
||||||
|
throw DbgException("is not debug range");
|
||||||
|
}
|
||||||
|
|
||||||
|
// find var in current scope
|
||||||
|
SymbolPtrList symList = func->findChildren(SymTagData);
|
||||||
|
SymbolPtrList::iterator itVar = symList.begin();
|
||||||
|
SymbolPtr symVar;
|
||||||
|
ULONG i = 0;
|
||||||
|
for (; itVar != symList.end(); ++itVar, ++i)
|
||||||
|
{
|
||||||
|
if ( i == index )
|
||||||
|
{
|
||||||
|
symVar = *itVar;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( itVar == symList.end() )
|
||||||
|
{
|
||||||
|
// find inners scopes
|
||||||
|
SymbolPtrList scopeList = func->findChildren(SymTagBlock);
|
||||||
|
SymbolPtrList::iterator itScope = scopeList.begin();
|
||||||
|
|
||||||
|
ULONG ipRva = static_cast<ULONG>( m_instructionOffset - mod->getBase());
|
||||||
|
|
||||||
|
for (; itScope != scopeList.end() && !symVar; ++itScope)
|
||||||
|
{
|
||||||
|
SymbolPtr scope = *itScope;
|
||||||
|
ULONG scopeRva = scope->getRva();
|
||||||
|
if (scopeRva <= ipRva && (scopeRva + scope->getSize()) > ipRva)
|
||||||
|
{
|
||||||
|
SymbolPtrList symList = scope->findChildren(SymTagData);
|
||||||
|
SymbolPtrList::iterator itVar = symList.begin();
|
||||||
|
|
||||||
|
for (; itVar != symList.end(); ++itVar, ++i)
|
||||||
|
{
|
||||||
|
if ( i == index )
|
||||||
|
{
|
||||||
|
symVar = *itVar;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !symVar )
|
||||||
|
throw DbgException("local var not found");
|
||||||
|
|
||||||
|
ULONG64 varAddr;
|
||||||
|
const LocationType locType = static_cast<LocationType>(symVar->getLocType());
|
||||||
|
switch (locType)
|
||||||
|
{
|
||||||
|
case LocIsStatic:
|
||||||
|
varAddr = mod->getBase() + symVar->getRva();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case LocIsRegRel:
|
||||||
|
{
|
||||||
|
RegRealativeId rri;
|
||||||
|
rri = static_cast<RegRealativeId>(symVar->getRegRealativeId());
|
||||||
|
varAddr = getValue(rri, symVar->getOffset());
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
BOOST_ASSERT(LocIsEnregistered == locType);
|
||||||
|
throw DbgException("");
|
||||||
|
}
|
||||||
|
|
||||||
|
TypeInfoPtr typeInfo = TypeInfo::getTypeInfo(symVar);
|
||||||
|
TypedVarPtr typedVar = TypedVar::getTypedVarByTypeInfo(typeInfo, varAddr);
|
||||||
|
typedVar->setDataKind( symVar->getDataKind() );
|
||||||
|
|
||||||
|
return python::object( typedVar );
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
python::object StackFrame::getParamByIndex( ULONG index )
|
||||||
|
{
|
||||||
|
ModulePtr mod = Module::loadModuleByOffset( m_instructionOffset);
|
||||||
|
|
||||||
|
LONG displacemnt;
|
||||||
|
SymbolPtr func = mod->getSymbolByVa( m_instructionOffset, SymTagFunction, &displacemnt );
|
||||||
|
|
||||||
|
#ifdef _DEBUG
|
||||||
|
std::string funcName;
|
||||||
|
funcName = func->getName();
|
||||||
|
#endif // _DEBUG
|
||||||
|
|
||||||
|
if (!IsInDebugRange(func, static_cast<ULONG>( m_instructionOffset - mod->getBase())))
|
||||||
|
{
|
||||||
|
throw DbgException("is not debug range");
|
||||||
|
}
|
||||||
|
|
||||||
|
// find var in current scope
|
||||||
|
SymbolPtrList symList = func->findChildren(SymTagData);
|
||||||
|
SymbolPtrList::iterator itVar = symList.begin();
|
||||||
|
SymbolPtr symVar;
|
||||||
|
for ( ULONG i = 0; itVar != symList.end(); ++itVar )
|
||||||
|
{
|
||||||
|
if ( (*itVar)->getDataKind() == DataIsParam )
|
||||||
|
{
|
||||||
|
if ( i == index )
|
||||||
|
{
|
||||||
|
symVar = *itVar;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !symVar )
|
||||||
|
throw DbgException("local var not found");
|
||||||
|
|
||||||
|
ULONG64 varAddr;
|
||||||
|
const LocationType locType = static_cast<LocationType>(symVar->getLocType());
|
||||||
|
switch (locType)
|
||||||
|
{
|
||||||
|
case LocIsStatic:
|
||||||
|
varAddr = mod->getBase() + symVar->getRva();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case LocIsRegRel:
|
||||||
|
{
|
||||||
|
RegRealativeId rri;
|
||||||
|
rri = static_cast<RegRealativeId>(symVar->getRegRealativeId());
|
||||||
|
varAddr = getValue(rri, symVar->getOffset());
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
BOOST_ASSERT(LocIsEnregistered == locType);
|
||||||
|
throw DbgException("");
|
||||||
|
}
|
||||||
|
|
||||||
|
TypeInfoPtr typeInfo = TypeInfo::getTypeInfo(symVar);
|
||||||
|
TypedVarPtr typedVar = TypedVar::getTypedVarByTypeInfo(typeInfo, varAddr);
|
||||||
|
typedVar->setDataKind( symVar->getDataKind() );
|
||||||
|
|
||||||
|
return python::object( typedVar );
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
python::list getCurrentStack()
|
python::list getCurrentStack()
|
||||||
{
|
{
|
||||||
std::vector<STACK_FRAME_DESC> frames;
|
std::vector<STACK_FRAME_DESC> frames;
|
||||||
@ -385,9 +546,9 @@ python::list getCurrentStackWow64()
|
|||||||
|
|
||||||
StackFramePtr getCurrentStackFrame()
|
StackFramePtr getCurrentStackFrame()
|
||||||
{
|
{
|
||||||
std::vector<STACK_FRAME_DESC> frames;
|
STACK_FRAME_DESC frame;
|
||||||
getStackTrace( frames );
|
getCurrentFrame( frame );
|
||||||
return StackFramePtr( new StackFrame( frames[0] ) );
|
return StackFramePtr( new StackFrame( frame ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
@ -46,13 +46,9 @@ public:
|
|||||||
|
|
||||||
python::object getParamByName( const std::string& name );
|
python::object getParamByName( const std::string& name );
|
||||||
|
|
||||||
python::object getLocalByIndex( ULONG index ){
|
python::object getLocalByIndex( ULONG index );
|
||||||
return python::long_(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
python::object getParamByIndex( ULONG index ){
|
python::object getParamByIndex( ULONG index );
|
||||||
return python::long_(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
@ -126,7 +122,7 @@ private:
|
|||||||
}
|
}
|
||||||
|
|
||||||
python::object getVarByIndex(ULONG index) const {
|
python::object getVarByIndex(ULONG index) const {
|
||||||
return python::long_(0L);
|
return m_frame->getParamByIndex(index);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -863,6 +863,33 @@ static void buildStacksFrames(
|
|||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
void getCurrentFrame(STACK_FRAME_DESC &frame )
|
||||||
|
{
|
||||||
|
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||||
|
|
||||||
|
HRESULT hres;
|
||||||
|
|
||||||
|
frame.number = 0;
|
||||||
|
|
||||||
|
hres = g_dbgEng->registers->GetInstructionOffset2( DEBUG_REGSRC_FRAME, &frame.instructionOffset );
|
||||||
|
if ( FAILED(hres) )
|
||||||
|
throw DbgException( "IDebugRegisters2::GetInstructionOffset2", hres );
|
||||||
|
|
||||||
|
hres = g_dbgEng->control->GetReturnOffset( &frame.returnOffset );
|
||||||
|
if ( FAILED(hres) )
|
||||||
|
throw DbgException( "IDebugControl::GetReturnOffset", hres );
|
||||||
|
|
||||||
|
hres = g_dbgEng->registers->GetFrameOffset2( DEBUG_REGSRC_FRAME, &frame.frameOffset );
|
||||||
|
if ( FAILED(hres) )
|
||||||
|
throw DbgException( "IDebugRegisters2::GetFrameOffset2", hres );
|
||||||
|
|
||||||
|
hres = g_dbgEng->registers->GetStackOffset2( DEBUG_REGSRC_FRAME, &frame.stackOffset );
|
||||||
|
if ( FAILED(hres) )
|
||||||
|
throw DbgException( "IDebugRegisters2::GetStackOffset2", hres );
|
||||||
|
}
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void getStackTrace(std::vector<STACK_FRAME_DESC> &frames)
|
void getStackTrace(std::vector<STACK_FRAME_DESC> &frames)
|
||||||
{
|
{
|
||||||
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
PyThread_StateRestore pyThreadRestore( g_dbgEng->pystate );
|
||||||
|
@ -23,6 +23,7 @@ def testEnumWindowsProc1Locals(testCase, locals):
|
|||||||
testCase.assertEqual( DataIsStaticLocal, locals["staticVar"].dataKind() )
|
testCase.assertEqual( DataIsStaticLocal, locals["staticVar"].dataKind() )
|
||||||
|
|
||||||
testCase.assertEqual( locals["dwProccessId"] + 1, locals["staticVar"] )
|
testCase.assertEqual( locals["dwProccessId"] + 1, locals["staticVar"] )
|
||||||
|
|
||||||
|
|
||||||
class LocalVarsTest(unittest.TestCase):
|
class LocalVarsTest(unittest.TestCase):
|
||||||
def testLocalVariable(self):
|
def testLocalVariable(self):
|
||||||
@ -41,3 +42,8 @@ class LocalVarsTest(unittest.TestCase):
|
|||||||
locals = pykd.getLocals()
|
locals = pykd.getLocals()
|
||||||
self.assertEqual( len(locals), 2 )
|
self.assertEqual( len(locals), 2 )
|
||||||
self.assertTrue( locals[0] == 7 or locals[1] == 7 )
|
self.assertTrue( locals[0] == 7 or locals[1] == 7 )
|
||||||
|
|
||||||
|
funcParams = pykd.getParams()
|
||||||
|
self.assertEqual( len(funcParams), 2 )
|
||||||
|
self.assertTrue( funcParams[0] == 7 or funcParams[1] == 7 )
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user