[0.1.x] added : typeInfo и typedVar classes support enum types

git-svn-id: https://pykd.svn.codeplex.com/svn@72711 9b283d60-5439-405e-af05-b73fd8c4d996
This commit is contained in:
SND\kernelnet_cp 2011-12-27 08:32:50 +00:00 committed by Mikhail I. Izmestev
parent 8fd90cf647
commit fd6ed0769e
12 changed files with 242 additions and 19 deletions

View File

@ -447,7 +447,7 @@ BOOST_PYTHON_MODULE( pykd )
python::def( "waitForEvent", &waitForEvent, python::def( "waitForEvent", &waitForEvent,
"Wait for events that breaks into the debugger" ); "Wait for events that breaks into the debugger" );
python::class_<TypeInfo, TypeInfoPtr, boost::noncopyable >("typeInfo", "Class representing typeInfo", python::no_init ) python::class_<TypeInfo, TypeInfoPtr, python::bases<intBase>, boost::noncopyable >("typeInfo", "Class representing typeInfo", python::no_init )
.def( "name", &TypeInfo::getName ) .def( "name", &TypeInfo::getName )
.def( "size", &TypeInfo::getSize ) .def( "size", &TypeInfo::getSize )
.def( "offset", &TypeInfo::getOffset ) .def( "offset", &TypeInfo::getOffset )
@ -605,7 +605,7 @@ BOOST_PYTHON_MODULE( pykd )
"Retrieves the offset of the symbol location" ) "Retrieves the offset of the symbol location" )
.def( "count", &pyDia::Symbol::getCount, .def( "count", &pyDia::Symbol::getCount,
"Retrieves the number of items in a list or array" ) "Retrieves the number of items in a list or array" )
.def( "value", &pyDia::Symbol::getValue, .def( "value", (python::object(pyDia::Symbol::*)())&pyDia::Symbol::getValue,
"Retrieves the value of a constant") "Retrieves the value of a constant")
.def( "isBasic", &pyDia::Symbol::isBasicType, .def( "isBasic", &pyDia::Symbol::isBasicType,
"Retrieves a flag of basic type for symbol") "Retrieves a flag of basic type for symbol")

View File

