#include "pch.h" #include "bootconfig.h" #include "logging.h" #include "veh.h" #include "xivfixes.h" HMODULE g_hModule; HINSTANCE g_hGameInstance = GetModuleHandleW(nullptr); DllExport DWORD WINAPI Initialize(LPVOID lpParam, HANDLE hMainThreadContinue) { logging::log_file.open(utils::get_env("DALAMUD_BOOT_LOGFILE"), std::ios_base::out | std::ios_base::app); if (bootconfig::is_show_console()) ConsoleSetup(L"Dalamud Boot"); if (!logging::log_file) { logging::print("Couldn't open log file!"); } logging::print("Dalamud.Boot Injectable, (c) 2021 XIVLauncher Contributors"); logging::print("Built at: " __DATE__ "@" __TIME__); if (bootconfig::is_wait_messagebox()) MessageBoxW(nullptr, L"Press OK to continue", L"Dalamud Boot", MB_OK); xivfixes::apply_all(true); if (bootconfig::is_wait_debugger()) { logging::print("Waiting for debugger to attach..."); while (!IsDebuggerPresent()) Sleep(100); logging::print("Debugger attached."); } const auto fs_module_path = utils::get_module_path(g_hModule); const auto runtimeconfig_path = std::filesystem::path(fs_module_path).replace_filename(L"Dalamud.runtimeconfig.json").wstring(); const auto module_path = std::filesystem::path(fs_module_path).replace_filename(L"Dalamud.dll").wstring(); // ============================== CLR ========================================= // void* entrypoint_vfn; int result = InitializeClrAndGetEntryPoint( g_hModule, runtimeconfig_path, module_path, L"Dalamud.EntryPoint, Dalamud", L"Initialize", L"Dalamud.EntryPoint+InitDelegate, Dalamud", &entrypoint_vfn); if (result != 0) return result; using custom_component_entry_point_fn = void (CORECLR_DELEGATE_CALLTYPE*)(LPVOID, HANDLE); const auto entrypoint_fn = reinterpret_cast(entrypoint_vfn); // ============================== VEH ======================================== // logging::print("Initializing VEH..."); if (utils::is_running_on_linux()) { logging::print("=> VEH was disabled, running on linux"); } else if (bootconfig::is_veh_enabled()) { if (veh::add_handler(bootconfig::is_veh_full())) logging::print("=> Done!"); else logging::print("=> Failed!"); } else { logging::print("VEH was disabled manually"); } // ============================== Dalamud ==================================== // logging::print("Initializing Dalamud..."); entrypoint_fn(lpParam, hMainThreadContinue); logging::print("Done!"); return 0; } BOOL APIENTRY DllMain(const HMODULE hModule, const DWORD dwReason, LPVOID lpReserved) { DisableThreadLibraryCalls(hModule); switch (dwReason) { case DLL_PROCESS_ATTACH: g_hModule = hModule; if (const auto mhStatus = MH_Initialize(); MH_OK != mhStatus) { logging::print("Failed to initialize MinHook (status={})", static_cast(mhStatus)); return FALSE; } logging::update_dll_load_status(true); break; case DLL_PROCESS_DETACH: logging::update_dll_load_status(false); xivfixes::apply_all(false); if (const auto mhStatus = MH_Uninitialize(); MH_OK != mhStatus) { logging::print("Failed to uninitialize MinHook (status={})", static_cast(mhStatus)); __fastfail(logging::MinHookUnload); } veh::remove_handler(); //logging::log_file.close(); break; } return TRUE; }