1
0
Fork 0

Moved “zydis_wrapper” into root repo

- Instead, we directly use Zydis as a submodule now
This commit is contained in:
Joel Höner 2017-09-23 21:44:18 +02:00 committed by Duncan Ogilvie
parent da0d4415e3
commit ca9401fdb7
21 changed files with 1505 additions and 271 deletions

6
.gitmodules vendored
View File

@ -10,6 +10,6 @@
[submodule "deps"]
path = deps
url = https://github.com/x64dbg/deps
[submodule "src/zydis_wrapper"]
path = src/zydis_wrapper
url = https://athre0z@github.com/athre0z/zydis-x64dbg-module.git
[submodule "src/zydis_wrapper/zydis"]
path = src/zydis_wrapper/zydis
url = https://github.com/zyantific/zydis.git

View File

@ -389,13 +389,13 @@
<LinkIncremental>false</LinkIncremental>
<OutDir>$(ProjectDir)..\..\bin\x64\</OutDir>
<TargetName>x64dbg</TargetName>
<IncludePath>$(ProjectDir)..\zydis_wrapper;$(ProjectDir)..\capstone_wrapper;$(ProjectDir);$(ProjectDir)analysis;$(ProjectDir)commands;$(IncludePath)</IncludePath>
<IncludePath>$(ProjectDir)..\zydis_wrapper;$(ProjectDir)..\zydis_wrapper\zydis\include;$(ProjectDir)..\capstone_wrapper;$(ProjectDir);$(ProjectDir)analysis;$(ProjectDir)commands;$(IncludePath)</IncludePath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<LinkIncremental>false</LinkIncremental>
<OutDir>$(ProjectDir)..\..\bin\x64d\</OutDir>
<TargetName>x64dbg</TargetName>
<IncludePath>$(ProjectDir)..\zydis_wrapper;$(ProjectDir)..\capstone_wrapper;$(ProjectDir);$(ProjectDir)analysis;$(ProjectDir)commands;$(IncludePath)</IncludePath>
<IncludePath>$(ProjectDir)..\zydis_wrapper;$(ProjectDir)..\zydis_wrapper\zydis\include;$(ProjectDir)..\capstone_wrapper;$(ProjectDir);$(ProjectDir)analysis;$(ProjectDir)commands;$(IncludePath)</IncludePath>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
@ -467,7 +467,7 @@
<SubSystem>Windows</SubSystem>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<AdditionalDependencies>$(ProjectDir)..\zydis_wrapper\bin\x64\zydis_wrapper.lib;$(ProjectDir)..\zydis_wrapper\Zydis\Zydis_x64.lib;$(ProjectDir)..\capstone_wrapper\bin\x64\capstone_wrapper.lib;$(ProjectDir)..\capstone_wrapper\capstone\capstone_x64.lib;ntdll\ntdll_x64.lib;keystone\keystone_x64.lib;yara\yara_x64.lib;lz4\lz4_x64.lib;jansson\jansson_x64.lib;DeviceNameResolver\DeviceNameResolver_x64.lib;XEDParse\XEDParse_x64.lib;$(SolutionDir)bin\x64\x64bridge.lib;dbghelp\dbghelp_x64.lib;TitanEngine\TitanEngine_x64.lib;ws2_32.lib;psapi.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;shlwapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalDependencies>$(ProjectDir)..\zydis_wrapper\bin\x64\zydis_wrapper.lib;$(ProjectDir)..\capstone_wrapper\bin\x64\capstone_wrapper.lib;$(ProjectDir)..\capstone_wrapper\capstone\capstone_x64.lib;ntdll\ntdll_x64.lib;keystone\keystone_x64.lib;yara\yara_x64.lib;lz4\lz4_x64.lib;jansson\jansson_x64.lib;DeviceNameResolver\DeviceNameResolver_x64.lib;XEDParse\XEDParse_x64.lib;$(SolutionDir)bin\x64\x64bridge.lib;dbghelp\dbghelp_x64.lib;TitanEngine\TitanEngine_x64.lib;ws2_32.lib;psapi.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;shlwapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
@ -491,7 +491,7 @@
<SubSystem>Windows</SubSystem>
<EnableCOMDATFolding>false</EnableCOMDATFolding>
<OptimizeReferences>false</OptimizeReferences>
<AdditionalDependencies>$(ProjectDir)..\zydis_wrapper\bin\x64d\zydis_wrapper.lib;$(ProjectDir)..\zydis_wrapper\Zydis\Zydis_x64.lib;$(ProjectDir)..\capstone_wrapper\bin\x64d\capstone_wrapper.lib;$(ProjectDir)..\capstone_wrapper\capstone\capstone_x64.lib;ntdll\ntdll_x64.lib;keystone\keystone_x64.lib;yara\yara_x64.lib;lz4\lz4_x64.lib;jansson\jansson_x64.lib;DeviceNameResolver\DeviceNameResolver_x64.lib;XEDParse\XEDParse_x64.lib;$(SolutionDir)bin\x64d\x64bridge.lib;dbghelp\dbghelp_x64.lib;TitanEngine\TitanEngine_x64.lib;ws2_32.lib;psapi.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;shlwapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalDependencies>$(ProjectDir)..\zydis_wrapper\bin\x64d\zydis_wrapper.lib;$(ProjectDir)..\capstone_wrapper\bin\x64d\capstone_wrapper.lib;$(ProjectDir)..\capstone_wrapper\capstone\capstone_x64.lib;ntdll\ntdll_x64.lib;keystone\keystone_x64.lib;yara\yara_x64.lib;lz4\lz4_x64.lib;jansson\jansson_x64.lib;DeviceNameResolver\DeviceNameResolver_x64.lib;XEDParse\XEDParse_x64.lib;$(SolutionDir)bin\x64d\x64bridge.lib;dbghelp\dbghelp_x64.lib;TitanEngine\TitanEngine_x64.lib;ws2_32.lib;psapi.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;shlwapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
</Link>
</ItemDefinitionGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />

View File

@ -1549,6 +1549,8 @@ Instruction_t Disassembly::DisassembleAt(dsint rva)
goto _exit;
if (cs_instr.instStr.startsWith("fstp")) // CS reports 3 operands but only prints 2 ... wat.
goto _exit;
if (cs_instr.instStr.startsWith("fnstsw")) // CS reports wrong 32 bit operand size (is 16)
goto _exit;
auto insn_hex = cs_instr.dump.toHex().toStdString();
auto cs = cs_instr.instStr.toStdString();

View File