@ -160,6 +160,13 @@ void Symbol::getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue)
throw Exception("Call IDiaSymbol::get_value", hres); throw Exception("Call IDiaSymbol::get_value", hres);
} }
void Symbol::getValue( VARIANT &vtValue)
{
HRESULT hres = m_symbol->get_value(&vtValue);
if (S_OK != hres)
throw Exception("Call IDiaSymbol::get_value", hres);
}
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
python::object Symbol::getValue() python::object Symbol::getValue()
@ -244,6 +251,13 @@ ULONG Symbol::getUdtKind()
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
ULONG Symbol::getDataKind()
{
return callSymbol(get_dataKind);
}
////////////////////////////////////////////////////////////////////////////////
ULONG Symbol::getRegisterId() ULONG Symbol::getRegisterId()
{ {
return callSymbol(get_registerId); return callSymbol(get_registerId);
@ -251,6 +265,13 @@ ULONG Symbol::getRegisterId()
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
bool Symbol::isConstant()
{
return !!callSymbol(get_constType);
}
////////////////////////////////////////////////////////////////////////////////
SymbolPtr Symbol::getChildByName(const std::string &_name) SymbolPtr Symbol::getChildByName(const std::string &_name)
{ {
DiaEnumSymbolsPtr symbols; DiaEnumSymbolsPtr symbols;

View File

@ -119,6 +119,7 @@ public:
static void getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue); static void getValueImpl(IDiaSymbol *_symbol, VARIANT &vtValue);
python::object getValue(); python::object getValue();
void getValue( VARIANT &vtValue);
bool isBasicType(); bool isBasicType();
@ -130,6 +131,8 @@ public:
ULONG getUdtKind(); ULONG getUdtKind();
ULONG getDataKind();
ULONG getRegisterId(); ULONG getRegisterId();
ULONG getMachineType() const { ULONG getMachineType() const {
@ -140,7 +143,11 @@ public:
ULONG getChildCount(); ULONG getChildCount();
SymbolPtr getChildByIndex(ULONG _index); SymbolPtr getChildByIndex(ULONG _index);
bool isConstant();
std::string print(); std::string print();
public: public:
typedef std::pair<ULONG, const char *> ValueNameEntry; typedef std::pair<ULONG, const char *> ValueNameEntry;

View File

@ -53,8 +53,8 @@ END
// //
VS_VERSION_INFO VERSIONINFO VS_VERSION_INFO VERSIONINFO
FILEVERSION 0,1,0,1 FILEVERSION 0,1,0,2
PRODUCTVERSION 0,1,0,1 PRODUCTVERSION 0,1,0,2
FILEFLAGSMASK 0x17L FILEFLAGSMASK 0x17L
#ifdef _DEBUG #ifdef _DEBUG
FILEFLAGS 0x1L FILEFLAGS 0x1L
@ -70,11 +70,11 @@ BEGIN
BLOCK "041904b0" BLOCK "041904b0"
BEGIN BEGIN
VALUE "FileDescription", "pykd - python extension for windbg" VALUE "FileDescription", "pykd - python extension for windbg"
VALUE "FileVersion", "0, 1, 0, 1" VALUE "FileVersion", "0, 1, 0, 2"
VALUE "InternalName", "pykd" VALUE "InternalName", "pykd"
VALUE "OriginalFilename", "pykd.dll" VALUE "OriginalFilename", "pykd.dll"
VALUE "ProductName", "pykd - python extension for windbg" VALUE "ProductName", "pykd - python extension for windbg"
VALUE "ProductVersion", "0, 1, 0, 1" VALUE "ProductVersion", "0, 1, 0, 2"
END END
END END
BLOCK "VarFileInfo" BLOCK "VarFileInfo"

View File

@ -41,6 +41,12 @@ TypedVarPtr TypedVar::getTypedVar( IDebugClient4 *client, const TypeInfoPtr& t
return tv; return tv;
} }
if ( typeInfo->isEnum() )
{
tv.reset( new EnumTypedVar( client, typeInfo, offset ) );
return tv;
}
throw DbgException( "can not create typedVar for this type" ); throw DbgException( "can not create typedVar for this type" );
return tv; return tv;
@ -161,4 +167,18 @@ BaseTypeVariant BitFieldVar::getValue()
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
BaseTypeVariant EnumTypedVar::getValue()
{
ULONG val = 0;
HRESULT hres;
hres = m_dataSpaces->ReadVirtual( m_offset, &val, m_typeInfo->getSize(), NULL );
if ( FAILED( hres ) )
throw MemoryException( m_offset, false );
return val;
};
///////////////////////////////////////////////////////////////////////////////////
} // end pykd namespace } // end pykd namespace

View File

@ -42,7 +42,7 @@ public:
} }
virtual std::string print() { virtual std::string print() {
return "TypeVar"; return "TypedVar";
} }
virtual ULONG getElementCount() { virtual ULONG getElementCount() {
@ -159,4 +159,15 @@ public:
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
class EnumTypedVar : public TypedVar {
public:
EnumTypedVar( IDebugClient4 *client, const TypeInfoPtr& typeInfo, ULONG64 offset ) : TypedVar(client, typeInfo, offset){}
virtual BaseTypeVariant getValue();
};
///////////////////////////////////////////////////////////////////////////////////
} // namespace pykd } // namespace pykd

View File

@ -23,6 +23,9 @@ TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &typeSym )
case SymTagPointerType: case SymTagPointerType:
return TypeInfoPtr( new PointerTypeInfo( typeSym ) ); return TypeInfoPtr( new PointerTypeInfo( typeSym ) );
case SymTagEnum:
return TypeInfoPtr( new EnumTypeInfo( typeSym ) );
} }
throw DbgException( "type name invalid" ); throw DbgException( "type name invalid" );
@ -30,9 +33,47 @@ TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &typeSym )
///////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////
BaseTypeVariant TypeInfo::getValue()
{
if ( !m_constant )
throw DbgException( "The 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 DbgException( "Failed to convert constatnt type" );
}
/////////////////////////////////////////////////////////////////////////////////////
TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &symScope, const std::string &symName ) TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &symScope, const std::string &symName )
{ {
size_t pos = symName.find_first_of( "*[" ); size_t pos = symName.find_first_of( "*[" );
CComVariant constVal;
if ( pos == std::string::npos ) if ( pos == std::string::npos )
{ {
@ -49,10 +90,19 @@ TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &symScope, const std::strin
return TypeInfoPtr( new BitFieldTypeInfo(typeSym) ); return TypeInfoPtr( new BitFieldTypeInfo(typeSym) );
} }
if ( typeSym->getDataKind() == DataIsConstant )
{
typeSym->getValue( constVal );
}
typeSym = typeSym->getType(); typeSym = typeSym->getType();
} }
return getTypeInfo( typeSym ); TypeInfoPtr ptr = getTypeInfo( typeSym );
ptr->setConstant( constVal );
return ptr;
} }
return getComplexType( symScope, symName ); return getComplexType( symScope, symName );
@ -60,7 +110,7 @@ TypeInfoPtr TypeInfo::getTypeInfo( pyDia::SymbolPtr &symScope, const std::strin
///////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////
static const boost::regex baseMatch("^(Char)|(WChar)|(Int2B)|(UInt2B)|(Int4B)|(UInt4B)|(Int8B)|(UInt8B)|(Long)|(ULong)|(Float)|(Bool)$" ); static const boost::regex baseMatch("^(Char)|(WChar)|(Int2B)|(UInt2B)|(Int4B)|(UInt4B)|(Int8B)|(UInt8B)|(Long)|(ULong)|(Float)|(Bool)|(Double)$" );
TypeInfoPtr TypeInfoPtr
TypeInfo::getBaseTypeInfo( const std::string &symName ) TypeInfo::getBaseTypeInfo( const std::string &symName )
@ -104,6 +154,9 @@ TypeInfo::getBaseTypeInfo( const std::string &symName )
if ( baseMatchResult[12].matched ) if ( baseMatchResult[12].matched )
return TypeInfoPtr( new TypeInfoWrapper<bool>("Bool") ); return TypeInfoPtr( new TypeInfoWrapper<bool>("Bool") );
if ( baseMatchResult[13].matched )
return TypeInfoPtr( new TypeInfoWrapper<double>("Double") );
} }
return TypeInfoPtr(); return TypeInfoPtr();
@ -124,6 +177,11 @@ TypeInfo::getBaseTypeInfo( pyDia::SymbolPtr &symbol )
return getBaseTypeInfo( sstr.str() ); return getBaseTypeInfo( sstr.str() );
} }
if ( symName == "Float" && symbol->getSize() == 8 )
{
symName = "Double";
}
return getBaseTypeInfo( symName ); return getBaseTypeInfo( symName );
} }

