mirror of
https://github.com/Mauler125/r5sdk.git
synced 2025-02-09 19:15:03 +01:00
Add prototype DirectX hook implementation
/* PROTOTYPE */
This commit is contained in:
parent
3be3bcd5c1
commit
21bc365a71
8
r5dev/include/id3dx.h
Normal file
8
r5dev/include/id3dx.h
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
void PrintDXAddress();
|
||||||
|
void InstallDXHooks();
|
||||||
|
void RemoveDXHooks();
|
||||||
|
void SetupDXSwapChain();
|
||||||
|
|
||||||
|
extern DWORD g_dThreadId;
|
294
r5dev/src/id3dx.cpp
Normal file
294
r5dev/src/id3dx.cpp
Normal file
@ -0,0 +1,294 @@
|
|||||||
|
#include <iomanip>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <d3d11.h>
|
||||||
|
#include <windows.h>
|
||||||
|
|
||||||
|
#include "id3dx.h"
|
||||||
|
#include "detours.h"
|
||||||
|
#include "overlay.h"
|
||||||
|
#include "patterns.h"
|
||||||
|
|
||||||
|
#include "imgui.h"
|
||||||
|
#include "imgui_impl_dx11.h"
|
||||||
|
#include "imgui_impl_win32.h"
|
||||||
|
|
||||||
|
#pragma comment(lib, "d3d11.lib")
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------
|
||||||
|
* _id3dx.cpp
|
||||||
|
*-----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
typedef HRESULT(__stdcall* IDXGISwapChainPresent)(IDXGISwapChain* pSwapChain, UINT nSyncInterval, UINT nFlags);
|
||||||
|
HRESULT __stdcall Present(IDXGISwapChain* pSwapChain, UINT nSyncInterval, UINT nFlags);
|
||||||
|
|
||||||
|
extern LRESULT CALLBACK DXGIMsgProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { return DefWindowProc(hwnd, uMsg, wParam, lParam); }
|
||||||
|
extern LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
static BOOL g_bShowMenu = false;
|
||||||
|
static BOOL g_bInitialized = false;
|
||||||
|
static BOOL g_bPresentHooked = false;
|
||||||
|
|
||||||
|
static HWND g_hGameWindow = NULL;
|
||||||
|
static WNDPROC g_oWndProc = NULL;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
static IDXGISwapChainPresent g_fnIDXGISwapChainPresent = nullptr;
|
||||||
|
static IDXGISwapChain* g_pSwapChain = nullptr;
|
||||||
|
static ID3D11DeviceContext* g_pDeviceContext = nullptr;
|
||||||
|
static ID3D11Device* g_pDevice = nullptr;
|
||||||
|
static ID3D11RenderTargetView* g_pRenderTargetView = nullptr;
|
||||||
|
|
||||||
|
DWORD g_dThreadId = NULL;
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
// Window
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
void Hook_SetCursorPosition(int a1, INT64 posX, INT64 posY)
|
||||||
|
{
|
||||||
|
if (g_bShowMenu) { return; }
|
||||||
|
return SetCursorPosition(a1, posX, posY);
|
||||||
|
}
|
||||||
|
|
||||||
|
LRESULT CALLBACK hWndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||||
|
{
|
||||||
|
ImGuiIO& io = ImGui::GetIO();
|
||||||
|
|
||||||
|
if (uMsg == WM_KEYUP)
|
||||||
|
{
|
||||||
|
if (wParam == VK_OEM_3)
|
||||||
|
{
|
||||||
|
g_bShowMenu = !g_bShowMenu;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (g_bShowMenu)
|
||||||
|
{
|
||||||
|
ImGui_ImplWin32_WndProcHandler(hWnd, uMsg, wParam, lParam);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return CallWindowProc(g_oWndProc, hWnd, uMsg, wParam, lParam);
|
||||||
|
}
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
// Present
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
HRESULT GetDeviceAndCtxFromSwapchain(IDXGISwapChain* pSwapChain, ID3D11Device** ppDevice, ID3D11DeviceContext** ppContext)
|
||||||
|
{
|
||||||
|
HRESULT ret = pSwapChain->GetDevice(__uuidof(ID3D11Device), (PVOID*)ppDevice);
|
||||||
|
if (SUCCEEDED(ret)) { (*ppDevice)->GetImmediateContext(ppContext); }
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
void GetPresent()
|
||||||
|
{
|
||||||
|
WNDCLASSEXA wc = { sizeof(WNDCLASSEX), CS_CLASSDC, DXGIMsgProc, 0L, 0L, GetModuleHandleA(NULL), NULL, NULL, NULL, NULL, "DX", NULL };
|
||||||
|
RegisterClassExA(&wc);
|
||||||
|
HWND hWnd = CreateWindowA("DX", NULL, WS_OVERLAPPEDWINDOW, 100, 100, 300, 300, NULL, NULL, wc.hInstance, NULL);
|
||||||
|
|
||||||
|
DXGI_SWAP_CHAIN_DESC sd;
|
||||||
|
D3D_FEATURE_LEVEL nFeatureLevelsSet = D3D_FEATURE_LEVEL_11_0;
|
||||||
|
D3D_FEATURE_LEVEL nFeatureLevelsSupported;
|
||||||
|
ZeroMemory(&sd, sizeof(sd));
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
sd.BufferCount = 1;
|
||||||
|
sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
|
||||||
|
sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
|
||||||
|
sd.BufferDesc.Height = 800;
|
||||||
|
sd.BufferDesc.Width = 600;
|
||||||
|
sd.BufferDesc.RefreshRate = { 60, 1 };
|
||||||
|
sd.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
|
||||||
|
sd.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
|
||||||
|
sd.Windowed = TRUE;
|
||||||
|
sd.OutputWindow = hWnd;//GetForegroundWindow();
|
||||||
|
sd.SampleDesc.Count = 1;
|
||||||
|
sd.SampleDesc.Quality = 0;
|
||||||
|
sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
g_hGameWindow = sd.OutputWindow;
|
||||||
|
UINT nFeatureLevelsRequested = 1;
|
||||||
|
HRESULT hr = 0;
|
||||||
|
IDXGISwapChain* pSwapChain = nullptr;
|
||||||
|
ID3D11Device* pDevice = nullptr;
|
||||||
|
ID3D11DeviceContext* pContext = nullptr;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
if (FAILED(hr = D3D11CreateDeviceAndSwapChain(NULL,
|
||||||
|
D3D_DRIVER_TYPE_HARDWARE,
|
||||||
|
NULL,
|
||||||
|
NULL,
|
||||||
|
&nFeatureLevelsSet,
|
||||||
|
nFeatureLevelsRequested,
|
||||||
|
D3D11_SDK_VERSION,
|
||||||
|
&sd,
|
||||||
|
&pSwapChain,
|
||||||
|
&pDevice,
|
||||||
|
&nFeatureLevelsSupported,
|
||||||
|
&pContext)))
|
||||||
|
{
|
||||||
|
std::cout << "VMT hook failed" << std::endl;
|
||||||
|
RemoveDXHooks();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
DWORD_PTR* pSwapChainVtable = nullptr;
|
||||||
|
DWORD_PTR* pContextVTable = nullptr;
|
||||||
|
DWORD_PTR* pDeviceVTable = nullptr;
|
||||||
|
|
||||||
|
pSwapChainVtable = (DWORD_PTR*)pSwapChain;
|
||||||
|
pSwapChainVtable = (DWORD_PTR*)pSwapChainVtable[0];
|
||||||
|
pContextVTable = (DWORD_PTR*)pContext;
|
||||||
|
pContextVTable = (DWORD_PTR*)pContextVTable[0];
|
||||||
|
pDeviceVTable = (DWORD_PTR*)pDevice;
|
||||||
|
pDeviceVTable = (DWORD_PTR*)pDeviceVTable[0];
|
||||||
|
|
||||||
|
g_fnIDXGISwapChainPresent = (IDXGISwapChainPresent)(DWORD_PTR)pSwapChainVtable[8];
|
||||||
|
|
||||||
|
pSwapChain->Release();
|
||||||
|
pContext->Release();
|
||||||
|
pDevice->Release();
|
||||||
|
|
||||||
|
g_bPresentHooked = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
// Init
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
void SetupImGui()
|
||||||
|
{
|
||||||
|
ImGui::CreateContext();
|
||||||
|
IMGUI_CHECKVERSION();
|
||||||
|
ImGuiIO& io = ImGui::GetIO(); (void)io;
|
||||||
|
ImGui_ImplWin32_Init(g_hGameWindow);
|
||||||
|
ImGui_ImplDX11_Init(g_pDevice, g_pDeviceContext);
|
||||||
|
ImGui::GetIO().ImeWindowHandle = g_hGameWindow;
|
||||||
|
io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard;
|
||||||
|
}
|
||||||
|
|
||||||
|
void DrawImGui()
|
||||||
|
{
|
||||||
|
ImGui_ImplWin32_NewFrame();
|
||||||
|
ImGui_ImplDX11_NewFrame();
|
||||||
|
|
||||||
|
ImGui::NewFrame();
|
||||||
|
|
||||||
|
if (g_bShowMenu)
|
||||||
|
{
|
||||||
|
bool bShowMenu = true;
|
||||||
|
ShowGameConsole(&bShowMenu);
|
||||||
|
}
|
||||||
|
|
||||||
|
ImGui::EndFrame();
|
||||||
|
ImGui::Render();
|
||||||
|
|
||||||
|
g_pDeviceContext->OMSetRenderTargets(1, &g_pRenderTargetView, NULL);
|
||||||
|
ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData());
|
||||||
|
}
|
||||||
|
|
||||||
|
void RenderTarget(IDXGISwapChain* pSwapChain)
|
||||||
|
{
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
DXGI_SWAP_CHAIN_DESC sd = { 0 };
|
||||||
|
ID3D11Texture2D* pBackBuffer = { 0 };
|
||||||
|
D3D11_RENDER_TARGET_VIEW_DESC render_target_view_desc;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
pSwapChain->GetDesc(&sd);
|
||||||
|
ZeroMemory(&render_target_view_desc, sizeof(render_target_view_desc));
|
||||||
|
|
||||||
|
g_hGameWindow = sd.OutputWindow;
|
||||||
|
render_target_view_desc.Format = sd.BufferDesc.Format;
|
||||||
|
render_target_view_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
pSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&pBackBuffer);
|
||||||
|
if (pBackBuffer != NULL) { g_pDevice->CreateRenderTargetView(pBackBuffer, &render_target_view_desc, &g_pRenderTargetView); }
|
||||||
|
pBackBuffer->Release();
|
||||||
|
}
|
||||||
|
|
||||||
|
HRESULT __stdcall Present(IDXGISwapChain* pSwapChain, UINT nSyncInterval, UINT nFlags)
|
||||||
|
{
|
||||||
|
if (!g_bInitialized)
|
||||||
|
{
|
||||||
|
if (FAILED(GetDeviceAndCtxFromSwapchain(pSwapChain, &g_pDevice, &g_pDeviceContext)))
|
||||||
|
{
|
||||||
|
return g_fnIDXGISwapChainPresent(pSwapChain, nSyncInterval, nFlags);
|
||||||
|
}
|
||||||
|
|
||||||
|
RenderTarget(pSwapChain);
|
||||||
|
SetupImGui();
|
||||||
|
|
||||||
|
g_oWndProc = (WNDPROC)SetWindowLongPtr(g_hGameWindow, GWLP_WNDPROC, (LONG_PTR)hWndProc);
|
||||||
|
g_bInitialized = true;
|
||||||
|
g_pSwapChain = pSwapChain;
|
||||||
|
}
|
||||||
|
|
||||||
|
DrawImGui();
|
||||||
|
g_bInitialized = true;
|
||||||
|
/////////////////////////////////////////////////////////////////////////////
|
||||||
|
return g_fnIDXGISwapChainPresent(pSwapChain, nSyncInterval, nFlags);
|
||||||
|
}
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
// Management
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
void InstallDXHooks()
|
||||||
|
{
|
||||||
|
DetourTransactionBegin();
|
||||||
|
DetourUpdateThread(GetCurrentThread());
|
||||||
|
DetourAttach((LPVOID*)&SetCursorPosition, &Hook_SetCursorPosition);
|
||||||
|
DetourAttach(&(LPVOID&)g_fnIDXGISwapChainPresent, (PBYTE)Present);
|
||||||
|
DetourTransactionCommit();
|
||||||
|
}
|
||||||
|
|
||||||
|
void RemoveDXHooks()
|
||||||
|
{
|
||||||
|
DetourTransactionBegin();
|
||||||
|
DetourUpdateThread(GetCurrentThread());
|
||||||
|
DetourDetach((LPVOID*)&SetCursorPosition, &Hook_SetCursorPosition);
|
||||||
|
DetourDetach(&(LPVOID&)g_fnIDXGISwapChainPresent, (PBYTE)Present);
|
||||||
|
DetourTransactionCommit();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PrintDXAddress()
|
||||||
|
{
|
||||||
|
std::cout << "--------------------------------------------------" << std::endl;
|
||||||
|
std::cout << " ID3D11DeviceContext : " << std::hex << g_pDeviceContext << std::endl;
|
||||||
|
std::cout << " ID3D11Device : " << std::hex << g_pDevice << std::endl;
|
||||||
|
std::cout << " ID3D11RenderTargetView : " << std::hex << g_pRenderTargetView << std::endl;
|
||||||
|
std::cout << " IDXGISwapChain : " << std::hex << g_pSwapChain << std::endl;
|
||||||
|
std::cout << " IDXGISwapChainPresent : " << std::hex << g_fnIDXGISwapChainPresent << std::endl;
|
||||||
|
std::cout << "--------------------------------------------------" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
// Main
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
DWORD __stdcall DXSwapChainWorker(LPVOID)
|
||||||
|
{
|
||||||
|
GetPresent();
|
||||||
|
InstallDXHooks();
|
||||||
|
if (!g_bPresentHooked) { ImGui_ImplWin32_Shutdown(); ImGui_ImplDX11_Shutdown(); RemoveDXHooks(); }
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SetupDXSwapChain()
|
||||||
|
{
|
||||||
|
// Create a worker thread for the console overlay
|
||||||
|
DWORD __stdcall DXSwapChainWorker(LPVOID);
|
||||||
|
HANDLE hThread = CreateThread(NULL, 0, DXSwapChainWorker, NULL, 0, &g_dThreadId);
|
||||||
|
|
||||||
|
if (hThread) { CloseHandle(hThread); }
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user