Code:
#include "DIPHOOK.h"
#define safe_release(x) if(x != NULL){ x->Release(); x = NULL;}
void Dx9Hook( LPCSTR D3D9 );
INT Thread_XD3DXINIT( );
LPDIRECT3DDEVICE9 pDevice;
DWORD * VTable;
BYTE DIPOpCodes[7];
DWORD dwDIP_hook, dwDIP_ret;
BYTE ImJumpingBack = 0x00;
D3DPRIMITIVETYPE PrimitiveType;
INT BaseIndex;
LPD3DXFONT pFont;
UINT MinIndex, NumVertices, StartIndex, PrimitiveCount, Device_Interface;
HRESULT (WINAPI* DrawIndexedPrimitive_Pointer) (LPDIRECT3DDEVICE9, D3DPRIMITIVETYPE, INT, UINT, UINT, UINT, UINT);
LPDIRECT3DVERTEXBUFFER9 Stream_Data;
LPDIRECT3DDEVICE9 g_pDevice=NULL;
UINT Offset = 0, m_Stride = 0;
IDirect3DTexture9* texBack=NULL,*texFront=NULL;
void SetLightChams(float A, float R, float G, float B, IDirect3DDevice9 *pDevice)
{
D3DMATERIAL9 pMaterial;
ZeroMemory(&pMaterial, sizeof(D3DMATERIAL9));
pDevice->SetRenderState(D3DRS_LIGHTING, TRUE); //Enable Lighting
//Ambient
pMaterial.Ambient.a = (A/255);
pMaterial.Ambient.r = (R/255);
pMaterial.Ambient.g = (G/255);
pMaterial.Ambient.b = (B/255);
//Diffuse
pMaterial.Diffuse.a = (A/255);
pMaterial.Diffuse.r = (R/255);
pMaterial.Diffuse.g = (G/255);
pMaterial.Diffuse.b = (B/255);
//Specular
pMaterial.Specular.a = (A/255);
pMaterial.Specular.r = (R/255);
pMaterial.Specular.g = (G/255);
pMaterial.Specular.b = (B/255);
pDevice->SetMaterial(&pMaterial);
}
void DoDIP(LPDIRECT3DDEVICE9 pDevice)
{
if(pDevice->GetStreamSource(0, &Stream_Data, &Offset, &m_Stride) == D3D_OK)
Stream_Data->Release();
if (g_pDevice != pDevice)
{
safe_release(g_pDevice)
g_pDevice = pDevice;
safe_release(texBack)
safe_release(texFront)
}
if (texBack == NULL)
{
GenerateTexture(pDevice, &texBack, 0xff0000ff);
}
if (texFront == NULL)
{
GenerateTexture(pDevice, &texFront, 0xff00ff00);
}
if( m_Stride == 44 || m_Stride == 36 || m_Stride == 32 || m_Stride == 36 || m_Stride == 40 || m_Stride == 42 )
{
DWORD dwOldZEnable = D3DZB_TRUE;
pDevice->SetTexture(0,0);
pDevice->SetTexture(0, texBack);
pDevice->GetRenderState(D3DRS_ZENABLE, &dwOldZEnable);
pDevice->SetRenderState(D3DRS_ZENABLE, D3DZB_FALSE);
pDIP(pDevice, PrimitiveType, BaseIndex, MinIndex, NumVertices, StartIndex, PrimitiveCount);
pDevice->SetRenderState(D3DRS_ZENABLE, dwOldZEnable);
pDevice->SetTexture(0,0);
pDevice->SetTexture(0, texFront);/* try? hmm hold
DWORD dwOldZEnable = D3DZB_TRUE;
pDevice->GetRenderState(D3DRS_ZENABLE, &dwOldZEnable);
pDevice->SetRenderState(D3DRS_ZENABLE, D3DZB_FALSE);
pDevice->SetRenderState(255,0,0,255, pDevice);
pDIP(pDevice, PrimitiveType, BaseIndex, MinIndex, NumVertices, StartIndex, PrimitiveCount);
pDevice->SetRenderState(D3DRS_ZENABLE, D3DZB_TRUE);
pDevice->SetRenderState(D3DRS_AMBIENT, D3DCOLOR_ARGB(255,0,255,0));*/
}
}
__declspec( naked ) void MyDIP(LPDIRECT3DDEVICE9 pDevice)
{
__asm
{
MOV EDI,DWORD PTR SS:[EBP+0x8]
XOR EBX,EBX
MOV pDevice, EDI;
PUSHFD
PUSHAD
MOV EAX,DWORD PTR SS:[EBP+0x20]
MOV DWORD PTR DS:[PrimitiveCount], EAX
MOV ECX,DWORD PTR SS:[EBP+0x1C]
MOV DWORD PTR DS:[StartIndex], ECX
MOV EDX,DWORD PTR SS:[EBP+0x18]
MOV DWORD PTR DS:[NumVertices], EDX
MOV EAX,DWORD PTR SS:[EBP+0x14]
MOV DWORD PTR DS:[MinIndex], EAX
MOV ECX,DWORD PTR SS:[EBP+0x10]
MOV DWORD PTR DS:[BaseIndex], ECX
MOV EDX,DWORD PTR SS:[EBP+0x0C]
MOV DWORD PTR DS:[PrimitiveType], EDX
MOV EAX,DWORD PTR SS:[EBP+0x08]
MOV DWORD PTR DS:[Device_Interface], EAX
// Get DIP Pointer
MOV ECX,DWORD PTR DS:[EDI]// pDevice
MOV EAX,DWORD PTR DS:[ECX+0x148]// DIP pointer
MOV DWORD PTR SS:[pDIP],EAX// need this
}
if( ImJumpingBack )
goto Jumpback;
ImJumpingBack = 0x01;
DoDIP(pDevice);
ImJumpingBack = 0x00;
Jumpback:
__asm
{
POPAD
POPFD
CMP EDI,EBX //replace patched code
jmp dwDIP_ret; //jump back to normal DIP
}
}
//Then make a thread
bool IsGameReadyForHook(void)
{
if( GetModuleHandle( "d3d9.dll" ) != NULL )
return true;
return false;
}
INT Thread_XD3DXINIT( )
{
while(!IsGameReadyForHook() )
Sleep(100);
Dx9Hook("d3d9.dll");
WriteOpCode((void *)DIPOpCodes, (void *)"\x8B\x7D\x08\x33\xDB\x3B\xFB", 7);
while( 1 )
{
Sleep( 1000 );
if(memcmp((void *)DIPOpCodes, (void *)dwDIP_hook, 7) == 0 )
DetourCreate((PBYTE)dwDIP_hook, (PBYTE)MyDIP, DETOUR_TYPE_NOP_NOP_JMP);
}
return NULL;
}
bool bCompare(const BYTE* pData, const BYTE* bMask, const char* szMask)
{
for(;*szMask;++szMask,++pData,++bMask)
if(*szMask=='x' && *pData!=*bMask) return 0;
return (*szMask) == NULL;
}
DWORD FindPattern(DWORD dwdwAdd,DWORD dwLen,BYTE *bMask,char * szMask)
{
for(DWORD i=0; i<dwLen; i++)
if (bCompare((BYTE*)(dwdwAdd+i),bMask,szMask)) return (DWORD)(dwdwAdd+i);
return 0;
}
//then your hook that goes in thread:
DWORD * FindDevice(VOID)//Finds the Device on Injection
{
DWORD Base = (DWORD)LoadLibraryW(L"d3d9.dll");
for(DWORD i = 0; i < 0x128000; i++ )
{
if ( (*(BYTE *)(Base+i+0x00))==0xC7
&& (*(BYTE *)(Base+i+0x01))==0x06
&& (*(BYTE *)(Base+i+0x06))==0x89
&& (*(BYTE *)(Base+i+0x07))==0x86
&& (*(BYTE *)(Base+i+0x0C))==0x89
&& (*(BYTE *)(Base+i+0x0D))==0x86 )
return (DWORD *)(Base + i + 2);
}
return NULL;
}
void Dx9Hook( LPCSTR D3D9 )
{
DWORD hD3D = NULL;
while (!hD3D) hD3D = (DWORD)GetModuleHandle(D3D9);
DWORD PPPDevice = FindPattern(hD3D, 0x128000, (PBYTE)"\xC7\x06\x00\x00\x00\x00\x89\x86\x00\x00\x00\x00\x89\x86", "xx????xx????xx");
memcpy( &VTable, (void *)(PPPDevice + 2), 4);
dwDIP_hook = VTable[82] + 0x2D;
dwDIP_ret = dwDIP_hook + 0x7;
*(PDWORD)&DrawIndexedPrimitive_Pointer = (DWORD)VTable[82];
}
BOOL WINAPI DllMain ( HMODULE hDll, DWORD dwReason, LPVOID lpReserved )
{
DisableThreadLibraryCalls(hDll);
if ( dwReason == DLL_PROCESS_ATTACH )
CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)Thread_XD3DXINIT, NULL, NULL, NULL);
return TRUE;
}