@ -190,7 +190,7 @@ Instruction_t CsQBeaEngine::DisassembleAt(byte_t* data, duint size, duint origBa
return DecodeDataAt(data, size, origBase, origInstRVA, type);
}
//tokenize
CsCapstoneTokenizer::InstructionToken cap;
CapstoneTokenizer::InstructionToken cap;
_tokenizer.Tokenize(origBase + origInstRVA, data, size, cap);
int len = _tokenizer.Size();
@ -269,7 +269,7 @@ Instruction_t CsQBeaEngine::DisassembleAt(byte_t* data, duint size, duint origBa
Instruction_t CsQBeaEngine::DecodeDataAt(byte_t* data, duint size, duint origBase, duint origInstRVA, ENCODETYPE type)
{
//tokenize
CsCapstoneTokenizer::InstructionToken cap;
CapstoneTokenizer::InstructionToken cap;
auto & infoIter = dataInstMap.find(type);
if(infoIter == dataInstMap.end())

View File

@ -4,6 +4,7 @@
#include <QString>
#include <vector>
#include "cs_capstone_gui.h"
#include "QBeaEngine.h" // for instruction_t
class EncodeMap;
class CodeFoldingHelper;

View File

@ -12,7 +12,7 @@ CapstoneTokenizer::CapstoneTokenizer(int maxModuleLength)
SetConfig(false, false, false, false, false, false, false);
}
CapstoneTokenizer::TokenColor colorNamesMap[CapstoneTokenizer::TokenType::Last];
static CapstoneTokenizer::TokenColor colorNamesMap[CapstoneTokenizer::TokenType::Last];
QHash<QString, int> CapstoneTokenizer::stringPoolMap;
int CapstoneTokenizer::poolId = 0;

View File

@ -7,18 +7,18 @@ CsCapstoneTokenizer::CsCapstoneTokenizer(int maxModuleLength)
: _maxModuleLength(maxModuleLength),
_success(false),
isNop(false),
_mnemonicType(TokenType::Uncategorized)
_mnemonicType(CapstoneTokenizer::TokenType::Uncategorized)
{
SetConfig(false, false, false, false, false, false, false);
}
CsCapstoneTokenizer::TokenColor colorNamesMap[CsCapstoneTokenizer::TokenType::Last];
static CapstoneTokenizer::TokenColor colorNamesMap[CapstoneTokenizer::TokenType::Last];
QHash<QString, int> CsCapstoneTokenizer::stringPoolMap;
int CsCapstoneTokenizer::poolId = 0;
void CsCapstoneTokenizer::addColorName(TokenType type, QString color, QString backgroundColor)
void CsCapstoneTokenizer::addColorName(CapstoneTokenizer::TokenType type, QString color, QString backgroundColor)
{
colorNamesMap[int(type)] = TokenColor(color, backgroundColor);
colorNamesMap[int(type)] = CapstoneTokenizer::TokenColor(color, backgroundColor);
}
void CsCapstoneTokenizer::addStringsToPool(const QString & strings)
@ -32,42 +32,42 @@ void CsCapstoneTokenizer::addStringsToPool(const QString & strings)
void CsCapstoneTokenizer::UpdateColors()
{
//filling
addColorName(TokenType::Comma, "InstructionCommaColor", "InstructionCommaBackgroundColor");
addColorName(TokenType::Space, "", "");
addColorName(TokenType::ArgumentSpace, "", "");
addColorName(TokenType::MemoryOperatorSpace, "", "");
addColorName(CapstoneTokenizer::TokenType::Comma, "InstructionCommaColor", "InstructionCommaBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::Space, "", "");
addColorName(CapstoneTokenizer::TokenType::ArgumentSpace, "", "");
addColorName(CapstoneTokenizer::TokenType::MemoryOperatorSpace, "", "");
//general instruction parts
addColorName(TokenType::Prefix, "InstructionPrefixColor", "InstructionPrefixBackgroundColor");
addColorName(TokenType::Uncategorized, "InstructionUncategorizedColor", "InstructionUncategorizedBackgroundColor");
addColorName(TokenType::Address, "InstructionAddressColor", "InstructionAddressBackgroundColor"); //jump/call destinations
addColorName(TokenType::Value, "InstructionValueColor", "InstructionValueBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::Prefix, "InstructionPrefixColor", "InstructionPrefixBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::Uncategorized, "InstructionUncategorizedColor", "InstructionUncategorizedBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::Address, "InstructionAddressColor", "InstructionAddressBackgroundColor"); //jump/call destinations
addColorName(CapstoneTokenizer::TokenType::Value, "InstructionValueColor", "InstructionValueBackgroundColor");
//mnemonics
addColorName(TokenType::MnemonicNormal, "InstructionMnemonicColor", "InstructionMnemonicBackgroundColor");
addColorName(TokenType::MnemonicPushPop, "InstructionPushPopColor", "InstructionPushPopBackgroundColor");
addColorName(TokenType::MnemonicCall, "InstructionCallColor", "InstructionCallBackgroundColor");
addColorName(TokenType::MnemonicRet, "InstructionRetColor", "InstructionRetBackgroundColor");
addColorName(TokenType::MnemonicCondJump, "InstructionConditionalJumpColor", "InstructionConditionalJumpBackgroundColor");
addColorName(TokenType::MnemonicUncondJump, "InstructionUnconditionalJumpColor", "InstructionUnconditionalJumpBackgroundColor");
addColorName(TokenType::MnemonicNop, "InstructionNopColor", "InstructionNopBackgroundColor");
addColorName(TokenType::MnemonicFar, "InstructionFarColor", "InstructionFarBackgroundColor");
addColorName(TokenType::MnemonicInt3, "InstructionInt3Color", "InstructionInt3BackgroundColor");
addColorName(TokenType::MnemonicUnusual, "InstructionUnusualColor", "InstructionUnusualBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicNormal, "InstructionMnemonicColor", "InstructionMnemonicBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicPushPop, "InstructionPushPopColor", "InstructionPushPopBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicCall, "InstructionCallColor", "InstructionCallBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicRet, "InstructionRetColor", "InstructionRetBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicCondJump, "InstructionConditionalJumpColor", "InstructionConditionalJumpBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicUncondJump, "InstructionUnconditionalJumpColor", "InstructionUnconditionalJumpBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicNop, "InstructionNopColor", "InstructionNopBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicFar, "InstructionFarColor", "InstructionFarBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicInt3, "InstructionInt3Color", "InstructionInt3BackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MnemonicUnusual, "InstructionUnusualColor", "InstructionUnusualBackgroundColor");
//memory
addColorName(TokenType::MemorySize, "InstructionMemorySizeColor", "InstructionMemorySizeBackgroundColor");
addColorName(TokenType::MemorySegment, "InstructionMemorySegmentColor", "InstructionMemorySegmentBackgroundColor");
addColorName(TokenType::MemoryBrackets, "InstructionMemoryBracketsColor", "InstructionMemoryBracketsBackgroundColor");
addColorName(TokenType::MemoryStackBrackets, "InstructionMemoryStackBracketsColor", "InstructionMemoryStackBracketsBackgroundColor");
addColorName(TokenType::MemoryBaseRegister, "InstructionMemoryBaseRegisterColor", "InstructionMemoryBaseRegisterBackgroundColor");
addColorName(TokenType::MemoryIndexRegister, "InstructionMemoryIndexRegisterColor", "InstructionMemoryIndexRegisterBackgroundColor");
addColorName(TokenType::MemoryScale, "InstructionMemoryScaleColor", "InstructionMemoryScaleBackgroundColor");
addColorName(TokenType::MemoryOperator, "InstructionMemoryOperatorColor", "InstructionMemoryOperatorBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemorySize, "InstructionMemorySizeColor", "InstructionMemorySizeBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemorySegment, "InstructionMemorySegmentColor", "InstructionMemorySegmentBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryBrackets, "InstructionMemoryBracketsColor", "InstructionMemoryBracketsBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryStackBrackets, "InstructionMemoryStackBracketsColor", "InstructionMemoryStackBracketsBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryBaseRegister, "InstructionMemoryBaseRegisterColor", "InstructionMemoryBaseRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryIndexRegister, "InstructionMemoryIndexRegisterColor", "InstructionMemoryIndexRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryScale, "InstructionMemoryScaleColor", "InstructionMemoryScaleBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MemoryOperator, "InstructionMemoryOperatorColor", "InstructionMemoryOperatorBackgroundColor");
//registers
addColorName(TokenType::GeneralRegister, "InstructionGeneralRegisterColor", "InstructionGeneralRegisterBackgroundColor");
addColorName(TokenType::FpuRegister, "InstructionFpuRegisterColor", "InstructionFpuRegisterBackgroundColor");
addColorName(TokenType::MmxRegister, "InstructionMmxRegisterColor", "InstructionMmxRegisterBackgroundColor");
addColorName(TokenType::XmmRegister, "InstructionXmmRegisterColor", "InstructionXmmRegisterBackgroundColor");
addColorName(TokenType::YmmRegister, "InstructionYmmRegisterColor", "InstructionYmmRegisterBackgroundColor");
addColorName(TokenType::ZmmRegister, "InstructionZmmRegisterColor", "InstructionZmmRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::GeneralRegister, "InstructionGeneralRegisterColor", "InstructionGeneralRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::FpuRegister, "InstructionFpuRegisterColor", "InstructionFpuRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::MmxRegister, "InstructionMmxRegisterColor", "InstructionMmxRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::XmmRegister, "InstructionXmmRegisterColor", "InstructionXmmRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::YmmRegister, "InstructionYmmRegisterColor", "InstructionYmmRegisterBackgroundColor");
addColorName(CapstoneTokenizer::TokenType::ZmmRegister, "InstructionZmmRegisterColor", "InstructionZmmRegisterBackgroundColor");
}
void CsCapstoneTokenizer::UpdateStringPool()
@ -109,9 +109,9 @@ void CsCapstoneTokenizer::UpdateStringPool()
addStringsToPool("xmm15 ymm15");
}
bool CsCapstoneTokenizer::Tokenize(duint addr, const unsigned char* data, int datasize, InstructionToken & instruction)
bool CsCapstoneTokenizer::Tokenize(duint addr, const unsigned char* data, int datasize, CapstoneTokenizer::InstructionToken & instruction)
{
_inst = InstructionToken();
_inst = CapstoneTokenizer::InstructionToken();
_success = _cp.DisassembleSafe(addr, data, datasize);
if(_success)
@ -124,9 +124,9 @@ bool CsCapstoneTokenizer::Tokenize(duint addr, const unsigned char* data, int da
{
if(i)
{
addToken(TokenType::Comma, ",");
addToken(CapstoneTokenizer::TokenType::Comma, ",");
if(_bArgumentSpaces)
addToken(TokenType::ArgumentSpace, " ");
addToken(CapstoneTokenizer::TokenType::ArgumentSpace, " ");
}
if(!tokenizeOperand(_cp[i]))
return false;
@ -135,14 +135,14 @@ bool CsCapstoneTokenizer::Tokenize(duint addr, const unsigned char* data, int da
else
{
isNop = false;
addToken(TokenType::MnemonicUnusual, "???");
addToken(CapstoneTokenizer::TokenType::MnemonicUnusual, "???");
}
if(_bNoHighlightOperands)
{
while(_inst.tokens.size() && _inst.tokens[_inst.tokens.size() - 1].type == TokenType::Space)
while(_inst.tokens.size() && _inst.tokens[_inst.tokens.size() - 1].type == CapstoneTokenizer::TokenType::Space)
_inst.tokens.pop_back();
for(SingleToken & token : _inst.tokens)
for(CapstoneTokenizer::SingleToken & token : _inst.tokens)
token.type = _mnemonicType;
}
@ -151,15 +151,15 @@ bool CsCapstoneTokenizer::Tokenize(duint addr, const unsigned char* data, int da
return true;
}
bool CsCapstoneTokenizer::TokenizeData(const QString & datatype, const QString & data, InstructionToken & instruction)
bool CsCapstoneTokenizer::TokenizeData(const QString & datatype, const QString & data, CapstoneTokenizer::InstructionToken & instruction)
{
_inst = InstructionToken();
_inst = CapstoneTokenizer::InstructionToken();
isNop = false;
if(!tokenizeMnemonic(TokenType::MnemonicNormal, datatype))
if(!tokenizeMnemonic(CapstoneTokenizer::TokenType::MnemonicNormal, datatype))
return false;
addToken(TokenType::Value, data);
addToken(CapstoneTokenizer::TokenType::Value, data);
instruction = _inst;
@ -200,7 +200,7 @@ const Capstone & CsCapstoneTokenizer::GetCapstone() const
return _cp;
}
void CsCapstoneTokenizer::TokenToRichText(const InstructionToken & instr, RichTextPainter::List & richTextList, const SingleToken* highlightToken)
void CsCapstoneTokenizer::TokenToRichText(const CapstoneTokenizer::InstructionToken & instr, RichTextPainter::List & richTextList, const CapstoneTokenizer::SingleToken* highlightToken)
{
QColor highlightColor = ConfigColor("InstructionHighlightColor");
for(const auto & token : instr.tokens)
@ -210,7 +210,7 @@ void CsCapstoneTokenizer::TokenToRichText(const InstructionToken & instr, RichTe
richText.highlightColor = highlightColor;
richText.flags = RichTextPainter::FlagNone;
richText.text = token.text;
if(token.type < TokenType::Last)
if(token.type < CapstoneTokenizer::TokenType::Last)
{
const auto & tokenColor = colorNamesMap[int(token.type)];
richText.flags = tokenColor.flags;
@ -221,7 +221,7 @@ void CsCapstoneTokenizer::TokenToRichText(const InstructionToken & instr, RichTe
}
}
bool CsCapstoneTokenizer::TokenFromX(const InstructionToken & instr, SingleToken & token, int x, CachedFontMetrics* fontMetrics)
bool CsCapstoneTokenizer::TokenFromX(const CapstoneTokenizer::InstructionToken & instr, CapstoneTokenizer::SingleToken & token, int x, CachedFontMetrics* fontMetrics)
{
if(x < instr.x) //before the first token
return false;
@ -241,18 +241,18 @@ bool CsCapstoneTokenizer::TokenFromX(const InstructionToken & instr, SingleToken
return false; //not found
}
bool CsCapstoneTokenizer::IsHighlightableToken(const SingleToken & token)
bool CsCapstoneTokenizer::IsHighlightableToken(const CapstoneTokenizer::SingleToken & token)
{
switch(token.type)
{
case TokenType::Comma:
case TokenType::Space:
case TokenType::ArgumentSpace:
case TokenType::Uncategorized:
case TokenType::MemoryOperatorSpace:
case TokenType::MemoryBrackets:
case TokenType::MemoryStackBrackets:
case TokenType::MemoryOperator:
case CapstoneTokenizer::TokenType::Comma:
case CapstoneTokenizer::TokenType::Space:
case CapstoneTokenizer::TokenType::ArgumentSpace:
case CapstoneTokenizer::TokenType::Uncategorized:
case CapstoneTokenizer::TokenType::MemoryOperatorSpace:
case CapstoneTokenizer::TokenType::MemoryBrackets:
case CapstoneTokenizer::TokenType::MemoryStackBrackets:
case CapstoneTokenizer::TokenType::MemoryOperator:
return false;
break;
}
@ -270,7 +270,7 @@ bool CsCapstoneTokenizer::tokenTextPoolEquals(const QString & a, const QString &
return found1.value() == found2.value();
}
bool CsCapstoneTokenizer::TokenEquals(const SingleToken* a, const SingleToken* b, bool ignoreSize)
bool CsCapstoneTokenizer::TokenEquals(const CapstoneTokenizer::SingleToken* a, const CapstoneTokenizer::SingleToken* b, bool ignoreSize)
{
if(!a || !b)
return false;
@ -284,13 +284,13 @@ bool CsCapstoneTokenizer::TokenEquals(const SingleToken* a, const SingleToken* b
return tokenTextPoolEquals(a->text, b->text);
}
void CsCapstoneTokenizer::addToken(TokenType type, QString text, const TokenValue & value)
void CsCapstoneTokenizer::addToken(CapstoneTokenizer::TokenType type, QString text, const CapstoneTokenizer::TokenValue & value)
{
switch(type)
{
case TokenType::Space:
case TokenType::ArgumentSpace:
case TokenType::MemoryOperatorSpace:
case CapstoneTokenizer::TokenType::Space:
case CapstoneTokenizer::TokenType::ArgumentSpace:
case CapstoneTokenizer::TokenType::MemoryOperatorSpace:
break;
default:
text = text.trimmed();
@ -298,26 +298,26 @@ void CsCapstoneTokenizer::addToken(TokenType type, QString text, const TokenValu
}
if(_bUppercase && !value.size)
text = text.toUpper();
_inst.tokens.push_back(SingleToken(isNop ? TokenType::MnemonicNop : type, text, value));
_inst.tokens.push_back(CapstoneTokenizer::SingleToken(isNop ? CapstoneTokenizer::TokenType::MnemonicNop : type, text, value));
}
void CsCapstoneTokenizer::addToken(TokenType type, const QString & text)
void CsCapstoneTokenizer::addToken(CapstoneTokenizer::TokenType type, const QString & text)
{
addToken(type, text, TokenValue());
addToken(type, text, CapstoneTokenizer::TokenValue());
}
void CsCapstoneTokenizer::addMemoryOperator(char operatorText)
{
if(_bMemorySpaces)
addToken(TokenType::MemoryOperatorSpace, " ");
addToken(CapstoneTokenizer::TokenType::MemoryOperatorSpace, " ");
QString text;
text += operatorText;
addToken(TokenType::MemoryOperator, text);
addToken(CapstoneTokenizer::TokenType::MemoryOperator, text);
if(_bMemorySpaces)
addToken(TokenType::MemoryOperatorSpace, " ");
addToken(CapstoneTokenizer::TokenType::MemoryOperatorSpace, " ");
}
QString CsCapstoneTokenizer::printValue(const TokenValue & value, bool expandModule, int maxModuleLength) const
QString CsCapstoneTokenizer::printValue(const CapstoneTokenizer::TokenValue & value, bool expandModule, int maxModuleLength) const
{
QString labelText;
char label_[MAX_LABEL_SIZE] = "";
@ -380,8 +380,8 @@ bool CsCapstoneTokenizer::tokenizePrefix()
if(hasPrefix)
{
addToken(TokenType::Prefix, prefixText);
addToken(TokenType::Space, " ");
addToken(CapstoneTokenizer::TokenType::Prefix, prefixText);
addToken(CapstoneTokenizer::TokenType::Space, " ");
}
return true;
@ -390,31 +390,31 @@ bool CsCapstoneTokenizer::tokenizePrefix()
bool CsCapstoneTokenizer::tokenizeMnemonic()
{
QString mnemonic = QString(_cp.Mnemonic().c_str());
_mnemonicType = TokenType::MnemonicNormal;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicNormal;
auto id = _cp.GetId();
if(isNop)
_mnemonicType = TokenType::MnemonicNop;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicNop;
else if(_cp.InGroup(CS_GRP_CALL))
_mnemonicType = TokenType::MnemonicCall;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicCall;
else if(_cp.InGroup(CS_GRP_JUMP) || _cp.IsLoop())
{
switch(id)
{
case X86_INS_JMP:
case X86_INS_LJMP:
_mnemonicType = TokenType::MnemonicUncondJump;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicUncondJump;
break;
default:
_mnemonicType = TokenType::MnemonicCondJump;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicCondJump;
break;
}
}
else if(_cp.IsInt3())
_mnemonicType = TokenType::MnemonicInt3;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicInt3;
else if(_cp.IsUnusual())
_mnemonicType = TokenType::MnemonicUnusual;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicUnusual;
else if(_cp.InGroup(CS_GRP_RET))
_mnemonicType = TokenType::MnemonicRet;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicRet;
else
{
switch(id)
@ -431,7 +431,7 @@ bool CsCapstoneTokenizer::tokenizeMnemonic()
case X86_INS_POPFQ:
case X86_INS_POPAL:
case X86_INS_POPAW:
_mnemonicType = TokenType::MnemonicPushPop;
_mnemonicType = CapstoneTokenizer::TokenType::MnemonicPushPop;
break;
default:
break;
@ -443,7 +443,7 @@ bool CsCapstoneTokenizer::tokenizeMnemonic()
return true;
}
bool CsCapstoneTokenizer::tokenizeMnemonic(TokenType type, const QString & mnemonic)
bool CsCapstoneTokenizer::tokenizeMnemonic(CapstoneTokenizer::TokenType type, const QString & mnemonic)
{
addToken(type, mnemonic);
if(_bTabbedMnemonic)
@ -452,10 +452,10 @@ bool CsCapstoneTokenizer::tokenizeMnemonic(TokenType type, const QString & mnemo
if(spaceCount > 0)
{
for(int i = 0; i < spaceCount; i++)
addToken(TokenType::Space, " ");
addToken(CapstoneTokenizer::TokenType::Space, " ");
}
}
addToken(TokenType::Space, " ");
addToken(CapstoneTokenizer::TokenType::Space, " ");
return true;
}
@ -478,22 +478,22 @@ bool CsCapstoneTokenizer::tokenizeOperand(const cs_x86_op & op)
bool CsCapstoneTokenizer::tokenizeRegOperand(const cs_x86_op & op)
{
auto registerType = TokenType::GeneralRegister;
auto registerType = CapstoneTokenizer::TokenType::GeneralRegister;
auto reg = op.reg;
if(reg >= X86_REG_FP0 && reg <= X86_REG_FP7)
registerType = TokenType::FpuRegister;
registerType = CapstoneTokenizer::TokenType::FpuRegister;
else if(reg >= X86_REG_ST0 && reg <= X86_REG_ST7)
registerType = TokenType::FpuRegister;
registerType = CapstoneTokenizer::TokenType::FpuRegister;
else if(reg >= X86_REG_MM0 && reg <= X86_REG_MM7)
registerType = TokenType::MmxRegister;
registerType = CapstoneTokenizer::TokenType::MmxRegister;
else if(reg >= X86_REG_XMM0 && reg <= X86_REG_XMM31)
registerType = TokenType::XmmRegister;
registerType = CapstoneTokenizer::TokenType::XmmRegister;
else if(reg >= X86_REG_YMM0 && reg <= X86_REG_YMM31)
registerType = TokenType::YmmRegister;
registerType = CapstoneTokenizer::TokenType::YmmRegister;
else if(reg >= X86_REG_ZMM0 && reg <= X86_REG_ZMM31)
registerType = TokenType::ZmmRegister;
registerType = CapstoneTokenizer::TokenType::ZmmRegister;
else if(reg == ArchValue(X86_REG_FS, X86_REG_GS))
registerType = TokenType::MnemonicUnusual;
registerType = CapstoneTokenizer::TokenType::MnemonicUnusual;
addToken(registerType, _cp.RegName(reg));
return true;
}
@ -501,10 +501,10 @@ bool CsCapstoneTokenizer::tokenizeRegOperand(const cs_x86_op & op)
bool CsCapstoneTokenizer::tokenizeImmOperand(const cs_x86_op & op)
{
auto value = duint(op.imm) & (duint(-1) >> (op.size ? 8 * (sizeof(duint) - op.size) : 0));
auto valueType = TokenType::Value;
auto valueType = CapstoneTokenizer::TokenType::Value;
if(_cp.InGroup(CS_GRP_JUMP) || _cp.InGroup(CS_GRP_CALL) || _cp.IsLoop())
valueType = TokenType::Address;
auto tokenValue = TokenValue(op.size, value);
valueType = CapstoneTokenizer::TokenType::Address;
auto tokenValue = CapstoneTokenizer::TokenValue(op.size, value);
addToken(valueType, printValue(tokenValue, true, _maxModuleLength), tokenValue);
return true;
}
@ -515,8 +515,8 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
const char* sizeText = _cp.MemSizeName(op.size);
if(!sizeText)
return false;
addToken(TokenType::MemorySize, QString(sizeText) + " ptr");
addToken(TokenType::Space, " ");
addToken(CapstoneTokenizer::TokenType::MemorySize, QString(sizeText) + " ptr");
addToken(CapstoneTokenizer::TokenType::Space, " ");
//memory segment
const auto & mem = op.mem;
@ -539,19 +539,19 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
break;
}
}
auto segmentType = op.reg == ArchValue(X86_REG_FS, X86_REG_GS) ? TokenType::MnemonicUnusual : TokenType::MemorySegment;
auto segmentType = op.reg == ArchValue(X86_REG_FS, X86_REG_GS) ? CapstoneTokenizer::TokenType::MnemonicUnusual : CapstoneTokenizer::TokenType::MemorySegment;
addToken(segmentType, segmentText);
addToken(TokenType::Uncategorized, ":");
addToken(CapstoneTokenizer::TokenType::Uncategorized, ":");
//memory opening bracket
auto bracketsType = TokenType::MemoryBrackets;
auto bracketsType = CapstoneTokenizer::TokenType::MemoryBrackets;
switch(mem.base)
{
case X86_REG_ESP:
case X86_REG_RSP:
case X86_REG_EBP:
case X86_REG_RBP:
bracketsType = TokenType::MemoryStackBrackets;
bracketsType = CapstoneTokenizer::TokenType::MemoryStackBrackets;
default:
break;
}
@ -561,8 +561,8 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
if(mem.base == X86_REG_RIP) //rip-relative (#replacement)
{
duint addr = _cp.Address() + duint(mem.disp) + _cp.Size();
TokenValue value = TokenValue(op.size, addr);
auto displacementType = DbgMemIsValidReadPtr(addr) ? TokenType::Address : TokenType::Value;
CapstoneTokenizer::TokenValue value = CapstoneTokenizer::TokenValue(op.size, addr);
auto displacementType = DbgMemIsValidReadPtr(addr) ? CapstoneTokenizer::TokenType::Address : CapstoneTokenizer::TokenType::Value;
addToken(displacementType, printValue(value, false, _maxModuleLength), value);
}
else //#base + #index * #scale + #displacement
@ -570,31 +570,31 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
bool prependPlus = false;
if(mem.base != X86_REG_INVALID) //base register
{
addToken(TokenType::MemoryBaseRegister, _cp.RegName(mem.base));
addToken(CapstoneTokenizer::TokenType::MemoryBaseRegister, _cp.RegName(mem.base));
prependPlus = true;
}
if(mem.index != X86_REG_INVALID) //index register
{
if(prependPlus)
addMemoryOperator('+');
addToken(TokenType::MemoryIndexRegister, _cp.RegName(mem.index));
addToken(CapstoneTokenizer::TokenType::MemoryIndexRegister, _cp.RegName(mem.index));
if(mem.scale > 1)
{
addMemoryOperator('*');
addToken(TokenType::MemoryScale, QString().sprintf("%d", mem.scale));
addToken(CapstoneTokenizer::TokenType::MemoryScale, QString().sprintf("%d", mem.scale));
}
prependPlus = true;
}
if(mem.disp)
{
char operatorText = '+';
TokenValue value(op.size, duint(mem.disp));
auto displacementType = DbgMemIsValidReadPtr(duint(mem.disp)) ? TokenType::Address : TokenType::Value;
CapstoneTokenizer::TokenValue value(op.size, duint(mem.disp));
auto displacementType = DbgMemIsValidReadPtr(duint(mem.disp)) ? CapstoneTokenizer::TokenType::Address : CapstoneTokenizer::TokenType::Value;
QString valueText;
if(mem.disp < 0)
{
operatorText = '-';
valueText = printValue(TokenValue(op.size, duint(mem.disp * -1)), false, _maxModuleLength);
valueText = printValue(CapstoneTokenizer::TokenValue(op.size, duint(mem.disp * -1)), false, _maxModuleLength);
}
else
valueText = printValue(value, false, _maxModuleLength);
@ -603,7 +603,7 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
addToken(displacementType, valueText, value);
}
else if(!prependPlus)
addToken(TokenType::Value, "0");
addToken(CapstoneTokenizer::TokenType::Value, "0");
}
//closing bracket
@ -613,6 +613,6 @@ bool CsCapstoneTokenizer::tokenizeMemOperand(const cs_x86_op & op)
bool CsCapstoneTokenizer::tokenizeInvalidOperand(const cs_x86_op & op)
{
addToken(TokenType::MnemonicUnusual, "???");
addToken(CapstoneTokenizer::TokenType::MnemonicUnusual, "???");
return true;
}

View File

@ -8,144 +8,14 @@
#include <QHash>
#include <QtCore>
#include "capstone_gui.h"
class CsCapstoneTokenizer
{
public:
enum class TokenType
{
//filling
Comma = 0,
Space,
ArgumentSpace,
MemoryOperatorSpace,
//general instruction parts
Prefix,
Uncategorized,
//mnemonics
MnemonicNormal,
MnemonicPushPop,
MnemonicCall,
MnemonicRet,
MnemonicCondJump,
MnemonicUncondJump,
MnemonicNop,
MnemonicFar,
MnemonicInt3,
MnemonicUnusual,
//values
Address, //jump/call destinations or displacements inside memory
Value,
//memory
MemorySize,
MemorySegment,
MemoryBrackets,
MemoryStackBrackets,
MemoryBaseRegister,
MemoryIndexRegister,
MemoryScale,
MemoryOperator, //'+', '-' and '*'
//registers
GeneralRegister,
FpuRegister,
MmxRegister,
XmmRegister,
YmmRegister,
ZmmRegister,
//last
Last
};
struct TokenValue
{
int size; //value size (in bytes), zero means no value
duint value; //actual value
TokenValue(int size, duint value) :
size(size),
value(value)
{
}
TokenValue() :
size(0),
value(0)
{
}
};
struct SingleToken
{
TokenType type; //token type
QString text; //token text
TokenValue value; //token value (if applicable)
SingleToken() :
type(TokenType::Uncategorized)
{
}
SingleToken(TokenType type, const QString & text, const TokenValue & value) :
type(type),
text(text),
value(value)
{
}
SingleToken(TokenType type, const QString & text) :
SingleToken(type, text, TokenValue())
{
}
};
struct InstructionToken
{
std::vector<SingleToken> tokens; //list of tokens that form the instruction
int x; //x of the first character
InstructionToken()
{
tokens.clear();
x = 0;
}
};
struct TokenColor
{
RichTextPainter::CustomRichTextFlags flags;
QColor color;
QColor backgroundColor;
TokenColor(QString color, QString backgroundColor)
{
if(color.length() && backgroundColor.length())
{
this->flags = RichTextPainter::FlagAll;
this->color = ConfigColor(color);
this->backgroundColor = ConfigColor(backgroundColor);
}
else if(color.length())
{
this->flags = RichTextPainter::FlagColor;
this->color = ConfigColor(color);
}
else if(backgroundColor.length())
{
this->flags = RichTextPainter::FlagBackground;
this->backgroundColor = ConfigColor(backgroundColor);
}
else
this->flags = RichTextPainter::FlagNone;
}
TokenColor()
: TokenColor("", "")
{
}
};
CsCapstoneTokenizer(int maxModuleLength);
bool Tokenize(duint addr, const unsigned char* data, int datasize, InstructionToken & instruction);
bool TokenizeData(const QString & datatype, const QString & data, InstructionToken & instruction);
bool Tokenize(duint addr, const unsigned char* data, int datasize, CapstoneTokenizer::InstructionToken & instruction);
bool TokenizeData(const QString & datatype, const QString & data, CapstoneTokenizer::InstructionToken & instruction);
void UpdateConfig();
void SetConfig(bool bUppercase, bool bTabbedMnemonic, bool bArgumentSpaces, bool bMemorySpaces, bool bNoHighlightOperands, bool bNoCurrentModuleText, bool b0xPrefixValues);
int Size() const;
@ -153,18 +23,18 @@ public:
static void UpdateColors();
static void UpdateStringPool();
static void TokenToRichText(const InstructionToken & instr, RichTextPainter::List & richTextList, const SingleToken* highlightToken);
static bool TokenFromX(const InstructionToken & instr, SingleToken & token, int x, CachedFontMetrics* fontMetrics);
static bool IsHighlightableToken(const SingleToken & token);
static bool TokenEquals(const SingleToken* a, const SingleToken* b, bool ignoreSize = true);
static void addColorName(TokenType type, QString color, QString backgroundColor);
static void TokenToRichText(const CapstoneTokenizer::InstructionToken & instr, RichTextPainter::List & richTextList, const CapstoneTokenizer::SingleToken* highlightToken);
static bool TokenFromX(const CapstoneTokenizer::InstructionToken & instr, CapstoneTokenizer::SingleToken & token, int x, CachedFontMetrics* fontMetrics);
static bool IsHighlightableToken(const CapstoneTokenizer::SingleToken & token);
static bool TokenEquals(const CapstoneTokenizer::SingleToken* a, const CapstoneTokenizer::SingleToken* b, bool ignoreSize = true);
static void addColorName(CapstoneTokenizer::TokenType type, QString color, QString backgroundColor);
static void addStringsToPool(const QString & regs);
static bool tokenTextPoolEquals(const QString & a, const QString & b);
private:
Capstone _cp;
bool isNop;
InstructionToken _inst;
CapstoneTokenizer::InstructionToken _inst;
bool _success;
int _maxModuleLength;
bool _bUppercase;
@ -174,19 +44,19 @@ private:
bool _bNoHighlightOperands;
bool _bNoCurrentModuleText;
bool _b0xPrefixValues;
TokenType _mnemonicType;
CapstoneTokenizer::TokenType _mnemonicType;
void addToken(TokenType type, QString text, const TokenValue & value);
void addToken(TokenType type, const QString & text);
void addToken(CapstoneTokenizer::TokenType type, QString text, const CapstoneTokenizer::TokenValue & value);
void addToken(CapstoneTokenizer::TokenType type, const QString & text);
void addMemoryOperator(char operatorText);
QString printValue(const TokenValue & value, bool expandModule, int maxModuleLength) const;
QString printValue(const CapstoneTokenizer::TokenValue & value, bool expandModule, int maxModuleLength) const;
static QHash<QString, int> stringPoolMap;
static int poolId;
bool tokenizePrefix();
bool tokenizeMnemonic();
bool tokenizeMnemonic(TokenType type, const QString & mnemonic);
bool tokenizeMnemonic(CapstoneTokenizer::TokenType type, const QString & mnemonic);
bool tokenizeOperand(const cs_x86_op & op);
bool tokenizeRegOperand(const cs_x86_op & op);
bool tokenizeImmOperand(const cs_x86_op & op);

View File

@ -68,7 +68,8 @@ INCLUDEPATH += \
Src/ThirdPartyLibs/snowman \
Src/ThirdPartyLibs/ldconvert \
../capstone_wrapper \
../zydis_wrapper
../zydis_wrapper \
../zydis_wrapper/zydis/include
# Resources, sources, headers, and forms
RESOURCES += \
@ -352,7 +353,6 @@ LIBS += -luser32 -ladvapi32 -lwinmm -lshell32
!contains(QMAKE_HOST.arch, x86_64) {
# Windows x86 (32bit) specific build
LIBS += -L"$$PWD/../zydis_wrapper/Zydis" -lZydis_x86
LIBS += -L"$$PWD/../zydis_wrapper/bin/x32$${DIR_SUFFIX}" -lzydis_wrapper
LIBS += -L"$$PWD/../capstone_wrapper/capstone" -lcapstone_x86
LIBS += -L"$$PWD/../capstone_wrapper/bin/x32$${DIR_SUFFIX}" -lcapstone_wrapper
@ -361,7 +361,6 @@ LIBS += -luser32 -ladvapi32 -lwinmm -lshell32
LIBS += -L"$${X64_BIN_DIR}" -lx32bridge
} else {
# Windows x64 (64bit) specific build
LIBS += -L"$$PWD/../zydis_wrapper/Zydis" -lZydis_x64
LIBS += -L"$$PWD/../zydis_wrapper/bin/x64$${DIR_SUFFIX}" -lzydis_wrapper
LIBS += -L"$$PWD/../capstone_wrapper/capstone" -lcapstone_x64
LIBS += -L"$$PWD/../capstone_wrapper/bin/x64$${DIR_SUFFIX}" -lcapstone_wrapper

@ -1 +0,0 @@
Subproject commit a9298c2f45d0bf1f482142aa15cde9e498de84f6

7
src/zydis_wrapper/.gitignore vendored Normal file
View File

@ -0,0 +1,7 @@
bin/
Release/
Debug/
*.sdf
*.opensdf
*.suo
.DS_Store

23
src/zydis_wrapper/LICENSE Normal file
View File

@ -0,0 +1,23 @@
The MIT License (MIT)
Copyright (c) 2016 x64dbg
Copyright (c) 2017 Joel Höner <athre0z@zyantific.com>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

View File

@ -0,0 +1,4 @@
zydis x64dbg module
===================
A "capstone_wrapper" implementation with Zydis.

View File

@ -0,0 +1,41 @@
#ifndef ZYDIS_EXPORT_H
#define ZYDIS_EXPORT_H
#ifdef ZYDIS_STATIC_DEFINE
# define ZYDIS_EXPORT
# define ZYDIS_NO_EXPORT
#else
# ifndef ZYDIS_EXPORT
# ifdef Zydis_EXPORTS
/* We are building this library */
# define ZYDIS_EXPORT
# else
/* We are using this library */
# define ZYDIS_EXPORT
# endif
# endif
# ifndef ZYDIS_NO_EXPORT
# define ZYDIS_NO_EXPORT
# endif
#endif
#ifndef ZYDIS_DEPRECATED
# define ZYDIS_DEPRECATED __attribute__ ((__deprecated__))
#endif
#ifndef ZYDIS_DEPRECATED_EXPORT
# define ZYDIS_DEPRECATED_EXPORT ZYDIS_EXPORT ZYDIS_DEPRECATED
#endif
#ifndef ZYDIS_DEPRECATED_NO_EXPORT
# define ZYDIS_DEPRECATED_NO_EXPORT ZYDIS_NO_EXPORT ZYDIS_DEPRECATED
#endif
#define DEFINE_NO_DEPRECATED 0
#if DEFINE_NO_DEPRECATED
# define ZYDIS_NO_DEPRECATED
#endif
#endif

@ -0,0 +1 @@
Subproject commit 38975c8d3d55e82cfda5f7e2bbe217ca59252866

View File

@ -0,0 +1,866 @@
#include "zydis_wrapper.h"
#include <windows.h>
bool Zydis::mInitialized = false;
ZydisDecoder Zydis::mZyDecoder;
ZydisFormatter Zydis::mZyFormatter;
void Zydis::GlobalInitialize()
{
if(!mInitialized)
{
mInitialized = true;
#ifdef _WIN64
ZydisDecoderInit(&mZyDecoder, ZYDIS_MACHINE_MODE_LONG_64, ZYDIS_ADDRESS_WIDTH_64);
#else //x86
ZydisDecoderInit(&mZyDecoder, ZYDIS_MACHINE_MODE_LEGACY_32, ZYDIS_ADDRESS_WIDTH_32);
#endif //_WIN64
ZydisFormatterInit(&mZyFormatter, ZYDIS_FORMATTER_STYLE_INTEL);
}
}
void Zydis::GlobalFinalize()
{
mInitialized = false;
}
Zydis::Zydis()
: mSuccess(false),
mExplicitOpCount(0)
{
GlobalInitialize();
}
Zydis::~Zydis()
{
}
bool Zydis::Disassemble(size_t addr, const unsigned char data[MAX_DISASM_BUFFER])
{
return Disassemble(addr, data, MAX_DISASM_BUFFER);
}
bool Zydis::Disassemble(size_t addr, const unsigned char* data, int size)
{
if(!data || !size)
return false;
mSuccess = false;
// Decode instruction.
if(!ZYDIS_SUCCESS(ZydisDecoderDecodeBuffer(
&mZyDecoder, data, size, addr, &mZyInstr
)))
return false;
// Format it to human readable representation.
if(!ZYDIS_SUCCESS(ZydisFormatterFormatInstruction(
&mZyFormatter,
const_cast<ZydisDecodedInstruction*>(&mZyInstr),
mInstrText,
sizeof(mInstrText)
)))
return false;
// Count explicit operands.
mExplicitOpCount = 0;
for(size_t i = 0; i < ZYDIS_MAX_OPERAND_COUNT; ++i)
{
auto & op = mZyInstr.operands[i];
// HACK (ath): Rebase IMM if relative (codebase expects it this way)
if (op.type == ZYDIS_OPERAND_TYPE_IMMEDIATE && op.imm.isRelative)
ZydisUtilsCalcAbsoluteTargetAddress(&mZyInstr, &op, &op.imm.value.u);
if (op.visibility != ZYDIS_OPERAND_VISIBILITY_EXPLICIT)
break;
++mExplicitOpCount;
}
mSuccess = true;
return true;
}
bool Zydis::DisassembleSafe(size_t addr, const unsigned char* data, int size)
{
unsigned char dataSafe[MAX_DISASM_BUFFER];
memset(dataSafe, 0, sizeof(dataSafe));
memcpy(dataSafe, data, min(MAX_DISASM_BUFFER, size_t(size)));
return Disassemble(addr, dataSafe);
}
const ZydisDecodedInstruction* Zydis::GetInstr() const
{
if(!Success())
return nullptr;
return &mZyInstr;
}
bool Zydis::Success() const
{
return mSuccess;
}
const char* Zydis::RegName(ZydisRegister reg) const
{
switch(reg)
{
case ZYDIS_REGISTER_ST0:
return "st(0)";
case ZYDIS_REGISTER_ST1:
return "st(1)";
case ZYDIS_REGISTER_ST2:
return "st(2)";
case ZYDIS_REGISTER_ST3:
return "st(3)";
case ZYDIS_REGISTER_ST4:
return "st(4)";
case ZYDIS_REGISTER_ST5:
return "st(5)";
case ZYDIS_REGISTER_ST6:
return "st(6)";
case ZYDIS_REGISTER_ST7:
return "st(7)";
default:
return ZydisRegisterGetString(reg);
}
}
std::string Zydis::OperandText(int opindex) const
{
if(!Success() || opindex >= mZyInstr.operandCount)
return "";
auto& op = mZyInstr.operands[opindex];
ZydisFormatterHookType type;
switch (op.type)
{
case ZYDIS_OPERAND_TYPE_IMMEDIATE:
type = ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_IMM; break;
case ZYDIS_OPERAND_TYPE_MEMORY:
type = ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_MEM; break;
case ZYDIS_OPERAND_TYPE_REGISTER:
type = ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_REG; break;
case ZYDIS_OPERAND_TYPE_POINTER:
type = ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_PTR; break;
default:
return "";
}
ZydisFormatterFormatOperandFunc fmtFunc = nullptr;
if (!ZYDIS_SUCCESS(ZydisFormatterSetHook(&mZyFormatter, type, (const void**)&fmtFunc)))
return "";
char buf[200] = "";
auto bufPtr = buf;
fmtFunc(
&mZyFormatter,
&bufPtr,
sizeof(buf),
(ZydisDecodedInstruction*)&mZyInstr,
(ZydisDecodedOperand*)&op
);
return buf;
}
int Zydis::Size() const
{
if(!Success())
return 1;
return GetInstr()->length;
}
size_t Zydis::Address() const
{
if(!Success())
return 0;
return size_t(GetInstr()->instrAddress);
}
bool Zydis::IsFilling() const
{
if(!Success())
return false;
switch(mZyInstr.mnemonic)
{
case ZYDIS_MNEMONIC_NOP:
case ZYDIS_MNEMONIC_INT3:
return true;
default:
return false;
}
}
bool Zydis::IsBranchType(std::underlying_type_t<BranchType> bt) const
{
if(!Success())
return false;
std::underlying_type_t<BranchType> ref = 0;
const auto & op0 = mZyInstr.operands[0];
switch(mZyInstr.mnemonic)
{
case ZYDIS_MNEMONIC_RET:
ref = BT_Ret;
break;
case ZYDIS_MNEMONIC_CALL:
ref = (op0.elementType == ZYDIS_ELEMENT_TYPE_STRUCT ||
op0.type == ZYDIS_OPERAND_TYPE_POINTER) ? BT_FarCall : BT_Call;
break;
case ZYDIS_MNEMONIC_JMP:
ref = (op0.elementType == ZYDIS_ELEMENT_TYPE_STRUCT ||
op0.type == ZYDIS_OPERAND_TYPE_POINTER) ? BT_FarJmp : BT_UncondJmp;
break;
case ZYDIS_MNEMONIC_JB:
case ZYDIS_MNEMONIC_JBE:
case ZYDIS_MNEMONIC_JCXZ:
case ZYDIS_MNEMONIC_JECXZ:
case ZYDIS_MNEMONIC_JKNZD:
case ZYDIS_MNEMONIC_JKZD:
case ZYDIS_MNEMONIC_JL:
case ZYDIS_MNEMONIC_JLE:
case ZYDIS_MNEMONIC_JNB:
case ZYDIS_MNEMONIC_JNBE:
case ZYDIS_MNEMONIC_JNL:
case ZYDIS_MNEMONIC_JNLE:
case ZYDIS_MNEMONIC_JNO:
case ZYDIS_MNEMONIC_JNP:
case ZYDIS_MNEMONIC_JNS:
case ZYDIS_MNEMONIC_JNZ:
case ZYDIS_MNEMONIC_JO:
case ZYDIS_MNEMONIC_JP:
case ZYDIS_MNEMONIC_JRCXZ:
case ZYDIS_MNEMONIC_JS:
case ZYDIS_MNEMONIC_JZ:
ref = BT_CondJmp;
break;
case ZYDIS_MNEMONIC_SYSCALL:
case ZYDIS_MNEMONIC_SYSENTER:
ref = BT_Syscall;
break;
case ZYDIS_MNEMONIC_SYSRET:
case ZYDIS_MNEMONIC_SYSEXIT:
ref = BT_Sysret;
break;
case ZYDIS_MNEMONIC_INT:
ref = BT_Int;
break;
case ZYDIS_MNEMONIC_INT3:
ref = BT_Int3;
break;
case ZYDIS_MNEMONIC_INT1:
ref = BT_Int1;
break;
case ZYDIS_MNEMONIC_XBEGIN:
ref = BT_Xbegin;
break;
case ZYDIS_MNEMONIC_XABORT:
ref = BT_Xabort;
break;
case ZYDIS_MNEMONIC_RSM:
ref = BT_Rsm;
break;
case ZYDIS_MNEMONIC_LOOP:
case ZYDIS_MNEMONIC_LOOPE:
case ZYDIS_MNEMONIC_LOOPNE:
ref = BT_Loop;
default:
;
}
return (bt & ref) != 0;
}
ZydisMnemonic Zydis::GetId() const
{
if(!Success())
DebugBreak();
return mZyInstr.mnemonic;
}
std::string Zydis::InstructionText(bool replaceRipRelative) const
{
if(!Success())
return "???";
std::string result = mInstrText;
#ifdef _WIN64
// TODO (ath): We can do that a whole lot sexier using formatter hooks
if(replaceRipRelative)
{
//replace [rip +/- 0x?] with the actual address
bool ripPlus = true;
auto found = result.find("[rip + ");
if(found == std::string::npos)
{
ripPlus = false;
found = result.find("[rip - ");
}
if(found != std::string::npos)
{
auto wVA = Address();
auto end = result.find("]", found);
auto ripStr = result.substr(found + 1, end - found - 1);
uint64_t offset;
sscanf_s(ripStr.substr(ripStr.rfind(' ') + 1).c_str(), "%llX", &offset);
auto dest = ripPlus ? (wVA + offset + Size()) : (wVA - offset + Size());
char buf[20];
sprintf_s(buf, "0x%llx", dest);
result.replace(found + 1, ripStr.length(), buf);
}
}
#endif //_WIN64
return result;
}
int Zydis::OpCount() const
{
if(!Success())
return 0;
return mExplicitOpCount;
}
const ZydisDecodedOperand & Zydis::operator[](int index) const
{
if(!Success() || index < 0 || index >= OpCount())
DebugBreak();
return mZyInstr.operands[index];
}
static bool isSafe64NopRegOp(const ZydisDecodedOperand & op)
{
if(op.type != ZYDIS_OPERAND_TYPE_REGISTER)
return true; //a non-register is safe
#ifdef _WIN64
switch(op.reg.value)
{
case ZYDIS_REGISTER_EAX:
case ZYDIS_REGISTER_EBX:
case ZYDIS_REGISTER_ECX:
case ZYDIS_REGISTER_EDX:
case ZYDIS_REGISTER_EBP:
case ZYDIS_REGISTER_ESP:
case ZYDIS_REGISTER_ESI:
case ZYDIS_REGISTER_EDI:
return false; //32 bit register modifications clear the high part of the 64 bit register
default:
return true; //all other registers are safe
}
#else
return true;
#endif //_WIN64
}
bool Zydis::IsNop() const
{
if(!Success())
return false;
const auto & ops = mZyInstr.operands;
switch(mZyInstr.mnemonic)
{
case ZYDIS_MNEMONIC_NOP:
case ZYDIS_MNEMONIC_PAUSE:
case ZYDIS_MNEMONIC_FNOP:
// nop
return true;
case ZYDIS_MNEMONIC_MOV:
case ZYDIS_MNEMONIC_CMOVB:
case ZYDIS_MNEMONIC_CMOVBE:
case ZYDIS_MNEMONIC_CMOVL:
case ZYDIS_MNEMONIC_CMOVLE:
case ZYDIS_MNEMONIC_CMOVNB:
case ZYDIS_MNEMONIC_CMOVNBE:
case ZYDIS_MNEMONIC_CMOVNL:
case ZYDIS_MNEMONIC_CMOVNLE:
case ZYDIS_MNEMONIC_CMOVNO:
case ZYDIS_MNEMONIC_CMOVNP:
case ZYDIS_MNEMONIC_CMOVNS:
case ZYDIS_MNEMONIC_CMOVNZ:
case ZYDIS_MNEMONIC_CMOVO:
case ZYDIS_MNEMONIC_CMOVP:
case ZYDIS_MNEMONIC_CMOVS:
case ZYDIS_MNEMONIC_CMOVZ:
case ZYDIS_MNEMONIC_MOVAPS:
case ZYDIS_MNEMONIC_MOVAPD:
case ZYDIS_MNEMONIC_MOVUPS:
case ZYDIS_MNEMONIC_MOVUPD:
case ZYDIS_MNEMONIC_XCHG:
// mov edi, edi
return ops[0].type == ZYDIS_OPERAND_TYPE_REGISTER
&& ops[1].type == ZYDIS_OPERAND_TYPE_REGISTER
&& ops[0].reg.value == ops[1].reg.value
&& isSafe64NopRegOp(ops[0]);
case ZYDIS_MNEMONIC_LEA:
{
// lea eax, [eax + 0]
auto reg = ops[0].reg.value;
auto mem = ops[1].mem;
return ops[0].type == ZYDIS_OPERAND_TYPE_REGISTER
&& ops[1].type == ZYDIS_OPERAND_TYPE_REGISTER
&& mem.disp.value == 0
&& ((mem.index == ZYDIS_REGISTER_NONE && mem.base == reg) ||
(mem.index == reg && mem.base == ZYDIS_REGISTER_NONE && mem.scale == 1))
&& isSafe64NopRegOp(ops[0]);
}
case ZYDIS_MNEMONIC_JB:
case ZYDIS_MNEMONIC_JBE:
case ZYDIS_MNEMONIC_JCXZ:
case ZYDIS_MNEMONIC_JECXZ:
case ZYDIS_MNEMONIC_JKNZD:
case ZYDIS_MNEMONIC_JKZD:
case ZYDIS_MNEMONIC_JL:
case ZYDIS_MNEMONIC_JLE:
case ZYDIS_MNEMONIC_JMP:
case ZYDIS_MNEMONIC_JNB:
case ZYDIS_MNEMONIC_JNBE:
case ZYDIS_MNEMONIC_JNL:
case ZYDIS_MNEMONIC_JNLE:
case ZYDIS_MNEMONIC_JNO:
case ZYDIS_MNEMONIC_JNP:
case ZYDIS_MNEMONIC_JNS:
case ZYDIS_MNEMONIC_JNZ:
case ZYDIS_MNEMONIC_JO:
case ZYDIS_MNEMONIC_JP:
case ZYDIS_MNEMONIC_JRCXZ:
case ZYDIS_MNEMONIC_JS:
case ZYDIS_MNEMONIC_JZ:
// jmp 0
return ops[0].type == ZYDIS_OPERAND_TYPE_IMMEDIATE
&& ops[0].imm.value.u == this->Address() + this->Size();
case ZYDIS_MNEMONIC_SHL:
case ZYDIS_MNEMONIC_SHR:
case ZYDIS_MNEMONIC_ROL:
case ZYDIS_MNEMONIC_ROR:
case ZYDIS_MNEMONIC_SAR:
// shl eax, 0
return ops[1].type == ZYDIS_OPERAND_TYPE_IMMEDIATE
&& ops[1].imm.value.u == 0
&& isSafe64NopRegOp(ops[0]);
case ZYDIS_MNEMONIC_SHLD:
case ZYDIS_MNEMONIC_SHRD:
// shld eax, ebx, 0
return ops[2].type == ZYDIS_OPERAND_TYPE_IMMEDIATE
&& ops[2].imm.value.u == 0
&& isSafe64NopRegOp(ops[0])
&& isSafe64NopRegOp(ops[1]);
default:
return false;
}
}
bool Zydis::IsPushPop() const
{
if(!Success())
return false;
switch(mZyInstr.meta.category)
{
case ZYDIS_CATEGORY_PUSH:
case ZYDIS_CATEGORY_POP:
return true;
default:
return false;
}
}
bool Zydis::IsUnusual() const
{
if(!Success())
return false;
auto id = mZyInstr.mnemonic;
return mZyInstr.attributes & ZYDIS_ATTRIB_IS_PRIVILEGED
|| id == ZYDIS_MNEMONIC_RDTSC
|| id == ZYDIS_MNEMONIC_SYSCALL
|| id == ZYDIS_MNEMONIC_SYSENTER
|| id == ZYDIS_MNEMONIC_CPUID
|| id == ZYDIS_MNEMONIC_RDTSCP
|| id == ZYDIS_MNEMONIC_RDRAND
|| id == ZYDIS_MNEMONIC_RDSEED
|| id == ZYDIS_MNEMONIC_UD1
|| id == ZYDIS_MNEMONIC_UD2;
}
std::string Zydis::Mnemonic() const
{
if(!Success())
return "???";
switch(mZyInstr.mnemonic)
{
case ZYDIS_MNEMONIC_JZ:
return "je";
case ZYDIS_MNEMONIC_JNZ:
return "jne";
case ZYDIS_MNEMONIC_JNBE:
return "ja";
case ZYDIS_MNEMONIC_JNB:
return "jae";
case ZYDIS_MNEMONIC_JNLE:
return "jg";
case ZYDIS_MNEMONIC_JNL:
return "jge";
case ZYDIS_MNEMONIC_CMOVNBE:
return "cmova";
case ZYDIS_MNEMONIC_CMOVNB:
return "cmovae";
case ZYDIS_MNEMONIC_CMOVZ:
return "cmove";
case ZYDIS_MNEMONIC_CMOVNLE:
return "cmovg";
case ZYDIS_MNEMONIC_CMOVNL:
return "cmovge";
case ZYDIS_MNEMONIC_CMOVNZ:
return "cmovne";
case ZYDIS_MNEMONIC_SETNBE:
return "seta";
case ZYDIS_MNEMONIC_SETNB:
return "setae";
case ZYDIS_MNEMONIC_SETZ:
return "sete";
case ZYDIS_MNEMONIC_SETNLE:
return "setg";
case ZYDIS_MNEMONIC_SETNL:
return "setge";
case ZYDIS_MNEMONIC_SETNZ:
return "setne";
default:
return ZydisMnemonicGetString(mZyInstr.mnemonic);
}
}
std::string Zydis::MnemonicId() const
{
// hax
return Mnemonic();
}
const char* Zydis::MemSizeName(int size) const
{
switch(size)
{
case 1:
return "byte";
case 2:
return "word";
case 4:
return "dword";
case 6:
return "fword";
case 8:
return "qword";
case 10:
return "tword";
case 14:
return "m14";
case 16:
return "xmmword";
case 28:
return "m28";
case 32:
return "yword";
case 64:
return "zword";
default:
return nullptr;
}
}
size_t Zydis::BranchDestination() const
{
if(!Success()
|| mZyInstr.operands[0].type != ZYDIS_OPERAND_TYPE_IMMEDIATE
|| !mZyInstr.operands[0].imm.isRelative)
return 0;
return mZyInstr.operands[0].imm.value.u;
}
size_t Zydis::ResolveOpValue(int opindex, const std::function<size_t(ZydisRegister)> & resolveReg) const
{
size_t dest = 0;
const auto & op = mZyInstr.operands[opindex];
switch(op.type)
{
case ZYDIS_OPERAND_TYPE_IMMEDIATE:
dest = size_t(op.imm.value.u);
break;
case ZYDIS_OPERAND_TYPE_REGISTER:
dest = resolveReg(op.reg.value);
break;
case ZYDIS_OPERAND_TYPE_MEMORY:
dest = size_t(op.mem.disp.value);
if(op.mem.base == ZYDIS_REGISTER_RIP) //rip-relative
dest += Address() + Size();
else
dest += resolveReg(op.mem.base) + resolveReg(op.mem.index) * op.mem.scale;
break;
default:
break;
}
return dest;
}
bool Zydis::IsBranchGoingToExecute(size_t cflags, size_t ccx) const
{
if(!Success())
return false;
return IsBranchGoingToExecute(mZyInstr.mnemonic, cflags, ccx);
}
bool Zydis::IsBranchGoingToExecute(ZydisMnemonic id, size_t cflags, size_t ccx)
{
auto bCF = (cflags & (1 << 0)) != 0;
auto bPF = (cflags & (1 << 2)) != 0;
auto bZF = (cflags & (1 << 6)) != 0;
auto bSF = (cflags & (1 << 7)) != 0;
auto bOF = (cflags & (1 << 11)) != 0;
switch(id)
{
case ZYDIS_MNEMONIC_CALL:
case ZYDIS_MNEMONIC_JMP:
case ZYDIS_MNEMONIC_RET:
return true;
case ZYDIS_MNEMONIC_JNB: //jump short if above or equal
return !bCF;
case ZYDIS_MNEMONIC_JNBE: //jump short if above
return !bCF && !bZF;
case ZYDIS_MNEMONIC_JBE: //jump short if below or equal/not above
return bCF || bZF;
case ZYDIS_MNEMONIC_JB: //jump short if below/not above nor equal/carry
return bCF;
case ZYDIS_MNEMONIC_JCXZ: //jump short if ecx register is zero
case ZYDIS_MNEMONIC_JECXZ: //jump short if ecx register is zero
case ZYDIS_MNEMONIC_JRCXZ: //jump short if rcx register is zero
return ccx == 0;
case ZYDIS_MNEMONIC_JZ: //jump short if equal
return bZF;
case ZYDIS_MNEMONIC_JNL: //jump short if greater or equal
return bSF == bOF;
case ZYDIS_MNEMONIC_JNLE: //jump short if greater
return !bZF && bSF == bOF;
case ZYDIS_MNEMONIC_JLE: //jump short if less or equal/not greater
return bZF || bSF != bOF;
case ZYDIS_MNEMONIC_JL: //jump short if less/not greater
return bSF != bOF;
case ZYDIS_MNEMONIC_JNZ: //jump short if not equal/not zero
return !bZF;
case ZYDIS_MNEMONIC_JNO: //jump short if not overflow
return !bOF;
case ZYDIS_MNEMONIC_JNP: //jump short if not parity/parity odd
return !bPF;
case ZYDIS_MNEMONIC_JNS: //jump short if not sign
return !bSF;
case ZYDIS_MNEMONIC_JO: //jump short if overflow
return bOF;
case ZYDIS_MNEMONIC_JP: //jump short if parity/parity even
return bPF;
case ZYDIS_MNEMONIC_JS: //jump short if sign
return bSF;
case ZYDIS_MNEMONIC_LOOP: //decrement count; jump short if ecx!=0
return ccx != 0;
case ZYDIS_MNEMONIC_LOOPE: //decrement count; jump short if ecx!=0 and zf=1
return ccx != 0 && bZF;
case ZYDIS_MNEMONIC_LOOPNE: //decrement count; jump short if ecx!=0 and zf=0
return ccx != 0 && !bZF;
default:
return false;
}
}
bool Zydis::IsConditionalGoingToExecute(size_t cflags, size_t ccx) const
{
if(!Success())
return false;
return IsConditionalGoingToExecute(mZyInstr.mnemonic, cflags, ccx);
}
bool Zydis::IsConditionalGoingToExecute(ZydisMnemonic id, size_t cflags, size_t ccx)
{
auto bCF = (cflags & (1 << 0)) != 0;
auto bPF = (cflags & (1 << 2)) != 0;
auto bZF = (cflags & (1 << 6)) != 0;
auto bSF = (cflags & (1 << 7)) != 0;
auto bOF = (cflags & (1 << 11)) != 0;
switch(id)
{
case ZYDIS_MNEMONIC_CMOVNBE: //conditional move - above/not below nor equal
return !bCF && !bZF;
case ZYDIS_MNEMONIC_CMOVNB: //conditional move - above or equal/not below/not carry
return !bCF;
case ZYDIS_MNEMONIC_CMOVB: //conditional move - below/not above nor equal/carry
return bCF;
case ZYDIS_MNEMONIC_CMOVBE: //conditional move - below or equal/not above
return bCF || bZF;
case ZYDIS_MNEMONIC_CMOVZ: //conditional move - equal/zero
return bZF;
case ZYDIS_MNEMONIC_CMOVNLE: //conditional move - greater/not less nor equal
return !bZF && bSF == bOF;
case ZYDIS_MNEMONIC_CMOVNL: //conditional move - greater or equal/not less
return bSF == bOF;
case ZYDIS_MNEMONIC_CMOVL: //conditional move - less/not greater nor equal
return bSF != bOF;
case ZYDIS_MNEMONIC_CMOVLE: //conditional move - less or equal/not greater
return bZF || bSF != bOF;
case ZYDIS_MNEMONIC_CMOVNZ: //conditional move - not equal/not zero
return !bZF;
case ZYDIS_MNEMONIC_CMOVNO: //conditional move - not overflow
return !bOF;
case ZYDIS_MNEMONIC_CMOVNP: //conditional move - not parity/parity odd
return !bPF;
case ZYDIS_MNEMONIC_CMOVNS: //conditional move - not sign
return !bSF;
case ZYDIS_MNEMONIC_CMOVO: //conditional move - overflow
return bOF;
case ZYDIS_MNEMONIC_CMOVP: //conditional move - parity/parity even
return bPF;
case ZYDIS_MNEMONIC_CMOVS: //conditional move - sign
return bSF;
case ZYDIS_MNEMONIC_FCMOVBE: //fp conditional move - below or equal
return bCF || bZF;
case ZYDIS_MNEMONIC_FCMOVB: //fp conditional move - below
return bCF;
case ZYDIS_MNEMONIC_FCMOVE: //fp conditional move - equal
return bZF;
case ZYDIS_MNEMONIC_FCMOVNBE: //fp conditional move - not below or equal
return !bCF && !bZF;
case ZYDIS_MNEMONIC_FCMOVNB: //fp conditional move - not below
return !bCF;
case ZYDIS_MNEMONIC_FCMOVNE: //fp conditional move - not equal
return !bZF;
case ZYDIS_MNEMONIC_FCMOVNU: //fp conditional move - not unordered
return !bPF;
case ZYDIS_MNEMONIC_FCMOVU: //fp conditional move - unordered
return bPF;
case ZYDIS_MNEMONIC_SETNBE: //set byte on condition - above/not below nor equal
return !bCF && !bZF;
case ZYDIS_MNEMONIC_SETNB: //set byte on condition - above or equal/not below/not carry
return !bCF;
case ZYDIS_MNEMONIC_SETB: //set byte on condition - below/not above nor equal/carry
return bCF;
case ZYDIS_MNEMONIC_SETBE: //set byte on condition - below or equal/not above
return bCF || bZF;
case ZYDIS_MNEMONIC_SETZ: //set byte on condition - equal/zero
return bZF;
case ZYDIS_MNEMONIC_SETNLE: //set byte on condition - greater/not less nor equal
return !bZF && bSF == bOF;
case ZYDIS_MNEMONIC_SETNL: //set byte on condition - greater or equal/not less
return bSF == bOF;
case ZYDIS_MNEMONIC_SETL: //set byte on condition - less/not greater nor equal
return bSF != bOF;
case ZYDIS_MNEMONIC_SETLE: //set byte on condition - less or equal/not greater
return bZF || bSF != bOF;
case ZYDIS_MNEMONIC_SETNZ: //set byte on condition - not equal/not zero
return !bZF;
case ZYDIS_MNEMONIC_SETNO: //set byte on condition - not overflow
return !bOF;
case ZYDIS_MNEMONIC_SETNP: //set byte on condition - not parity/parity odd
return !bPF;
case ZYDIS_MNEMONIC_SETNS: //set byte on condition - not sign
return !bSF;
case ZYDIS_MNEMONIC_SETO: //set byte on condition - overflow
return bOF;
case ZYDIS_MNEMONIC_SETP: //set byte on condition - parity/parity even
return bPF;
case ZYDIS_MNEMONIC_SETS: //set byte on condition - sign
return bSF;
default:
return true;
}
}
void Zydis::RegInfo(uint8_t regs[ZYDIS_REGISTER_MAX_VALUE + 1]) const
{
memset(regs, 0, sizeof(uint8_t) * (ZYDIS_REGISTER_MAX_VALUE + 1));
if(!Success() || IsNop())
return;
for(int i = 0; i < OpCount(); i++)
{
const auto & op = mZyInstr.operands[i];
switch(op.type)
{
case ZYDIS_OPERAND_TYPE_REGISTER:
{
if(op.action & ZYDIS_OPERAND_ACTION_MASK_READ)
regs[op.reg.value] |= Read;
if(op.action & ZYDIS_OPERAND_ACTION_MASK_WRITE)
regs[op.reg.value] |= Write;
regs[op.reg.value] |= op.visibility == ZYDIS_OPERAND_VISIBILITY_EXPLICIT ?
Explicit : Implicit;
}
break;
case ZYDIS_OPERAND_TYPE_MEMORY:
{
if(op.mem.segment == ZYDIS_REGISTER_NONE)
{
switch(op.mem.base)
{
#ifdef _WIN64
case ZYDIS_REGISTER_RSP:
case ZYDIS_REGISTER_RBP:
#else //x86
case ZYDIS_REGISTER_ESP:
case ZYDIS_REGISTER_EBP:
#endif //_WIN64
regs[ZYDIS_REGISTER_SS] |= Read | Explicit;
break;
default:
regs[ZYDIS_REGISTER_DS] |= Read | Explicit;
break;
}
}
else
regs[op.mem.segment] |= Read | Explicit;
regs[op.mem.base] |= Read | Explicit;
regs[op.mem.index] |= Read | Explicit;
}
break;
default:
break;
}
}
}
const char* Zydis::FlagName(ZydisCPUFlag flag) const
{
switch(flag)
{
case ZYDIS_CPUFLAG_AF:
return "AF";
case ZYDIS_CPUFLAG_CF:
return "CF";
case ZYDIS_CPUFLAG_SF:
return "SF";
case ZYDIS_CPUFLAG_ZF:
return "ZF";
case ZYDIS_CPUFLAG_PF:
return "PF";
case ZYDIS_CPUFLAG_OF:
return "OF";
case ZYDIS_CPUFLAG_TF:
return "TF";
case ZYDIS_CPUFLAG_IF:
return "IF";
case ZYDIS_CPUFLAG_DF:
return "DF";
case ZYDIS_CPUFLAG_NT:
return "NT";
case ZYDIS_CPUFLAG_RF:
return "RF";
default:
return nullptr;
}
}

View File

@ -0,0 +1,109 @@
#ifndef ZYDIS_WRAPPER_H
#define ZYDIS_WRAPPER_H
#include "Zydis/Zydis.h"
#include <functional>
#define MAX_DISASM_BUFFER 16
class Zydis
{
public:
static void GlobalInitialize();
static void GlobalFinalize();
Zydis();
Zydis(const Zydis & capstone) = delete;
~Zydis();
bool Disassemble(size_t addr, const unsigned char data[MAX_DISASM_BUFFER]);
bool Disassemble(size_t addr, const unsigned char* data, int size);
bool DisassembleSafe(size_t addr, const unsigned char* data, int size);
const ZydisDecodedInstruction* GetInstr() const;
bool Success() const;
const char* RegName(ZydisRegister reg) const;
std::string OperandText(int opindex) const;
int Size() const;
size_t Address() const;
bool IsFilling() const;
bool IsUnusual() const;
bool IsNop() const;
bool IsPushPop() const;
ZydisMnemonic GetId() const;
std::string InstructionText(bool replaceRipRelative = true) const;
int OpCount() const;
const ZydisDecodedOperand & operator[](int index) const;
std::string Mnemonic() const;
std::string MnemonicId() const;
const char* MemSizeName(int size) const;
size_t BranchDestination() const;
size_t ResolveOpValue(int opindex, const std::function<size_t(ZydisRegister)> & resolveReg) const;
bool IsBranchGoingToExecute(size_t cflags, size_t ccx) const;
static bool IsBranchGoingToExecute(ZydisMnemonic id, size_t cflags, size_t ccx);
bool IsConditionalGoingToExecute(size_t cflags, size_t ccx) const;
static bool IsConditionalGoingToExecute(ZydisMnemonic id, size_t cflags, size_t ccx);
enum RegInfoAccess : uint8_t
{
None = 1 << 0,
Read = 1 << 0,
Write = 1 << 1,
Implicit = 1 << 2,
Explicit = 1 << 3
};
void RegInfo(uint8_t info[ZYDIS_REGISTER_MAX_VALUE + 1]) const;
const char* FlagName(ZydisCPUFlag flag) const;
enum BranchType : uint16_t
{
// Basic types.
BT_Ret = 1 << 0,
BT_Call = 1 << 1,
BT_FarCall = 1 << 2,
BT_Syscall = 1 << 3, // Also sysenter
BT_Sysret = 1 << 4, // Also sysexit
BT_Int = 1 << 5,
BT_Int3 = 1 << 6,
BT_Int1 = 1 << 7,
BT_Iret = 1 << 8,
BT_CondJmp = 1 << 9,
BT_UncondJmp = 1 << 10,
BT_FarJmp = 1 << 11,
BT_Xbegin = 1 << 12,
BT_Xabort = 1 << 13,
BT_Rsm = 1 << 14,
BT_Loop = 1 << 15,
BT_Jmp = BT_CondJmp | BT_UncondJmp,
// Semantic groups (behaves like XX).
BT_CallSem = BT_Call | BT_Syscall | BT_Int,
BT_RetSem = BT_Ret | BT_Sysret | BT_Iret | BT_Rsm | BT_Xabort,
BT_IntSem = BT_Int | BT_Int1 | BT_Int3 | BT_Syscall,
BT_IretSem = BT_Iret | BT_Sysret,
BT_JmpSem = BT_Jmp | BT_Loop,
BT_Rtm = BT_Xabort | BT_Xbegin,
BT_CtxSwitch = BT_IntSem | BT_IretSem | BT_Rsm | BT_FarCall | BT_FarJmp,
BT_Any = std::underlying_type_t<BranchType>(-1)
};
bool IsBranchType(std::underlying_type_t<BranchType> bt) const;
// Shortcuts.
bool IsRet () const { return IsBranchType(BT_Ret); }
bool IsCall () const { return IsBranchType(BT_Call); }
bool IsJump () const { return IsBranchType(BT_Jmp); }
bool IsLoop () const { return IsBranchType(BT_Loop); }
bool IsInt3 () const { return IsBranchType(BT_Int3); }
private:
static ZydisDecoder mZyDecoder;
static ZydisFormatter mZyFormatter;
static bool mInitialized;
ZydisDecodedInstruction mZyInstr;
char mInstrText[200];
bool mSuccess;
uint8_t mExplicitOpCount;
};
#endif //ZYDIS_WRAPPER_H

View File

@ -0,0 +1,28 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 2013
VisualStudioVersion = 12.0.40629.0
MinimumVisualStudioVersion = 10.0.40219.1
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "zydis_wrapper", "zydis_wrapper.vcxproj", "{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Win32 = Debug|Win32
Debug|x64 = Debug|x64
Release|Win32 = Release|Win32
Release|x64 = Release|x64
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Debug|Win32.ActiveCfg = Debug|Win32
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Debug|Win32.Build.0 = Debug|Win32
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Debug|x64.ActiveCfg = Debug|x64
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Debug|x64.Build.0 = Debug|x64
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Release|Win32.ActiveCfg = Release|Win32
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Release|Win32.Build.0 = Release|Win32
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Release|x64.ActiveCfg = Release|x64
{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}.Release|x64.Build.0 = Release|x64
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
EndGlobal

View File

@ -0,0 +1,173 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="12.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{3B2C1EE1-FDEC-4D85-BE46-3C6A5EA69883}</ProjectGuid>
<RootNamespace>zydis_wrapper</RootNamespace>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>StaticLibrary</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v120_xp</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>StaticLibrary</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v120_xp</PlatformToolset>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>StaticLibrary</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v120_xp</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>StaticLibrary</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v120_xp</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>MultiByte</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<TargetExt>.lib</TargetExt>
<OutDir>$(ProjectDir)bin\x32\</OutDir>
<IntDir>$(Platform)\$(Configuration)\</IntDir>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<TargetExt>.lib</TargetExt>
<OutDir>$(ProjectDir)bin\x64\</OutDir>
<IncludePath>$(ProjectDir);$(IncludePath);$(ProjectDir)\zydis\include;$(ProjectDir)\zydis\src</IncludePath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<TargetExt>.lib</TargetExt>
<OutDir>$(ProjectDir)bin\x32d\</OutDir>
<IntDir>$(Platform)\$(Configuration)\</IntDir>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<TargetExt>.lib</TargetExt>
<OutDir>$(ProjectDir)bin\x64d\</OutDir>
<IncludePath>$(ProjectDir);$(IncludePath);$(ProjectDir)\zydis\include;$(ProjectDir)\zydis\src</IncludePath>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<WholeProgramOptimization>false</WholeProgramOptimization>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<WholeProgramOptimization>false</WholeProgramOptimization>
</ClCompile>
<Link>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
</Link>
</ItemDefinitionGroup>
<ItemGroup>
<ClCompile Include="zydis\src\Decoder.c" />
<ClCompile Include="zydis\src\DecoderData.c" />
<ClCompile Include="zydis\src\FormatHelper.c" />
<ClCompile Include="zydis\src\Formatter.c" />
<ClCompile Include="zydis\src\MetaInfo.c" />
<ClCompile Include="zydis\src\Mnemonic.c" />
<ClCompile Include="zydis\src\Register.c" />
<ClCompile Include="zydis\src\SharedData.c" />
<ClCompile Include="zydis\src\Utils.c" />
<ClCompile Include="zydis\src\Zydis.c" />
<ClCompile Include="zydis_wrapper.cpp" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="zydis\include\Zydis\CommonTypes.h" />
<ClInclude Include="zydis\include\Zydis\Decoder.h" />
<ClInclude Include="zydis\include\Zydis\DecoderTypes.h" />
<ClInclude Include="zydis\include\Zydis\Defines.h" />
<ClInclude Include="zydis\include\Zydis\Encoder.h" />
<ClInclude Include="zydis\include\Zydis\Formatter.h" />
<ClInclude Include="zydis\include\Zydis\MetaInfo.h" />
<ClInclude Include="zydis\include\Zydis\Mnemonic.h" />
<ClInclude Include="zydis\include\Zydis\Register.h" />
<ClInclude Include="zydis\include\Zydis\SharedTypes.h" />
<ClInclude Include="zydis\include\Zydis\Status.h" />
<ClInclude Include="zydis\include\Zydis\Utils.h" />
<ClInclude Include="zydis\include\Zydis\Zydis.h" />
<ClInclude Include="zydis\src\DecoderData.h" />
<ClInclude Include="zydis\src\FormatHelper.h" />
<ClInclude Include="zydis\src\SharedData.h" />
<ClInclude Include="zydis_wrapper.h" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

View File

@ -0,0 +1,107 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup>
<Filter Include="Source Files">
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
</Filter>
<Filter Include="Header Files">
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
<Extensions>h;hh;hpp;hxx;hm;inl;inc;xsd</Extensions>
</Filter>
<Filter Include="Header Files\Zydis">
<UniqueIdentifier>{0f43347f-70ba-4bf2-b8bc-ae1df066b27a}</UniqueIdentifier>
</Filter>
<Filter Include="Source Files\Zydis">
<UniqueIdentifier>{9b6d6e4c-4e1e-48b2-b8ba-1b926c7c7302}</UniqueIdentifier>
</Filter>
</ItemGroup>
<ItemGroup>
<ClCompile Include="zydis_wrapper.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Decoder.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\DecoderData.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\FormatHelper.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Formatter.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\MetaInfo.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Mnemonic.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Register.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\SharedData.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Utils.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
<ClCompile Include="zydis\src\Zydis.c">
<Filter>Source Files\Zydis</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="zydis_wrapper.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\CommonTypes.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Decoder.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\DecoderTypes.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Defines.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Encoder.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Formatter.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\MetaInfo.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Mnemonic.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Register.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\SharedTypes.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Status.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Utils.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\include\Zydis\Zydis.h">
<Filter>Header Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\src\DecoderData.h">
<Filter>Source Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\src\FormatHelper.h">
<Filter>Source Files\Zydis</Filter>
</ClInclude>
<ClInclude Include="zydis\src\SharedData.h">
<Filter>Source Files\Zydis</Filter>
</ClInclude>
</ItemGroup>
</Project>

View File

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup />
</Project>