fix(encoding): fix Chinese garbling

This commit is contained in:
Changhua 2025-03-08 11:41:44 +08:00
parent ce0fb49956
commit 4a4914743f
4 changed files with 50 additions and 32 deletions

View File

@ -70,6 +70,12 @@ inline void FreeBuffer(void *buffer)
{
if (buffer) HeapFree(GetProcessHeap(), 8, buffer);
}
inline int MsgBox(HWND hWnd, const std::string &text, const std::string &caption = "WCF", UINT uType = MB_OK)
{
std::wstring wText = s2w(text);
std::wstring wCaption = s2w(caption);
return MessageBoxW(nullptr, wText.c_str(), wCaption.c_str(), uType);
}
template <typename T> static T *AllocBuffer(size_t count)
{

View File

@ -4,11 +4,13 @@
#include "psapi.h"
#include "util.h"
using namespace std;
static void handle_injection_error(HANDLE process, LPVOID remote_address, const std::string &error_msg)
{
MessageBoxA(NULL, error_msg.c_str(), "Error", MB_ICONERROR);
util::MsgBox(NULL, error_msg.c_str(), "Error", MB_ICONERROR);
if (remote_address) {
VirtualFreeEx(process, remote_address, 0, MEM_RELEASE);
}
@ -22,7 +24,7 @@ HMODULE get_target_module_base(HANDLE process, const string &dll)
DWORD needed;
HMODULE modules[512];
if (!EnumProcessModulesEx(process, modules, sizeof(modules), &needed, LIST_MODULES_64BIT)) {
MessageBoxA(NULL, "获取模块失败", "get_target_module_base", 0);
util::MsgBox(NULL, "获取模块失败", "get_target_module_base", 0);
return NULL;
}
@ -44,7 +46,7 @@ HANDLE inject_dll(DWORD pid, const string &dll_path, HMODULE *injected_base)
// 1. 打开目标进程
HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pid);
if (!hProcess) {
MessageBoxA(NULL, "打开进程失败", "inject_dll", 0);
util::MsgBox(NULL, "打开进程失败", "inject_dll", 0);
return NULL;
}
@ -90,19 +92,19 @@ bool eject_dll(HANDLE process, HMODULE dll_base)
{
HMODULE k32 = GetModuleHandleA("kernel32.dll");
if (!k32) {
MessageBoxA(NULL, "获取 kernel32 失败", "eject_dll", 0);
util::MsgBox(NULL, "获取 kernel32 失败", "eject_dll", 0);
return false;
}
FARPROC libAddr = GetProcAddress(k32, "FreeLibraryAndExitThread");
if (!libAddr) {
MessageBoxA(NULL, "获取 FreeLibrary 失败", "eject_dll", 0);
util::MsgBox(NULL, "获取 FreeLibrary 失败", "eject_dll", 0);
return false;
}
HANDLE hThread = CreateRemoteThread(process, NULL, 0, (LPTHREAD_START_ROUTINE)libAddr, (LPVOID)dll_base, 0, NULL);
if (!hThread) {
MessageBoxA(NULL, "FreeLibrary 调用失败!", "eject_dll", 0);
util::MsgBox(NULL, "FreeLibrary 调用失败!", "eject_dll", 0);
return false;
}
@ -116,7 +118,7 @@ static uint64_t get_func_offset(const string &dll_path, const string &func_name)
{
HMODULE dll = LoadLibraryA(dll_path.c_str());
if (!dll) {
MessageBoxA(NULL, "获取 DLL 失败", "get_func_offset", 0);
util::MsgBox(NULL, "获取 DLL 失败", "get_func_offset", 0);
return 0;
}
@ -157,7 +159,7 @@ bool call_dll_func_ex(HANDLE process, const string &dll_path, HMODULE dll_base,
uint64_t pFunc = reinterpret_cast<uint64_t>(dll_base) + offset;
LPVOID pRemoteAddress = VirtualAllocEx(process, NULL, size, MEM_COMMIT, PAGE_READWRITE);
if (!pRemoteAddress) {
MessageBoxA(NULL, "申请内存失败", "call_dll_func_ex", 0);
util::MsgBox(NULL, "申请内存失败", "call_dll_func_ex", 0);
return false;
}
@ -166,7 +168,7 @@ bool call_dll_func_ex(HANDLE process, const string &dll_path, HMODULE dll_base,
HANDLE hThread = CreateRemoteThread(process, NULL, 0, (LPTHREAD_START_ROUTINE)pFunc, pRemoteAddress, 0, NULL);
if (!hThread) {
VirtualFreeEx(process, pRemoteAddress, 0, MEM_RELEASE);
MessageBoxA(NULL, "远程调用失败", "call_dll_func_ex", 0);
util::MsgBox(NULL, "远程调用失败", "call_dll_func_ex", 0);
return false;
}

View File

@ -14,6 +14,8 @@
#include "injector.h"
#include "util.h"
extern "C" IMAGE_DOS_HEADER __ImageBase;
static bool injected = false;
static HANDLE wcProcess = NULL;
static HMODULE spyBase = NULL;
@ -26,38 +28,46 @@ constexpr char WCFSPYDLL_DEBUG[] = "spy_debug.dll";
constexpr std::string_view DISCLAIMER_FLAG = ".license_accepted.flag";
constexpr std::string_view DISCLAIMER_TEXT_FILE = "DISCLAIMER.md";
static std::optional<std::string> read_disclaimer_text(const std::string &path)
{
std::ifstream file(path, std::ios::binary);
if (!file.is_open()) {
return std::nullopt; // 文件打开失败
}
namespace fs = std::filesystem;
return std::string((std::istreambuf_iterator<char>(file)), std::istreambuf_iterator<char>());
static fs::path get_module_directory()
{
char buffer[MAX_PATH] = { 0 };
HMODULE hModule = reinterpret_cast<HMODULE>(&__ImageBase);
GetModuleFileNameA(hModule, buffer, MAX_PATH);
fs::path modulePath(buffer);
return modulePath.parent_path();
}
static bool show_disclaimer()
{
if (std::filesystem::exists(DISCLAIMER_FLAG)) {
fs::path sdk_path = get_module_directory();
if (fs::exists(sdk_path / DISCLAIMER_FLAG)) {
return true;
}
auto disclaimerTextOpt = read_disclaimer_text(std::string(DISCLAIMER_TEXT_FILE));
if (!disclaimerTextOpt || disclaimerTextOpt->empty()) {
MessageBoxA(NULL, "免责声明文件为空或读取失败。", "错误", MB_ICONERROR);
fs::path path = sdk_path / DISCLAIMER_TEXT_FILE;
std::ifstream file(path, std::ios::binary);
if (!file.is_open()) {
util::MsgBox(NULL, "免责声明文件读取失败。", "错误", MB_ICONERROR);
return false;
}
int result
= MessageBoxA(NULL, disclaimerTextOpt->c_str(), "免责声明", MB_ICONWARNING | MB_OKCANCEL | MB_DEFBUTTON2);
auto disclaimerText = std::string((std::istreambuf_iterator<char>(file)), std::istreambuf_iterator<char>());
if (disclaimerText.empty()) {
util::MsgBox(NULL, "免责声明文件为空", "错误", MB_ICONERROR);
return false;
}
int result = util::MsgBox(NULL, disclaimerText.c_str(), "免责声明", MB_ICONWARNING | MB_OKCANCEL | MB_DEFBUTTON2);
if (result == IDCANCEL) {
MessageBoxA(NULL, "您拒绝了免责声明,程序将退出。", "提示", MB_ICONINFORMATION);
util::MsgBox(NULL, "您拒绝了免责声明,程序将退出。", "提示", MB_ICONINFORMATION);
return false;
}
std::ofstream flagFile(std::string(DISCLAIMER_FLAG), std::ios::out | std::ios::trunc);
std::ofstream flagFile(sdk_path / DISCLAIMER_FLAG, std::ios::out | std::ios::trunc);
if (!flagFile) {
MessageBoxA(NULL, "无法创建协议标志文件。", "错误", MB_ICONERROR);
util::MsgBox(NULL, "无法创建协议标志文件。", "错误", MB_ICONERROR);
return false;
}
flagFile << "User accepted the license agreement.";
@ -70,12 +80,12 @@ static std::string get_dll_path(bool debug)
char buffer[MAX_PATH] = { 0 };
GetModuleFileNameA(GetModuleHandleA(WCFSDKDLL), buffer, MAX_PATH);
std::filesystem::path path(buffer);
fs::path path(buffer);
path.remove_filename(); // 只保留目录路径
path /= debug ? WCFSPYDLL_DEBUG : WCFSPYDLL;
if (!std::filesystem::exists(path)) {
MessageBoxA(NULL, path.string().c_str(), "文件不存在", MB_ICONERROR);
if (!fs::exists(path)) {
util::MsgBox(NULL, path.string().c_str(), "文件不存在", MB_ICONERROR);
return "";
}
@ -98,21 +108,21 @@ int WxInitSDK(bool debug, int port)
status = util::open_wechat(wcPid);
if (status != 0) {
MessageBoxA(NULL, "打开微信失败", "WxInitSDK", 0);
util::MsgBox(NULL, "打开微信失败", "WxInitSDK", 0);
return status;
}
std::this_thread::sleep_for(std::chrono::seconds(2)); // 等待微信打开
wcProcess = inject_dll(wcPid, spyDllPath, &spyBase);
if (wcProcess == NULL) {
MessageBoxA(NULL, "注入失败", "WxInitSDK", 0);
util::MsgBox(NULL, "注入失败", "WxInitSDK", 0);
return -1;
}
injected = true;
util::PortPath pp = { 0 };
pp.port = port;
snprintf(pp.path, MAX_PATH, "%s", std::filesystem::current_path().string().c_str());
snprintf(pp.path, MAX_PATH, "%s", fs::current_path().string().c_str());
status = -3; // TODO: 统一错误码
bool success = call_dll_func_ex(wcProcess, spyDllPath, spyBase, "InitSpy", (LPVOID)&pp, sizeof(util::PortPath),

View File

@ -25,7 +25,7 @@ int Init(void *args)
std::string msg = fmt::format("WCF 支持版本: {},当前版本: {}", SUPPORT_VERSION, version);
if (version != SUPPORT_VERSION) {
LOG_ERROR(msg);
MessageBoxA(NULL, msg.c_str(), "微信版本错误", MB_ICONERROR);
util::MsgBox(NULL, msg.c_str(), "微信版本错误", MB_ICONERROR);
return -2;
}