nuclear@0: /************************************************************************************ nuclear@0: nuclear@0: Filename : Util_SystemInfo.cpp nuclear@0: Content : Various operations to get information about the system nuclear@0: Created : September 26, 2014 nuclear@0: Author : Kevin Jenkins nuclear@0: nuclear@0: Copyright : Copyright 2014 Oculus VR, LLC All Rights reserved. nuclear@0: nuclear@0: Licensed under the Oculus VR Rift SDK License Version 3.2 (the "License"); nuclear@0: you may not use the Oculus VR Rift SDK except in compliance with the License, nuclear@0: which is provided at the time of installation or download, or which nuclear@0: otherwise accompanies this software in either electronic or hard copy form. nuclear@0: nuclear@0: You may obtain a copy of the License at nuclear@0: nuclear@0: http://www.oculusvr.com/licenses/LICENSE-3.2 nuclear@0: nuclear@0: Unless required by applicable law or agreed to in writing, the Oculus VR SDK nuclear@0: distributed under the License is distributed on an "AS IS" BASIS, nuclear@0: WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. nuclear@0: See the License for the specific language governing permissions and nuclear@0: limitations under the License. nuclear@0: nuclear@0: ************************************************************************************/ nuclear@0: nuclear@0: #include "Util_SystemInfo.h" nuclear@0: #include "../Kernel/OVR_Timer.h" nuclear@0: #include "../Kernel/OVR_Threads.h" nuclear@0: #include "../Kernel/OVR_Log.h" nuclear@0: #include "../Kernel/OVR_Array.h" nuclear@0: nuclear@0: /* nuclear@0: // Disabled, can't link RiftConfigUtil nuclear@0: #ifdef OVR_OS_WIN32 nuclear@0: #define _WIN32_DCOM nuclear@0: #include nuclear@0: #include nuclear@0: nuclear@0: # pragma comment(lib, "wbemuuid.lib") nuclear@0: #endif nuclear@0: */ nuclear@0: nuclear@0: nuclear@0: namespace OVR { namespace Util { nuclear@0: nuclear@0: // From http://blogs.msdn.com/b/oldnewthing/archive/2005/02/01/364563.aspx nuclear@0: #if defined (OVR_OS_WIN64) || defined (OVR_OS_WIN32) nuclear@0: nuclear@0: #pragma comment(lib, "version.lib") nuclear@0: nuclear@0: typedef BOOL(WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL); nuclear@0: BOOL Is64BitWindows() nuclear@0: { nuclear@0: #if defined(_WIN64) nuclear@0: return TRUE; // 64-bit programs run only on Win64 nuclear@0: #elif defined(_WIN32) nuclear@0: // 32-bit programs run on both 32-bit and 64-bit Windows nuclear@0: // so must sniff nuclear@0: BOOL f64 = FALSE; nuclear@0: LPFN_ISWOW64PROCESS fnIsWow64Process; nuclear@0: nuclear@0: fnIsWow64Process = (LPFN_ISWOW64PROCESS)GetProcAddress(GetModuleHandle(L"kernel32"), "IsWow64Process"); nuclear@0: if (NULL != fnIsWow64Process) nuclear@0: { nuclear@0: return fnIsWow64Process(GetCurrentProcess(), &f64) && f64; nuclear@0: } nuclear@0: return FALSE; nuclear@0: #else nuclear@0: return FALSE; // Win64 does not support Win16 nuclear@0: #endif nuclear@0: } nuclear@0: #endif nuclear@0: nuclear@0: const char * OSAsString() nuclear@0: { nuclear@0: #if defined (OVR_OS_IPHONE) nuclear@0: return "IPhone"; nuclear@0: #elif defined (OVR_OS_DARWIN) nuclear@0: return "Darwin"; nuclear@0: #elif defined (OVR_OS_MAC) nuclear@0: return "Mac"; nuclear@0: #elif defined (OVR_OS_BSD) nuclear@0: return "BSD"; nuclear@0: #elif defined (OVR_OS_WIN64) || defined (OVR_OS_WIN32) nuclear@0: if (Is64BitWindows()) nuclear@0: return "Win64"; nuclear@0: else nuclear@0: return "Win32"; nuclear@0: #elif defined (OVR_OS_ANDROID) nuclear@0: return "Android"; nuclear@0: #elif defined (OVR_OS_LINUX) nuclear@0: return "Linux"; nuclear@0: #elif defined (OVR_OS_BSD) nuclear@0: return "BSD"; nuclear@0: #else nuclear@0: return "Other"; nuclear@0: #endif nuclear@0: } nuclear@0: nuclear@0: uint64_t GetGuidInt() nuclear@0: { nuclear@0: uint64_t g = Timer::GetTicksNanos(); nuclear@0: nuclear@0: uint64_t lastTime, thisTime; nuclear@0: int j; nuclear@0: // Sleep a small random time, then use the last 4 bits as a source of randomness nuclear@0: for (j = 0; j < 8; j++) nuclear@0: { nuclear@0: lastTime = Timer::GetTicksNanos(); nuclear@0: Thread::MSleep(1); nuclear@0: Thread::MSleep(0); nuclear@0: thisTime = Timer::GetTicksNanos(); nuclear@0: uint64_t diff = thisTime - lastTime; nuclear@0: unsigned int diff4Bits = (unsigned int)(diff & 15); nuclear@0: diff4Bits <<= 32 - 4; nuclear@0: diff4Bits >>= j * 4; nuclear@0: ((char*)&g)[j] ^= diff4Bits; nuclear@0: } nuclear@0: nuclear@0: return g; nuclear@0: } nuclear@0: String GetGuidString() nuclear@0: { nuclear@0: uint64_t guid = GetGuidInt(); nuclear@0: nuclear@0: char buff[64]; nuclear@0: #if defined(OVR_CC_MSVC) nuclear@0: OVR_sprintf(buff, sizeof(buff), "%I64u", guid); nuclear@0: #else nuclear@0: OVR_sprintf(buff, sizeof(buff), "%llu", (unsigned long long) guid); nuclear@0: #endif nuclear@0: return String(buff); nuclear@0: } nuclear@0: nuclear@0: const char * GetProcessInfo() nuclear@0: { nuclear@0: #if defined (OVR_CPU_X86_64 ) nuclear@0: return "64 bit"; nuclear@0: #elif defined (OVR_CPU_X86) nuclear@0: return "32 bit"; nuclear@0: #else nuclear@0: return "TODO"; nuclear@0: #endif nuclear@0: } nuclear@0: #ifdef OVR_OS_WIN32 nuclear@0: nuclear@0: nuclear@0: String OSVersionAsString() nuclear@0: { nuclear@0: return GetSystemFileVersionString("\\kernel32.dll"); nuclear@0: } nuclear@0: String GetSystemFileVersionString(String filePath) nuclear@0: { nuclear@0: char strFilePath[MAX_PATH]; // Local variable nuclear@0: UINT sysDirLen = GetSystemDirectoryA(strFilePath, ARRAYSIZE(strFilePath)); nuclear@0: if (sysDirLen != 0) nuclear@0: { nuclear@0: OVR_strcat(strFilePath, MAX_PATH, filePath.ToCStr()); nuclear@0: return GetFileVersionString(strFilePath); nuclear@0: } nuclear@0: else nuclear@0: { nuclear@0: return "GetSystemDirectoryA failed"; nuclear@0: } nuclear@0: } nuclear@0: // See http://stackoverflow.com/questions/940707/how-do-i-programatically-get-the-version-of-a-dll-or-exe-file nuclear@0: String GetFileVersionString(String filePath) nuclear@0: { nuclear@0: String result; nuclear@0: nuclear@0: DWORD dwSize = GetFileVersionInfoSizeA(filePath.ToCStr(), NULL); nuclear@0: if (dwSize == 0) nuclear@0: { nuclear@0: OVR_DEBUG_LOG(("Error in GetFileVersionInfoSizeA: %d (for %s)", GetLastError(), filePath.ToCStr())); nuclear@0: result = filePath + " not found"; nuclear@0: } nuclear@0: else nuclear@0: { nuclear@0: BYTE* pVersionInfo = new BYTE[dwSize]; nuclear@0: if (!pVersionInfo) nuclear@0: { nuclear@0: OVR_DEBUG_LOG(("Out of memory allocating %d bytes (for %s)", dwSize, filePath.ToCStr())); nuclear@0: result = "Out of memory"; nuclear@0: } nuclear@0: else nuclear@0: { nuclear@0: if (!GetFileVersionInfoA(filePath.ToCStr(), 0, dwSize, pVersionInfo)) nuclear@0: { nuclear@0: OVR_DEBUG_LOG(("Error in GetFileVersionInfo: %d (for %s)", GetLastError(), filePath.ToCStr())); nuclear@0: result = "Cannot get version info"; nuclear@0: } nuclear@0: else nuclear@0: { nuclear@0: VS_FIXEDFILEINFO* pFileInfo = NULL; nuclear@0: UINT pLenFileInfo = 0; nuclear@0: if (!VerQueryValue(pVersionInfo, TEXT("\\"), (LPVOID*)&pFileInfo, &pLenFileInfo)) nuclear@0: { nuclear@0: OVR_DEBUG_LOG(("Error in VerQueryValue: %d (for %s)", GetLastError(), filePath.ToCStr())); nuclear@0: result = "File has no version info"; nuclear@0: } nuclear@0: else nuclear@0: { nuclear@0: int major = (pFileInfo->dwFileVersionMS >> 16) & 0xffff; nuclear@0: int minor = (pFileInfo->dwFileVersionMS) & 0xffff; nuclear@0: int hotfix = (pFileInfo->dwFileVersionLS >> 16) & 0xffff; nuclear@0: int other = (pFileInfo->dwFileVersionLS) & 0xffff; nuclear@0: nuclear@0: char str[128]; nuclear@0: OVR::OVR_sprintf(str, 128, "%d.%d.%d.%d", major, minor, hotfix, other); nuclear@0: nuclear@0: result = str; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: delete[] pVersionInfo; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: return result; nuclear@0: } nuclear@0: nuclear@0: nuclear@0: String GetDisplayDriverVersion() nuclear@0: { nuclear@0: return GetSystemFileVersionString("\\OVRDisplay32.dll"); nuclear@0: } nuclear@0: String GetCameraDriverVersion() nuclear@0: { nuclear@0: return GetSystemFileVersionString("\\drivers\\OCUSBVID.sys"); nuclear@0: } nuclear@0: nuclear@0: // From http://stackoverflow.com/questions/9524309/enumdisplaydevices-function-not-working-for-me nuclear@0: void GetGraphicsCardList( Array< String > &gpus) nuclear@0: { nuclear@0: gpus.Clear(); nuclear@0: nuclear@0: DISPLAY_DEVICEA dd; nuclear@0: nuclear@0: dd.cb = sizeof(dd); nuclear@0: nuclear@0: DWORD deviceNum = 0; nuclear@0: while( EnumDisplayDevicesA(NULL, deviceNum, &dd, 0) ){ nuclear@0: if (dd.StateFlags & DISPLAY_DEVICE_PRIMARY_DEVICE) nuclear@0: gpus.PushBack(dd.DeviceString); nuclear@0: deviceNum++; nuclear@0: } nuclear@0: } nuclear@0: #else nuclear@0: nuclear@0: // used for driver files nuclear@0: nuclear@0: String GetFileVersionString(String /*filePath*/) nuclear@0: { nuclear@0: return String(); nuclear@0: } nuclear@0: nuclear@0: String GetSystemFileVersionString(String /*filePath*/) nuclear@0: { nuclear@0: return String(); nuclear@0: } nuclear@0: nuclear@0: String GetDisplayDriverVersion() nuclear@0: { nuclear@0: return String(); nuclear@0: } nuclear@0: nuclear@0: String GetCameraDriverVersion() nuclear@0: { nuclear@0: return String(); nuclear@0: } nuclear@0: nuclear@0: #ifdef OVR_OS_MAC nuclear@0: //use objective c source nuclear@0: #else nuclear@0: nuclear@0: //todo linux, this requires searching /var/ files nuclear@0: void GetGraphicsCardList(OVR::Array< OVR::String > &gpus) nuclear@0: { nuclear@0: gpus.Clear(); nuclear@0: } nuclear@0: String OSVersionAsString() nuclear@0: { nuclear@0: return String(); nuclear@0: } nuclear@0: #endif //OVR_OS_MAC nuclear@0: #endif // WIN32 nuclear@0: nuclear@0: } } // namespace OVR { namespace Util {