Code:
using System;
using Voodoo;
namespace VoodooTest
{
class Program
{
private static uint g_clientConnection = 0x011CA260;
private static uint s_curMgr;
private static Memory mgr;
static void Main()
{
Console.WindowWidth = Console.LargestWindowWidth;
mgr = new Memory("World of Warcraft");
g_clientConnection = mgr.Read<uint>(g_clientConnection);
s_curMgr = mgr.Read<uint>(0x011CA260, 0x2864);
string name = mgr.ReadString(0x11CA298, true);
Console.WriteLine(name);
ReadObjectList();
Console.WriteLine(LuaDoString("TargetLastTarget()"));
Console.ReadLine();
}
static uint LuaDoString(string luaString)
{
using (CodeCave cc = mgr.CreateCodeCave(luaString.Length + 1))
{
cc.WriteString(luaString, true);
using (CodeCave cc1 = mgr.CreateCodeCave())
{
// A few ways to inject ASM :)
/*
cc1.AsmAddLine("mov EDX, [0x0{0}]", g_clientConnection.ToString("X"));
cc1.AsmAddLine("mov EDX, [EDX+0x{0}]", s_curMgr.ToString("X"));
cc1.AsmAddLine("FS mov EAX, [0x2C]");
cc1.AsmAddLine("mov EAX, [EAX]");
cc1.AsmAddLine("add EAX, 8");
cc1.AsmAddLine("mov [EAX], EDX"); // End UpdateCurMgr
cc1.AsmAddLine("mov ecx, 0x0092E887");
cc1.AsmAddLine("mov eax, " + cc.AllocationAddress);
cc1.AsmAddLine("push ecx");
cc1.AsmAddLine("push eax");
cc1.AsmAddLine("push eax");
cc1.AsmAddLine("mov eax, 0x0077DEF0");
cc1.AsmAddLine("call eax");
cc1.AsmAddLine("add esp, 0xC");
cc1.AsmAddLine("retn")
return cc1.AsmInjectAndExecute();
*/
/*
cc1.AsmAddLine("mov EDX, [0x0" + g_clientConnection.ToString("X"),
"mov EDX, [EDX+0x" + s_curMgr.ToString("X"),
"FS mov EAX, [0x2C]",
"mov EAX, [EAX]",
"add EAX, 8",
"mov [EAX], EDX",
"mov ecx, 0x0092E887",
"mov eax, " + cc.AllocationAddress,
"push ecx",
"push eax",
"push eax",
"mov eax, 0x0077DEF0",
"call eax",
"add esp, 0xC",
"retn");
*/
return cc1.AsmInjectAndExecute(
"mov EDX, [0x0" + g_clientConnection.ToString("X"),
"mov EDX, [EDX+0x" + s_curMgr.ToString("X"),
"FS mov EAX, [0x2C]",
"mov EAX, [EAX]",
"add EAX, 8",
"mov [EAX], EDX",
"mov ecx, 0x0092E887",
"mov eax, " + cc.AllocationAddress,
"push ecx",
"push eax",
"push eax",
"mov eax, 0x0077DEF0",
"call eax",
"add esp, 0xC",
"retn");
}
}
}
static void ReadObjectList()
{
ulong localGuid = mgr.Read<ulong>(s_curMgr + 0xC0);
Console.WriteLine("LocalGUID: 0x{0:X016}", localGuid);
uint curObj = mgr.Read<uint>(s_curMgr + 0xAC);
while (curObj != 0 && (curObj & 1) == 0)
{
uint curpObj = mgr.Read<uint>(curObj + 0x8);
ulong objGuid = mgr.Read<ulong>(curpObj + ((uint)eObjectFields.OBJECT_FIELD_GUID * 4)); // 0x0
float X = mgr.Read<float>(curpObj + ((uint)eGameObjectFields.GAMEOBJECT_POS_X * 4));
float Y = mgr.Read<float>(curpObj + ((uint)eGameObjectFields.GAMEOBJECT_POS_Y * 4));
float Z = mgr.Read<float>(curpObj + ((uint)eGameObjectFields.GAMEOBJECT_POS_Z * 4));
float Facing = mgr.Read<float>(curpObj + ((uint) eGameObjectFields.GAMEOBJECT_FACING * 4));
int Type = mgr.Read<int>(curpObj + ((uint) eObjectFields.OBJECT_FIELD_TYPE * 4));
Console.WriteLine(
"Type: {6} Object: 0x{0:X08} -- GUID: 0x{1:X016} X: {2} Y: {3} Z: {4} Facing: {5}", curObj,
objGuid, X, Y, Z, Facing, (eObjType)Type);
uint nextObj = mgr.Read<uint>((curObj + 0x3C));
if (nextObj == curObj)
break;
curObj = nextObj;
}
}
}
}
Again, don't expect any of that to actually compile, or make sense in some parts. (I know for a fact some of it won't work, but as I said, it's just an API example.)