From e66b61aa6750e709212c0bffafd3b55f5e19c57c Mon Sep 17 00:00:00 2001 From: Changhua Date: Tue, 2 Jul 2024 22:03:59 +0800 Subject: [PATCH] Refactoring --- WeChatFerry/spy/Spy.vcxproj | 2 - WeChatFerry/spy/Spy.vcxproj.filters | 6 - WeChatFerry/spy/exec_sql.cpp | 1 - WeChatFerry/spy/funcs.cpp | 3 +- WeChatFerry/spy/load_calls.cpp | 55 --------- WeChatFerry/spy/load_calls.h | 5 - WeChatFerry/spy/spy.cpp | 14 ++- WeChatFerry/spy/spy.h | 2 + WeChatFerry/spy/spy_types.h | 180 ---------------------------- WeChatFerry/spy/sqlite3.h | 4 +- WeChatFerry/spy/user_info.cpp | 25 ++-- 11 files changed, 31 insertions(+), 266 deletions(-) delete mode 100644 WeChatFerry/spy/load_calls.cpp delete mode 100644 WeChatFerry/spy/load_calls.h diff --git a/WeChatFerry/spy/Spy.vcxproj b/WeChatFerry/spy/Spy.vcxproj index b587e00..0c44f9a 100644 --- a/WeChatFerry/spy/Spy.vcxproj +++ b/WeChatFerry/spy/Spy.vcxproj @@ -237,7 +237,6 @@ xcopy /y $(OutDir)$(TargetFileName) $(SolutionDir)..\clients\python\wcferry - @@ -260,7 +259,6 @@ xcopy /y $(OutDir)$(TargetFileName) $(SolutionDir)..\clients\python\wcferry - diff --git a/WeChatFerry/spy/Spy.vcxproj.filters b/WeChatFerry/spy/Spy.vcxproj.filters index 9cb084c..f2b9096 100644 --- a/WeChatFerry/spy/Spy.vcxproj.filters +++ b/WeChatFerry/spy/Spy.vcxproj.filters @@ -30,9 +30,6 @@ 头文件 - - 头文件 - 头文件 @@ -104,9 +101,6 @@ 源文件 - - 源文件 - 源文件 diff --git a/WeChatFerry/spy/exec_sql.cpp b/WeChatFerry/spy/exec_sql.cpp index 51e5f81..5de9628 100644 --- a/WeChatFerry/spy/exec_sql.cpp +++ b/WeChatFerry/spy/exec_sql.cpp @@ -1,7 +1,6 @@ #include #include "exec_sql.h" -#include "load_calls.h" #include "log.h" #include "sqlite3.h" #include "util.h" diff --git a/WeChatFerry/spy/funcs.cpp b/WeChatFerry/spy/funcs.cpp index 8266b76..9ff3edc 100644 --- a/WeChatFerry/spy/funcs.cpp +++ b/WeChatFerry/spy/funcs.cpp @@ -24,6 +24,7 @@ extern QWORD g_WeChatWinDllAddr; #define HEADER_GIF1 0x47 #define HEADER_GIF2 0x49 +#define OS_LOGIN_STATUS 0x5AB86A8 #define OS_GET_SNS_DATA_MGR 0x22A91C0 #define OS_GET_SNS_FIRST_PAGE 0x2ED9080 #define OS_GET_SNS_TIMELINE_MGR 0x2E6B110 @@ -48,7 +49,7 @@ typedef QWORD (*PushAttachTask_t)(QWORD, QWORD, QWORD, QWORD); typedef QWORD (*GetOCRManager_t)(); typedef QWORD (*DoOCRTask_t)(QWORD, QWORD, QWORD, QWORD, QWORD, QWORD); -int IsLogin(void) { return (int)GET_QWORD(g_WeChatWinDllAddr + g_WxCalls.login); } +int IsLogin(void) { return (int)GET_QWORD(g_WeChatWinDllAddr + OS_LOGIN_STATUS); } static string get_key(uint8_t header1, uint8_t header2, uint8_t *key) { diff --git a/WeChatFerry/spy/load_calls.cpp b/WeChatFerry/spy/load_calls.cpp deleted file mode 100644 index 01f9545..0000000 --- a/WeChatFerry/spy/load_calls.cpp +++ /dev/null @@ -1,55 +0,0 @@ -#include -#include - -#include "load_calls.h" - -#define SUPPORT_VERSION L"3.9.10.27" - -WxCalls_t wxCalls = { - 0x5AB86A8, // Login Status - { 0x5AB7FB8, 0x5AB8098, 0x5AB7FD8, 0x5A7E190 }, // User Info: wxid, nickname, mobile, home - { 0x1C1E690, 0x238DDD0, 0x1C1FF10 }, // Send Text Message - /* Receive Message: - Hook, call, msgId, type, isSelf, ts, roomId, content, wxid, sign, thumb, extra, msgXml */ - { 0x00, 0x2205510, 0x30, 0x38, 0x3C, 0x44, 0x48, 0x88, 0x240, 0x260, 0x280, 0x2A0, 0x308 }, - { 0x1C28800, 0x1C1FF10, 0x1C1E690, 0x2383560 }, // Send Image Message - { 0x1C28800, 0x1C1FF10, 0x1C23630, 0x21969E0 }, // Send File Message - { 0xB8A70, 0x3ED5E0, 0x107F00, 0x3ED7B0, 0x2386FE4 }, // Send xml Message - { 0x771980, 0x4777E0, 0x239E888 }, // Send Emotion Message - /* Get Contacts: - call1, call2, wxId, Code, Remark,Name,Gender,Country,Province,City*/ - { 0x00, 0x00, 0x10, 0x30, 0x80, 0xA0, 0x0E, 0x00, 0x00, 0x00 }, - /* Exec Sql: - Exec, base, start, end, slot, name*/ - { 0x141BDF0, 0x2366934, 0x1428, 0x142C, 0x3C, 0x50 }, - { 0xA17D50, 0xF59E40, 0xA18BD0, 0xA17E70 }, // Accept New Friend application - { 0x1C4E200, 0x221B8A0, 0x00 }, // Add chatroom members - { 0x1C4E200, 0x221BEE0, 0x00 }, // Delete chatroom members - { 0x7B2E60, 0x15E2C20, 0x79C250 }, // Receive transfer - /* Receive PYQ - hook, call, call1, call2, call3, start, end, ts, wxid, content, xml, step*/ - { 0x14F9E15, 0x14FA0A0, 0xC39680, 0x14E2140, 0x14E21E0, 0x20, 0x24, 0x2C, 0x18, 0x3C, 0x384, 0xB48 }, - /* call1, call2, call3, call4, call5, call6*/ - { 0x76F010, 0x792700, 0xBC0370, 0x80F110, 0x82BB40, 0x756E30}, - /* call1, call2, call3, call4, call5*/ - {0x76F010, 0x792700, 0xBC0370, 0xBB5F70, 0x756E30}, - {0x1C27D50, 0x1C27120, 0x1C23630, 0x21A09C0}, // Send Rich Text Message - {0x2D669B0}, // Send Pat Message - {0x221B280, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // Invite chatroom members - /* call1, call2, call3 */ - {0x80A800, 0x80F270, 0x13DA3E0}, - {0x238D350}, // Forward message - /* call1, call2, url */ - {0xAE9DB0, 0xCDA6F0, 0x3040DE8} -}; - -int LoadCalls(const wchar_t *version, WxCalls_t *calls) -{ - if (wcscmp(version, SUPPORT_VERSION) != 0) { - return -1; - } - - memcpy_s(calls, sizeof(WxCalls_t), &wxCalls, sizeof(WxCalls_t)); - - return 0; -} diff --git a/WeChatFerry/spy/load_calls.h b/WeChatFerry/spy/load_calls.h deleted file mode 100644 index 2f8410e..0000000 --- a/WeChatFerry/spy/load_calls.h +++ /dev/null @@ -1,5 +0,0 @@ -#pragma once - -#include "spy_types.h" - -int LoadCalls(const wchar_t *version, WxCalls_t *calls); diff --git a/WeChatFerry/spy/spy.cpp b/WeChatFerry/spy/spy.cpp index ef711fe..576276c 100644 --- a/WeChatFerry/spy/spy.cpp +++ b/WeChatFerry/spy/spy.cpp @@ -1,14 +1,20 @@ #include -#include "load_calls.h" #include "log.h" #include "rpc_server.h" #include "spy.h" #include "util.h" -WxCalls_t g_WxCalls = { 0 }; UINT64 g_WeChatWinDllAddr = 0; +static bool IsWxVersionMatched(const wchar_t *version) +{ + if (wcscmp(version, SUPPORT_VERSION) != 0) { + return false; + } + return true; +} + void InitSpy(LPVOID args) { @@ -19,7 +25,7 @@ void InitSpy(LPVOID args) g_WeChatWinDllAddr = (UINT64)GetModuleHandle(L"WeChatWin.dll"); // 获取wechatWin模块地址 if (g_WeChatWinDllAddr == 0) { LOG_ERROR("获取 wechatWin.dll 模块地址失败"); - return; + return; // TODO: 退出进程,避免后面操作失败 } if (!GetWeChatVersion(version)) { // 获取微信版本 @@ -27,7 +33,7 @@ void InitSpy(LPVOID args) return; } LOG_INFO("WeChat version: {}", Wstring2String(version).c_str()); - if (LoadCalls(version, &g_WxCalls) != 0) { // 加载微信版本对应的Call地址 + if (!IsWxVersionMatched(version)) { LOG_ERROR("不支持当前版本"); MessageBox(NULL, L"不支持当前版本", L"错误", 0); return; diff --git a/WeChatFerry/spy/spy.h b/WeChatFerry/spy/spy.h index 3aa41dd..f985134 100644 --- a/WeChatFerry/spy/spy.h +++ b/WeChatFerry/spy/spy.h @@ -2,5 +2,7 @@ #include "framework.h" +#define SUPPORT_VERSION L"3.9.10.27" + void InitSpy(int port); void CleanupSpy(); diff --git a/WeChatFerry/spy/spy_types.h b/WeChatFerry/spy/spy_types.h index ded8abc..7fd1008 100644 --- a/WeChatFerry/spy/spy_types.h +++ b/WeChatFerry/spy/spy_types.h @@ -4,186 +4,6 @@ #include typedef uint64_t QWORD; -typedef struct UserInfoCall { - DWORD wxid; - DWORD nickName; - DWORD mobile; - DWORD home; -} UserInfoCall_t; - -typedef struct RecvMsg { - DWORD hook; // Hook地址 - DWORD call; // Call地址 - DWORD msgId; // 消息ID地址 - DWORD type; // 消息类型地址 - DWORD isSelf; // 是否自己发送标志地址 - DWORD ts; // TimeStamp - DWORD roomId; // 群聊时,为群ID;私聊时,为微信ID - DWORD content; // 消息内容地址 - DWORD wxid; // 私聊时,为空;群聊时,为发送者微信ID - DWORD sign; // Sign - DWORD thumb; // 缩略图 - DWORD extra; // 附加数据 - DWORD msgXml; // 消息xml内容地址 -} RecvMsg_t; - -typedef struct SendText { - DWORD call1; - DWORD call2; - DWORD call3; -} SendText_t; - -typedef struct Sendfile { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; -} Sendfile_t; - -typedef struct Contact { - DWORD base; - DWORD head; - DWORD wxId; - DWORD wxCode; - DWORD wxRemark; - DWORD wxName; - DWORD wxGender; - DWORD wxCountry; - DWORD wxProvince; - DWORD wxCity; -} Contact_t; - -typedef struct Sql { - DWORD exec; - DWORD base; - DWORD start; - DWORD end; - DWORD slot; - DWORD name; -} Sql_t; - -typedef struct NewFriend { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; -} NewFriend_t; - -typedef struct RoomMember { - DWORD call1; - DWORD call2; - DWORD call3; -} RoomMember_t; - -typedef struct Xml { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; - DWORD param; -} Xml_t; - -typedef struct TF { - DWORD call1; - DWORD call2; - DWORD call3; -} TF_t; - -typedef struct Pyq { - DWORD hook; - DWORD call; - DWORD call1; - DWORD call2; - DWORD call3; - DWORD start; - DWORD end; - DWORD ts; - DWORD wxid; - DWORD content; - DWORD xml; - DWORD step; -} Pyq_t; - -typedef struct DlAttach { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; - DWORD call5; - DWORD call6; -} DlAttach_t; - -typedef struct RevokeMsg { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; - DWORD call5; -} RevokeMsg_t; - -typedef struct CallRichText { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; -} CallRichText_t; - -typedef struct CallPatMsg { - DWORD call1; -} CallPatMsg_t; - -typedef struct CallInviteCM { - DWORD call1; - DWORD call2; - DWORD call3; - DWORD call4; - DWORD call5; - DWORD call6; - DWORD call7; - DWORD call8; -} CallInviteCM_t; - -typedef struct CallOcr { - DWORD call1; - DWORD call2; - DWORD call3; -} CallOcr_t; - -typedef struct CallFm { - DWORD call1; -} CallFm_t; - -typedef struct CallRfLoginQr { - DWORD call1; - DWORD call2; - DWORD url; -} CallRfLoginQr_t; - -typedef struct WxCalls { - DWORD login; // 登录状态 - UserInfoCall_t ui; // 用户信息 - SendText_t sendText; // 发送消息 - RecvMsg_t recvMsg; // 接收消息 - Sendfile_t sendImg; // 发送图片 - Sendfile_t sendFile; // 发送文件 - Xml_t sendXml; // 发送XML - Sendfile_t sendEmo; // 发送表情 - Contact_t contact; // 获取联系人 - Sql_t sql; // 执行 SQL - NewFriend_t anf; // 通过好友申请 - RoomMember_t arm; // 添加群成员 - RoomMember_t drm; // 删除群成员 - TF_t tf; // 接收转账 - Pyq_t pyq; // 接收朋友圈消息 - DlAttach_t da; // 下载资源(图片、文件、视频) - RevokeMsg_t rm; // 撤回消息 - CallRichText_t rt; // 发送消息卡片 - CallPatMsg_t pm; // 发送拍一拍消息 - CallInviteCM_t irm; // 邀请群成员 - CallOcr_t ocr; // OCR - CallFm_t fm; // 转发消息 - CallRfLoginQr_t rlq; // 刷新登录二维码 -} WxCalls_t; struct WxString { const wchar_t *wptr; diff --git a/WeChatFerry/spy/sqlite3.h b/WeChatFerry/spy/sqlite3.h index fe34ab7..09bc15d 100644 --- a/WeChatFerry/spy/sqlite3.h +++ b/WeChatFerry/spy/sqlite3.h @@ -1,7 +1,9 @@ -#pragma once +#pragma once #include "Windows.h" +#include "spy_types.h" + #define SQLITE_OK 0 /* Successful result */ /* beginning-of-error-codes */ diff --git a/WeChatFerry/spy/user_info.cpp b/WeChatFerry/spy/user_info.cpp index f2e370d..28f8543 100644 --- a/WeChatFerry/spy/user_info.cpp +++ b/WeChatFerry/spy/user_info.cpp @@ -1,17 +1,20 @@ #include "user_info.h" -#include "load_calls.h" #include "log.h" #include "util.h" -extern WxCalls_t g_WxCalls; extern UINT64 g_WeChatWinDllAddr; +#define OS_USER_HOME 0x5A7E190 +#define OS_USER_WXID 0x5AB7FB8 +#define OS_USER_NAME 0x5AB8098 +#define OS_USER_MOBILE 0x5AB7FD8 + static char home[MAX_PATH] = { 0 }; string GetHomePath() { if (home[0] == 0) { - string path = Wstring2String(GET_WSTRING(g_WeChatWinDllAddr + g_WxCalls.ui.home)) + "\\WeChat Files\\"; + string path = Wstring2String(GET_WSTRING(g_WeChatWinDllAddr + OS_USER_HOME)) + "\\WeChat Files\\"; strncpy_s(home, path.c_str(), path.size()); } @@ -22,15 +25,15 @@ string GetSelfWxid() { UINT64 wxidType = 0; try { - wxidType = GET_UINT64(g_WeChatWinDllAddr + g_WxCalls.ui.wxid + 0x18); + wxidType = GET_UINT64(g_WeChatWinDllAddr + OS_USER_WXID + 0x18); if (wxidType == 0xF) { - return GET_STRING_FROM_P(g_WeChatWinDllAddr + g_WxCalls.ui.wxid); + return GET_STRING_FROM_P(g_WeChatWinDllAddr + OS_USER_WXID); } else { - return GET_STRING(g_WeChatWinDllAddr + g_WxCalls.ui.wxid); + return GET_STRING(g_WeChatWinDllAddr + OS_USER_WXID); } } catch (...) { LOG_ERROR("wxid type: {:#x}", wxidType); - LOG_BUFFER((uint8_t *)(g_WeChatWinDllAddr + g_WxCalls.ui.wxid), 20); + LOG_BUFFER((uint8_t *)(g_WeChatWinDllAddr + OS_USER_WXID), 20); return "empty_wxid"; } } @@ -41,14 +44,14 @@ UserInfo_t GetUserInfo() ui.wxid = GetSelfWxid(); - UINT64 nameType = GET_UINT64(g_WeChatWinDllAddr + g_WxCalls.ui.nickName + 0x18); + UINT64 nameType = GET_UINT64(g_WeChatWinDllAddr + OS_USER_NAME + 0x18); if (nameType == 0xF) { - ui.name = GET_STRING_FROM_P(g_WeChatWinDllAddr + g_WxCalls.ui.nickName); + ui.name = GET_STRING_FROM_P(g_WeChatWinDllAddr + OS_USER_NAME); } else { // 0x1F - ui.name = GET_STRING(g_WeChatWinDllAddr + g_WxCalls.ui.nickName); + ui.name = GET_STRING(g_WeChatWinDllAddr + OS_USER_NAME); } - ui.mobile = GET_STRING_FROM_P(g_WeChatWinDllAddr + g_WxCalls.ui.mobile); + ui.mobile = GET_STRING_FROM_P(g_WeChatWinDllAddr + OS_USER_MOBILE); ui.home = GetHomePath(); return ui;