mirror of https://github.com/x64dbg/GleeBug
initial Static.Pattern
This commit is contained in:
parent
da7988c71f
commit
6393ae8ffe
|
|
@ -165,6 +165,7 @@
|
||||||
<ClCompile Include="Debugger.Thread.Registers.GetSet.cpp" />
|
<ClCompile Include="Debugger.Thread.Registers.GetSet.cpp" />
|
||||||
<ClCompile Include="Static.BufferFile.cpp" />
|
<ClCompile Include="Static.BufferFile.cpp" />
|
||||||
<ClCompile Include="Static.File.cpp" />
|
<ClCompile Include="Static.File.cpp" />
|
||||||
|
<ClCompile Include="Static.Pattern.cpp" />
|
||||||
<ClCompile Include="Static.Pe.cpp" />
|
<ClCompile Include="Static.Pe.cpp" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|
@ -181,6 +182,7 @@
|
||||||
<ClInclude Include="Static.BufferFile.h" />
|
<ClInclude Include="Static.BufferFile.h" />
|
||||||
<ClInclude Include="Static.File.h" />
|
<ClInclude Include="Static.File.h" />
|
||||||
<ClInclude Include="Static.Global.h" />
|
<ClInclude Include="Static.Global.h" />
|
||||||
|
<ClInclude Include="Static.Pattern.h" />
|
||||||
<ClInclude Include="Static.Pe.h" />
|
<ClInclude Include="Static.Pe.h" />
|
||||||
<ClInclude Include="Static.Pe.Section.h" />
|
<ClInclude Include="Static.Pe.Section.h" />
|
||||||
<ClInclude Include="Static.Region.h" />
|
<ClInclude Include="Static.Region.h" />
|
||||||
|
|
|
||||||
|
|
@ -71,6 +71,9 @@
|
||||||
<ClCompile Include="Static.BufferFile.cpp">
|
<ClCompile Include="Static.BufferFile.cpp">
|
||||||
<Filter>Source Files</Filter>
|
<Filter>Source Files</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="Static.Pattern.cpp">
|
||||||
|
<Filter>Source Files</Filter>
|
||||||
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClInclude Include="Debugger.h">
|
<ClInclude Include="Debugger.h">
|
||||||
|
|
@ -121,5 +124,8 @@
|
||||||
<ClInclude Include="Static.Pe.Section.h">
|
<ClInclude Include="Static.Pe.Section.h">
|
||||||
<Filter>Header Files</Filter>
|
<Filter>Header Files</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
<ClInclude Include="Static.Pattern.h">
|
||||||
|
<Filter>Header Files</Filter>
|
||||||
|
</ClInclude>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
|
@ -0,0 +1,171 @@
|
||||||
|
#include "Static.Pattern.h"
|
||||||
|
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
namespace GleeBug
|
||||||
|
{
|
||||||
|
string Pattern::FormatPattern(const string & patterntext)
|
||||||
|
{
|
||||||
|
string result;
|
||||||
|
result.reserve(patterntext.length());
|
||||||
|
for (auto ch : patterntext)
|
||||||
|
{
|
||||||
|
if (ch >= '0' && ch <= '9' || ch >= 'A' && ch <= 'F' || ch >= 'a' && ch <= 'f' || ch == '?')
|
||||||
|
result += ch;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Pattern::Transform(const std::string & patterntext, std::vector<Byte> & pattern)
|
||||||
|
{
|
||||||
|
pattern.clear();
|
||||||
|
auto formattext = FormatPattern(patterntext);
|
||||||
|
auto len = formattext.length();
|
||||||
|
if (!len)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (len % 2) //not a multiple of 2
|
||||||
|
{
|
||||||
|
formattext += '?';
|
||||||
|
len++;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto hexChToInt = [](char ch)
|
||||||
|
{
|
||||||
|
if (ch >= '0' && ch <= '9')
|
||||||
|
return ch - '0';
|
||||||
|
if (ch >= 'A' && ch <= 'F')
|
||||||
|
return ch - 'A' + 10;
|
||||||
|
if (ch >= 'a' && ch <= 'f')
|
||||||
|
return ch - 'a' + 10;
|
||||||
|
return -1;
|
||||||
|
};
|
||||||
|
|
||||||
|
Byte newByte;
|
||||||
|
auto j = 0;
|
||||||
|
for (auto ch : formattext)
|
||||||
|
{
|
||||||
|
if (ch == '?') //wildcard
|
||||||
|
{
|
||||||
|
newByte.nibble[j].wildcard = true; //match anything
|
||||||
|
}
|
||||||
|
else //hex
|
||||||
|
{
|
||||||
|
newByte.nibble[j].wildcard = false;
|
||||||
|
newByte.nibble[j].data = hexChToInt(ch) & 0xF;
|
||||||
|
}
|
||||||
|
|
||||||
|
j++;
|
||||||
|
if (j == 2) //two nibbles = one byte
|
||||||
|
{
|
||||||
|
j = 0;
|
||||||
|
pattern.push_back(newByte);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t Pattern::Find(const uint8* data, size_t datasize, const std::vector<Byte> & pattern)
|
||||||
|
{
|
||||||
|
auto MatchByte = [](uint8 byte, const Byte & pbyte)
|
||||||
|
{
|
||||||
|
auto matched = 0;
|
||||||
|
|
||||||
|
unsigned char n1 = (byte >> 4) & 0xF;
|
||||||
|
if (pbyte.nibble[0].wildcard)
|
||||||
|
matched++;
|
||||||
|
else if (pbyte.nibble[0].data == n1)
|
||||||
|
matched++;
|
||||||
|
|
||||||
|
unsigned char n2 = byte & 0xF;
|
||||||
|
if (pbyte.nibble[1].wildcard)
|
||||||
|
matched++;
|
||||||
|
else if (pbyte.nibble[1].data == n2)
|
||||||
|
matched++;
|
||||||
|
|
||||||
|
return matched == 2;
|
||||||
|
};
|
||||||
|
|
||||||
|
auto searchpatternsize = pattern.size();
|
||||||
|
for (size_t i = 0, pos = 0; i < datasize; i++) //search for the pattern
|
||||||
|
{
|
||||||
|
if (MatchByte(data[i], pattern.at(pos))) //check if our pattern matches the current byte
|
||||||
|
{
|
||||||
|
pos++;
|
||||||
|
if (pos == searchpatternsize) //everything matched
|
||||||
|
return i - searchpatternsize + 1;
|
||||||
|
}
|
||||||
|
else if (pos > 0) //fix by Computer_Angel
|
||||||
|
{
|
||||||
|
i -= pos;
|
||||||
|
pos = 0; //reset current pattern position
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t Pattern::Find(const uint8* data, size_t datasize, unsigned char* pattern, size_t patternsize)
|
||||||
|
{
|
||||||
|
if (patternsize > datasize)
|
||||||
|
patternsize = datasize;
|
||||||
|
for (size_t i = 0, pos = 0; i < datasize; i++)
|
||||||
|
{
|
||||||
|
if (data[i] == pattern[pos])
|
||||||
|
{
|
||||||
|
pos++;
|
||||||
|
if (pos == patternsize)
|
||||||
|
return i - patternsize + 1;
|
||||||
|
}
|
||||||
|
else if (pos > 0)
|
||||||
|
{
|
||||||
|
i -= pos;
|
||||||
|
pos = 0; //reset current pattern position
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t Pattern::Find(const uint8* data, size_t datasize, const char* pattern)
|
||||||
|
{
|
||||||
|
string patterntext(pattern);
|
||||||
|
vector<Byte> searchpattern;
|
||||||
|
if (!Transform(patterntext, searchpattern))
|
||||||
|
return -1;
|
||||||
|
return Find(data, datasize, searchpattern);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Pattern::Write(uint8* data, size_t datasize, const char* pattern)
|
||||||
|
{
|
||||||
|
vector<Byte> writepattern;
|
||||||
|
string patterntext(pattern);
|
||||||
|
if (!Transform(patterntext, writepattern))
|
||||||
|
return;
|
||||||
|
|
||||||
|
auto writepatternsize = writepattern.size();
|
||||||
|
if (writepatternsize > datasize)
|
||||||
|
writepatternsize = datasize;
|
||||||
|
|
||||||
|
auto WriteByte = [](uint8* byte, const Byte & pbyte)
|
||||||
|
{
|
||||||
|
unsigned char n1 = (*byte >> 4) & 0xF;
|
||||||
|
unsigned char n2 = *byte & 0xF;
|
||||||
|
if (!pbyte.nibble[0].wildcard)
|
||||||
|
n1 = pbyte.nibble[0].data;
|
||||||
|
if (!pbyte.nibble[1].wildcard)
|
||||||
|
n2 = pbyte.nibble[1].data;
|
||||||
|
*byte = ((n1 << 4) & 0xF0) | (n2 & 0xF);
|
||||||
|
};
|
||||||
|
|
||||||
|
for (size_t i = 0; i < writepatternsize; i++)
|
||||||
|
WriteByte(&data[i], writepattern.at(i));
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Pattern::Snr(uint8* data, size_t datasize, const char* searchpattern, const char* replacepattern)
|
||||||
|
{
|
||||||
|
auto found = Find(data, datasize, searchpattern);
|
||||||
|
if (found == -1)
|
||||||
|
return false;
|
||||||
|
Write(data + found, datasize - found, replacepattern);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
#ifndef STATIC_PATTERN_H
|
||||||
|
#define STATIC_PATTERN_H
|
||||||
|
|
||||||
|
#include "Static.Global.h"
|
||||||
|
|
||||||
|
namespace GleeBug
|
||||||
|
{
|
||||||
|
class Pattern
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
struct Byte
|
||||||
|
{
|
||||||
|
struct Nibble
|
||||||
|
{
|
||||||
|
uint8 data;
|
||||||
|
bool wildcard;
|
||||||
|
} nibble[2];
|
||||||
|
};
|
||||||
|
|
||||||
|
static std::string FormatPattern(const std::string & pattern);
|
||||||
|
static bool Transform(const std::string & patterntext, std::vector<Byte> & pattern);
|
||||||
|
static size_t Find(const uint8* data, size_t datasize, const std::vector<Byte> & pattern);
|
||||||
|
static size_t Find(const uint8* data, size_t datasize, unsigned char* pattern, size_t patternsize);
|
||||||
|
static size_t Find(const uint8* data, size_t datasize, const char* pattern);
|
||||||
|
static void Write(uint8* data, size_t datasize, const char* pattern);
|
||||||
|
static bool Snr(uint8* data, size_t datasize, const char* searchpattern, const char* replacepattern);
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif //STATIC_PATTERN_H
|
||||||
Loading…
Reference in New Issue