优化rip的速度
This commit is contained in:
@@ -1007,6 +1007,8 @@ struct moudle_export {
|
||||
uint64_t function_address;
|
||||
void* function_callback;
|
||||
uint64_t ordinal;
|
||||
uc_hook sys_ook;
|
||||
|
||||
};
|
||||
struct moudle_import {
|
||||
char name[MAX_PATH];
|
||||
|
||||
@@ -548,7 +548,10 @@ auto Sandbox::InitEnv(std::shared_ptr<BasicPeInfo> peInfo) -> void {
|
||||
}
|
||||
mapSystemModuleToVmByName("kernelbase.dll");
|
||||
}
|
||||
// 闭合ldr
|
||||
FinalizeLdrLinks();
|
||||
// 给所有导入表加c3
|
||||
/*
|
||||
for (const auto& module : this->GetModuleList()) {
|
||||
// 遍历导出函数查找对应名称
|
||||
for (const auto& exp : module->export_function) {
|
||||
@@ -556,6 +559,15 @@ auto Sandbox::InitEnv(std::shared_ptr<BasicPeInfo> peInfo) -> void {
|
||||
uc_mem_write(m_ucEngine, inMemAddr, "\xCC", sizeof(char));
|
||||
}
|
||||
}
|
||||
*/
|
||||
// 挂导入表钩子
|
||||
for (const auto& module : this->GetModuleList()) {
|
||||
// 遍历导出函数查找对应名称
|
||||
for (const auto& exp : module->export_function) {
|
||||
auto inMemAddr = module->base + exp->function_address;
|
||||
uc_hook_add(m_ucEngine, &exp->sys_ook, UC_HOOK_CODE, sandboxCallbacks::handleApiCall,(void*)this, inMemAddr, inMemAddr + 5, 0);
|
||||
}
|
||||
}
|
||||
uc_err ucErr = uc_mem_map(m_ucEngine, m_peInfo->RecImageBase,
|
||||
m_peInfo->peSize, UC_PROT_ALL);
|
||||
if (ucErr != UC_ERR_OK) {
|
||||
@@ -682,7 +694,6 @@ auto Sandbox::Run(uint64_t address) -> void {
|
||||
// 为参数腾出空间
|
||||
rsp -= 3 * 4; // 三个参数:hinstDLL, fdwReason, lpvReserved
|
||||
uc_reg_write(m_ucEngine, UC_X86_REG_ESP, &rsp);
|
||||
|
||||
// 按照从右到左的顺序压栈
|
||||
uint32_t lpvReserved = 0; // 第三个参数为NULL
|
||||
uint32_t reason = dll_fdwReason; // DLL_PROCESS_ATTACH
|
||||
@@ -704,6 +715,7 @@ auto Sandbox::Run(uint64_t address) -> void {
|
||||
}
|
||||
}
|
||||
err = uc_emu_start(m_ucEngine, entryPoint, m_peInfo->imageEnd, timeout, 0);
|
||||
|
||||
// 2. 有自定义地址 再跑自定义地址
|
||||
std::cerr << "Entry Point Emulation error: " << uc_strerror(err)
|
||||
<< std::endl;
|
||||
|
||||
@@ -247,6 +247,8 @@ class Sandbox {
|
||||
}
|
||||
auto TestLdrListTraversal() -> bool;
|
||||
|
||||
auto FinalizeLdrLinks() -> void;
|
||||
|
||||
// 注册COM相关API
|
||||
void RegisterComApis();
|
||||
|
||||
@@ -338,6 +340,8 @@ class Sandbox {
|
||||
auto AddModuleToLdr(const std::shared_ptr<struct_moudle>& module) -> void;
|
||||
|
||||
|
||||
auto CloseLdrList(uint64_t listHeadAddr, size_t entryLinkOffset) -> void;
|
||||
|
||||
auto DumpLdrList(const char* listName, uint64_t ldrDataBase, size_t listOffset, size_t entryLinkOffset) -> void;
|
||||
|
||||
// 创建LDR_DATA_TABLE_ENTRY结构
|
||||
|
||||
@@ -66,140 +66,142 @@ auto Api_GetCurrentThread(void* sandbox, uc_engine* uc, uint64_t address)
|
||||
printf("[*] GetCurrentThread called, returning pseudo-handle 0x%llx\n",
|
||||
pseudo_handle);
|
||||
}
|
||||
auto Api_LoadLibraryA(void* sandbox, uc_engine* uc, uint64_t address) -> void {
|
||||
auto context = static_cast<Sandbox*>(sandbox);
|
||||
uint64_t params_address = 0;
|
||||
|
||||
// 获取参数地址
|
||||
if (context->GetPeInfo()->isX64) {
|
||||
uc_reg_read(uc, UC_X86_REG_RCX, ¶ms_address);
|
||||
} else {
|
||||
uint64_t ebp_address = 0;
|
||||
uc_reg_read(uc, UC_X86_REG_ESP, &ebp_address);
|
||||
ebp_address += 0x4;
|
||||
uc_mem_read(uc, ebp_address, ¶ms_address, 0x4);
|
||||
}
|
||||
|
||||
uint64_t return_address = 0;
|
||||
std::string module_name;
|
||||
char buffer[MAX_PATH];
|
||||
size_t i = 0;
|
||||
|
||||
// 读取模块名称
|
||||
if (params_address != 0) {
|
||||
do {
|
||||
uint8_t byte;
|
||||
uc_mem_read(uc, params_address + i, &byte, 1);
|
||||
buffer[i] = byte;
|
||||
i++;
|
||||
} while (buffer[i - 1] != 0 && i < MAX_PATH);
|
||||
|
||||
if (i > 0 && i < MAX_PATH) {
|
||||
module_name = std::string(buffer);
|
||||
// 确保模块名以.dll结尾(不区分大小写)
|
||||
if (module_name.length() > 4) {
|
||||
std::string ext = module_name.substr(module_name.length() - 4);
|
||||
if (_stricmp(ext.c_str(), ".dll") != 0) {
|
||||
module_name += ".dll";
|
||||
}
|
||||
} else {
|
||||
module_name += ".dll";
|
||||
}
|
||||
std::string fuck_up_api_ms = module_name;
|
||||
if (fuck_up_api_ms.find("api-ms-") != std::string::npos) {
|
||||
module_name = getDllNameFromApiSetMap(fuck_up_api_ms);
|
||||
if (module_name.size() <= 1) __debugbreak();
|
||||
}
|
||||
|
||||
// 从模块列表中查找对应模块
|
||||
for (const auto& module : context->GetModuleList()) {
|
||||
if ((*module).name == module_name.c_str()) {
|
||||
return_address = (*module).base;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
printf("[*] LoadLibraryA: Module=%s, Base=0x%llx\n", module_name.c_str(),
|
||||
return_address);
|
||||
uc_reg_write(uc,
|
||||
context->GetPeInfo()->isX64 ? UC_X86_REG_RAX : UC_X86_REG_EAX,
|
||||
&return_address);
|
||||
}
|
||||
auto Api_LoadLibraryExW(void* sandbox, uc_engine* uc, uint64_t address)
|
||||
-> void {
|
||||
// 统一的LoadLibrary辅助函数
|
||||
auto LoadLibraryHelper(void* sandbox, uc_engine* uc, uint64_t address,
|
||||
bool isWideChar, bool isEx = false) -> void {
|
||||
auto context = static_cast<Sandbox*>(sandbox);
|
||||
uint64_t module_name_address = 0;
|
||||
uint64_t flags = 0;
|
||||
|
||||
// 获取参数
|
||||
if (context->GetPeInfo()->isX64) {
|
||||
// x64: rcx = lpLibFileName, r8 = dwFlags
|
||||
uc_reg_read(uc, UC_X86_REG_RCX, &module_name_address);
|
||||
uc_reg_read(uc, UC_X86_REG_R8, &flags);
|
||||
} else {
|
||||
// x86: 从栈上读取参数
|
||||
if (isEx) {
|
||||
uc_reg_read(uc, UC_X86_REG_R8, &flags);
|
||||
}
|
||||
}
|
||||
else {
|
||||
uint64_t esp_address = 0;
|
||||
uc_reg_read(uc, UC_X86_REG_ESP, &esp_address);
|
||||
esp_address += 0x4; // 跳过返回地址
|
||||
uc_mem_read(uc, esp_address, &module_name_address, 0x4);
|
||||
esp_address += 0x8; // 跳过hFile参数
|
||||
uc_mem_read(uc, esp_address, &flags, 0x4);
|
||||
|
||||
if (isEx) {
|
||||
esp_address += 0x8; // 跳过hFile参数
|
||||
uc_mem_read(uc, esp_address, &flags, 0x4);
|
||||
}
|
||||
}
|
||||
|
||||
uint64_t return_address = 0;
|
||||
std::wstring module_name;
|
||||
wchar_t buffer[MAX_PATH];
|
||||
size_t i = 0;
|
||||
std::string ansi_name;
|
||||
|
||||
bool isApiSetMapMeme = false;
|
||||
// 读取宽字符模块名称
|
||||
|
||||
// 读取模块名称
|
||||
if (module_name_address != 0) {
|
||||
do {
|
||||
uint16_t wchar;
|
||||
uc_mem_read(uc, module_name_address + (i * 2), &wchar, 2);
|
||||
buffer[i] = wchar;
|
||||
i++;
|
||||
} while (buffer[i - 1] != 0 && i < MAX_PATH);
|
||||
if (isWideChar) {
|
||||
// 读取宽字符串
|
||||
std::wstring module_name;
|
||||
wchar_t buffer[MAX_PATH];
|
||||
size_t i = 0;
|
||||
|
||||
if (i > 0 && i < MAX_PATH) {
|
||||
module_name = std::wstring(buffer);
|
||||
std::string ansi_name(module_name.begin(), module_name.end());
|
||||
do {
|
||||
uint16_t wchar;
|
||||
uc_mem_read(uc, module_name_address + (i * 2), &wchar, 2);
|
||||
buffer[i] = wchar;
|
||||
i++;
|
||||
} while (buffer[i - 1] != 0 && i < MAX_PATH);
|
||||
|
||||
std::string fuck_up_api_ms = ansi_name;
|
||||
if (ansi_name.length() > 4) {
|
||||
std::string ext = ansi_name.substr(ansi_name.length() - 4);
|
||||
if (_stricmp(ext.c_str(), ".dll") != 0) {
|
||||
ansi_name += ".dll";
|
||||
}
|
||||
} else {
|
||||
if (i > 0 && i < MAX_PATH) {
|
||||
module_name = std::wstring(buffer);
|
||||
ansi_name = std::string(module_name.begin(), module_name.end());
|
||||
}
|
||||
}
|
||||
else {
|
||||
// 读取ASCII字符串
|
||||
char buffer[MAX_PATH];
|
||||
size_t i = 0;
|
||||
|
||||
do {
|
||||
uint8_t byte;
|
||||
uc_mem_read(uc, module_name_address + i, &byte, 1);
|
||||
buffer[i] = byte;
|
||||
i++;
|
||||
} while (buffer[i - 1] != 0 && i < MAX_PATH);
|
||||
|
||||
if (i > 0 && i < MAX_PATH) {
|
||||
ansi_name = std::string(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
// 确保模块名以.dll结尾
|
||||
if (ansi_name.length() > 4) {
|
||||
std::string ext = ansi_name.substr(ansi_name.length() - 4);
|
||||
if (_stricmp(ext.c_str(), ".dll") != 0) {
|
||||
ansi_name += ".dll";
|
||||
}
|
||||
if (ansi_name.find("api-ms-") != std::string::npos) {
|
||||
ansi_name = getDllNameFromApiSetMap(ansi_name);
|
||||
isApiSetMapMeme = true;
|
||||
// if (ansi_name.size() <= 1) __debugbreak();
|
||||
}
|
||||
}
|
||||
else {
|
||||
ansi_name += ".dll";
|
||||
}
|
||||
|
||||
// 从模块列表中查找对应模块
|
||||
for (const auto& module : context->GetModuleList()) {
|
||||
if ((*module).name == ansi_name.c_str()) {
|
||||
return_address = (*module).base;
|
||||
break;
|
||||
}
|
||||
// 处理api-ms-前缀
|
||||
if (ansi_name.find("api-ms-") != std::string::npos) {
|
||||
ansi_name = getDllNameFromApiSetMap(ansi_name);
|
||||
isApiSetMapMeme = true;
|
||||
if (!isEx && ansi_name.size() <= 1) __debugbreak();
|
||||
}
|
||||
|
||||
// 从模块列表中查找对应模块
|
||||
for (const auto& module : context->GetModuleList()) {
|
||||
if ((*module).name == ansi_name.c_str()) {
|
||||
return_address = (*module).base;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
printf("[*] LoadLibraryExW: Module=%ls, Flags=0x%llx, Base=0x%llx\n",
|
||||
module_name.c_str(), flags, return_address);
|
||||
if (return_address == 0 && isApiSetMapMeme) {
|
||||
// 根据调用的函数输出日志
|
||||
if (isEx) {
|
||||
printf("[*] LoadLibraryExW: Module=%s, Flags=0x%llx, Base=0x%llx\n",
|
||||
ansi_name.c_str(), flags, return_address);
|
||||
}
|
||||
else {
|
||||
if (isWideChar) {
|
||||
printf("[*] LoadLibraryW: Module=%s, Base=0x%llx\n",
|
||||
ansi_name.c_str(), return_address);
|
||||
}
|
||||
else {
|
||||
printf("[*] LoadLibraryA: Module=%s, Base=0x%llx\n",
|
||||
ansi_name.c_str(), return_address);
|
||||
}
|
||||
}
|
||||
|
||||
// 处理API set映射失败的特殊情况
|
||||
if (return_address == 0 && isApiSetMapMeme && isEx) {
|
||||
// 找不到就不管他了,操
|
||||
return_address = 0x1337;
|
||||
}
|
||||
|
||||
// 设置返回值
|
||||
uc_reg_write(uc,
|
||||
context->GetPeInfo()->isX64 ? UC_X86_REG_RAX : UC_X86_REG_EAX,
|
||||
&return_address);
|
||||
context->GetPeInfo()->isX64 ? UC_X86_REG_RAX : UC_X86_REG_EAX,
|
||||
&return_address);
|
||||
}
|
||||
|
||||
// LoadLibraryA函数包装器
|
||||
auto Api_LoadLibraryA(void* sandbox, uc_engine* uc, uint64_t address) -> void {
|
||||
LoadLibraryHelper(sandbox, uc, address, false);
|
||||
}
|
||||
|
||||
// 新增的LoadLibraryW函数包装器
|
||||
auto Api_LoadLibraryW(void* sandbox, uc_engine* uc, uint64_t address) -> void {
|
||||
LoadLibraryHelper(sandbox, uc, address, true);
|
||||
}
|
||||
|
||||
// LoadLibraryExW函数包装器
|
||||
auto Api_LoadLibraryExW(void* sandbox, uc_engine* uc, uint64_t address) -> void {
|
||||
LoadLibraryHelper(sandbox, uc, address, true, true);
|
||||
}
|
||||
auto Api_GetProcAddress(void* sandbox, uc_engine* uc, uint64_t address)
|
||||
-> void {
|
||||
@@ -1376,7 +1378,9 @@ auto Sandbox::InitApiHooks() -> void {
|
||||
_fakeApi{.func = Api_VariantClear, .paramCount = 1};
|
||||
auto FakeApi_SysAllocString =
|
||||
_fakeApi{.func = Api_SysAllocString, .paramCount = 1};
|
||||
|
||||
auto FakeApi_LoadLibraryW =
|
||||
_fakeApi{ .func = Api_LoadLibraryW, .paramCount = 1 };
|
||||
|
||||
api_map = {
|
||||
{"GetSystemTimeAsFileTime",
|
||||
std::make_shared<_fakeApi>(FakeApi_GetSystemTimeAsFileTime)},
|
||||
@@ -1519,6 +1523,7 @@ auto Sandbox::InitApiHooks() -> void {
|
||||
{"VariantInit", std::make_shared<_fakeApi>(FakeApi_VariantInit)},
|
||||
{"VariantClear", std::make_shared<_fakeApi>(FakeApi_VariantClear)},
|
||||
{"SysAllocString", std::make_shared<_fakeApi>(FakeApi_SysAllocString)},
|
||||
{"LoadLibraryW", std::make_shared<_fakeApi>(FakeApi_LoadLibraryW)},
|
||||
};
|
||||
}
|
||||
auto Sandbox::EmulateApi(uc_engine* uc, uint64_t address, uint64_t rip,
|
||||
|
||||
@@ -1,11 +1,30 @@
|
||||
#include "sandbox_callbacks.h"
|
||||
// 通用模板函数实现绝对值
|
||||
template <typename T>
|
||||
inline T duck_abs(T value) {
|
||||
// 针对有符号类型
|
||||
if constexpr (std::is_signed<T>::value) {
|
||||
return value < 0 ? -value : value;
|
||||
}
|
||||
// 无符号类型直接返回
|
||||
else {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
// 或者使用这个更简单的实现
|
||||
inline uint64_t duck_abs(int64_t a, int64_t b) {
|
||||
uint64_t diff = (a > b) ? (uint64_t)(a - b) : (uint64_t)(b - a);
|
||||
return diff;
|
||||
}
|
||||
|
||||
namespace sandboxCallbacks {
|
||||
static uint64_t lastRip = 0;
|
||||
void handleCodeRun(uc_engine* uc, uint64_t address, uint32_t size,
|
||||
void* userData) {
|
||||
uint64_t currentRip = 0;
|
||||
uint64_t currentRsp = 0;
|
||||
uint64_t currentRax = 0;
|
||||
static uint64_t lastRip = 0;
|
||||
auto* sandbox = static_cast<Sandbox*>(userData);
|
||||
if (!sandbox) return;
|
||||
|
||||
@@ -66,7 +85,9 @@ void handleCodeRun(uc_engine* uc, uint64_t address, uint32_t size,
|
||||
if (currentSectionIndex >= 0) {
|
||||
sandbox->SetLastExecuteSectionIndex(currentSectionIndex);
|
||||
}
|
||||
/*
|
||||
auto [lastReadImpAddr, lastImp] = sandbox->GetLastImpRead();
|
||||
|
||||
if (lastImp != nullptr && currentRip == lastReadImpAddr) {
|
||||
printf(
|
||||
"direct call function [%s]%s at file address: %llx lastRip: "
|
||||
@@ -76,19 +97,24 @@ void handleCodeRun(uc_engine* uc, uint64_t address, uint32_t size,
|
||||
sandbox->EmulateApi(uc, lastReadImpAddr, currentRip, lastImp->name);
|
||||
sandbox->SetLastImpRead(0, nullptr);
|
||||
} else {
|
||||
for (auto module : sandbox->GetModuleList()) {
|
||||
for (auto item : module->export_function) {
|
||||
const auto vmAddress = module->base + item->function_address;
|
||||
if (vmAddress == currentRip) {
|
||||
printf("[!!!]detect no correct call, currentRip: 0x%llx\n",
|
||||
currentRip);
|
||||
sandbox->SetLastImpRead(0, nullptr);
|
||||
|
||||
if (duck_abs(currentRip - address) > PAGE_SIZE) {
|
||||
for (auto module : sandbox->GetModuleList()) {
|
||||
for (auto item : module->export_function) {
|
||||
const auto vmAddress = module->base + item->function_address;
|
||||
if (vmAddress == currentRip) {
|
||||
printf("[!!!]detect no correct call, currentRip: 0x%llx\n",
|
||||
currentRip);
|
||||
sandbox->SetLastImpRead(0, nullptr);
|
||||
|
||||
sandbox->EmulateApi(uc, vmAddress, currentRip, item->name);
|
||||
sandbox->EmulateApi(uc, vmAddress, currentRip, item->name);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
*/
|
||||
lastRip = currentRip;
|
||||
if (LOG_LEVEL > 2) {
|
||||
// 使用Capstone反汇编
|
||||
@@ -107,6 +133,43 @@ void handleCodeRun(uc_engine* uc, uint64_t address, uint32_t size,
|
||||
}
|
||||
}
|
||||
|
||||
void handleApiCall(uc_engine* uc, uint64_t address, uint32_t size, void* userData)
|
||||
{
|
||||
uint64_t currentRip = 0;
|
||||
auto* sandbox = static_cast<Sandbox*>(userData);
|
||||
if (!sandbox) return;
|
||||
|
||||
uc_reg_read(uc,
|
||||
sandbox->GetPeInfo()->isX64 ? UC_X86_REG_RIP : UC_X86_REG_EIP,
|
||||
¤tRip);
|
||||
|
||||
auto [lastReadImpAddr, lastImp] = sandbox->GetLastImpRead();
|
||||
|
||||
if (lastImp != nullptr && currentRip == lastReadImpAddr) {
|
||||
printf(
|
||||
"direct call function [%s]%s at file address: %llx lastRip: "
|
||||
"%llx\n",
|
||||
lastImp->dll_name,
|
||||
lastImp->name, address, lastRip);
|
||||
sandbox->EmulateApi(uc, lastReadImpAddr, currentRip, lastImp->name);
|
||||
sandbox->SetLastImpRead(0, nullptr);
|
||||
}
|
||||
else {
|
||||
for (auto module : sandbox->GetModuleList()) {
|
||||
for (auto item : module->export_function) {
|
||||
const auto vmAddress = module->base + item->function_address;
|
||||
if (vmAddress == currentRip) {
|
||||
printf("[!!!]detect no correct call, currentRip: 0x%llx\n",
|
||||
currentRip);
|
||||
sandbox->SetLastImpRead(0, nullptr);
|
||||
|
||||
sandbox->EmulateApi(uc, vmAddress, currentRip, item->name);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void handleMemoryRead(uc_engine* uc, uc_mem_type type, uint64_t address,
|
||||
int size, int64_t value, void* userData) {
|
||||
auto* sandbox = static_cast<Sandbox*>(userData);
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
namespace sandboxCallbacks {
|
||||
void handleCodeRun(uc_engine* uc, uint64_t address, uint32_t size,
|
||||
void* userData);
|
||||
void handleApiCall(uc_engine* uc, uint64_t address, uint32_t size, void* userData);
|
||||
void handleMemoryRead(uc_engine* uc, uc_mem_type type, uint64_t address,
|
||||
int size, int64_t value, void* userData);
|
||||
void handleMemoryUnmapRead(uc_engine* uc, uc_mem_type type, uint64_t address,
|
||||
|
||||
@@ -283,7 +283,80 @@ auto Sandbox::TestLdrListTraversal() -> bool {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
auto Sandbox::FinalizeLdrLinks() -> void {
|
||||
if (!m_peInfo->isX64) {
|
||||
return;
|
||||
}
|
||||
|
||||
// <20><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>ͷ<EFBFBD><CDB7>ַ
|
||||
uint64_t inLoadOrderListHead = m_peb64.Ldr + offsetof(X64_PEB_LDR_DATA, InLoadOrderModuleList);
|
||||
uint64_t inMemoryOrderListHead = m_peb64.Ldr + offsetof(X64_PEB_LDR_DATA, InMemoryOrderModuleList);
|
||||
uint64_t inInitOrderListHead = m_peb64.Ldr + offsetof(X64_PEB_LDR_DATA, InInitializationOrderModuleList);
|
||||
|
||||
// <20>պ<EFBFBD>InLoadOrderModuleList<73><74><EFBFBD><EFBFBD>
|
||||
CloseLdrList(inLoadOrderListHead, offsetof(LDR_DATA_TABLE_ENTRY, InLoadOrderLinks));
|
||||
|
||||
// <20>պ<EFBFBD>InMemoryOrderModuleList<73><74><EFBFBD><EFBFBD>
|
||||
CloseLdrList(inMemoryOrderListHead, offsetof(LDR_DATA_TABLE_ENTRY, InMemoryOrderLinks));
|
||||
|
||||
// <20>պ<EFBFBD>InInitializationOrderModuleList<73><74><EFBFBD><EFBFBD>
|
||||
CloseLdrList(inInitOrderListHead, offsetof(LDR_DATA_TABLE_ENTRY, InInitializationOrderLinks));
|
||||
}
|
||||
|
||||
auto Sandbox::CloseLdrList(uint64_t listHeadAddr, size_t entryLinkOffset) -> void {
|
||||
LIST_ENTRY listHead;
|
||||
uc_mem_read(m_ucEngine, listHeadAddr, &listHead, sizeof(LIST_ENTRY));
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϊ<EFBFBD>գ<EFBFBD><D5A3><EFBFBD><EFBFBD>账<EFBFBD><E8B4A6>
|
||||
if (listHead.Flink == (LIST_ENTRY*)listHeadAddr) {
|
||||
return;
|
||||
}
|
||||
|
||||
// <20>ҵ<EFBFBD><D2B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>Ԫ<EFBFBD><D4AA>
|
||||
uint64_t currentLink = (uint64_t)listHead.Flink;
|
||||
uint64_t lastLink = 0;
|
||||
|
||||
while (currentLink != listHeadAddr && currentLink != 0) {
|
||||
LIST_ENTRY currentEntry;
|
||||
uc_mem_read(m_ucEngine, currentLink, ¤tEntry, sizeof(LIST_ENTRY));
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϊ<EFBFBD>ջ<EFBFBD>ָ<EFBFBD><D6B8><EFBFBD>Լ<EFBFBD><D4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ǰ<EFBFBD>ڵ<EFBFBD><DAB5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD>Ч<EFBFBD>ڵ<EFBFBD>
|
||||
if (currentEntry.Flink == nullptr ||
|
||||
(uint64_t)currentEntry.Flink == currentLink ||
|
||||
(uint64_t)currentEntry.Flink == 0) {
|
||||
lastLink = currentLink;
|
||||
break;
|
||||
}
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͷ<EFBFBD><CDB7>˵<EFBFBD><CBB5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ȷ<EFBFBD>պ<EFBFBD>
|
||||
if ((uint64_t)currentEntry.Flink == listHeadAddr) {
|
||||
return; // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ȷ<EFBFBD>պϣ<D5BA><CFA3><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
|
||||
}
|
||||
|
||||
lastLink = currentLink;
|
||||
currentLink = (uint64_t)currentEntry.Flink;
|
||||
}
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD>ҵ<EFBFBD><D2B5><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>Ԫ<EFBFBD>أ<EFBFBD><D8A3><EFBFBD><EFBFBD><EFBFBD><DEB8><EFBFBD><EFBFBD><EFBFBD>
|
||||
if (lastLink != 0) {
|
||||
// <20><>ȡ<EFBFBD><C8A1><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>Ԫ<EFBFBD><D4AA>
|
||||
LIST_ENTRY lastEntry;
|
||||
uc_mem_read(m_ucEngine, lastLink, &lastEntry, sizeof(LIST_ENTRY));
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>Ԫ<EFBFBD>ص<EFBFBD>Flinkָ<6B><D6B8><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͷ
|
||||
lastEntry.Flink = (LIST_ENTRY*)listHeadAddr;
|
||||
uc_mem_write(m_ucEngine, lastLink, &lastEntry, sizeof(LIST_ENTRY));
|
||||
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͷ<EFBFBD><CDB7>Blinkָ<6B><D6B8><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB>Ԫ<EFBFBD><D4AA>
|
||||
listHead.Blink = (LIST_ENTRY*)lastLink;
|
||||
uc_mem_write(m_ucEngine, listHeadAddr, &listHead, sizeof(LIST_ENTRY));
|
||||
|
||||
if (LOG_LEVEL > 4) {
|
||||
printf("<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ͷ=0x%llx, <20><><EFBFBD><EFBFBD>Ԫ<EFBFBD><D4AA>=0x%llx\n",
|
||||
listHeadAddr, lastLink);
|
||||
}
|
||||
}
|
||||
}
|
||||
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ӡָ<D3A1><D6B8><EFBFBD><EFBFBD>LDR<44><52><EFBFBD><EFBFBD>
|
||||
auto Sandbox::DumpLdrList(const char* listName, uint64_t ldrDataBase, size_t listOffset, size_t entryLinkOffset) -> void {
|
||||
if (LOG_LEVEL > 4) {
|
||||
|
||||
Reference in New Issue
Block a user