Add DXGIDebug logic to help track memory leaks, fix SRV leak it discovered

d3d11
Caleb Cornett 2024-02-07 08:02:49 -06:00 committed by cosmonaut
parent db6ad7fb6a
commit 5f3dd6ba8a
2 changed files with 81 additions and 1 deletions

View File

@ -29,10 +29,12 @@
#define D3D11_NO_HELPERS
#define CINTERFACE
#define COBJMACROS
#include <d3d11.h>
#include <d3d11_1.h>
#include <dxgi.h>
#include <dxgi1_6.h>
#include <dxgidebug.h>
#include <d3dcompiler.h>
#include "Refresh_Driver.h"
@ -45,9 +47,11 @@
#define D3D11_DLL "d3d11.dll"
#define DXGI_DLL "dxgi.dll"
#define DXGIDEBUG_DLL "dxgidebug.dll"
#define D3D11_CREATE_DEVICE_FUNC "D3D11CreateDevice"
#define D3DCOMPILE_FUNC "D3DCompile"
#define CREATE_DXGI_FACTORY1_FUNC "CreateDXGIFactory1"
#define DXGI_GET_DEBUG_INTERFACE_FUNC "DXGIGetDebugInterface"
#define WINDOW_DATA "Refresh_D3D11WindowData"
#define UBO_BUFFER_SIZE 16000 /* 16KB */
@ -463,8 +467,11 @@ typedef struct D3D11Renderer
ID3D11DeviceContext *immediateContext;
IDXGIFactory1 *factory;
IDXGIAdapter1 *adapter;
IDXGIDebug *dxgiDebug;
IDXGIInfoQueue *dxgiInfoQueue;
void *d3d11_dll;
void *dxgi_dll;
void *dxgidebug_dll;
void *d3dcompiler_dll;
uint8_t debugMode;
@ -612,9 +619,25 @@ static void D3D11_DestroyDevice(
IDXGIAdapter_Release(renderer->adapter);
IDXGIFactory_Release(renderer->factory);
/* Report leaks and clean up debug objects */
if (renderer->dxgiDebug)
{
IDXGIDebug_ReportLiveObjects(renderer->dxgiDebug, D3D_IID_DXGI_DEBUG_ALL, DXGI_DEBUG_RLO_ALL);
IDXGIDebug_Release(renderer->dxgiDebug);
}
if (renderer->dxgiInfoQueue)
{
IDXGIInfoQueue_Release(renderer->dxgiInfoQueue);
}
/* Release the DLLs */
SDL_UnloadObject(renderer->d3d11_dll);
SDL_UnloadObject(renderer->dxgi_dll);
if (renderer->dxgidebug_dll)
{
SDL_UnloadObject(renderer->dxgidebug_dll);
}
SDL_UnloadObject(renderer->d3dcompiler_dll);
/* Free the primary Refresh structures */
@ -1842,7 +1865,18 @@ static void D3D11_QueueDestroyTexture(
Refresh_Texture *texture
) {
D3D11Texture *d3d11Texture = (D3D11Texture*) texture;
if (d3d11Texture->shaderView)
{
ID3D11ShaderResourceView_Release(d3d11Texture->shaderView);
}
if (d3d11Texture->targetView)
{
ID3D11View_Release(d3d11Texture->targetView);
}
ID3D11Resource_Release(d3d11Texture->handle);
SDL_free(d3d11Texture);
}
@ -3052,6 +3086,42 @@ static uint8_t D3D11_PrepareDriver(
return 1;
}
static void D3D11_INTERNAL_TryInitializeDXGIDebug(D3D11Renderer *renderer)
{
PFN_DXGI_GET_DEBUG_INTERFACE DXGIGetDebugInterfaceFunc;
HRESULT res;
renderer->dxgidebug_dll = SDL_LoadObject(DXGIDEBUG_DLL);
if (renderer->dxgidebug_dll == NULL)
{
Refresh_LogWarn("Could not find " DXGIDEBUG_DLL);
return;
}
DXGIGetDebugInterfaceFunc = SDL_LoadFunction(
renderer->dxgidebug_dll,
DXGI_GET_DEBUG_INTERFACE_FUNC
);
if (DXGIGetDebugInterfaceFunc == NULL)
{
Refresh_LogWarn("Could not load function: " DXGI_GET_DEBUG_INTERFACE_FUNC);
return;
}
res = DXGIGetDebugInterfaceFunc(&D3D_IID_IDXGIDebug, &renderer->dxgiDebug);
if (FAILED(res))
{
Refresh_LogWarn("Could not get IDXGIDebug interface");
}
/* FIXME: Actually do something with the info queue! */
res = DXGIGetDebugInterfaceFunc(&D3D_IID_IDXGIInfoQueue, &renderer->dxgiInfoQueue);
if (FAILED(res))
{
Refresh_LogWarn("Could not get IDXGIInfoQueue interface");
}
}
static Refresh_Device* D3D11_CreateDevice(
uint8_t debugMode
) {
@ -3141,6 +3211,12 @@ static Refresh_Device* D3D11_CreateDevice(
/* Get information about the selected adapter. Used for logging info. */
IDXGIAdapter1_GetDesc1(renderer->adapter, &adapterDesc);
/* Initialize the DXGI debug layer, if applicable */
if (debugMode)
{
D3D11_INTERNAL_TryInitializeDXGIDebug(renderer);
}
/* Load the D3D library */
renderer->d3d11_dll = SDL_LoadObject(D3D11_DLL);
if (renderer->d3d11_dll == NULL)

View File

@ -26,11 +26,15 @@
/* Function Pointer Signatures */
typedef HRESULT(WINAPI* PFN_CREATE_DXGI_FACTORY1)(const GUID* riid, void** ppFactory);
typedef HRESULT(WINAPI* PFN_DXGI_GET_DEBUG_INTERFACE)(const GUID* riid, void** ppDebug);
/* IIDs (from https://magnumdb.com) */
static const IID D3D_IID_IDXGIFactory1 = { 0x770aae78,0xf26f,0x4dba,{0xa8,0x29,0x25,0x3c,0x83,0xd1,0xb3,0x87} };
static const IID D3D_IID_IDXGIFactory6 = { 0xc1b6694f,0xff09,0x44a9,{0xb0,0x3c,0x77,0x90,0x0a,0x0a,0x1d,0x17} };
static const IID D3D_IID_IDXGIAdapter1 = { 0x29038f61,0x3839,0x4626,{0x91,0xfd,0x08,0x68,0x79,0x01,0x1a,0x05} };
static const IID D3D_IID_ID3D11Texture2D = { 0x6f15aaf2,0xd208,0x4e89,{0x9a,0xb4,0x48,0x95,0x35,0xd3,0x4f,0x9c} };
static const IID D3D_IID_ID3D11Device1 = { 0xa04bfb29,0x08ef,0x43d6,{0xa4,0x9c,0xa9,0xbd,0xbd,0xcb,0xe6,0x86} };
static const IID D3D_IID_IDXGIDebug = { 0x119e7452,0xde9e,0x40fe,{0x88,0x06,0x88,0xf9,0x0c,0x12,0xb4,0x41} };
static const IID D3D_IID_IDXGIInfoQueue = { 0xd67441c7,0x672a,0x476f,{0x9e,0x82,0xcd,0x55,0xb4,0x49,0x49,0xce} };
static const GUID D3D_IID_DXGI_DEBUG_ALL = { 0xe48ae283,0xda80,0x490b,{0x87,0xe6,0x43,0xe9,0xa9,0xcf,0xda,0x08} };