From 1e8f93e6ea6da9dfa6bf8b7bb204112deb0d68a7 Mon Sep 17 00:00:00 2001 From: momo5502 Date: Sat, 17 Sep 2022 13:42:25 +0200 Subject: [PATCH] Some demonware fixes --- src/client/component/console.cpp | 4 + src/client/component/demonware.cpp | 93 +++++-------------- src/client/game/demonware/keys.cpp | 2 +- .../game/demonware/servers/auth3_server.cpp | 6 +- .../game/demonware/servers/lobby_server.cpp | 8 +- src/client/game/demonware/service.hpp | 2 +- .../game/demonware/services/bdStorage.cpp | 14 +-- src/common/utils/hook.cpp | 10 +- src/common/utils/hook.hpp | 2 +- 9 files changed, 48 insertions(+), 93 deletions(-) diff --git a/src/client/component/console.cpp b/src/client/component/console.cpp index 3f1c6dc6..2e00d166 100644 --- a/src/client/component/console.cpp +++ b/src/client/component/console.cpp @@ -20,6 +20,10 @@ namespace console void print_message(const char* message) { +#ifndef NDEBUG + OutputDebugStringA(message); +#endif + if (started && !terminate_runner) { game::Com_Printf(0, 0, "%s", message); diff --git a/src/client/component/demonware.cpp b/src/client/component/demonware.cpp index bba912cf..4f95fd3b 100644 --- a/src/client/component/demonware.cpp +++ b/src/client/component/demonware.cpp @@ -18,12 +18,13 @@ namespace demonware { namespace { - volatile bool exit_server; - std::thread server_thread; - utils::concurrency::container> blocking_sockets; - utils::concurrency::container> socket_map; - server_registry tcp_servers; - server_registry udp_servers; + std::atomic_bool exit_server{false}; + std::thread server_thread{}; + utils::concurrency::container> blocking_sockets{}; + utils::concurrency::container> socket_map{}; + server_registry tcp_servers{}; + server_registry udp_servers{}; + std::unordered_map original_imports{}; tcp_server* find_server(const SOCKET socket) { @@ -118,7 +119,7 @@ namespace demonware int getaddrinfo_stub(const char* name, const char* service, const addrinfo* hints, addrinfo** res) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[ network ]: [getaddrinfo]: \"%s\" \"%s\"\n", name, service); #endif @@ -201,7 +202,7 @@ namespace demonware hostent* gethostbyname_stub(const char* name) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[ network ]: [gethostbyname]: \"%s\"\n", name); #endif @@ -424,63 +425,6 @@ namespace demonware } } - void bd_logger_stub() - { - //printf("logged\n"); - } - -#ifdef DW_DEBUG - void a(unsigned int n) - { - printf("bdAuth: Auth task failed with HTTP code [%u]\n", n); - } - - void b(unsigned int n) - { - printf("bdAuth: Decoded client ticket of unexpected size [%u]\n", n); - } - - void c(unsigned int n) - { - printf("bdAuth: Decoded server ticket of unexpected size [%u]\n", n); - } - - void d() - { - printf("bdAuth: Auth ticket magic number mismatch\n"); - } - - void e() - { - printf("bdAuth: Cross Authentication completed\n"); - } - - void f() - { - printf("bdAuth: Auth task reply contains invalid data / format\n"); - } - - void g(unsigned int n) - { - printf("bdAuth: Auth task returned with error code [%u]\n", n); - } - - void h(unsigned int n) - { - printf("bdAuth: Invalid or No Task ID [%u] in Auth reply\n", n); - } - - void i() - { - printf("bdAuth: Received reply from DemonWare Auth server\n"); - } - - void l() - { - printf("bdAuth: Unknown error\n"); - } -#endif - utils::hook::detour handle_auth_reply_hook; bool handle_auth_reply_stub(void* a1, void* a2, void* a3) @@ -503,14 +447,16 @@ namespace demonware { const utils::nt::library game_module{}; - auto result = false; - result = result || utils::hook::iat(game_module, "wsock32.dll", process, stub); - result = result || utils::hook::iat(game_module, "WS2_32.dll", process, stub); + std::optional> result{}; + if(!result) result = utils::hook::iat(game_module, "wsock32.dll", process, stub); + if(!result) result = utils::hook::iat(game_module, "WS2_32.dll", process, stub); if (!result) { throw std::runtime_error("Failed to hook: " + process); } + + original_imports[result->first] = result->second; } } @@ -546,9 +492,9 @@ namespace demonware register_hook("getpeername", io::getpeername_stub); register_hook("getsockname", io::getsockname_stub); - //utils::hook::set(0x7C0AD9_b, 0x0); // CURLOPT_SSL_VERIFYPEER - //utils::hook::set(0x7C0AC5_b, 0xAF); // CURLOPT_SSL_VERIFYHOST - //utils::hook::set(0xA1327C_b, 0x0); // HTTPS -> HTTP + utils::hook::set(0x14293E829_g, 0x0); // CURLOPT_SSL_VERIFYPEER + utils::hook::set(0x15F3CCFED_g, 0xAF); // CURLOPT_SSL_VERIFYHOST + utils::hook::set(0x1430B9810_g, 0x0); // HTTPS -> HTTP utils::hook::copy_string(0x1430B96E0_g, "http://prod.umbrella.demonware.net"); utils::hook::copy_string(0x1430B9BE0_g, "http://prod.uno.demonware.net/v1.0"); @@ -587,6 +533,11 @@ namespace demonware { server_thread.join(); } + + for (const auto& import : original_imports) + { + utils::hook::set(import.first, import.second); + } } }; } diff --git a/src/client/game/demonware/keys.cpp b/src/client/game/demonware/keys.cpp index 645ef2d3..1d259f0c 100644 --- a/src/client/game/demonware/keys.cpp +++ b/src/client/game/demonware/keys.cpp @@ -89,7 +89,7 @@ namespace demonware std::memcpy(data.m_dec_key, &out_3[40], 16); std::memcpy(data.m_enc_key, &out_3[56], 16); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW] Response id: %s\n", utils::string::dump_hex(std::string(&out_2[8], 8)).data()); printf("[DW] Hash verify: %s\n", utils::string::dump_hex(std::string(&out_3[20], 20)).data()); printf("[DW] AES dec key: %s\n", utils::string::dump_hex(std::string(&out_3[40], 16)).data()); diff --git a/src/client/game/demonware/servers/auth3_server.cpp b/src/client/game/demonware/servers/auth3_server.cpp index 02a6adc5..f3e0bf04 100644 --- a/src/client/game/demonware/servers/auth3_server.cpp +++ b/src/client/game/demonware/servers/auth3_server.cpp @@ -38,7 +38,7 @@ namespace demonware { if (packet.starts_with("POST /auth/")) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [auth]: user requested authentication.\n"); #endif return; @@ -81,7 +81,7 @@ namespace demonware } } -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [auth]: authenticating user %s\n", token.data() + 64); #endif @@ -161,7 +161,7 @@ namespace demonware this->send_reply(&reply); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [auth]: user successfully authenticated.\n"); #endif } diff --git a/src/client/game/demonware/servers/lobby_server.cpp b/src/client/game/demonware/servers/lobby_server.cpp index 98c2dd73..c19b0a53 100644 --- a/src/client/game/demonware/servers/lobby_server.cpp +++ b/src/client/game/demonware/servers/lobby_server.cpp @@ -65,7 +65,7 @@ namespace demonware } else if (size == 0xC8) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [lobby]: received client_header_ack.\n"); #endif @@ -81,7 +81,7 @@ namespace demonware raw_reply reply(packet_2); this->send_reply(&reply); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [lobby]: sending server_header_ack.\n"); #endif return; @@ -98,7 +98,7 @@ namespace demonware if (type == 0x82) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [lobby]: received client_auth.\n"); #endif std::string packet_3(packet.data(), packet.size() - 8); // this 8 are client hash check? @@ -113,7 +113,7 @@ namespace demonware raw_reply reply(response); this->send_reply(&reply); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [lobby]: sending server_auth_done.\n"); #endif return; diff --git a/src/client/game/demonware/service.hpp b/src/client/game/demonware/service.hpp index 0e90b84c..2fc121a1 100644 --- a/src/client/game/demonware/service.hpp +++ b/src/client/game/demonware/service.hpp @@ -51,7 +51,7 @@ namespace demonware if (it != this->tasks_.end()) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW] %s: executing task '%d'\n", name_.data(), this->task_id_); #endif diff --git a/src/client/game/demonware/services/bdStorage.cpp b/src/client/game/demonware/services/bdStorage.cpp index a8ead05b..4a44fc3e 100644 --- a/src/client/game/demonware/services/bdStorage.cpp +++ b/src/client/game/demonware/services/bdStorage.cpp @@ -57,7 +57,7 @@ namespace demonware } } -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: missing publisher file: %s\n", name.data()); #endif @@ -76,7 +76,7 @@ namespace demonware buffer->read_uint16(&offset); buffer->read_string(&filename); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: list publisher files: %s\n", filename.data()); #endif @@ -106,7 +106,7 @@ namespace demonware buffer->read_string(&unk); buffer->read_string(&filename); -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: loading publisher file: %s\n", filename.data()); #endif @@ -114,7 +114,7 @@ namespace demonware if (this->load_publisher_resource(filename, data)) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: sending publisher file: %s, size: %lld\n", filename.data(), data.size()); #endif @@ -171,7 +171,7 @@ namespace demonware info->filename = filename; info->data = data; -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: set user file: %s\n", filename.data()); #endif @@ -206,7 +206,7 @@ namespace demonware const auto path = get_user_file_path(filename); if (!utils::io::read_file(path, &data)) { -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: get user file: missing file: %s, %s, %s\n", game.data(), filename.data(), platform.data()); #endif continue; @@ -222,7 +222,7 @@ namespace demonware reply->add(response); ++count; -#ifdef DW_DEBUG +#ifndef NDEBUG printf("[DW]: [bdStorage]: get user file: %s, %s, %s\n", game.data(), filename.data(), platform.data()); #endif } diff --git a/src/common/utils/hook.cpp b/src/common/utils/hook.cpp index ec45b548..e28196d5 100644 --- a/src/common/utils/hook.cpp +++ b/src/common/utils/hook.cpp @@ -345,22 +345,22 @@ namespace utils::hook } } - bool iat(const nt::library& library, const std::string& target_library, const std::string& process, void* stub) + std::optional> iat(const nt::library& library, const std::string& target_library, const std::string& process, void* stub) { - if (!library.is_valid()) return false; + if (!library.is_valid()) return {}; auto* const ptr = library.get_iat_entry(target_library, process); - if (!ptr) return false; + if (!ptr) return {}; store_original_data(ptr, sizeof(*ptr)); DWORD protect; VirtualProtect(ptr, sizeof(*ptr), PAGE_EXECUTE_READWRITE, &protect); - *ptr = stub; + std::swap(*ptr, stub); VirtualProtect(ptr, sizeof(*ptr), protect, &protect); - return true; + return {{ptr, stub}}; } void nop(void* place, const size_t length) diff --git a/src/common/utils/hook.hpp b/src/common/utils/hook.hpp index 7469376b..ff9aead0 100644 --- a/src/common/utils/hook.hpp +++ b/src/common/utils/hook.hpp @@ -147,7 +147,7 @@ namespace utils::hook void un_move(); }; - bool iat(const nt::library& library, const std::string& target_library, const std::string& process, void* stub); + std::optional> iat(const nt::library& library, const std::string& target_library, const std::string& process, void* stub); void nop(void* place, size_t length); void nop(size_t place, size_t length);