Hallo,
ich habe hier ein Problem mit der VTable, bei dem ich mir nicht ganz sicher bin, ob ich nicht einfach etwas übersehe.
Ich erstelle mit IDirect3D9::CreateDevice() ein IDirect3DDevice9 und initialisiere damit meinen Pointer auf die VTable:
SD3DDeviceVTable ist ein einfaches Struct, in dem die ganzen Memberfunktionen sind:
Wenn ich jetzt mit DetourFunction eine Funktion hooke, funktioniert alles ohne Probleme:
Wenn ich jetzt allerdings die Adresse direkt in der VTable verändern möchte, klappt das zwar auch, allerdings ruft das Zielprogramm meinen Hook nie auf. Wenn ich mit dem Debugger den Aufruf einer Funktion abfange & die VTable des Device Pointers anschaue, hat die eine ganz andere Adresse als die meines Device Pointers - somit schreibe ich zwar in gültigen Speicher, allerdings halt in welchen, der von keinem anderen Device verwendet wird.
Die VTable im Konstruktor von CD3DBase wird zwar gesetzt, allerdings später scheinbar nochmals ersetzt, somit hat es keinen Nutzen, einfach die VTable, die das Pattern zurückgibt, zu verwenden (bereits getestet).
Hat jemand eine Idee, weshalb es für das Interface mehrere VTables gibt, obwohl die Aufrufe von CreateDevice fast identisch sind?
Das Zielprogramm ist übrigens momentan ein von mir selbst geschriebenes, soll später natürlich aber auch bei anderen Programmen funktionieren.
ich habe hier ein Problem mit der VTable, bei dem ich mir nicht ganz sicher bin, ob ich nicht einfach etwas übersehe.
Ich erstelle mit IDirect3D9::CreateDevice() ein IDirect3DDevice9 und initialisiere damit meinen Pointer auf die VTable:
Code:
m_device = CreateDevice(); m_vtable = *reinterpret_cast<SD3DDeviceVTable **>(m_device);
Code:
struct SD3DDeviceVTable
{
CD3DDeviceFunction& operator[](DWORD index)
{
return reinterpret_cast<CD3DDeviceFunction *>(this)[index];
}
#pragma pack(push, 1)
union
{
CD3DDeviceFunction *QueryInterface_Raw; // 0
HRESULT(__stdcall *QueryInterface)(LPDIRECT3DDEVICE9, REFIID, void**);
};
//usw...
};
Code:
nd::CD3DDevice d3d; auto &present = d3d[PRESENT_INDEX]; present_orig = reinterpret_cast<Present_t>(DetourFunction(present, reinterpret_cast<PBYTE>(&present_hk)));
Die VTable im Konstruktor von CD3DBase wird zwar gesetzt, allerdings später scheinbar nochmals ersetzt, somit hat es keinen Nutzen, einfach die VTable, die das Pattern zurückgibt, zu verwenden (bereits getestet).
Hat jemand eine Idee, weshalb es für das Interface mehrere VTables gibt, obwohl die Aufrufe von CreateDevice fast identisch sind?
Das Zielprogramm ist übrigens momentan ein von mir selbst geschriebenes, soll später natürlich aber auch bei anderen Programmen funktionieren.