static int trylock(const std::multimap<std::wstring, unsigned long long int> &pids) { if (! initialize(pids, L"Wow.exe", L"WoW.exe")) return false; p_playerBase=getPlayerBase(); if (p_playerBase != 0) { float apos[3], afront[3], atop[3], cpos[3], cfront[3], ctop[3]; std::string context; std::wstring identity; if (fetch(apos, afront, atop, cpos, cfront, ctop, context, identity)) return true; } generic_unlock(); return false; }
static int trylock() { h = NULL; DWORD pid=getProcess(L"Wow.exe"); if (!pid) return false; h=OpenProcess(PROCESS_VM_READ, false, pid); if (!h) { #ifdef _DEBUG DWORD dwError; wchar_t errBuf[256]; dwError = GetLastError(); FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM, NULL, dwError, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR)errBuf, sizeof(errBuf),NULL); std::cout << "Error in OpenProcess: "; std::wcout << errBuf << std::endl; #endif return false; } p_playerBase=getPlayerBase(); if (p_playerBase != 0) { float apos[3], afront[3], atop[3], cpos[3], cfront[3], ctop[3]; std::string context; std::wstring identity; if (fetch(apos, afront, atop, cpos, cfront, ctop, context, identity)) { return true; } } CloseHandle(h); h = NULL; return false; }
static int fetch(float *avatar_pos, float *avatar_front, float *avatar_top, float *camera_pos, float *camera_front, float *camera_top, std::string &context, std::wstring &identity) { /* clear position */ for (int i=0; i<3; i++) { avatar_pos[i]=avatar_front[i]=avatar_top[i]=camera_pos[i]=camera_front[i]=camera_top[i]=0.0; } /* are we still looking at the right object? */ uint64_t peekGUID, tempGUID; peekGUID=getInt64(p_playerBase+0x30); if (g_playerGUID != peekGUID) { /* no? Try to resynch to the new address. Happens when walking through portals quickly (aka no or short loading screen) */ tempGUID = g_playerGUID; p_playerBase=getPlayerBase(); if (tempGUID != g_playerGUID) { /* GUID of actor changed, likely a character and/or realm change */ wow.refresh(); } peekGUID=getInt64(p_playerBase+0x30); if (g_playerGUID != peekGUID) { /* no? we are still getting the expected GUID for our avatar, but we don't have it's current position */ return true; } } context.clear(); std::wstringstream identityStream; identityStream << wow.getNameAvatar(); identity = identityStream.str(); BOOL ok = true; // Wow stores as // North/South (+ North) // East/West (+ West) // Up/Down (+Up) // ... which isn't a right-hand coordinate system. float pos[3]; ok = ok && peekProc((BYTE *) p_playerBase + 0x798, pos, sizeof(float)*3); if (! ok) { if (g_playerGUID == 0xffffffffffffffff) { return false; } else if (g_playerGUID == 0) { return true; } else { /* FIXME need a better way to mark PlayerBase invalid */ g_playerGUID=0; return true; /* we got a good reference for an avatar, but no good position */ } } /* convert wow -> right hand coordinate system */ avatar_pos[0] = -pos[1]; avatar_pos[1] = pos[2]; avatar_pos[2] = pos[0]; float heading=0.0; ok = ok && peekProc((BYTE *) p_playerBase + 0x7A8, &heading, sizeof(heading)); if (! ok) return false; float pitch=0.0; ok = ok && peekProc((BYTE *) p_playerBase + 0x7AC, &pitch, sizeof(pitch)); if (! ok) return false; /* TODO use yaw (heading) and pitch angles */ /* FIXME sin/cos (heading) is right from the numbers, but (-heading) is right from the sound position */ avatar_front[0]=-sin(heading); avatar_front[1]=0.0; avatar_front[2]=cos(heading); // Dummy top vector, can't tilt your head sideways in wow. avatar_top[0]= 0.0; avatar_top[1]= 1.0; avatar_top[2]= 0.0; getCamera(camera_pos, camera_front, camera_top); if (! ok) return false; // printf("P %f %f %f -- %f %f %f \n", avatar_pos[0], avatar_pos[1], avatar_pos[2], avatar_front[0], avatar_front[1], avatar_front[2]); // is it a unit length vector? if (fabs((avatar_front[0]*avatar_front[0]+avatar_front[1]*avatar_front[1]+avatar_front[2]*avatar_front[2])-1.0)>0.5) { // printf("F %f %f %f\n", front[0], front[1], front[2]); return false; } // are we around 0/0/0 if ((fabs(avatar_pos[0])<0.1) && (fabs(avatar_pos[1])<0.1) && (fabs(avatar_pos[2])<0.1)) { // printf("P %f %f %f\n", avatar_pos[0], avatar_pos[1], avatar_pos[2]); return false; } return true; }