DBG: resolved issue #78 (added virtual module support)
This commit is contained in:
parent
6612e59d81
commit
5634206e85
|
@ -478,7 +478,7 @@ static BOOL CALLBACK SymRegisterCallbackProc64(HANDLE hProcess, ULONG ActionCode
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
static bool cbSetModuleBreakpoints(const BREAKPOINT* bp)
|
||||
bool cbSetModuleBreakpoints(const BREAKPOINT* bp)
|
||||
{
|
||||
if(!bp->enabled)
|
||||
return true;
|
||||
|
|
|
@ -126,6 +126,7 @@ bool cbDeleteAllMemoryBreakpoints(const BREAKPOINT* bp);
|
|||
bool cbDeleteAllHardwareBreakpoints(const BREAKPOINT* bp);
|
||||
DWORD WINAPI threadAttachLoop(void* lpParameter);
|
||||
void cbDetach();
|
||||
bool cbSetModuleBreakpoints(const BREAKPOINT* bp);
|
||||
|
||||
//variables
|
||||
extern PROCESS_INFORMATION* fdProcessInfo;
|
||||
|
|
|
@ -1953,6 +1953,48 @@ CMDRESULT cbInstrExanalyse(int argc, char* argv[])
|
|||
return STATUS_CONTINUE;
|
||||
}
|
||||
|
||||
CMDRESULT cbInstrVirtualmod(int argc, char* argv[])
|
||||
{
|
||||
if(argc < 3)
|
||||
{
|
||||
dputs("Not enough arguments!");
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
uint base;
|
||||
if(!valfromstring(argv[2], &base))
|
||||
{
|
||||
dputs("Invalid parameter [base]!");
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
if(!MemIsValidReadPtr(base))
|
||||
{
|
||||
dputs("Invalid memory address!");
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
uint size;
|
||||
if(argc < 4)
|
||||
base = MemFindBaseAddr(base, &size);
|
||||
else if(!valfromstring(argv[3], &size))
|
||||
{
|
||||
dputs("Invalid parameter [size]");
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
auto name = String("virtual:\\") + (argv[1]);
|
||||
if(!ModLoad(base, size, name.c_str()))
|
||||
{
|
||||
dputs("Failed to load module (ModLoad)...");
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
|
||||
char modname[256] = "";
|
||||
if(ModNameFromAddr(base, modname, true))
|
||||
BpEnumAll(cbSetModuleBreakpoints, modname);
|
||||
|
||||
dprintf("Virtual module \"%s\" loaded on %p[%p]!\n", argv[1], base, size);
|
||||
GuiUpdateAllViews();
|
||||
return STATUS_CONTINUE;
|
||||
}
|
||||
|
||||
CMDRESULT cbInstrVisualize(int argc, char* argv[])
|
||||
{
|
||||
if(argc < 3)
|
||||
|
|
|
@ -73,5 +73,6 @@ CMDRESULT cbInstrVisualize(int argc, char* argv[]);
|
|||
CMDRESULT cbInstrMeminfo(int argc, char* argv[]);
|
||||
CMDRESULT cbInstrCfanalyse(int argc, char* argv[]);
|
||||
CMDRESULT cbInstrExanalyse(int argc, char* argv[]);
|
||||
CMDRESULT cbInstrVirtualmod(int argc, char* argv[]);
|
||||
|
||||
#endif // _INSTRUCTIONS_H
|
||||
|
|
|
@ -3,9 +3,36 @@
|
|||
#include "threading.h"
|
||||
#include "symbolinfo.h"
|
||||
#include "murmurhash.h"
|
||||
#include "memory.h"
|
||||
#include "console.h"
|
||||
#include "label.h"
|
||||
|
||||
std::map<Range, MODINFO, RangeCompare> modinfo;
|
||||
|
||||
static void getModuleInfo(MODINFO & info, ULONG_PTR FileMapVA)
|
||||
{
|
||||
// Get the entry point
|
||||
info.entry = GetPE32DataFromMappedFile(FileMapVA, 0, UE_OEP) + info.base;
|
||||
|
||||
// Enumerate all PE sections
|
||||
int sectionCount = (int)GetPE32DataFromMappedFile(FileMapVA, 0, UE_SECTIONNUMBER);
|
||||
|
||||
for(int i = 0; i < sectionCount; i++)
|
||||
{
|
||||
MODSECTIONINFO curSection;
|
||||
|
||||
curSection.addr = GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONVIRTUALOFFSET) + info.base;
|
||||
curSection.size = GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONVIRTUALSIZE);
|
||||
const char* sectionName = (const char*)GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONNAME);
|
||||
|
||||
// Escape section name when needed
|
||||
strcpy_s(curSection.name, StringUtils::Escape(sectionName).c_str());
|
||||
|
||||
// Add entry to the vector
|
||||
info.sections.push_back(curSection);
|
||||
}
|
||||
}
|
||||
|
||||
bool ModLoad(uint Base, uint Size, const char* FullPath)
|
||||
{
|
||||
// Handle a new module being loaded
|
||||
|
@ -30,6 +57,8 @@ bool ModLoad(uint Base, uint Size, const char* FullPath)
|
|||
strcpy_s(file, fileStart + 1);
|
||||
fileStart[0] = '\0';
|
||||
}
|
||||
else
|
||||
strcpy_s(file, FullPath);
|
||||
}
|
||||
|
||||
// Calculate module hash from full file name
|
||||
|
@ -59,28 +88,17 @@ bool ModLoad(uint Base, uint Size, const char* FullPath)
|
|||
HANDLE FileMap;
|
||||
ULONG_PTR FileMapVA;
|
||||
WString wszFullPath = StringUtils::Utf8ToUtf16(FullPath);
|
||||
if(StaticFileLoadW(wszFullPath.c_str(), UE_ACCESS_READ, false, &FileHandle, &LoadedSize, &FileMap, &FileMapVA))
|
||||
|
||||
bool bVirtual = strstr(FullPath, "virtual:\\") == FullPath;
|
||||
Memory<unsigned char*> data(Size);
|
||||
MemRead(Base, data(), data.size());
|
||||
if(bVirtual) //virtual module
|
||||
{
|
||||
// Get the entry point
|
||||
info.entry = GetPE32DataFromMappedFile(FileMapVA, 0, UE_OEP) + info.base;
|
||||
|
||||
// Enumerate all PE sections
|
||||
int sectionCount = (int)GetPE32DataFromMappedFile(FileMapVA, 0, UE_SECTIONNUMBER);
|
||||
|
||||
for(int i = 0; i < sectionCount; i++)
|
||||
{
|
||||
MODSECTIONINFO curSection;
|
||||
|
||||
curSection.addr = GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONVIRTUALOFFSET) + info.base;
|
||||
curSection.size = GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONVIRTUALSIZE);
|
||||
const char* sectionName = (const char*)GetPE32DataFromMappedFile(FileMapVA, i, UE_SECTIONNAME);
|
||||
|
||||
// Escape section name when needed
|
||||
strcpy_s(curSection.name, StringUtils::Escape(sectionName).c_str());
|
||||
|
||||
// Add entry to the vector
|
||||
info.sections.push_back(curSection);
|
||||
}
|
||||
getModuleInfo(info, (ULONG_PTR)data());
|
||||
}
|
||||
else if(StaticFileLoadW(wszFullPath.c_str(), UE_ACCESS_READ, false, &FileHandle, &LoadedSize, &FileMap, &FileMapVA)) //physical module
|
||||
{
|
||||
getModuleInfo(info, FileMapVA);
|
||||
StaticFileUnloadW(wszFullPath.c_str(), false, FileHandle, LoadedSize, FileMap, FileMapVA);
|
||||
}
|
||||
|
||||
|
@ -89,6 +107,17 @@ bool ModLoad(uint Base, uint Size, const char* FullPath)
|
|||
modinfo.insert(std::make_pair(Range(Base, Base + Size - 1), info));
|
||||
EXCLUSIVE_RELEASE();
|
||||
|
||||
// Put labels for virtual module exports
|
||||
if(bVirtual)
|
||||
{
|
||||
if(info.entry >= Base && info.entry < Base + Size)
|
||||
LabelSet(info.entry, "EntryPoint", false);
|
||||
apienumexports(Base, [](uint base, const char* mod, const char* name, uint addr)
|
||||
{
|
||||
LabelSet(addr, name, false);
|
||||
});
|
||||
}
|
||||
|
||||
SymUpdateModuleList();
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -205,6 +205,7 @@ static void registercommands()
|
|||
dbgcmdnew("cfanal\1cfanalyse\1cfanalyze", cbInstrCfanalyse, true); //control flow analysis
|
||||
dbgcmdnew("analyse_nukem\1analyze_nukem\1anal_nukem", cbInstrAnalyseNukem, true); //secret analysis command #2
|
||||
dbgcmdnew("exanal\1exanalyse\1exanalyze", cbInstrExanalyse, true); //exception directory analysis
|
||||
dbgcmdnew("virtualmod", cbInstrVirtualmod, true); //virtual module
|
||||
}
|
||||
|
||||
static bool cbCommandProvider(char* cmd, int maxlen)
|
||||
|
|
Loading…
Reference in New Issue