Use D3DCompiler_47.dll for D3D9 context.

This commit is contained in:
driver1998 2019-05-12 11:15:45 +08:00
parent e010d06c5c
commit 21d2008676
9 changed files with 194 additions and 12 deletions

View File

@ -47,7 +47,11 @@
#ifdef _WIN32
#include "Common/CommonWindows.h"
// Want to avoid including the full header here as it includes d3dx.h
#if PPSSPP_API(D3DX9)
int GetD3DXVersion();
#elif PPSSPP_API(D3D9_D3DCOMPILER)
int GetD3DCompilerVersion();
#endif
#endif
static const char *logLevelList[] = {
@ -464,7 +468,11 @@ void SystemInfoScreen::CreateViews() {
deviceSpecs->Add(new InfoItem(si->T("Driver Version"), System_GetProperty(SYSPROP_GPUDRIVER_VERSION)));
#if !PPSSPP_PLATFORM(UWP)
if (GetGPUBackend() == GPUBackend::DIRECT3D9) {
#if PPSSPP_API(D3DX9)
deviceSpecs->Add(new InfoItem(si->T("D3DX Version"), StringFromFormat("%d", GetD3DXVersion())));
#elif PPSSPP_API(D3D9_D3DCOMPILER)
deviceSpecs->Add(new InfoItem(si->T("D3DCompiler Version"), StringFromFormat("%d", GetD3DCompilerVersion())));
#endif
}
#endif
#endif

View File

@ -1,3 +1,5 @@
#include "ppsspp_config.h"
#include "Common/CommonWindows.h"
#include <d3d9.h>
@ -16,7 +18,12 @@
#include "Windows/W32Util/Misc.h"
#include "thin3d/thin3d.h"
#include "thin3d/thin3d_create.h"
#if PPSSPP_API(D3DX9)
#include "thin3d/d3dx9_loader.h"
#elif PPSSPP_API(D3D9_D3DCOMPILER)
#include "thin3d/d3d9_d3dcompiler_loader.h"
#endif
void D3D9Context::SwapBuffers() {
if (has9Ex_) {
@ -64,11 +71,19 @@ bool D3D9Context::Init(HINSTANCE hInst, HWND wnd, std::string *error_message) {
return false;
}
#if PPSSPP_API(D3DX9)
int d3dx_version = LoadD3DX9Dynamic();
if (!d3dx_version) {
*error_message = "D3DX DLL not found! Try reinstalling DirectX.";
return false;
}
#elif PPSSPP_API(D3D9_D3DCOMPILER)
bool result = LoadD3DCompilerDynamic();
if (!result) {
*error_message = "D3DCompiler not found! Try reinstalling DirectX.";
return false;
}
#endif
g_pfnCreate9ex = (DIRECT3DCREATE9EX)GetProcAddress(hD3D9_, "Direct3DCreate9Ex");
has9Ex_ = (g_pfnCreate9ex != NULL) && IsVistaOrHigher();
@ -208,7 +223,11 @@ void D3D9Context::Shutdown() {
device_->EndScene();
device_->Release();
d3d_->Release();
#if PPSSPP_API(D3DX9)
UnloadD3DXDynamic();
#elif PPSSPP_API(D3D9_D3DCOMPILER)
UnloadD3DCompiler();
#endif
DX9::pD3Ddevice = nullptr;
DX9::pD3DdeviceEx = nullptr;
device_ = nullptr;

View File

@ -1,16 +1,30 @@
#ifdef _WIN32
#include "ppsspp_config.h"
#include "d3d9_shader.h"
#include "thin3d/d3dx9_loader.h"
#include "Common/CommonFuncs.h"
#if PPSSPP_API(D3DX9)
#include "thin3d/d3dx9_loader.h"
// They are the same types, just different names.
#define LPD3D_SHADER_MACRO LPD3DXMACRO
#define LPD3DINCLUDE LPD3DXINCLUDE
#define LPD3DBLOB LPD3DXBUFFER
#elif PPSSPP_API(D3D9_D3DCOMPILER)
#include "thin3d/d3d9_d3dcompiler_loader.h"
#endif
struct ID3DXConstantTable;
namespace DX9 {
bool CompilePixelShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DPIXELSHADER9 *pShader, LPD3DXCONSTANTTABLE *pShaderTable, std::string &errorMessage) {
ID3DXBuffer *pShaderCode = nullptr;
ID3DXBuffer *pErrorMsg = nullptr;
bool CompilePixelShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DPIXELSHADER9 *pShader, ID3DXConstantTable **pShaderTable, std::string &errorMessage) {
LPD3DBLOB pShaderCode = nullptr;
LPD3DBLOB pErrorMsg = nullptr;
// Compile pixel shader.
#if PPSSPP_API(D3DX9)
HRESULT hr = dyn_D3DXCompileShader(code,
(UINT)strlen(code),
nullptr,
@ -21,6 +35,19 @@ bool CompilePixelShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DPI
&pShaderCode,
&pErrorMsg,
pShaderTable);
#elif PPSSPP_API(D3D9_D3DCOMPILER)
HRESULT hr = dyn_D3DCompile(code,
(UINT)strlen(code),
nullptr,
nullptr,
nullptr,
"main",
"ps_2_0",
0,
0,
&pShaderCode,
&pErrorMsg);
#endif
if (pErrorMsg) {
errorMessage = (CHAR *)pErrorMsg->GetBufferPointer();
@ -46,11 +73,12 @@ bool CompilePixelShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DPI
return true;
}
bool CompileVertexShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DVERTEXSHADER9 *pShader, LPD3DXCONSTANTTABLE *pShaderTable, std::string &errorMessage) {
ID3DXBuffer *pShaderCode = nullptr;
ID3DXBuffer *pErrorMsg = nullptr;
bool CompileVertexShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DVERTEXSHADER9 *pShader, ID3DXConstantTable **pShaderTable, std::string &errorMessage) {
LPD3DBLOB pShaderCode = nullptr;
LPD3DBLOB pErrorMsg = nullptr;
// Compile pixel shader.
#if PPSSPP_API(D3DX9)
HRESULT hr = dyn_D3DXCompileShader(code,
(UINT)strlen(code),
nullptr,
@ -61,6 +89,19 @@ bool CompileVertexShader(LPDIRECT3DDEVICE9 device, const char *code, LPDIRECT3DV
&pShaderCode,
&pErrorMsg,
pShaderTable);
#elif PPSSPP_API(D3D9_D3DCOMPILER)
HRESULT hr = dyn_D3DCompile(code,
(UINT)strlen(code),
nullptr,
nullptr,
nullptr,
"main",
"vs_2_0",
0,
0,
&pShaderCode,
&pErrorMsg);
#endif
if (pErrorMsg) {
errorMessage = (CHAR *)pErrorMsg->GetBufferPointer();

View File

@ -419,6 +419,7 @@
<ClInclude Include="json\json_reader.h" />
<ClInclude Include="net\websocket_server.h" />
<ClInclude Include="thin3d\d3d11_loader.h" />
<ClInclude Include="thin3d\d3d9_d3dcompiler_loader.h" />
<ClInclude Include="thin3d\DataFormat.h" />
<ClInclude Include="thin3d\DataFormatGL.h" />
<ClInclude Include="thin3d\GLQueueRunner.h" />
@ -1129,6 +1130,7 @@
<ClCompile Include="math\dataconv.cpp" />
<ClCompile Include="net\websocket_server.cpp" />
<ClCompile Include="thin3d\d3d11_loader.cpp" />
<ClCompile Include="thin3d\d3d9_d3dcompiler_loader.cpp" />
<ClCompile Include="thin3d\DataFormatGL.cpp" />
<ClCompile Include="thin3d\GLQueueRunner.cpp" />
<ClCompile Include="thin3d\GLRenderManager.cpp" />

View File

@ -347,6 +347,9 @@
<ClInclude Include="data\base64.h">
<Filter>data</Filter>
</ClInclude>
<ClInclude Include="thin3d\d3d9_d3dcompiler_loader.h">
<Filter>thin3d</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="gfx\gl_debug_log.cpp">
@ -826,6 +829,9 @@
<ClCompile Include="data\base64.cpp">
<Filter>data</Filter>
</ClCompile>
<ClCompile Include="thin3d\d3d9_d3dcompiler_loader.cpp">
<Filter>thin3d</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<Filter Include="gfx">

View File

@ -0,0 +1,62 @@
#include <assert.h>
#include <Windows.h>
#include <D3Dcompiler.h>
#include "thin3d/d3d9_d3dcompiler_loader.h"
static HMODULE g_D3DCompileModule;
extern pD3DCompile ptr_D3DCompile;
int d3dcompiler_version = 47;
#define GB_MAKE_STR(s) # s
#define GB_MAKE_STR2(x) GB_MAKE_STR(x)
#define GB_D3D9_D3DCOMPILER_LOADER_CHECK_ENTRY_NULL_PTR(funcname) assert(false && GB_MAKE_STR2(funcname) );
bool LoadD3DCompilerDynamic() {
g_D3DCompileModule = LoadLibrary(D3DCOMPILER_DLL);
#if PPSSPP_ARCH(X86)
// Workaround for distributing both 32-bit and 64-bit versions of the DLL.
if (!g_D3DCompileModule)
g_D3DCompileModule = LoadLibrary(L"D3dcompiler_47.x86.dll");
#endif
if (!g_D3DCompileModule) {
g_D3DCompileModule = LoadLibrary(L"D3dcompiler_42.dll");
d3dcompiler_version = 42;
}
if (!g_D3DCompileModule) {
return false;
} else {
ptr_D3DCompile = (pD3DCompile)GetProcAddress(g_D3DCompileModule, "D3DCompile");
return true;
}
}
int GetD3DCompilerVersion() {
return d3dcompiler_version;
}
bool UnloadD3DCompiler() {
if (!g_D3DCompileModule)
return false;
if (g_D3DCompileModule) {
FreeLibrary(g_D3DCompileModule);
g_D3DCompileModule = nullptr;
}
return true;
}
HRESULT dyn_D3DCompile(LPCSTR pSrcData, UINT SrcDataSize, LPCSTR pFileName, CONST D3D_SHADER_MACRO* pDefines,
LPD3DINCLUDE pInclude, LPCSTR pEntrypoint, LPCSTR pTarget,
UINT Flags1, UINT Flags2, LPD3DBLOB* ppShader, LPD3DBLOB* ppErrorMsgs)
{
if (!g_D3DCompileModule) {
GB_D3D9_D3DCOMPILER_LOADER_CHECK_ENTRY_NULL_PTR(D3DCompile)
}
return ptr_D3DCompile(pSrcData, SrcDataSize, pFileName, pDefines, pInclude, pEntrypoint, pTarget, Flags1, Flags2, ppShader, ppErrorMsgs);
}

View File

@ -0,0 +1,15 @@
#pragma once
#include "ppsspp_config.h"
#include <Windows.h>
#include <D3Dcompiler.h>
bool LoadD3DCompilerDynamic();
HRESULT dyn_D3DCompile(LPCSTR pSrcData, UINT SrcDataSize, LPCSTR pFileName, CONST D3D_SHADER_MACRO* pDefines,
LPD3DINCLUDE pInclude, LPCSTR pEntrypoint, LPCSTR pTarget,
UINT Flags1, UINT Flags2, LPD3DBLOB* ppShader, LPD3DBLOB* ppErrorMsgs);
bool UnloadD3DCompiler();
int GetD3DCompilerVersion();

View File

@ -2,6 +2,8 @@
#include <cstdio>
#include <cstdint>
#include "ppsspp_config.h"
#ifdef _DEBUG
#define D3D_DEBUG_INFO
#endif
@ -10,15 +12,26 @@
#ifdef USE_CRT_DBG
#undef new
#endif
#if PPSSPP_API(D3DX9)
#include <d3dx9.h>
#ifdef USE_CRT_DBG
#define new DBG_NEW
#endif
#include "thin3d/d3dx9_loader.h"
// They are the same types, just different names.
#define LPD3D_SHADER_MACRO LPD3DXMACRO
#define LPD3DINCLUDE LPD3DXINCLUDE
#define LPD3DBLOB LPD3DXBUFFER
#elif PPSSPP_API(D3D9_D3DCOMPILER)
#include <D3Dcompiler.h>
#include "thin3d/d3d9_d3dcompiler_loader.h"
#endif
#include "base/logging.h"
#include "math/lin/matrix4x4.h"
#include "thin3d/thin3d.h"
#include "thin3d/d3dx9_loader.h"
#include "gfx/d3d9_state.h"
namespace Draw {
@ -969,14 +982,18 @@ void D3D9Context::SetStencilRef(uint8_t ref) {
}
bool D3D9ShaderModule::Compile(LPDIRECT3DDEVICE9 device, const uint8_t *data, size_t size) {
LPD3DXMACRO defines = nullptr;
LPD3DXINCLUDE includes = nullptr;
LPD3D_SHADER_MACRO defines = nullptr;
LPD3DINCLUDE includes = nullptr;
DWORD flags = 0;
LPD3DXBUFFER codeBuffer = nullptr;
LPD3DXBUFFER errorBuffer = nullptr;
LPD3DBLOB codeBuffer = nullptr;
LPD3DBLOB errorBuffer = nullptr;
const char *source = (const char *)data;
const char *profile = stage_ == ShaderStage::FRAGMENT ? "ps_2_0" : "vs_2_0";
#if PPSSPP_API(D3DX9)
HRESULT hr = dyn_D3DXCompileShader(source, (UINT)strlen(source), defines, includes, "main", profile, flags, &codeBuffer, &errorBuffer, nullptr);
#elif PPSSPP_API(D3D9_D3DCOMPILER)
HRESULT hr = dyn_D3DCompile(source, (UINT)strlen(source), nullptr, defines, includes, "main", profile, 0, 0, &codeBuffer, &errorBuffer);
#endif
if (FAILED(hr)) {
const char *error = errorBuffer ? (const char *)errorBuffer->GetBufferPointer() : "(no errorbuffer returned)";
if (hr == ERROR_MOD_NOT_FOUND) {
@ -1186,11 +1203,19 @@ void D3D9Context::HandleEvent(Event ev, int width, int height, void *param1, voi
}
DrawContext *T3DCreateDX9Context(IDirect3D9 *d3d, IDirect3D9Ex *d3dEx, int adapterId, IDirect3DDevice9 *device, IDirect3DDevice9Ex *deviceEx) {
#if PPSSPP_API(D3DX9)
int d3dx_ver = LoadD3DX9Dynamic();
if (!d3dx_ver) {
ELOG("Failed to load D3DX9!");
return NULL;
}
#elif PPSSPP_API(D3D9_D3DCOMPILER)
bool result = LoadD3DCompilerDynamic();
if (!result) {
ELOG("Failed to load D3DCompiler!");
return NULL;
}
#endif
return new D3D9Context(d3d, d3dEx, adapterId, device, deviceEx);
}

View File

@ -125,6 +125,10 @@
#if PPSSPP_PLATFORM(WINDOWS)
#if !PPSSPP_PLATFORM(UWP)
#define PPSSPP_API_D3D9 1
// Comment this and uncomment PPSSPP_API_D3DX9 if D3DX9 is prefered.
#define PPSSPP_API_D3D9_D3DCOMPILER 1
// #define PPSSPP_API_D3DX9 1
#endif
#define PPSSPP_API_D3D11 1
#endif