View File

@ -3,6 +3,7 @@
#include <string> #include <string>
#include "diawrapper.h" #include "diawrapper.h"
#include "intbase.h"
namespace pykd { namespace pykd {
@ -13,7 +14,7 @@ typedef boost::shared_ptr<TypeInfo> TypeInfoPtr;
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
class TypeInfo : boost::noncopyable { class TypeInfo : boost::noncopyable, public intBase {
public: public:
@ -36,9 +37,11 @@ public:
virtual ULONG getSize() = 0; virtual ULONG getSize() = 0;
virtual TypeInfoPtr getField( const std::string &fieldName ) { virtual TypeInfoPtr getField( const std::string &fieldName ) {
throw DbgException( "there is no fields" ); throw DbgException( "there is no fields" );
} }
virtual BaseTypeVariant getValue();
virtual bool isBasicType() { virtual bool isBasicType() {
return false; return false;
} }
@ -59,6 +62,10 @@ public:
return false; return false;
} }
virtual bool isEnum() {
return false;
}
virtual ULONG getCount() { virtual ULONG getCount() {
throw DbgException( "there is no element" ); throw DbgException( "there is no element" );
} }
@ -84,6 +91,12 @@ public:
m_offset = offset; m_offset = offset;
} }
void setConstant( const VARIANT& var )
{
m_constant = true;
m_constantValue = var;
}
protected: protected:
std::string getComplexName(); std::string getComplexName();
@ -95,6 +108,10 @@ protected:
TypeInfoPtr getRecurciveComplexType( TypeInfoPtr &lowestType, std::string &suffix, ULONG ptrSize ); TypeInfoPtr getRecurciveComplexType( TypeInfoPtr &lowestType, std::string &suffix, ULONG ptrSize );
ULONG m_offset; ULONG m_offset;
bool m_constant;
VARIANT m_constantValue;
}; };
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
@ -198,7 +215,41 @@ protected:
pyDia::SymbolPtr m_dia; pyDia::SymbolPtr m_dia;
}; };
///////////////////////////////////////////////////////////////////////////////////
class EnumTypeInfo : public TypeInfo
{
public:
EnumTypeInfo ( pyDia::SymbolPtr &symbol ) :
m_dia( symbol )
{}
protected:
virtual std::string getName() {
return m_dia->getName();
}
virtual ULONG getSize() {
return (ULONG)m_dia->getSize();
}
virtual TypeInfoPtr getField( const std::string &fieldName ) {
pyDia::SymbolPtr field = m_dia->getChildByName( fieldName );
TypeInfoPtr ti = TypeInfo::getTypeInfo( m_dia, fieldName );
ti->setOffset( 0 );
return ti;
}
virtual bool isEnum() {
return true;
}
pyDia::SymbolPtr m_dia;
};
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
class PointerTypeInfo : public TypeInfo { class PointerTypeInfo : public TypeInfo {

View File

@ -33,6 +33,7 @@ class IntBaseTest( unittest.TestCase ):
self.assertTrue( True == intBase(True) ) self.assertTrue( True == intBase(True) )
self.assertTrue( False == intBase(0) ) self.assertTrue( False == intBase(0) )
self.assertTrue( True == intBase(1) ) self.assertTrue( True == intBase(1) )
self.assertTrue( intBase(1) == intBase(1) )
def testNe( self ): def testNe( self ):
self.assertTrue( 0xFE != intBase(0xFF) ) self.assertTrue( 0xFE != intBase(0xFF) )
@ -43,7 +44,8 @@ class IntBaseTest( unittest.TestCase ):
self.assertTrue( -20 + 1 != intBase(-20) ) self.assertTrue( -20 + 1 != intBase(-20) )
self.assertTrue( -2000 + 1 != intBase(-2000) ) self.assertTrue( -2000 + 1 != intBase(-2000) )
self.assertTrue( -20000000000 + 1 != intBase(-20000000000) ) self.assertTrue( -20000000000 + 1 != intBase(-20000000000) )
self.assertTrue( -0x8000000000000000 - 1 != intBase(-0x8000000000000000) ) self.assertTrue( -0x8000000000000000 - 1 != intBase(-0x8000000000000000) )
self.assertTrue( intBase(1) != intBase(2) )
def testLtGt( self ): def testLtGt( self ):
self.assertTrue( 0xFE < intBase(0xFF) and intBase(0xFE) < 0xFF ) self.assertTrue( 0xFE < intBase(0xFF) and intBase(0xFE) < 0xFF )
@ -51,6 +53,7 @@ class IntBaseTest( unittest.TestCase ):
self.assertTrue( 0xFFFFFFFFFFFFFFFE < intBase(0xFFFFFFFFFFFFFFFF) ) self.assertTrue( 0xFFFFFFFFFFFFFFFE < intBase(0xFFFFFFFFFFFFFFFF) )
self.assertFalse(0xFFFFFFFFFFFFFFFF < intBase(0xFFFFFFFFFFFFFFFE) ) self.assertFalse(0xFFFFFFFFFFFFFFFF < intBase(0xFFFFFFFFFFFFFFFE) )
self.assertTrue( intBase(0xFFFFFFFFFFFFFFFE) < 0xFFFFFFFFFFFFFFFF ) self.assertTrue( intBase(0xFFFFFFFFFFFFFFFE) < 0xFFFFFFFFFFFFFFFF )
self.assertTrue( intBase(1) < intBase(2) )
def testLeGe( self ): def testLeGe( self ):
self.assertTrue( 0xFE <= intBase(0xFF) and intBase(0xFE) <= 0xFF ) self.assertTrue( 0xFE <= intBase(0xFF) and intBase(0xFE) <= 0xFF )
@ -59,6 +62,7 @@ class IntBaseTest( unittest.TestCase ):
self.assertTrue( 0xFFFFFFFFFFFFFFFE <= intBase(0xFFFFFFFFFFFFFFFF) ) self.assertTrue( 0xFFFFFFFFFFFFFFFE <= intBase(0xFFFFFFFFFFFFFFFF) )
self.assertFalse(0xFFFFFFFFFFFFFFFF <= intBase(0xFFFFFFFFFFFFFFFE) ) self.assertFalse(0xFFFFFFFFFFFFFFFF <= intBase(0xFFFFFFFFFFFFFFFE) )
self.assertTrue( intBase(0xFFFFFFFFFFFFFFFF) <= 0xFFFFFFFFFFFFFFFF ) self.assertTrue( intBase(0xFFFFFFFFFFFFFFFF) <= 0xFFFFFFFFFFFFFFFF )
self.assertFalse( intBase(1) >= intBase(2) )
def testAdd( self ): def testAdd( self ):
self.assertEqual( 10, intBase(5) + 5 ) self.assertEqual( 10, intBase(5) + 5 )
@ -71,6 +75,7 @@ class IntBaseTest( unittest.TestCase ):
self.assertEqual( 0x7fffffffffffffff + 1, intBase(0x7fffffffffffffff) + 1) self.assertEqual( 0x7fffffffffffffff + 1, intBase(0x7fffffffffffffff) + 1)
self.assertEqual( -0x8000000000000000 + 10, intBase(-0x8000000000000000) + 10 ) self.assertEqual( -0x8000000000000000 + 10, intBase(-0x8000000000000000) + 10 )
self.assertEqual( 0, intBase(-0x8000000000000000) + 0x8000000000000000 ) self.assertEqual( 0, intBase(-0x8000000000000000) + 0x8000000000000000 )
self.assertEqual( 5, intBase(3) + intBase(2) )
def testSub( self ): def testSub( self ):
self.assertEqual( 0, intBase(5) - 5 ) self.assertEqual( 0, intBase(5) - 5 )
@ -81,6 +86,7 @@ class IntBaseTest( unittest.TestCase ):
self.assertEqual( -20, intBase(-10) -10 ) self.assertEqual( -20, intBase(-10) -10 )
self.assertEqual( -10, 10 - intBase(20) ) self.assertEqual( -10, 10 - intBase(20) )
self.assertEqual( -0xFFFFFFFF - 1, intBase(-0xFFFFFFFF) - 1 ) self.assertEqual( -0xFFFFFFFF - 1, intBase(-0xFFFFFFFF) - 1 )
self.assertEqual( 5, intBase(7) - intBase(2) )
def testMul( self ): def testMul( self ):
self.assertEqual( 4, intBase(2) * 2 ) self.assertEqual( 4, intBase(2) * 2 )
@ -90,12 +96,14 @@ class IntBaseTest( unittest.TestCase ):
self.assertEqual( 0x7fffffffffffffff * 2, intBase(0x7fffffffffffffff) * 2) self.assertEqual( 0x7fffffffffffffff * 2, intBase(0x7fffffffffffffff) * 2)
self.assertEqual( 0x80000000*2, intBase(0x80000000)*2 ) self.assertEqual( 0x80000000*2, intBase(0x80000000)*2 )
self.assertEqual( -0x80000000*2, 2 * intBase(-0x80000000)) self.assertEqual( -0x80000000*2, 2 * intBase(-0x80000000))
self.assertEqual( 14, intBase(7)*intBase(2) )
def testDiv( self ): def testDiv( self ):
self.assertEqual( 1, intBase(2) / 2 ) self.assertEqual( 1, intBase(2) / 2 )
self.assertEqual( 2, 5 / intBase(2) ) self.assertEqual( 2, 5 / intBase(2) )
self.assertEqual( -1, 2 / intBase(-2) ) self.assertEqual( -1, 2 / intBase(-2) )
self.assertEqual( 1, -2 / intBase(-2) ) self.assertEqual( 1, -2 / intBase(-2) )
self.assertEqual( 3, intBase(7)/intBase(2) )
try: try:
-2 / intBase(0) -2 / intBase(0)
@ -109,11 +117,18 @@ class IntBaseTest( unittest.TestCase ):
except ZeroDivisionError: except ZeroDivisionError:
self.assertTrue( True ) self.assertTrue( True )
try:
intBase(0)/intBase(0)
self.assertTrue( False )
except ZeroDivisionError:
self.assertTrue( True )
def testMod( self ): def testMod( self ):
self.assertEqual( 1, intBase(3) % 2 ) self.assertEqual( 1, intBase(3) % 2 )
self.assertEqual( 0, intBase(3) % 3 ) self.assertEqual( 0, intBase(3) % 3 )
self.assertEqual( 1, 3 % intBase(2) ) self.assertEqual( 1, 3 % intBase(2) )
self.assertEqual( 0, 3 % intBase(3) ) self.assertEqual( 0, 3 % intBase(3) )
self.assertEqual( 2, intBase(5) % intBase(3) )
def testShift( self ): def testShift( self ):
self.assertEqual( 0xFFFFFFFF >> 8, intBase(0xFFFFFFFF) >> 8 ) self.assertEqual( 0xFFFFFFFF >> 8, intBase(0xFFFFFFFF) >> 8 )

View File

@ -100,3 +100,15 @@ class TypedVarTest( unittest.TestCase ):
self.assertEqual( 2, len( tvl ) ) self.assertEqual( 2, len( tvl ) )
self.assertEqual( 1, tvl[0].m_field3 ) self.assertEqual( 1, tvl[0].m_field3 )
self.assertEqual( 0, tvl[1].m_field4 ) self.assertEqual( 0, tvl[1].m_field4 )
def testEqual(self):
tv1 = target.module.typedVar("g_structTest")
tv2 = target.module.typedVar("intMatrix")
self.assertEqual( tv1.m_field3, tv2[0][1] )
def testEnum(self):
tv = target.module.typedVar("g_classChild")
self.assertEqual( 3, tv.m_enumField )
self.assertEqual( target.module.type("enumType").THREE, tv.m_enumField )

View File

@ -76,5 +76,17 @@ class TypeInfoTest( unittest.TestCase ):
self.assertEqual( "ULong:2", ti.m_bit6_7.name() ) self.assertEqual( "ULong:2", ti.m_bit6_7.name() )
self.assertEqual( 2, ti.m_bit6_7.bitWidth() ) self.assertEqual( 2, ti.m_bit6_7.bitWidth() )
self.assertEqual( 6, ti.m_bit6_7.bitOffset() ) self.assertEqual( 6, ti.m_bit6_7.bitOffset() )
def testEnum(self):
ti = target.module.type("enumType")
self.assertTrue( hasattr( ti, "TWO" ) )
self.assertEqual( 4, ti.TWO.size() )
ti = target.module.type("classChild")
self.assertEqual( "enumType", ti.m_enumField.name() )
def testUnion(self):
ti = target.module.type("unionTest")
self.assertEqual( 0, ti.m_doubleValue.offset() )
self.assertEqual( 0, ti.m_bits.offset() )
self.assertEqual( ti.size(), ti.m_doubleValue.size() )

View File

@ -28,6 +28,7 @@ struct structWithBits {
union unionTest { union unionTest {
ULONG m_value; ULONG m_value;
double m_doubleValue;
structWithBits m_bits; structWithBits m_bits;
}; };
@ -84,16 +85,30 @@ int ((*ptrIntMatrix1))[2][3] = &intMatrix;
char *(*ptrStrArray)[2] = &strArray; char *(*ptrStrArray)[2] = &strArray;
enum enumType {
ONE = 1,
TWO = 2,
THREE = 3
};
class classChild : public classBase { class classChild : public classBase {
public: public:
int m_childField; int m_childField;
int m_childField2; int m_childField2;
structTest m_childField3; structTest m_childField3;
enumType m_enumField;
void childMethod() const {} void childMethod() const {}
virtual void virtFunc() {} virtual void virtFunc() {}
virtual void virtFunc2() {} virtual void virtFunc2() {}
classChild() :
m_enumField( THREE )
{}
}; };
classChild g_classChild;
struct struct2 { struct struct2 {
structTest m_struct; structTest m_struct;
unionTest m_union; unionTest m_union;
@ -184,6 +199,7 @@ void FuncWithName0()
std::cout << g_structTest1.m_field2; std::cout << g_structTest1.m_field2;
std::cout << ptrIntMatrix1; std::cout << ptrIntMatrix1;
std::cout << g_bigValue; std::cout << g_bigValue;
std::cout << g_classChild.m_enumField;
} }
void FuncWithName1(int a) void FuncWithName1(int a)