From 2d4a808f3950cd93c8a092a43604bccddd3a366f Mon Sep 17 00:00:00 2001 From: FakeMichau <49685661+FakeMichau@users.noreply.github.com> Date: Mon, 15 Sep 2025 14:04:31 +0200 Subject: [PATCH] Clean up FSR 4 upgrade --- OptiScaler/OptiScaler.vcxproj | 1 + OptiScaler/OptiScaler.vcxproj.filters | 3 + OptiScaler/fsr4/FSR4Upgrade.cpp | 490 ++++++++++++++++++++++++++ OptiScaler/fsr4/FSR4Upgrade.h | 104 +----- OptiScaler/hooks/Crypt32_Hooks.h | 4 +- OptiScaler/hooks/Kernel_Hooks.h | 2 + 6 files changed, 514 insertions(+), 90 deletions(-) create mode 100644 OptiScaler/fsr4/FSR4Upgrade.cpp diff --git a/OptiScaler/OptiScaler.vcxproj b/OptiScaler/OptiScaler.vcxproj index c5a18ad0..76689f79 100644 --- a/OptiScaler/OptiScaler.vcxproj +++ b/OptiScaler/OptiScaler.vcxproj @@ -478,6 +478,7 @@ copy NUL "$(SolutionDir)x64\Release\a\!! EXTRACT ALL FILES TO GAME FOLDER !!" /Y + diff --git a/OptiScaler/OptiScaler.vcxproj.filters b/OptiScaler/OptiScaler.vcxproj.filters index fda4730c..1be84760 100644 --- a/OptiScaler/OptiScaler.vcxproj.filters +++ b/OptiScaler/OptiScaler.vcxproj.filters @@ -890,6 +890,9 @@ Source Files + + Source Files + diff --git a/OptiScaler/fsr4/FSR4Upgrade.cpp b/OptiScaler/fsr4/FSR4Upgrade.cpp new file mode 100644 index 00000000..3e438fe0 --- /dev/null +++ b/OptiScaler/fsr4/FSR4Upgrade.cpp @@ -0,0 +1,490 @@ +#include "FSR4Upgrade.h" + +#include +#include +#include +#include +#include +#include +#include "FSR4ModelSelection.h" + +static HMODULE moduleAmdxc64 = nullptr; +static HMODULE fsr4Module = nullptr; + +static AmdExtFfxCapability* amdExtFfxThird = nullptr; +static AmdExtFfxCapability2* amdExtFfxSecond = nullptr; +static AmdExtFfxQuery* amdExtFfxQuery = nullptr; +static AmdExtFfxQuery* o_amdExtFfxQuery = nullptr; +static AmdExtFfxApi* amdExtFfxApi = nullptr; + +static PFN_AmdExtD3DCreateInterface o_AmdExtD3DCreateInterface = nullptr; + +#pragma region GDI32 + +// Manually define structures +typedef struct _D3DKMT_UMDFILENAMEINFO_L +{ + UINT Version; + WCHAR UmdFileName[MAX_PATH]; +} D3DKMT_UMDFILENAMEINFO_L; + +typedef struct _D3DKMT_ADAPTERINFO_L +{ + UINT hAdapter; + LUID AdapterLuid; + ULONG NumOfSources; + BOOL bPrecisePresentRegionsPreferred; +} D3DKMT_ADAPTERINFO_L; + +typedef struct _D3DKMT_QUERYADAPTERINFO_L +{ + UINT hAdapter; + UINT Type; + VOID* pPrivateDriverData; + UINT PrivateDriverDataSize; +} D3DKMT_QUERYADAPTERINFO_L; + +typedef struct _D3DKMT_ENUMADAPTERS_L +{ + ULONG NumAdapters; + D3DKMT_ADAPTERINFO_L Adapters[16]; +} D3DKMT_ENUMADAPTERS_L; + +typedef struct _D3DKMT_CLOSEADAPTER_L +{ + UINT hAdapter; // in: adapter handle +} D3DKMT_CLOSEADAPTER_L; + +// Function pointers +typedef UINT (*PFN_D3DKMTQueryAdapterInfo_L)(D3DKMT_QUERYADAPTERINFO_L*); +typedef UINT (*PFN_D3DKMTEnumAdapters_L)(D3DKMT_ENUMADAPTERS_L*); +typedef UINT (*PFN_D3DKMTCloseAdapter)(D3DKMT_CLOSEADAPTER_L*); + +std::vector GetDriverStore() +{ + std::vector result; + + // Load D3DKMT functions dynamically + bool libraryLoaded = false; + HMODULE hGdi32 = KernelBaseProxy::GetModuleHandleW_()(L"Gdi32.dll"); + + if (hGdi32 == nullptr) + { + hGdi32 = NtdllProxy::LoadLibraryExW_Ldr(L"Gdi32.dll", NULL, 0); + libraryLoaded = hGdi32 != nullptr; + } + + if (hGdi32 == nullptr) + { + LOG_ERROR("Failed to load Gdi32.dll"); + return result; + } + + do + { + auto o_D3DKMTEnumAdapters = + (PFN_D3DKMTEnumAdapters_L) KernelBaseProxy::GetProcAddress_()(hGdi32, "D3DKMTEnumAdapters"); + auto o_D3DKMTQueryAdapterInfo = + (PFN_D3DKMTQueryAdapterInfo_L) KernelBaseProxy::GetProcAddress_()(hGdi32, "D3DKMTQueryAdapterInfo"); + auto o_D3DKMTCloseAdapter = + (PFN_D3DKMTCloseAdapter) KernelBaseProxy::GetProcAddress_()(hGdi32, "D3DKMTCloseAdapter"); + + if (o_D3DKMTEnumAdapters == nullptr || o_D3DKMTQueryAdapterInfo == nullptr || o_D3DKMTCloseAdapter == nullptr) + { + LOG_ERROR("Failed to resolve D3DKMT functions"); + break; + } + + D3DKMT_UMDFILENAMEINFO_L umdFileInfo = {}; + D3DKMT_QUERYADAPTERINFO_L queryAdapterInfo = {}; + + queryAdapterInfo.Type = 1; // KMTQAITYPE_UMDRIVERNAME + queryAdapterInfo.pPrivateDriverData = &umdFileInfo; + queryAdapterInfo.PrivateDriverDataSize = sizeof(umdFileInfo); + + D3DKMT_ENUMADAPTERS_L enumAdapters = {}; + + // Query the number of adapters first + if (o_D3DKMTEnumAdapters(&enumAdapters) != 0) + { + LOG_ERROR("Failed to enumerate adapters."); + break; + } + + // If there are any adapters, the first one should be in the list + if (enumAdapters.NumAdapters > 0) + { + for (size_t i = 0; i < enumAdapters.NumAdapters; i++) + { + D3DKMT_ADAPTERINFO_L adapter = enumAdapters.Adapters[i]; + queryAdapterInfo.hAdapter = adapter.hAdapter; + + auto hr = o_D3DKMTQueryAdapterInfo(&queryAdapterInfo); + + if (hr != 0) + LOG_ERROR("Failed to query adapter info {:X}", hr); + else + result.push_back(std::filesystem::path(umdFileInfo.UmdFileName).parent_path()); + + D3DKMT_CLOSEADAPTER_L closeAdapter = {}; + closeAdapter.hAdapter = adapter.hAdapter; + auto closeResult = o_D3DKMTCloseAdapter(&closeAdapter); + if (closeResult != 0) + LOG_ERROR("D3DKMTCloseAdapter error: {:X}", closeResult); + } + } + else + { + LOG_ERROR("No adapters found."); + break; + } + + } while (false); + + if (libraryLoaded) + NtdllProxy::FreeLibrary_Ldr(hGdi32); + + return result; +} + +#pragma endregion + +void CheckForGPU() +{ + if (Config::Instance()->Fsr4Update.has_value()) + return; + + // Call init for any case + DxgiProxy::Init(); + + IDXGIFactory* factory = nullptr; + HRESULT result = DxgiProxy::CreateDxgiFactory_()(__uuidof(factory), &factory); + + if (result != S_OK || factory == nullptr) + return; + + UINT adapterIndex = 0; + DXGI_ADAPTER_DESC adapterDesc {}; + IDXGIAdapter* adapter; + + while (factory->EnumAdapters(adapterIndex, &adapter) == S_OK) + { + if (adapter == nullptr) + { + adapterIndex++; + continue; + } + + State::Instance().skipSpoofing = true; + result = adapter->GetDesc(&adapterDesc); + State::Instance().skipSpoofing = false; + + if (result == S_OK && adapterDesc.VendorId != VendorId::Microsoft) + { + std::wstring szName(adapterDesc.Description); + std::string descStr = std::format("Adapter: {}, VRAM: {} MB", wstring_to_string(szName), + adapterDesc.DedicatedVideoMemory / (1024 * 1024)); + LOG_INFO("{}", descStr); + + // If GPU is AMD + if (adapterDesc.VendorId == VendorId::AMD) + { + // If GPU Name contains 90XX or GFX12 (Linux) always set it to true + if (szName.find(L" 90") != std::wstring::npos || szName.find(L" GFX12") != std::wstring::npos) + Config::Instance()->Fsr4Update.set_volatile_value(true); + } + } + else + { + LOG_DEBUG("Can't get description of adapter: {}", adapterIndex); + } + + adapter->Release(); + adapter = nullptr; + adapterIndex++; + } + + factory->Release(); + factory = nullptr; + + LOG_INFO("Fsr4Update: {}", Config::Instance()->Fsr4Update.value_or_default()); +} + +struct AmdExtFfxApi : public IAmdExtFfxApi +{ + PFN_UpdateFfxApiProvider o_UpdateFfxApiProvider = nullptr; + + HRESULT STDMETHODCALLTYPE UpdateFfxApiProvider(void* pData, uint32_t dataSizeInBytes) override + { + LOG_INFO("UpdateFfxApiProvider called"); + + if (o_UpdateFfxApiProvider == nullptr) + { + fsr4Module = NtdllProxy::LoadLibraryExW_Ldr(L"amdxcffx64.dll", NULL, 0); + + if (fsr4Module == nullptr) + { + auto storePath = GetDriverStore(); + + for (size_t i = 0; i < storePath.size(); i++) + { + if (fsr4Module == nullptr) + { + auto dllPath = storePath[i] / L"amdxcffx64.dll"; + LOG_DEBUG("Trying to load: {}", wstring_to_string(dllPath.c_str())); + fsr4Module = NtdllProxy::LoadLibraryExW_Ldr(dllPath.c_str(), NULL, 0); + + if (fsr4Module != nullptr) + { + LOG_INFO("amdxcffx64 loaded from {}", dllPath.string()); + break; + } + } + } + } + else + { + LOG_INFO("amdxcffx64 loaded from game folder"); + } + + if (fsr4Module == nullptr) + { + LOG_ERROR("Failed to load amdxcffx64.dll"); + return E_NOINTERFACE; + } + + auto sdk2upscalingModule = KernelBaseProxy::GetModuleHandleA_()("amd_fidelityfx_upscaler_dx12.dll"); + constexpr bool unhookOld = false; + + if (sdk2upscalingModule != nullptr) + FSR4ModelSelection::Hook(sdk2upscalingModule, unhookOld); + else + FSR4ModelSelection::Hook(fsr4Module, unhookOld); + + o_UpdateFfxApiProvider = + (PFN_UpdateFfxApiProvider) KernelBaseProxy::GetProcAddress_()(fsr4Module, "UpdateFfxApiProvider"); + + if (o_UpdateFfxApiProvider == nullptr) + { + LOG_ERROR("Failed to get UpdateFfxApiProvider"); + return E_NOINTERFACE; + } + } + + if (o_UpdateFfxApiProvider != nullptr) + { + State::DisableChecks(1); + auto result = o_UpdateFfxApiProvider(pData, dataSizeInBytes); + LOG_INFO("UpdateFfxApiProvider called, result: {} ({:X})", result == S_OK ? "Ok" : "Error", (UINT) result); + State::EnableChecks(1); + return result; + } + + return E_NOINTERFACE; + } + + HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override { return E_NOTIMPL; } + + ULONG __stdcall AddRef(void) override { return 0; } + + ULONG __stdcall Release(void) override { return 0; } +}; + +#define STUB(number) \ + HRESULT STDMETHODCALLTYPE unknown##number() \ + { \ + LOG_FUNC(); \ + return S_OK; \ + } + +struct AmdExtFfxCapability2 : public IAmdExtFfxCapability2 +{ + STUB(1) + HRESULT STDMETHODCALLTYPE IsSupported(uint64_t a) + { + LOG_TRACE(": {}", a); + return S_OK; + } + STUB(3) + + HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override { return E_NOTIMPL; } + ULONG __stdcall AddRef(void) override { return 0; } + ULONG __stdcall Release(void) override { return 0; } +}; + +struct AmdExtFfxCapability : public IAmdExtFfxCapability +{ + STUB(1) + STUB(2) + STUB(3) + STUB(4) + STUB(5) + STUB(6) + STUB(7) + STUB(8) + STUB(9) + STUB(10) + STUB(11) + STUB(12) + STUB(13) + HRESULT STDMETHODCALLTYPE CheckWMMASupport(uint64_t* a, uint8_t* data) + { + LOG_TRACE(": {}", *a); + + *reinterpret_cast(&data[0x00]) = 16; + *reinterpret_cast(&data[0x08]) = 16; + *reinterpret_cast(&data[0x10]) = 16; + + *reinterpret_cast(&data[0x18]) = 11; + *reinterpret_cast(&data[0x1C]) = 11; + + *reinterpret_cast(&data[0x20]) = 1; + *reinterpret_cast(&data[0x24]) = 1; + + data[0x28] = 0; + + return S_OK; + } + + HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override { return E_NOTIMPL; } + ULONG __stdcall AddRef(void) override { return 0; } + ULONG __stdcall Release(void) override { return 0; } +}; + +struct AmdExtFfxQuery : public IAmdExtFfxQuery +{ + HRESULT STDMETHODCALLTYPE queryInternal(IUnknown* pOuter, REFIID riid, void** ppvObject) override + { + if (riid == __uuidof(IAmdExtFfxCapability2)) + { + if (amdExtFfxSecond == nullptr) + amdExtFfxSecond = new AmdExtFfxCapability2(); + + *ppvObject = amdExtFfxSecond; + + LOG_INFO("Custom IAmdExtFfxCapability2 queried, returning custom AmdExtFfxCapability2"); + + return S_OK; + } + else if (riid == __uuidof(IAmdExtFfxCapability)) + { + if (amdExtFfxThird == nullptr) + amdExtFfxThird = new AmdExtFfxCapability(); + + *ppvObject = amdExtFfxThird; + + LOG_INFO("Custom IAmdExtFfxCapability queried, returning custom AmdExtFfxCapability"); + + return S_OK; + } + else if (o_amdExtFfxQuery) + { + return o_amdExtFfxQuery->queryInternal(pOuter, riid, ppvObject); + } + + return E_NOINTERFACE; + } + + HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override + { + if (o_amdExtFfxQuery) + return o_amdExtFfxQuery->QueryInterface(riid, ppvObject); + + return E_NOTIMPL; + } + ULONG __stdcall AddRef(void) override + { + if (o_amdExtFfxQuery) + return o_amdExtFfxQuery->AddRef(); + + return 0; + } + ULONG __stdcall Release(void) override + { + if (o_amdExtFfxQuery) + return o_amdExtFfxQuery->Release(); + + return 0; + } +}; + +void InitFSR4Update() +{ + if (Config::Instance()->Fsr4Update.has_value() && !Config::Instance()->Fsr4Update.value()) + return; + + if (o_AmdExtD3DCreateInterface != nullptr) + return; + + LOG_DEBUG(""); + + // For FSR4 Upgrade + moduleAmdxc64 = KernelBaseProxy::GetModuleHandleW_()(L"amdxc64.dll"); + if (moduleAmdxc64 == nullptr) + moduleAmdxc64 = NtdllProxy::LoadLibraryExW_Ldr(L"amdxc64.dll", NULL, 0); + + if (moduleAmdxc64 != nullptr) + { + LOG_INFO("amdxc64.dll loaded"); + o_AmdExtD3DCreateInterface = (PFN_AmdExtD3DCreateInterface) KernelBaseProxy::GetProcAddress_()( + moduleAmdxc64, "AmdExtD3DCreateInterface"); + + if (o_AmdExtD3DCreateInterface != nullptr) + { + LOG_DEBUG("Hooking AmdExtD3DCreateInterface"); + DetourTransactionBegin(); + DetourUpdateThread(GetCurrentThread()); + DetourAttach(&(PVOID&) o_AmdExtD3DCreateInterface, hkAmdExtD3DCreateInterface); + DetourTransactionCommit(); + } + } + else + { + LOG_INFO("Failed to load amdxc64.dll"); + } +} + +HMODULE GetFSR4Module() { return fsr4Module; } + +HRESULT STDMETHODCALLTYPE hkAmdExtD3DCreateInterface(IUnknown* pOuter, REFIID riid, void** ppvObject) +{ + CheckForGPU(); + + if (!Config::Instance()->Fsr4Update.value_or_default() && o_AmdExtD3DCreateInterface != nullptr) + return o_AmdExtD3DCreateInterface(pOuter, riid, ppvObject); + + // Proton bleeding edge ships amdxc64 that is missing some required functions + else if (riid == __uuidof(IAmdExtFfxQuery) && State::Instance().isRunningOnLinux) + { + // Required for the custom AmdExtFfxApi, lack of it triggers visual glitches + if (amdExtFfxQuery == nullptr) + amdExtFfxQuery = new AmdExtFfxQuery(); + + *ppvObject = amdExtFfxQuery; + + LOG_INFO("IAmdExtFfxQuery queried, returning custom AmdExtFfxQuery"); + + if (o_AmdExtD3DCreateInterface != nullptr && o_amdExtFfxQuery == nullptr) + o_AmdExtD3DCreateInterface(pOuter, riid, (void**) &o_amdExtFfxQuery); + + return S_OK; + } + + else if (riid == __uuidof(IAmdExtFfxApi)) + { + if (amdExtFfxApi == nullptr) + amdExtFfxApi = new AmdExtFfxApi(); + + // Return custom one + *ppvObject = amdExtFfxApi; + + LOG_INFO("IAmdExtFfxApi queried, returning custom AmdExtFfxApi"); + + return S_OK; + } + + else if (o_AmdExtD3DCreateInterface != nullptr) + return o_AmdExtD3DCreateInterface(pOuter, riid, ppvObject); + + return E_NOINTERFACE; +} \ No newline at end of file diff --git a/OptiScaler/fsr4/FSR4Upgrade.h b/OptiScaler/fsr4/FSR4Upgrade.h index be818cdf..3490934d 100644 --- a/OptiScaler/fsr4/FSR4Upgrade.h +++ b/OptiScaler/fsr4/FSR4Upgrade.h @@ -3,14 +3,18 @@ #include #include -#include +#include #include #include -#include -#include -#include "FSR4ModelSelection.h" +#include + +// Forward declarations +struct AmdExtFfxApi; +struct AmdExtFfxQuery; +struct AmdExtFfxCapability2; +struct AmdExtFfxCapability; typedef HRESULT(__cdecl* PFN_AmdExtD3DCreateInterface)(IUnknown* pOuter, REFIID riid, void** ppvObject); @@ -68,7 +72,7 @@ inline static std::vector GetDriverStore() if (hGdi32 == nullptr) { - hGdi32 = NtdllProxy::LoadLibraryExW_Ldr(L"Gdi32.dll", NULL, 0); + hGdi32 = KernelBaseProxy::LoadLibraryExW_()(L"Gdi32.dll", NULL, 0); libraryLoaded = hGdi32 != nullptr; } @@ -140,7 +144,7 @@ inline static std::vector GetDriverStore() } while (false); if (libraryLoaded) - NtdllProxy::FreeLibrary_Ldr(hGdi32); + KernelBaseProxy::FreeLibrary_()(hGdi32); return result; } @@ -155,7 +159,7 @@ inline static std::vector GetDriverStore() } MIDL_INTERFACE("F714E11A-B54E-4E0F-ABC5-DF58B18133D1") -IAmdExtFfxThird : public IUnknown +IAmdExtFfxCapability : public IUnknown { virtual HRESULT unknown1() = 0; // not used virtual HRESULT unknown2() = 0; // not used @@ -170,87 +174,11 @@ IAmdExtFfxThird : public IUnknown virtual HRESULT unknown11() = 0; // not used virtual HRESULT unknown12() = 0; // not used virtual HRESULT unknown13() = 0; // not used - virtual HRESULT unknown14(uint64_t* a, uint8_t* data) = 0; + virtual HRESULT CheckWMMASupport(uint64_t* a, uint8_t* data) = 0; }; -struct AmdExtFfxThird : public IAmdExtFfxThird -{ - STUB(1) - STUB(2) - STUB(3) - STUB(4) - STUB(5) - STUB(6) - STUB(7) - STUB(8) - STUB(9) - STUB(10) - STUB(11) - STUB(12) - STUB(13) - HRESULT STDMETHODCALLTYPE unknown14(uint64_t* a, uint8_t* data) - { - LOG_TRACE(": {}", *a); - - *reinterpret_cast(&data[0x00]) = 16; - *reinterpret_cast(&data[0x08]) = 16; - *reinterpret_cast(&data[0x10]) = 16; - - *reinterpret_cast(&data[0x18]) = 11; - *reinterpret_cast(&data[0x1C]) = 11; - - *reinterpret_cast(&data[0x20]) = 1; - *reinterpret_cast(&data[0x24]) = 1; - - data[0x28] = 0; - - return S_OK; - } - - HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override { return E_NOTIMPL; } - ULONG __stdcall AddRef(void) override { return 0; } - ULONG __stdcall Release(void) override { return 0; } -}; - -static AmdExtFfxThird* _amdExtFfxThird = nullptr; - -// Internal interfaces needed for custom the IAmdExtFfxApi -MIDL_INTERFACE("BA019D53-CCAB-4CBD-B56A-7230ED4330AD") -IAmdExtFfxSecond : public IUnknown -{ - public: - virtual HRESULT unknown1() = 0; // not used - virtual HRESULT unknown2(uint64_t a) = 0; - virtual HRESULT unknown3() = 0; -}; - -struct AmdExtFfxSecond : public IAmdExtFfxSecond -{ - HRESULT STDMETHODCALLTYPE unknown1() - { - LOG_FUNC(); - return S_OK; - } - HRESULT STDMETHODCALLTYPE unknown2(uint64_t a) - { - LOG_TRACE(": {}", a); - return S_OK; - } - HRESULT STDMETHODCALLTYPE unknown3() - { - LOG_FUNC(); - return S_OK; - } - - HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObject) override { return E_NOTIMPL; } - ULONG __stdcall AddRef(void) override { return 0; } - ULONG __stdcall Release(void) override { return 0; } -}; - -static AmdExtFfxSecond* _amdExtFfxSecond = nullptr; - MIDL_INTERFACE("014937EC-9288-446F-A9AC-D75A8E3A984F") -IAmdExtFfxFirst : public IUnknown +IAmdExtFfxQuery : public IUnknown { public: virtual HRESULT queryInternal(IUnknown * pOuter, REFIID riid, void** ppvObject) = 0; @@ -315,7 +243,7 @@ struct AmdExtFfxApi : public IAmdExtFfxApi if (o_UpdateFfxApiProvider == nullptr) { - fsr4Module = NtdllProxy::LoadLibraryExW_Ldr(L"amdxcffx64.dll", NULL, 0); + fsr4Module = KernelBaseProxy::LoadLibraryExW_()(L"amdxcffx64.dll", NULL, 0); if (fsr4Module == nullptr) { @@ -327,7 +255,7 @@ struct AmdExtFfxApi : public IAmdExtFfxApi { auto dllPath = storePath[i] / L"amdxcffx64.dll"; LOG_DEBUG("Trying to load: {}", wstring_to_string(dllPath.c_str())); - fsr4Module = NtdllProxy::LoadLibraryExW_Ldr(dllPath.c_str(), NULL, 0); + fsr4Module = KernelBaseProxy::LoadLibraryExW_()(dllPath.c_str(), NULL, 0); if (fsr4Module != nullptr) { @@ -507,7 +435,7 @@ inline void InitFSR4Update() // For FSR4 Upgrade moduleAmdxc64 = KernelBaseProxy::GetModuleHandleW_()(L"amdxc64.dll"); if (moduleAmdxc64 == nullptr) - moduleAmdxc64 = NtdllProxy::LoadLibraryExW_Ldr(L"amdxc64.dll", NULL, 0); + moduleAmdxc64 = KernelBaseProxy::LoadLibraryExW_()(L"amdxc64.dll", NULL, 0); if (moduleAmdxc64 != nullptr) { diff --git a/OptiScaler/hooks/Crypt32_Hooks.h b/OptiScaler/hooks/Crypt32_Hooks.h index 78dd89cb..465f521e 100644 --- a/OptiScaler/hooks/Crypt32_Hooks.h +++ b/OptiScaler/hooks/Crypt32_Hooks.h @@ -26,11 +26,11 @@ static BOOL hkCryptQueryObject(DWORD dwObjectType, const void* pvObject, DWORD d // It's applied even if ffx is already signed, could be improved if (pathString.contains("amd_fidelityfx_dx12.dll") || - pathString.contains("amd_fidelityfx_vk.dll") && fsr4Module) + pathString.contains("amd_fidelityfx_vk.dll") && GetFSR4Module()) { LOG_DEBUG("Replacing FFX with a signed dll"); WCHAR signedDll[256] {}; - GetModuleFileNameW(fsr4Module, signedDll, 256); + GetModuleFileNameW(GetFSR4Module(), signedDll, 256); return o_CryptQueryObject(dwObjectType, signedDll, dwExpectedContentTypeFlags, dwExpectedFormatTypeFlags, dwFlags, pdwMsgAndCertEncodingType, pdwContentType, pdwFormatType, phCertStore, diff --git a/OptiScaler/hooks/Kernel_Hooks.h b/OptiScaler/hooks/Kernel_Hooks.h index a583bc6c..1a94278a 100644 --- a/OptiScaler/hooks/Kernel_Hooks.h +++ b/OptiScaler/hooks/Kernel_Hooks.h @@ -28,6 +28,8 @@ #include #include +#include + #include #pragma intrinsic(_ReturnAddress)