diff --git a/UnleashedRecomp/CMakeLists.txt b/UnleashedRecomp/CMakeLists.txt index a33b334..4bae402 100644 --- a/UnleashedRecomp/CMakeLists.txt +++ b/UnleashedRecomp/CMakeLists.txt @@ -112,7 +112,6 @@ endif() set(SWA_CPU_CXX_SOURCES "cpu/guest_thread.cpp" - "cpu/code_cache.cpp" ) set(SWA_GPU_CXX_SOURCES diff --git a/UnleashedRecomp/api/SWA.inl b/UnleashedRecomp/api/SWA.inl index d6ef4c5..acffd8f 100644 --- a/UnleashedRecomp/api/SWA.inl +++ b/UnleashedRecomp/api/SWA.inl @@ -1,6 +1,5 @@ #pragma once -#include #include #include diff --git a/UnleashedRecomp/apu/audio.cpp b/UnleashedRecomp/apu/audio.cpp index 9f0f2de..50683c8 100644 --- a/UnleashedRecomp/apu/audio.cpp +++ b/UnleashedRecomp/apu/audio.cpp @@ -3,7 +3,7 @@ #include #include "audio.h" -#include "cpu/code_cache.h" +#include #define AUDIO_DRIVER_KEY (uint32_t)('DAUD') @@ -21,7 +21,7 @@ uint32_t XAudioRegisterRenderDriverClient(be* callback, be* #endif *driver = AUDIO_DRIVER_KEY; - XAudioRegisterClient(KeFindHostFunction(*callback), callback[1]); + XAudioRegisterClient(g_memory.FindFunction(*callback), callback[1]); return 0; } diff --git a/UnleashedRecomp/apu/driver/sdl2_driver.cpp b/UnleashedRecomp/apu/driver/sdl2_driver.cpp index 3015608..de01543 100644 --- a/UnleashedRecomp/apu/driver/sdl2_driver.cpp +++ b/UnleashedRecomp/apu/driver/sdl2_driver.cpp @@ -1,7 +1,5 @@ #include "sdl2_driver.h" -#include #include -#include #include static PPCFunc* g_clientCallback{}; @@ -50,7 +48,7 @@ static void AudioThread() if ((queuedAudioSize / callbackAudioSize) <= MAX_LATENCY) { ctx.ppcContext.r3.u32 = g_clientCallbackParam; - g_clientCallback(ctx.ppcContext, reinterpret_cast(g_memory.base)); + g_clientCallback(ctx.ppcContext, g_memory.base); } auto now = std::chrono::steady_clock::now(); diff --git a/UnleashedRecomp/apu/driver/xaudio_driver.cpp b/UnleashedRecomp/apu/driver/xaudio_driver.cpp index 1d98ca9..97fc0b3 100644 --- a/UnleashedRecomp/apu/driver/xaudio_driver.cpp +++ b/UnleashedRecomp/apu/driver/xaudio_driver.cpp @@ -1,9 +1,7 @@ #include #include "xaudio_driver.h" #include -#include #include -#include #include #include @@ -55,7 +53,7 @@ PPC_FUNC(DriverLoop) WaitForSingleObject(g_audioSemaphore, INFINITE); ctx.r3.u64 = g_clientCallbackParam; - GuestCode::Run((void*)g_clientCallback, &ctx); + g_clientCallback(ctx, g_memory.base); } } diff --git a/UnleashedRecomp/cpu/code_cache.cpp b/UnleashedRecomp/cpu/code_cache.cpp deleted file mode 100644 index bbbebc4..0000000 --- a/UnleashedRecomp/cpu/code_cache.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include -#include "code_cache.h" -#include "ppc_context.h" - -CodeCache::CodeCache() -{ -#ifdef _WIN32 - bucket = (char*)VirtualAlloc(nullptr, 0x200000000, MEM_RESERVE, PAGE_READWRITE); - assert(bucket != nullptr); -#else - bucket = (char*)mmap(NULL, 0x200000000, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0); - assert(bucket != (char*)MAP_FAILED); -#endif -} - -CodeCache::~CodeCache() -{ -#ifdef _WIN32 - VirtualFree(bucket, 0, MEM_RELEASE); -#else - munmap(bucket, 0x200000000); -#endif -} - -void CodeCache::Init() -{ - for (size_t i = 0; PPCFuncMappings[i].guest != 0; i++) - { - if (PPCFuncMappings[i].host != nullptr) - { -#ifdef _WIN32 - VirtualAlloc(bucket + PPCFuncMappings[i].guest * 2, sizeof(void*), MEM_COMMIT, PAGE_READWRITE); -#endif - *(void**)(bucket + PPCFuncMappings[i].guest * 2) = (void*)PPCFuncMappings[i].host; - } - } -} - -void CodeCache::Insert(uint32_t guest, PPCFunc* host) -{ -#ifdef _WIN32 - VirtualAlloc(bucket + static_cast(guest) * 2, sizeof(void*), MEM_COMMIT, PAGE_READWRITE); -#endif - *reinterpret_cast(bucket + static_cast(guest) * 2) = host; -} - -void* CodeCache::Find(uint32_t guest) const -{ - return *reinterpret_cast(bucket + static_cast(guest) * 2); -} - -SWA_API PPCFunc* KeFindHostFunction(uint32_t guest) -{ - return reinterpret_cast(g_codeCache.Find(guest)); -} - -SWA_API void KeInsertHostFunction(uint32_t guest, PPCFunc* function) -{ - g_codeCache.Insert(guest, function); -} diff --git a/UnleashedRecomp/cpu/code_cache.h b/UnleashedRecomp/cpu/code_cache.h deleted file mode 100644 index e2a1d5a..0000000 --- a/UnleashedRecomp/cpu/code_cache.h +++ /dev/null @@ -1,19 +0,0 @@ -#pragma once - -struct CodeCache -{ - char* bucket{}; - - CodeCache(); - ~CodeCache(); - - void Init(); - void Insert(uint32_t guest, PPCFunc* host); - - void* Find(uint32_t guest) const; -}; - -SWA_API PPCFunc* KeFindHostFunction(uint32_t guest); -SWA_API void KeInsertHostFunction(uint32_t guest, PPCFunc* function); - -extern CodeCache g_codeCache; diff --git a/UnleashedRecomp/cpu/guest_code.h b/UnleashedRecomp/cpu/guest_code.h deleted file mode 100644 index 4177b05..0000000 --- a/UnleashedRecomp/cpu/guest_code.h +++ /dev/null @@ -1,23 +0,0 @@ -#pragma once -#include "ppc_context.h" -#include - -struct GuestCode -{ - inline static void Run(void* hostAddress, PPCContext* ctx, void* baseAddress) - { - ctx->fpscr.loadFromHost(); - reinterpret_cast(hostAddress)(*ctx, reinterpret_cast(baseAddress)); - } - - inline static void Run(void* hostAddress, PPCContext* ctx) - { - ctx->fpscr.loadFromHost(); - reinterpret_cast(hostAddress)(*ctx, reinterpret_cast(g_memory.base)); - } - - inline static void Run(void* hostAddress) - { - Run(hostAddress, GetPPCContext()); - } -}; diff --git a/UnleashedRecomp/cpu/guest_thread.cpp b/UnleashedRecomp/cpu/guest_thread.cpp index 290fc51..3086b91 100644 --- a/UnleashedRecomp/cpu/guest_thread.cpp +++ b/UnleashedRecomp/cpu/guest_thread.cpp @@ -3,8 +3,6 @@ #include #include #include -#include "code_cache.h" -#include "guest_code.h" #include "ppc_context.h" constexpr size_t PCR_SIZE = 0xAB0; @@ -29,7 +27,6 @@ GuestThreadContext::GuestThreadContext(uint32_t cpuNumber) *(uint32_t*)(thread + PCR_SIZE + 0x10) = 0xFFFFFFFF; // that one TLS entry that felt quirky *(uint32_t*)(thread + PCR_SIZE + TLS_SIZE + 0x14C) = ByteSwap(GuestThread::GetCurrentThreadId()); // thread id - ppcContext.fn = (uint8_t*)g_codeCache.bucket; ppcContext.r1.u64 = g_memory.MapVirtual(thread + PCR_SIZE + TLS_SIZE + TEB_SIZE + STACK_SIZE); // stack pointer ppcContext.r13.u64 = g_memory.MapVirtual(thread); ppcContext.fpscr.loadFromHost(); @@ -78,7 +75,7 @@ uint32_t GuestThread::Start(const GuestThreadParams& params) GuestThreadContext ctx(cpuNumber); ctx.ppcContext.r3.u64 = params.value; - reinterpret_cast(g_codeCache.Find(params.function))(ctx.ppcContext, reinterpret_cast(g_memory.base)); + g_memory.FindFunction(params.function)(ctx.ppcContext, g_memory.base); return ctx.ppcContext.r3.u32; } diff --git a/UnleashedRecomp/gpu/video.cpp b/UnleashedRecomp/gpu/video.cpp index a634594..af9badc 100644 --- a/UnleashedRecomp/gpu/video.cpp +++ b/UnleashedRecomp/gpu/video.cpp @@ -6,8 +6,6 @@ #include #include -#include -#include #include #include #include @@ -1682,7 +1680,7 @@ static uint32_t CreateDevice(uint32_t a1, uint32_t a2, uint32_t a3, uint32_t a4, memset(device, 0, sizeof(*device)); uint32_t functionOffset = 0x443344; // D3D - g_codeCache.Insert(functionOffset, HostToGuestFunction); + g_memory.InsertFunction(functionOffset, HostToGuestFunction); for (size_t i = 0; i < std::size(device->setRenderStateFunctions); i++) device->setRenderStateFunctions[i] = functionOffset; @@ -1690,7 +1688,7 @@ static uint32_t CreateDevice(uint32_t a1, uint32_t a2, uint32_t a3, uint32_t a4, for (auto& [state, function] : g_setRenderStateFunctions) { functionOffset += 4; - g_codeCache.Insert(functionOffset, function); + g_memory.InsertFunction(functionOffset, function); device->setRenderStateFunctions[state / 4] = functionOffset; } diff --git a/UnleashedRecomp/kernel/function.h b/UnleashedRecomp/kernel/function.h index ecd246b..7c6beee 100644 --- a/UnleashedRecomp/kernel/function.h +++ b/UnleashedRecomp/kernel/function.h @@ -314,19 +314,18 @@ T GuestToHostFunction(const TFunction& func, TArgs&&... argv) auto& currentCtx = *GetPPCContext(); PPCContext newCtx; // NOTE: No need for zero initialization, has lots of unnecessary code generation. - newCtx.fn = currentCtx.fn; newCtx.r1 = currentCtx.r1; newCtx.r13 = currentCtx.r13; newCtx.fpscr = currentCtx.fpscr; - _translate_args_to_guest(newCtx, (uint8_t*)g_memory.base, args); + _translate_args_to_guest(newCtx, g_memory.base, args); SetPPCContext(newCtx); if constexpr (std::is_function_v) - func(newCtx, (uint8_t*)g_memory.base); + func(newCtx, g_memory.base); else - (*(PPCFunc**)(newCtx.fn + uint64_t(func) * 2))(newCtx, (uint8_t*)g_memory.base); + g_memory.FindFunction(func)(newCtx, g_memory.base); currentCtx.fpscr = newCtx.fpscr; SetPPCContext(currentCtx); diff --git a/UnleashedRecomp/kernel/heap.cpp b/UnleashedRecomp/kernel/heap.cpp index 56718f2..2f83f47 100644 --- a/UnleashedRecomp/kernel/heap.cpp +++ b/UnleashedRecomp/kernel/heap.cpp @@ -8,10 +8,7 @@ constexpr size_t RESERVED_END = 0xA0000000; void Heap::Init() { - g_memory.Alloc(0x20000, RESERVED_BEGIN - 0x20000, MEM_COMMIT); heap = o1heapInit(g_memory.Translate(0x20000), RESERVED_BEGIN - 0x20000); - - g_memory.Alloc(RESERVED_END, 0x100000000 - RESERVED_END, MEM_COMMIT); physicalHeap = o1heapInit(g_memory.Translate(RESERVED_END), 0x100000000 - RESERVED_END); } diff --git a/UnleashedRecomp/kernel/memory.cpp b/UnleashedRecomp/kernel/memory.cpp index 76f9925..3e7468f 100644 --- a/UnleashedRecomp/kernel/memory.cpp +++ b/UnleashedRecomp/kernel/memory.cpp @@ -1,48 +1,30 @@ #include #include "memory.h" -Memory::Memory(void* address, size_t size) : size(size) +Memory::Memory() { #ifdef _WIN32 - base = (char*)VirtualAlloc(address, size, MEM_RESERVE, PAGE_READWRITE); + base = (uint8_t*)VirtualAlloc((void*)0x100000000ull, PPC_MEMORY_SIZE + PPC_FUNC_TABLE_SIZE, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); if (base == nullptr) - base = (char*)VirtualAlloc(nullptr, size, MEM_RESERVE, PAGE_READWRITE); -#else - base = (char*)mmap(address, size, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0); + base = (uint8_t*)VirtualAlloc(nullptr, PPC_MEMORY_SIZE + PPC_FUNC_TABLE_SIZE, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); - if (base == (char*)MAP_FAILED) - base = (char*)mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0); + DWORD oldProtect; + VirtualProtect(base, 4096, PAGE_NOACCESS, &oldProtect); +#else + base = (uint8_t*)mmap((void*)0x100000000ull, PPC_MEMORY_SIZE + PPC_FUNC_TABLE_SIZE, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0); + + if (base == (uint8_t*)MAP_FAILED) + base = (uint8_t*)mmap(NULL, PPC_MEMORY_SIZE + PPC_FUNC_TABLE_SIZE, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0); mprotect(base, 4096, PROT_NONE); #endif -} -void* Memory::Alloc(size_t offset, size_t size, uint32_t type) -{ -#ifdef _WIN32 - return VirtualAlloc(base + offset, size, type, PAGE_READWRITE); -#else - return base + offset; -#endif -} - -void* Memory::Commit(size_t offset, size_t size) -{ -#ifdef _WIN32 - return Alloc(offset, size, MEM_COMMIT); -#else - return base + offset; -#endif -} - -void* Memory::Reserve(size_t offset, size_t size) -{ -#ifdef _WIN32 - return Alloc(offset, size, MEM_RESERVE); -#else - return base + offset; -#endif + for (size_t i = 0; PPCFuncMappings[i].guest != 0; i++) + { + if (PPCFuncMappings[i].host != nullptr) + InsertFunction(PPCFuncMappings[i].guest, PPCFuncMappings[i].host); + } } void* MmGetHostAddress(uint32_t ptr) diff --git a/UnleashedRecomp/kernel/memory.h b/UnleashedRecomp/kernel/memory.h index 2411b19..3f693fc 100644 --- a/UnleashedRecomp/kernel/memory.h +++ b/UnleashedRecomp/kernel/memory.h @@ -5,29 +5,21 @@ #define MEM_RESERVE 0x00002000 #endif -class Memory +struct Memory { -public: - char* base{}; - size_t size{}; - size_t guestBase{}; + uint8_t* base{}; - Memory(void* address, size_t size); - - void* Alloc(size_t offset, size_t size, uint32_t type); - - void* Commit(size_t offset, size_t size); - void* Reserve(size_t offset, size_t size); + Memory(); bool IsInMemoryRange(const void* host) const noexcept { - return host >= base && host < (base + size); + return host >= base && host < (base + PPC_MEMORY_SIZE); } void* Translate(size_t offset) const noexcept { if (offset) - assert(offset < 0x100000000ull); + assert(offset < PPC_MEMORY_SIZE); return base + offset; } @@ -37,7 +29,17 @@ public: if (host) assert(IsInMemoryRange(host)); - return static_cast(static_cast(host) - base); + return static_cast(static_cast(host) - base); + } + + PPCFunc* FindFunction(uint32_t guest) const noexcept + { + return *reinterpret_cast(base + PPC_FUNC_TABLE_OFFSET + (uint64_t(guest) * 2)); + } + + void InsertFunction(uint32_t guest, PPCFunc* host) + { + *reinterpret_cast(base + PPC_FUNC_TABLE_OFFSET + (uint64_t(guest) * 2)) = host; } }; diff --git a/UnleashedRecomp/main.cpp b/UnleashedRecomp/main.cpp index da354c8..6a6c3bc 100644 --- a/UnleashedRecomp/main.cpp +++ b/UnleashedRecomp/main.cpp @@ -1,5 +1,4 @@ #include -#include #include #include #include @@ -25,9 +24,8 @@ const size_t XMAIOBegin = 0x7FEA0000; const size_t XMAIOEnd = XMAIOBegin + 0x0000FFFF; -Memory g_memory{ reinterpret_cast(0x100000000), 0x100000000 }; +Memory g_memory; Heap g_userHeap; -CodeCache g_codeCache; XDBFWrapper g_xdbfWrapper; std::unordered_map g_xdbfTextureCache; @@ -37,11 +35,7 @@ void HostStartup() CoInitializeEx(nullptr, COINIT_MULTITHREADED); #endif - g_memory.Alloc(0x10000, 0x1000, MEM_COMMIT); g_userHeap.Init(); - g_codeCache.Init(); - - g_memory.Alloc(XMAIOBegin, 0xFFFF, MEM_COMMIT); hid::Init(); } @@ -109,8 +103,6 @@ uint32_t LdrLoadModule(const std::filesystem::path &path) auto* xex = reinterpret_cast(loadResult.data()); auto security = reinterpret_cast((char*)xex + xex->AddressOfSecurityInfo); - g_memory.Alloc(security->ImageBase, security->SizeOfImage, MEM_COMMIT); - auto format = Xex2FindOptionalHeader(xex, XEX_HEADER_FILE_FORMAT_INFO); auto entry = *Xex2FindOptionalHeader(xex, XEX_HEADER_ENTRY_POINT); ByteSwapInplace(entry); diff --git a/UnleashedRecomp/patches/audio_patches.cpp b/UnleashedRecomp/patches/audio_patches.cpp index eb8c416..af75d3f 100644 --- a/UnleashedRecomp/patches/audio_patches.cpp +++ b/UnleashedRecomp/patches/audio_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/camera_patches.cpp b/UnleashedRecomp/patches/camera_patches.cpp index 83ec4df..17cdf42 100644 --- a/UnleashedRecomp/patches/camera_patches.cpp +++ b/UnleashedRecomp/patches/camera_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/fps_patches.cpp b/UnleashedRecomp/patches/fps_patches.cpp index 70886c2..3c4b81a 100644 --- a/UnleashedRecomp/patches/fps_patches.cpp +++ b/UnleashedRecomp/patches/fps_patches.cpp @@ -1,5 +1,4 @@ -#include -#include +#include #include #include #include @@ -87,13 +86,13 @@ bool LoadingUpdateMidAsmHook(PPCRegister& r31) double deltaTime = std::min(std::chrono::duration(now - g_prev).count(), 1.0 / 15.0); g_prev = now; - uint8_t* base = reinterpret_cast(g_memory.base); + uint8_t* base = g_memory.base; uint32_t application = PPC_LOAD_U32(PPC_LOAD_U32(r31.u32 + 4)); uint32_t update = PPC_LOAD_U32(PPC_LOAD_U32(application) + 20); g_ppcContext->r3.u32 = application; g_ppcContext->f1.f64 = deltaTime; - reinterpret_cast(g_codeCache.Find(update))(*g_ppcContext, base); + g_memory.FindFunction(update)(*g_ppcContext, base); bool loading = PPC_LOAD_U8(0x83367A4C); if (loading) diff --git a/UnleashedRecomp/patches/misc_patches.cpp b/UnleashedRecomp/patches/misc_patches.cpp index 7a36884..33ac846 100644 --- a/UnleashedRecomp/patches/misc_patches.cpp +++ b/UnleashedRecomp/patches/misc_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/object_patches.cpp b/UnleashedRecomp/patches/object_patches.cpp index 31b6361..b7ebe36 100644 --- a/UnleashedRecomp/patches/object_patches.cpp +++ b/UnleashedRecomp/patches/object_patches.cpp @@ -1,5 +1,3 @@ -#include - // CObjFlame::CObjFlame // A field is not zero initialized, // causing collisions to constantly get created diff --git a/UnleashedRecomp/patches/player_patches.cpp b/UnleashedRecomp/patches/player_patches.cpp index a55fd7e..9d0003c 100644 --- a/UnleashedRecomp/patches/player_patches.cpp +++ b/UnleashedRecomp/patches/player_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/resident_patches.cpp b/UnleashedRecomp/patches/resident_patches.cpp index 1a27622..0235238 100644 --- a/UnleashedRecomp/patches/resident_patches.cpp +++ b/UnleashedRecomp/patches/resident_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/ui/CHudPause_patches.cpp b/UnleashedRecomp/patches/ui/CHudPause_patches.cpp index 4627389..dbc1b47 100644 --- a/UnleashedRecomp/patches/ui/CHudPause_patches.cpp +++ b/UnleashedRecomp/patches/ui/CHudPause_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/ui/CTitleStateIntro_patches.cpp b/UnleashedRecomp/patches/ui/CTitleStateIntro_patches.cpp index 2022f80..29c0b4b 100644 --- a/UnleashedRecomp/patches/ui/CTitleStateIntro_patches.cpp +++ b/UnleashedRecomp/patches/ui/CTitleStateIntro_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/ui/CTitleStateMenu_patches.cpp b/UnleashedRecomp/patches/ui/CTitleStateMenu_patches.cpp index ceed607..12cc739 100644 --- a/UnleashedRecomp/patches/ui/CTitleStateMenu_patches.cpp +++ b/UnleashedRecomp/patches/ui/CTitleStateMenu_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/UnleashedRecomp/patches/video_patches.cpp b/UnleashedRecomp/patches/video_patches.cpp index e0ff0e0..cbe4ce5 100644 --- a/UnleashedRecomp/patches/video_patches.cpp +++ b/UnleashedRecomp/patches/video_patches.cpp @@ -1,4 +1,3 @@ -#include #include #include #include diff --git a/tools/PowerRecomp b/tools/PowerRecomp index 4650dc6..de28409 160000 --- a/tools/PowerRecomp +++ b/tools/PowerRecomp @@ -1 +1 @@ -Subproject commit 4650dc69fb40d0e5857fe28c40e85eec7c97edf7 +Subproject commit de2840970ffc3161a4cb8743b10ddd4da93bdc9f