From 2210a97d6159301685bfe0cf7c762c75e7732704 Mon Sep 17 00:00:00 2001 From: HolographicHat Date: Sun, 24 Dec 2023 23:59:24 +0800 Subject: [PATCH] 4.3 --- lib/YaeAchievementLib.vcxproj | 3 +- lib/src/dllmain.cpp | 92 ++++++++---------------- lib/src/il2cpp-api-functions.h | 1 - lib/src/il2cpp-appdata.h | 15 ++-- lib/src/il2cpp-functions.h | 18 ++--- lib/src/il2cpp-init.cpp | 25 ++++--- lib/src/il2cpp-types-ptr.h | 2 + lib/src/il2cpp-types.h | 30 ++------ lib/src/il2cpp-unity-functions.h | 3 - lib/src/util.h | 3 - res/proto/AchievementAllDataNotify.proto | 8 +-- src/GlobalVars.cs | 4 +- 12 files changed, 69 insertions(+), 135 deletions(-) delete mode 100644 lib/src/il2cpp-api-functions.h create mode 100644 lib/src/il2cpp-types-ptr.h delete mode 100644 lib/src/il2cpp-unity-functions.h diff --git a/lib/YaeAchievementLib.vcxproj b/lib/YaeAchievementLib.vcxproj index 9f48be0..2533cdf 100644 --- a/lib/YaeAchievementLib.vcxproj +++ b/lib/YaeAchievementLib.vcxproj @@ -110,12 +110,11 @@ - + - diff --git a/lib/src/dllmain.cpp b/lib/src/dllmain.cpp index 5af644c..495fc36 100644 --- a/lib/src/dllmain.cpp +++ b/lib/src/dllmain.cpp @@ -1,78 +1,46 @@ -#include "pch.h" +// ReSharper disable CppCStyleCast +// ReSharper disable CppInconsistentNaming +// ReSharper disable CppClangTidyModernizeUseStdPrint +// ReSharper disable CppClangTidyClangDiagnosticCastAlign +// ReSharper disable CppClangTidyHicppMultiwayPathsCovered +// ReSharper disable CppDefaultCaseNotHandledInSwitchStatement +// ReSharper disable CppClangTidyClangDiagnosticCastFunctionTypeStrict + +#include "pch.h" #include "util.h" #include "il2cpp-init.h" -using Genshin::ByteArray, Genshin::ClientKcpEvent, Genshin::KcpPacket, Genshin::KcpEventType; -using std::to_string; +using Genshin::ByteArray; HWND unityWnd = nullptr; HANDLE hPipe = nullptr; -// Allow Protocol: GetPlayerTokenRsp, PlayerLoginRsp, AchievementAllDataNotify, PingRsp -std::set PacketWhitelist = { 1574, 1548, 29462, 2794 }; - -bool OnPacket(KcpPacket* pkt) { - if (pkt->data == nullptr) return true; - auto len = pkt->length; - auto data = (ByteArray*)new BYTE[len + 32]; - data->max_length = len; - memcpy(data->vector, pkt->data, len); - Genshin::XorEncrypt(&data, len, nullptr); - if (ReadMapped(data->vector, 0) != 0x4567) { - delete[] data; - return true; - } - if (!PacketWhitelist.contains(ReadMapped(data->vector, 2))) { - //ifdef _DEBUG - printf("Blocked cmdid: %d\n", ReadMapped(data->vector, 2)); - //endif - delete[] data; - return false; - } - printf("Passed cmdid: %d\n", ReadMapped(data->vector, 2)); - if (ReadMapped(data->vector, 2) == 29462) { - const auto headLength = ReadMapped(data->vector, 4); - const auto dataLength = ReadMapped(data->vector, 6); - const auto cStr = base64_encode(data->vector + 10 + headLength, dataLength) + "\n"; - WriteFile(hPipe, cStr.c_str(), cStr.length(), nullptr, nullptr); - CloseHandle(hPipe); - auto manager = Genshin::GetSingletonInstance(Genshin::GetSingletonManager(), il2cpp_string_new("GameManager")); - Genshin::ForceQuit(manager); - } - delete[] data; - return true; -} - std::string checksum; namespace Hook { - void SetVersion(void* obj, Il2CppString* value, void* method) { - const auto version = ToString(value); - value = string_new(version + " YaeAchievement"); - CALL_ORIGIN(SetVersion, obj, value, method); - } - - bool KcpRecv(void* client, ClientKcpEvent* evt, void* method) { - const auto result = CALL_ORIGIN(KcpRecv, client, evt, method); - if (result == 0 || evt->fields.type != KcpEventType::EventRecvMsg) { - return result; + ByteArray* UnityEngine_RecordUserData(const INT type) { + if (type == 0) { + const auto arr = new ByteArray {}; + const auto len = checksum.length(); + arr->max_length = len; + memcpy(&arr->vector[0], checksum.data(), len); + return arr; } - return OnPacket(evt->fields.packet) ? result : false; - } - - ByteArray* UnityEngine_RecordUserData(INT type) { return new ByteArray {}; } - VOID SetChecksum(LPVOID obj, Il2CppString* value) { - CALL_ORIGIN(SetChecksum, obj, il2cpp_string_new(checksum.c_str())); - } - - VOID RequestLogin(LPVOID obj, LPVOID token, UINT32 uid) { - HookManager::install(Genshin::SetChecksum, SetChecksum); - CALL_ORIGIN(RequestLogin, obj, token, uid); - HookManager::detach(SetChecksum); + void OnAchievementAllDataNotify(LPVOID obj, const LPVOID ntf) { + const auto cos = Genshin::il2cpp_object_new(*Genshin::CodedOutputStream__TypeInfo); + const auto len = Genshin::CalculateSize(ntf); + const auto buf = (ByteArray*) new uint8_t[0x20 + len] {}; + buf->max_length = len; + Genshin::CodedOutputStreamInit(cos, buf, 0, len); + Genshin::ProtoWriteTo(ntf, cos); + const auto str = base64_encode(buf->vector, len) + "\n"; + WriteFile(hPipe, str.c_str(), (DWORD) str.length(), nullptr, nullptr); + CloseHandle(hPipe); + ExitProcess(0); } } @@ -89,9 +57,7 @@ void Run(HMODULE* phModule) { const auto result = Genshin::RecordUserData(i); checksum += string(reinterpret_cast(&result->vector[0]), result->max_length); } - HookManager::install(Genshin::KcpRecv, Hook::KcpRecv); - HookManager::install(Genshin::SetVersion, Hook::SetVersion); - HookManager::install(Genshin::RequestLogin, Hook::RequestLogin); + HookManager::install(Genshin::OnAchievementAllDataNotify, Hook::OnAchievementAllDataNotify); HookManager::install(Genshin::UnityEngine_RecordUserData, Hook::UnityEngine_RecordUserData); hPipe = CreateFile(R"(\\.\pipe\YaeAchievementPipe)", GENERIC_WRITE, 0, nullptr, OPEN_EXISTING, 0, nullptr); if (hPipe == INVALID_HANDLE_VALUE) { diff --git a/lib/src/il2cpp-api-functions.h b/lib/src/il2cpp-api-functions.h deleted file mode 100644 index b8a9c75..0000000 --- a/lib/src/il2cpp-api-functions.h +++ /dev/null @@ -1 +0,0 @@ -DO_API(0x4243d0, 0x420bf0, Il2CppString*, il2cpp_string_new, (const char* str)); diff --git a/lib/src/il2cpp-appdata.h b/lib/src/il2cpp-appdata.h index 485b7e8..546829a 100644 --- a/lib/src/il2cpp-appdata.h +++ b/lib/src/il2cpp-appdata.h @@ -1,20 +1,19 @@ +// ReSharper disable CppClangTidyBugproneMacroParentheses + #pragma once #include "il2cpp-types.h" -// IL2CPP APIs -#define DO_API(ca, oa, r, n, p) extern r (*n) p -#include "il2cpp-api-functions.h" -#undef DO_API - // Application-specific functions #define DO_APP_FUNC(ca, oa, r, n, p) extern r (*n) p +#define DO_UNI_FUNC(ca, oa, r, n, p) extern r (*n) p namespace Genshin { #include "il2cpp-functions.h" } +#undef DO_UNI_FUNC #undef DO_APP_FUNC -#define DO_UNI_FUNC(ca, oa, r, n, p) extern r (*n) p +#define DO_TYPEDEF(ca, oa, n) extern n##__Class **n##__TypeInfo namespace Genshin { -#include "il2cpp-unity-functions.h" +#include "il2cpp-types-ptr.h" } -#undef DO_UNI_FUNC +#undef DO_TYPEDEF \ No newline at end of file diff --git a/lib/src/il2cpp-functions.h b/lib/src/il2cpp-functions.h index 4ba6d1e..8455bf9 100644 --- a/lib/src/il2cpp-functions.h +++ b/lib/src/il2cpp-functions.h @@ -2,20 +2,16 @@ using namespace Genshin; // DO_APP_FUNC(CN_OFFSET, OS_OFFSET, RETURN, FUNC_NAME, (ARGS...)); -DO_APP_FUNC(0x1929870, 0x1922c30, void, SetVersion, (void* obj, Il2CppString* value, void* method)); +DO_APP_FUNC(0x4F1EF0, 0x545600, LPVOID, il2cpp_object_new, (LPVOID t)); -DO_APP_FUNC(0x6e7d020, 0x6e38a10, ByteArray*, RecordUserData, (int32_t nType)); +DO_APP_FUNC(0x052818B0, 0x0529E520, ByteArray*, RecordUserData, (int32_t nType)); -DO_APP_FUNC(0x2b13f40, 0x2b09ce0, void, XorEncrypt, (ByteArray** data, int length, void* method)); +DO_APP_FUNC(0x05DCBE60, 0x05DF2F40, void, OnAchievementAllDataNotify, (LPVOID obj, LPVOID ntf)); -DO_APP_FUNC(0x2d79560, 0x2d6e6f0, bool, KcpRecv, (void* client, ClientKcpEvent* evt, void* method)); +DO_APP_FUNC(0x043EC0B0, 0x043FA380, int, CalculateSize, (LPVOID obj)); -DO_APP_FUNC(0x20004f0, 0x1ff8530, VOID, RequestLogin, (LPVOID obj, LPVOID token, UINT uid)); +DO_APP_FUNC(0x043EBFF0, 0x043FA2C0, void, ProtoWriteTo, (LPVOID obj, LPVOID output)); -DO_APP_FUNC(0x130ead0, 0x1b90950, VOID, SetChecksum, (LPVOID obj, Il2CppString* value)); +DO_APP_FUNC(0x06F08220, 0x06F3F280, void, CodedOutputStreamInit, (LPVOID obj, LPVOID buffer, int offset, int length)); -DO_APP_FUNC(0x2266e40, 0x225eb50, VOID, ForceQuit, (LPVOID obj)); - -DO_APP_FUNC(0x60af410, 0x60735f0, LPVOID, GetSingletonManager, ()); - -DO_APP_FUNC(0x60af140, 0x6073320, LPVOID, GetSingletonInstance, (LPVOID obj, Il2CppString* value)); +DO_UNI_FUNC(0x105970, 0x105970, ByteArray*, UnityEngine_RecordUserData, (int32_t nType)); diff --git a/lib/src/il2cpp-init.cpp b/lib/src/il2cpp-init.cpp index ec7c369..bedc197 100644 --- a/lib/src/il2cpp-init.cpp +++ b/lib/src/il2cpp-init.cpp @@ -1,22 +1,22 @@ +// ReSharper disable CppClangTidyBugproneMacroParentheses + #include "pch.h" #include "il2cpp-init.h" -#define DO_API(ca, oa, r, n, p) r (*n) p -#include "il2cpp-api-functions.h" -#undef DO_API - #define DO_APP_FUNC(ca, oa, r, n, p) r (*n) p +#define DO_UNI_FUNC(ca, oa, r, n, p) r (*n) p namespace Genshin { #include "il2cpp-functions.h" } +#undef DO_UNI_FUNC #undef DO_APP_FUNC -#define DO_UNI_FUNC(ca, oa, r, n, p) r (*n) p +#define DO_TYPEDEF(ca, oa, n) n##__Class **n##__TypeInfo namespace Genshin { -#include "il2cpp-unity-functions.h" +#include "il2cpp-types-ptr.h" } -#undef DO_UNI_FUNC +#undef DO_TYPEDEF using std::string; @@ -27,13 +27,12 @@ void InitIL2CPP() { auto hBase = GetModuleHandle("UserAssembly.dll"); auto bAddr = (UINT64)hBase; auto cAddr = (UINT64)GetModuleHandle("UnityPlayer.dll"); - #define DO_API(ca, oa, r, n, p) n = (r (*) p)(bAddr + (isCN ? ca : oa)) - #include "il2cpp-api-functions.h" - #undef DO_API #define DO_APP_FUNC(ca, oa, r, n, p) n = (r (*) p)(bAddr + (isCN ? ca : oa)) - #include "il2cpp-functions.h" - #undef DO_APP_FUNC #define DO_UNI_FUNC(ca, oa, r, n, p) n = (r (*) p)(cAddr + (isCN ? ca : oa)) - #include "il2cpp-unity-functions.h" + #include "il2cpp-functions.h" #undef DO_UNI_FUNC + #undef DO_APP_FUNC + #define DO_TYPEDEF(ca, oa, n) n##__TypeInfo = (n##__Class **)(bAddr + (isCN ? ca : oa)) + #include "il2cpp-types-ptr.h" + #undef DO_TYPEDEF } diff --git a/lib/src/il2cpp-types-ptr.h b/lib/src/il2cpp-types-ptr.h new file mode 100644 index 0000000..499766f --- /dev/null +++ b/lib/src/il2cpp-types-ptr.h @@ -0,0 +1,2 @@ +// LFGDACFKABF +DO_TYPEDEF(0x2965BA0, 0, CodedOutputStream); diff --git a/lib/src/il2cpp-types.h b/lib/src/il2cpp-types.h index 81525b3..dd428c4 100644 --- a/lib/src/il2cpp-types.h +++ b/lib/src/il2cpp-types.h @@ -1,3 +1,6 @@ +// ReSharper disable CppClangTidyClangDiagnosticReservedIdentifier +// ReSharper disable CppClangTidyBugproneReservedIdentifier + #pragma once #pragma region IL2CPPInternalTypes @@ -36,30 +39,7 @@ namespace Genshin { il2cpp_array_size_t max_length; uint8_t vector[32]; }; - - struct KcpPacket { - BYTE* data; - UINT32 length; + + struct CodedOutputStream__Class { }; - - enum class KcpEventType : int { - EventNotSet = -1, - EventConnect = 0, - EventConnectFailed = 1, - EventDisconnect = 2, - EventRecvMsg = 3, - EventCount = 4, - }; - - struct KcpEvent_Fields { - KcpEventType type; - UINT32 token; - UINT32 data; - KcpPacket* packet; - }; - - struct ClientKcpEvent { - KcpEvent_Fields fields; - }; - } diff --git a/lib/src/il2cpp-unity-functions.h b/lib/src/il2cpp-unity-functions.h deleted file mode 100644 index 76b5796..0000000 --- a/lib/src/il2cpp-unity-functions.h +++ /dev/null @@ -1,3 +0,0 @@ -using namespace Genshin; - -DO_UNI_FUNC(0x105550, 0x105550, ByteArray*, UnityEngine_RecordUserData, (int32_t nType)); diff --git a/lib/src/util.h b/lib/src/util.h index 7787f67..9a83192 100644 --- a/lib/src/util.h +++ b/lib/src/util.h @@ -8,9 +8,6 @@ HWND FindMainWindowByPID(DWORD pid); string ToString(Il2CppString* str, UINT codePage = CP_ACP); std::string base64_encode(BYTE const* buf, unsigned int bufLen); -#define cstring_new(str) il2cpp_string_new(str) -#define string_new(str) cstring_new((str).c_str()) - #define ErrorDialogT(title, msg) MessageBox(unityWnd, msg, title, MB_OK | MB_ICONERROR | MB_SYSTEMMODAL); #define ErrorDialog(msg) ErrorDialogT("YaeAchievement", msg) #define Win32ErrorDialog(code) ErrorDialogT("YaeAchievement", ("CRITICAL ERROR!\nError code: " + std::to_string(GetLastError()) + "-"#code"\n\nPlease take the screenshot and contact developer by GitHub Issue to solve this problem\nNOT MIHOYO/COGNOSPHERE CUSTOMER SERVICE!").c_str()) diff --git a/res/proto/AchievementAllDataNotify.proto b/res/proto/AchievementAllDataNotify.proto index beefd50..71a621b 100644 --- a/res/proto/AchievementAllDataNotify.proto +++ b/res/proto/AchievementAllDataNotify.proto @@ -10,12 +10,12 @@ message Achievement { REWARD_TAKEN = 3; } uint32 timestamp = 11; - uint32 current = 12; + uint32 current = 15; uint32 total = 3; - uint32 id = 15; - Status status = 7; + uint32 id = 14; + Status status = 8; } message AchievementAllDataNotify { - repeated Achievement list = 8; + repeated Achievement list = 9; } diff --git a/src/GlobalVars.cs b/src/GlobalVars.cs index 178d222..015c1f1 100644 --- a/src/GlobalVars.cs +++ b/src/GlobalVars.cs @@ -20,8 +20,8 @@ public static class GlobalVars { public static readonly string CachePath = Path.Combine(DataPath, "cache"); public static readonly string LibFilePath = Path.Combine(DataPath, "YaeAchievement.dll"); - public const uint AppVersionCode = 42; - public const string AppVersionName = "3.2"; + public const uint AppVersionCode = 43; + public const string AppVersionName = "3.3"; public const string PipeName = "YaeAchievementPipe"; public const string BucketHost = "https://cn-cd-1259389942.file.myqcloud.com";