/** sys_thread_cpu_time : void -> float <doc>Return the most accurate CPU time spent in user mode in the current thread (in seconds)</doc> **/ static value sys_thread_cpu_time() { #if defined(NEKO_WINDOWS) FILETIME unused; FILETIME utime; if( !GetThreadTimes(GetCurrentThread(),&unused,&unused,&unused,&utime) ) neko_error(); return alloc_float( ((tfloat)utime.dwHighDateTime) * 65.536 * 6.5536 + (((tfloat)utime.dwLowDateTime) / 10000000) ); #elif defined(NEKO_MAC) val_throw(alloc_string("sys_thread_cpu_time not implmented on OSX")); return val_null; #else struct timespec t; if( clock_gettime(CLOCK_THREAD_CPUTIME_ID,&t) ) neko_error(); return alloc_float( t.tv_sec + t.tv_nsec * 1e-9 ); #endif }
//----------------------------------------------------------------------------- // 取得執行緒執行時間 bool GetRunTime(IN unsigned long ulThreadID, OUT __int64 &i64KernelTime, OUT __int64 &i64UserTime) { C_WHandle ccThread = OpenThread(THREAD_QUERY_INFORMATION, FALSE, ulThreadID); if(ccThread == nullptr) return C_NOutput::Instance().Error(ERRORNSTD, __T("thread null")); FILETIME tCreateTime, tExitTime, tKernelTime, tUserTime; if(GetThreadTimes(static_cast<HANDLE>(ccThread), &tCreateTime, &tExitTime, &tKernelTime, &tUserTime) == FALSE) return C_NOutput::Instance().Error(ERRORNSTD, C_ErrorWin(), __T("get thread runtime failed")); i64KernelTime = (Int64ShllMod32(tKernelTime.dwHighDateTime, 32) | tKernelTime.dwLowDateTime); i64UserTime = (Int64ShllMod32(tUserTime.dwHighDateTime, 32) | tUserTime.dwLowDateTime); return true; }
extern "C" __declspec(dllexport) DWORD GetProcessMainThreadId(DWORD procId) { #ifndef MAKEULONGLONG #define MAKEULONGLONG(ldw, hdw) ((ULONGLONG(hdw) << 32) | ((ldw) & 0xFFFFFFFF)) #endif #ifndef MAXULONGLONG #define MAXULONGLONG ((ULONGLONG)~((ULONGLONG)0)) #endif DWORD dwMainThreadID = 0; ULONGLONG ullMinCreateTime = MAXULONGLONG; //includes all threads in the system HANDLE hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0); if (hThreadSnap != INVALID_HANDLE_VALUE) { THREADENTRY32 th32; th32.dwSize = sizeof(THREADENTRY32); BOOL bOK = TRUE; //Enumerate all threads in the system and filter on th32OwnerProcessID = pid for (bOK = Thread32First(hThreadSnap, &th32); bOK ; bOK = Thread32Next(hThreadSnap, &th32)) { //if (th32.dwSize >= FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(th32.th32OwnerProcessID)) { if (th32.th32OwnerProcessID == procId && (th32.dwSize >= FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(th32.th32OwnerProcessID))) { //_tprintf(_T("DEBUG Enumerate Process (%ld) Thread Id: %ld\n"), procId, th32.th32ThreadID); HANDLE hThread = OpenThread(THREAD_QUERY_INFORMATION, TRUE, th32.th32ThreadID); if (hThread) { FILETIME afTimes[4] = {0}; if (GetThreadTimes(hThread, &afTimes[0], &afTimes[1], &afTimes[2], &afTimes[3])) { ULONGLONG ullTest = MAKEULONGLONG(afTimes[0].dwLowDateTime, afTimes[0].dwHighDateTime); if (ullTest && ullTest < ullMinCreateTime) { //check each thread's creation time ullMinCreateTime = ullTest; dwMainThreadID = th32.th32ThreadID; // let it be main thread } } CloseHandle(hThread); //must close opened thread } } } #ifndef UNDER_CE CloseHandle(hThreadSnap); //close thread snapshot #else CloseToolhelp32Snapshot(hThreadSnap); //close thread snapshot #endif } return dwMainThreadID; //returns main thread id or returns 0 if can't find it }
// Returns the time the current thread has spent executing, in milliseconds. static inline unsigned getCPUTime() { #if OS(DARWIN) mach_msg_type_number_t infoCount = THREAD_BASIC_INFO_COUNT; thread_basic_info_data_t info; // Get thread information mach_port_t threadPort = mach_thread_self(); thread_info(threadPort, THREAD_BASIC_INFO, reinterpret_cast<thread_info_t>(&info), &infoCount); mach_port_deallocate(mach_task_self(), threadPort); unsigned time = info.user_time.seconds * 1000 + info.user_time.microseconds / 1000; time += info.system_time.seconds * 1000 + info.system_time.microseconds / 1000; return time; #elif OS(WINDOWS) union { FILETIME fileTime; unsigned long long fileTimeAsLong; } userTime, kernelTime; // GetThreadTimes won't accept NULL arguments so we pass these even though // they're not used. FILETIME creationTime, exitTime; GetThreadTimes(GetCurrentThread(), &creationTime, &exitTime, &kernelTime.fileTime, &userTime.fileTime); return static_cast<unsigned>(userTime.fileTimeAsLong / 10000 + kernelTime.fileTimeAsLong / 10000); #elif OS(SYMBIAN) RThread current; TTimeIntervalMicroSeconds cpuTime; TInt err = current.GetCpuTime(cpuTime); ASSERT_WITH_MESSAGE(err == KErrNone, "GetCpuTime failed with %d", err); return cpuTime.Int64() / 1000; #elif PLATFORM(BREWMP) // This function returns a continuously and linearly increasing millisecond // timer from the time the device was powered on. // There is only one thread in BREW, so this is enough. return GETUPTIMEMS(); #else // FIXME: We should return the time the current thread has spent executing. return currentTime() * 1000; #endif }
qtimestamp getTimestamp() { #ifdef Q_OS_WINCE // This implementation is based on code found here: // http://social.msdn.microsoft.com/Forums/en/vssmartdevicesnative/thread/74870c6c-76c5-454c-8533-812cfca585f8 HANDLE currentThread = GetCurrentThread(); FILETIME creationTime, exitTime, kernalTime, userTime; GetThreadTimes(currentThread, &creationTime, &exitTime, &kernalTime, &userTime); ULARGE_INTEGER uli; uli.LowPart = userTime.dwLowDateTime; uli.HighPart = userTime.dwHighDateTime; ULONGLONG systemTimeInMS = uli.QuadPart/10000; return static_cast<qtimestamp>(systemTimeInMS); #else return clock(); #endif }
int Ten18::Util::EnumerateNativeThreads(bool traceFullInfo, const char* msg) { Ten18_UNUSED(traceFullInfo); DebugOut(msg); int numThreads = 0; auto snapshot = MakeScoped(CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0), [] (HANDLE snapshot) { Ten18_HOPE_FOR.True = CloseHandle(snapshot); }); Ten18_EXPECT.Not(INVALID_HANDLE_VALUE) = static_cast<HANDLE>(snapshot); THREADENTRY32 te = {}; te.dwSize = sizeof(te); const auto minSizeOfInterest = (std::min)((FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(te.th32OwnerProcessID)), (FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(te.th32ThreadID))); if (Thread32First(snapshot, &te)) { do { if (te.dwSize >= minSizeOfInterest) if (te.th32OwnerProcessID == GetCurrentProcessId()) { ++numThreads; auto thread = MakeScoped(OpenThread(THREAD_QUERY_INFORMATION, FALSE, te.th32ThreadID), [] (HANDLE t) { Ten18_HOPE_FOR.NotZero = CloseHandle(t); }); Ten18_EXPECT.NotNull = static_cast<HANDLE>(thread); ULONG64 cycleTime = 0; Ten18_EXPECT.True = QueryThreadCycleTime(thread, &cycleTime); FILETIME create, exit, kernel, user; Ten18_EXPECT.True = GetThreadTimes(thread, &create, &exit, &kernel, &user); Format("\tNative Thread %0 - Create: %1, Exit: %2, Kernel: %3, User: %4, Cycles: %5", te.th32ThreadID, create.dwLowDateTime, exit.dwLowDateTime, kernel.dwLowDateTime, user.dwLowDateTime, static_cast<int>(cycleTime)).DebugOut(); } te.dwSize = sizeof(te); } while (Thread32Next(snapshot, &te)); } Format("Number of Native Threads: %0", numThreads).DebugOut(); return numThreads; }
int main( int argc , char* argv[] ) { double t = Time(); cmdLineParse( argc-1 , &argv[1] , sizeof(params)/sizeof(cmdLineReadable*) , params , 1 ); if( Density.set ) Execute< 2 , PlyValueVertex< Real > , true >( argc , argv ); else Execute< 2 , PlyVertex< Real > , false >( argc , argv ); #ifdef _WIN32 if( Performance.set ) { HANDLE cur_thread=GetCurrentThread(); FILETIME tcreat, texit, tkernel, tuser; if( GetThreadTimes( cur_thread , &tcreat , &texit , &tkernel , &tuser ) ) printf( "Time (Wall/User/Kernel): %.2f / %.2f / %.2f\n" , Time()-t , to_seconds( tuser ) , to_seconds( tkernel ) ); else printf( "Time: %.2f\n" , Time()-t ); HANDLE h = GetCurrentProcess(); PROCESS_MEMORY_COUNTERS pmc; if( GetProcessMemoryInfo( h , &pmc , sizeof(pmc) ) ) printf( "Peak Memory (MB): %d\n" , pmc.PeakWorkingSetSize>>20 ); }
unsigned long long CTraceFn::ThreadTime() { unsigned long long ret( 0 ); FILETIME creationTime; FILETIME exitTime; FILETIME kernelTime; FILETIME userTime; if( GetThreadTimes( GetCurrentThread(), &creationTime, &exitTime, &kernelTime, &userTime ) ) { unsigned long long theKernelTime( static_cast< unsigned long long >( kernelTime.dwHighDateTime ) << 32 | kernelTime.dwLowDateTime ); unsigned long long theUserTime( static_cast< unsigned long long >( userTime.dwHighDateTime ) << 32 | userTime.dwLowDateTime ); ret = ( theKernelTime + theUserTime ); } return ret; }
int getrusage(int who, struct rusage *usage) { FILETIME creation_time, exit_time, kernel_time, user_time; PROCESS_MEMORY_COUNTERS pmc; memset(usage, 0, sizeof(struct rusage)); if(who == RUSAGE_SELF) { if(!GetProcessTimes(GetCurrentProcess(), &creation_time, &exit_time, &kernel_time, &user_time)) { fprintf(stdout, "failed at GetProcessTimes\n"); return -1; } if(!GetProcessMemoryInfo(GetCurrentProcess(), &pmc, sizeof(pmc))) { fprintf(stdout, "failed at GetProcessMemoryInfo\n"); return -1; } usage_to_timeval(&kernel_time, &usage->ru_stime); usage_to_timeval(&user_time, &usage->ru_utime); usage->ru_majflt = pmc.PageFaultCount; usage->ru_maxrss = pmc.PeakWorkingSetSize / 1024; return 0; } else if(who == RUSAGE_THREAD) { if(!GetThreadTimes(GetCurrentThread(), &creation_time, &exit_time, &kernel_time, &user_time)) { fprintf(stdout, "failed at GetThreadTimes\n"); return -1; } usage_to_timeval(&kernel_time, &usage->ru_stime); usage_to_timeval(&user_time, &usage->ru_utime); return 0; } else { return -1; } }
// Stop the timer void HPFCounter::Stop() { if(m_start.QuadPart) { QueryPerformanceCounter(&m_end); m_total += ((double)(m_end.QuadPart - m_start.QuadPart)) / (double)m_frequency.QuadPart; m_start.QuadPart = 0L; m_end .QuadPart = 0L; } // Get the thread times, ignoring creation and end FILETIME creation = { 0, 0}; FILETIME exitTime = { 0, 0}; FILETIME kernelTime = { 0, 0}; FILETIME userTime = { 0, 0}; GetThreadTimes(GetCurrentThread(),&creation,&exitTime,&kernelTime,&userTime); // TRACE ("Thread times\n"); // TRACE ("- User hi : %x\n",userTime.dwHighDateTime); // TRACE ("- User lo : %x\n",userTime.dwLowDateTime); // TRACE ("- Kernel hi : %x\n",kernelTime.dwHighDateTime); // TRACE ("- Kernel lo : %x\n\n",kernelTime.dwLowDateTime); // Calculate how much kernel time we just used since last time FILETIME slice = SubFiletimes(&kernelTime,&m_kernelTime); m_kernelTimeSlice = AddFiletimes(&m_kernelTimeSlice,&slice); m_kernelTime = kernelTime; // TRACE("Kernel Slice times\n"); // TRACE ("- slice hi : %x\n",m_kernelTimeSlice.dwHighDateTime); // TRACE ("- slice lo : %x\n",m_kernelTimeSlice.dwLowDateTime); // Calculate how much user time we just used since last time slice = SubFiletimes(&userTime,&m_userTime); m_userTimeSlice = AddFiletimes(&m_userTimeSlice,&slice); m_userTime = userTime; // TRACE("User Slice times\n"); // TRACE ("- slice hi : %x\n",m_userTimeSlice.dwHighDateTime); // TRACE ("- slice lo : %x\n",m_userTimeSlice.dwLowDateTime); }
POV_ULONG Timer::GetThreadTime () const { FILETIME ct; FILETIME et; __int64 kt; __int64 ut; BOOL success; POV_ASSERT (mCPUTimeSupported); success = GetThreadTimes (mThreadHandle, &ct, &et, reinterpret_cast<FILETIME *>(&kt), reinterpret_cast<FILETIME *>(&ut)); POV_ASSERT (success); if (!success) return 0; return ((kt + ut) / 10000); }
void xbt_os_threadtimer_stop(xbt_os_timer_t timer) { #if HAVE_POSIX_GETTIME clock_gettime(CLOCK_THREAD_CPUTIME_ID, &(timer->stop)); #elif HAVE_GETTIMEOFDAY && defined(__MACH__) && defined(__APPLE__) mach_msg_type_number_t count = THREAD_BASIC_INFO_COUNT; thread_basic_info_data_t thi_data; thread_basic_info_t thi = &thi_data; thread_info(mach_thread_self(), THREAD_BASIC_INFO, (thread_info_t)thi, &count); timer->stop.tv_usec = thi->system_time.microseconds + thi->user_time.microseconds; timer->stop.tv_sec = thi->system_time.seconds + thi->user_time.seconds; #elif HAVE_GETTIMEOFDAY //if nothing else is available, return just time gettimeofday(&(timer->stop), NULL); #elif defined(_WIN32) HANDLE h = GetCurrentThread(); FILETIME creationTime, exitTime, kernelTime, userTime; GetThreadTimes(h, &creationTime, &exitTime, &kernelTime, &userTime); w32_times_to_timeval(&timer->stop, &kernelTime, &userTime); #endif }
static void stop_timer (void) { #ifdef _WIN32 #ifdef __MINGW32CE__ GetThreadTimes (GetCurrentThread (), &stopped_at.creation_time, &stopped_at.exit_time, &stopped_at.kernel_time, &stopped_at.user_time); #else GetProcessTimes (GetCurrentProcess (), &stopped_at.creation_time, &stopped_at.exit_time, &stopped_at.kernel_time, &stopped_at.user_time); #endif #else struct tms tmp; times (&tmp); stopped_at = tmp.tms_utime; #endif }
double currentCPUTime() { #if OS(DARWIN) mach_msg_type_number_t infoCount = THREAD_BASIC_INFO_COUNT; thread_basic_info_data_t info; // Get thread information mach_port_t threadPort = mach_thread_self(); thread_info(threadPort, THREAD_BASIC_INFO, reinterpret_cast<thread_info_t>(&info), &infoCount); mach_port_deallocate(mach_task_self(), threadPort); double time = info.user_time.seconds + info.user_time.microseconds / 1000000.; time += info.system_time.seconds + info.system_time.microseconds / 1000000.; return time; #elif OS(WINDOWS) union { FILETIME fileTime; unsigned long long fileTimeAsLong; } userTime, kernelTime; // GetThreadTimes won't accept null arguments so we pass these even though // they're not used. FILETIME creationTime, exitTime; GetThreadTimes(GetCurrentThread(), &creationTime, &exitTime, &kernelTime.fileTime, &userTime.fileTime); return userTime.fileTimeAsLong / 10000000. + kernelTime.fileTimeAsLong / 10000000.; #elif OS(QNX) struct timespec time; if (clock_gettime(CLOCK_THREAD_CPUTIME_ID, &time)) CRASH(); return time.tv_sec + time.tv_nsec / 1.0e9; #else // FIXME: We should return the time the current thread has spent executing. // use a relative time from first call in order to avoid an overflow static double firstTime = currentTime(); return currentTime() - firstTime; #endif }
static DWORD GetMainThreadId() { std::vector<ThreadInfo> threads; HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0); if (snapshot != INVALID_HANDLE_VALUE) { THREADENTRY32 thread_entry; thread_entry.dwSize = sizeof(thread_entry); if (Thread32First(snapshot, &thread_entry)) { DWORD process_id = GetProcessId(GetCurrentProcess()); do { if (thread_entry.dwSize >= FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(thread_entry.th32OwnerProcessID)) { if (thread_entry.th32OwnerProcessID == process_id) { ThreadInfo thread = {0}; thread.id = thread_entry.th32ThreadID; threads.push_back(thread); } } thread_entry.dwSize = sizeof(thread_entry); } while (Thread32Next(snapshot, &thread_entry)); } CloseHandle(snapshot); } for (std::vector<ThreadInfo>::iterator it = threads.begin(); it != threads.end(); it++) { ThreadInfo &info = *it; HANDLE handle = GetThreadHandle(info.id, THREAD_QUERY_INFORMATION); GetThreadTimes(handle, &info.creation_time, &info.exit_time, &info.kernel_time, &info.user_time); } threads.erase(std::remove_if(threads.begin(), threads.end(), InvalidThread()), threads.end()); if (!threads.empty()) { return std::min_element(threads.begin(), threads.end(), CompareThreads())->id; } return 0; }
/** * Return the amount of USER time used by a thread. * * @param[in] thread * @return actual time on USER used by thread (nanoseconds) or * negative value if not supported. */ I_64 VMCALL hythread_get_user_time (hythread_t thread) { #if defined(WIN32) FILETIME creationTime, exitTime, kernelTime, userTime; I_64 totalTime; /* WARNING! Not supported on Win95! Need to test to ensure this fails gracefully */ if (GetThreadTimes (thread->handle, &creationTime, &exitTime, &kernelTime, &userTime)) { totalTime = ((I_64) userTime. dwLowDateTime | ((I_64) userTime.dwHighDateTime << 32)); /* totalTime is in 100's of nanos. Convert to nanos */ return totalTime * 100; } #endif /* WIN32 */ return -1; }
void set_breakpoints(void) { HANDLE hTool32 = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0); if(hTool32 != INVALID_HANDLE_VALUE) { THREADENTRY32 thread_entry32; thread_entry32.dwSize = sizeof(THREADENTRY32); FILETIME exit_time, kernel_time, user_time; FILETIME creation_time; FILETIME prev_creation_time; prev_creation_time.dwLowDateTime = 0xFFFFFFFF; prev_creation_time.dwHighDateTime = INT_MAX; HANDLE hMainThread = NULL; if(Thread32First(hTool32, &thread_entry32)) { do { if(thread_entry32.dwSize >= FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(thread_entry32.th32OwnerProcessID) && thread_entry32.th32OwnerProcessID == GetCurrentProcessId() && thread_entry32.th32ThreadID != GetCurrentThreadId()) { HANDLE hThread = OpenThread(THREAD_SET_CONTEXT | THREAD_GET_CONTEXT | THREAD_QUERY_INFORMATION, FALSE, thread_entry32.th32ThreadID); GetThreadTimes(hThread, &creation_time, &exit_time, &kernel_time, &user_time); if(CompareFileTime(&creation_time, &prev_creation_time) == -1) { memcpy(&prev_creation_time, &creation_time, sizeof(FILETIME)); if(hMainThread != NULL) CloseHandle(hMainThread); hMainThread = hThread; } else CloseHandle(hThread); } thread_entry32.dwSize = sizeof(THREADENTRY32); } while(Thread32Next(hTool32, &thread_entry32)); AddVectoredExceptionHandler(1, ExceptionFilter); CONTEXT thread_context = {CONTEXT_DEBUG_REGISTERS}; thread_context.Dr0 = func_addr; thread_context.Dr7 = (1 << 0); SetThreadContext(hMainThread, &thread_context); CloseHandle(hMainThread); } CloseHandle(hTool32); } }
void xbt_os_threadtimer_resume(xbt_os_timer_t timer) { #ifdef HAVE_POSIX_GETTIME timer->elapse.tv_sec += timer->stop.tv_sec - timer->start.tv_sec; timer->elapse.tv_nsec += timer->stop.tv_nsec - timer->start.tv_nsec; clock_gettime(CLOCK_THREAD_CPUTIME_ID, &(timer->start)); #elif defined(HAVE_GETTIMEOFDAY) && defined(__MACH__) && defined(__APPLE__) timer->elapse.tv_sec += timer->stop.tv_sec - timer->start.tv_sec; timer->elapse.tv_usec += timer->stop.tv_usec - timer->start.tv_usec; mach_msg_type_number_t count = THREAD_BASIC_INFO_COUNT; thread_basic_info_data_t thi_data; thread_basic_info_t thi = &thi_data; thread_info(mach_thread_self(), THREAD_BASIC_INFO, (thread_info_t)thi, &count); timer->start.tv_usec = thi->system_time.microseconds + thi->user_time.microseconds; timer->start.tv_sec = thi->system_time.seconds + thi->user_time.seconds; #elif defined(HAVE_GETTIMEOFDAY) timer->elapse.tv_sec += timer->stop.tv_sec - timer->start.tv_sec; timer->elapse.tv_usec += timer->stop.tv_usec - timer->start.tv_usec; gettimeofday(&(timer->start), NULL); #elif defined(_XBT_WIN32) timer->elapse.tv_sec += timer->stop.tv_sec - timer->start.tv_sec; timer->elapse.tv_usec += timer->stop.tv_usec - timer->start.tv_usec; # if defined(WIN32_WCE) || (_WIN32_WINNT < 0x0400) THROW_UNIMPLEMENTED; # else HANDLE h = GetCurrentThread(); FILETIME creationTime, exitTime, kernelTime, userTime; GetThreadTimes(h, &creationTime, &exitTime, &kernelTime, &userTime); unsigned __int64 ktm, utm; ktm = (unsigned __int64) kernelTime.dwHighDateTime << 32; ktm |= kernelTime.dwLowDateTime; ktm /= 10; utm = (unsigned __int64) userTime.dwHighDateTime << 32; utm |= userTime.dwLowDateTime; utm /= 10; timer->start.tv_sec = (long) (ktm / 1000000L) + (long) (utm / 1000000L); timer->start.tv_usec = (long) (ktm % 1000000L) + (long) (utm % 1000000L); # endif /* windows version checker */ #endif }
void ProcessImpl::timesImpl(long& userTime, long& kernelTime) { FILETIME ftCreation; FILETIME ftExit; FILETIME ftKernel; FILETIME ftUser; if (GetThreadTimes(GetCurrentThread(), &ftCreation, &ftExit, &ftKernel, &ftUser) != 0) { ULARGE_INTEGER time; time.LowPart = ftKernel.dwLowDateTime; time.HighPart = ftKernel.dwHighDateTime; kernelTime = long(time.QuadPart/10000000L); time.LowPart = ftUser.dwLowDateTime; time.HighPart = ftUser.dwHighDateTime; userTime = long(time.QuadPart/10000000L); } else { userTime = kernelTime = -1; } }
/**返回当前线程创建到退出消耗的CPU时间 */ void mvg::synch::getCurrentThreadTimes( time_t &creationTime, time_t &exitTime, double &cpuTime) { MVG_START FILETIME timCreat, timExit, timKernel, timUser; uint64_t t; HANDLE threadHandle; // 根据ID得到当前线程的handle threadHandle = OpenThread(READ_CONTROL | THREAD_QUERY_INFORMATION, FALSE, GetCurrentThreadId()); // threadId); if (!threadHandle) THROW_EXCEPTION("Cannot open the thread with the given 'threadId'"); if (!GetThreadTimes(threadHandle, &timCreat, &timExit, &timKernel, &timUser)) { CloseHandle(threadHandle); THROW_EXCEPTION("Error accessing thread times!"); } CloseHandle(threadHandle); t = (((uint64_t)timCreat.dwHighDateTime) << 32) | timCreat.dwLowDateTime; creationTime = (t - 116444736000000000ULL) / 10000000; t = (((uint64_t)timExit.dwHighDateTime) << 32) | timExit.dwLowDateTime; exitTime = (t - 116444736000000000ULL) / 10000000; // CPU时间是用户+内核 int64_t t1 = (((uint64_t)timKernel.dwHighDateTime) << 32) | timKernel.dwLowDateTime; int64_t t2 = (((uint64_t)timUser.dwHighDateTime) << 32) | timUser.dwLowDateTime; cpuTime = ((double)(t1 + t2)) * 100e-9; // FILETIME counts intervals of 100ns MVG_END }
void CThreadPerformanceCounter::DoPerformanceCount() { if(m_TreadHandle) { m_CycleCount++; if(m_CountIntervalTimer.IsTimeOut(m_CountIntervalTime)) { m_CountIntervalTimer.SaveTime(); UINT64 CurPerformanceCount=CEasyTimerEx::GetTime(); float CPUTime=(float)(CurPerformanceCount-m_StartPerformanceCount)/CEasyTimerEx::TIME_UNIT_PER_SECOND; m_StartPerformanceCount=CurPerformanceCount; m_CycleTime=CPUTime*1000.0f/m_CycleCount; m_CycleCount=0; UINT64 CurCPUUsedTime; #ifdef WIN32 FILETIME CreationTime,ExitTime,KernelTime,UserTime; if(!GetThreadTimes(m_TreadHandle, &CreationTime,&ExitTime, &KernelTime,&UserTime)) { PrintSystemLog(0,_T("获取线程CPU时间失败%d"),GetLastError()); } CurCPUUsedTime=((UINT64)KernelTime.dwLowDateTime)|(((UINT64)KernelTime.dwHighDateTime)<<32); CurCPUUsedTime+=((UINT64)UserTime.dwLowDateTime)|(((UINT64)UserTime.dwHighDateTime)<<32); #else timespec OrginTime; clock_gettime(CLOCK_THREAD_CPUTIME_ID,&OrginTime); CurCPUUsedTime=(UINT64)OrginTime.tv_sec*1000000000+OrginTime.tv_nsec; #endif m_CPUUsedRate=(float)(CurCPUUsedTime-m_StartCPUUsedTime)/(CPUTime*m_CPUCount*10000000.0f); m_StartCPUUsedTime=CurCPUUsedTime; } } }
float CThread::GetRelativeUsage() { unsigned __int64 iTime = GetTickCount(); iTime *= 10000; // convert into 100ns tics // only update every 1 second if( iTime < m_iLastTime + 1000*10000 ) return m_fLastUsage; FILETIME CreationTime, ExitTime, UserTime, KernelTime; if( GetThreadTimes( m_ThreadHandle, &CreationTime, &ExitTime, &KernelTime, &UserTime ) ) { unsigned __int64 iUsage = 0; iUsage += (((unsigned __int64)UserTime.dwHighDateTime) << 32) + ((unsigned __int64)UserTime.dwLowDateTime); iUsage += (((unsigned __int64)KernelTime.dwHighDateTime) << 32) + ((unsigned __int64)KernelTime.dwLowDateTime); m_fLastUsage = (float)( iUsage - m_iLastUsage ) / (float)( iTime - m_iLastTime ); m_iLastUsage = iUsage; m_iLastTime = iTime; return m_fLastUsage; } return 0.0f; }
TimerWord ThreadUserTimer::GetCurrentTimerValue() { #if defined(CRYPTOPP_WIN32_AVAILABLE) && defined(THREAD_TIMER_AVAILABLE) static bool getCurrentThreadImplemented = true; if (getCurrentThreadImplemented) { FILETIME now, ignored; if (!GetThreadTimes(GetCurrentThread(), &ignored, &ignored, &ignored, &now)) { const DWORD lastError = GetLastError(); if (lastError == ERROR_CALL_NOT_IMPLEMENTED) { getCurrentThreadImplemented = false; goto GetCurrentThreadNotImplemented; } throw Exception(Exception::OTHER_ERROR, "ThreadUserTimer: GetThreadTimes failed with error " + IntToString(lastError)); } return now.dwLowDateTime + ((TimerWord)now.dwHighDateTime << 32); } GetCurrentThreadNotImplemented: return (TimerWord)clock() * (10*1000*1000 / CLOCKS_PER_SEC); #elif defined(CRYPTOPP_WIN32_AVAILABLE) && !defined(THREAD_TIMER_AVAILABLE) LARGE_INTEGER now; if (!QueryPerformanceCounter(&now)) { const DWORD lastError = GetLastError(); throw Exception(Exception::OTHER_ERROR, "ThreadUserTimer: QueryPerformanceCounter failed with error " + IntToString(lastError)); } return now.QuadPart; #elif defined(CRYPTOPP_UNIX_AVAILABLE) tms now; times(&now); return now.tms_utime; #else return clock(); #endif }
/* * This function is called on a timer, and it will monitor * frequently changing quantities such as the state of physical and * virtual memory, the state of the process's message queue, which * window is in the foreground, which owns the clipboard, etc. */ void noise_regular(void) { HWND w; DWORD z; POINT pt; MEMORYSTATUS memstat; FILETIME times[4]; #ifdef MPEXT EnterCriticalSection(&noise_section); #endif w = GetForegroundWindow(); random_add_noise(&w, sizeof(w)); w = GetCapture(); random_add_noise(&w, sizeof(w)); w = GetClipboardOwner(); random_add_noise(&w, sizeof(w)); z = GetQueueStatus(QS_ALLEVENTS); random_add_noise(&z, sizeof(z)); GetCursorPos(&pt); random_add_noise(&pt, sizeof(pt)); GlobalMemoryStatus(&memstat); random_add_noise(&memstat, sizeof(memstat)); GetThreadTimes(GetCurrentThread(), times, times + 1, times + 2, times + 3); random_add_noise(×, sizeof(times)); GetProcessTimes(GetCurrentProcess(), times, times + 1, times + 2, times + 3); random_add_noise(×, sizeof(times)); #ifdef MPEXT LeaveCriticalSection(&noise_section); #endif }
DWORD GetProcessMainThread(DWORD dwProcID) { DWORD dwMainThreadID = 0; ULONGLONG ullMinCreateTime = MAXULONGLONG; HANDLE hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0); if (hThreadSnap != INVALID_HANDLE_VALUE) { THREADENTRY32 th32; th32.dwSize = sizeof(THREADENTRY32); BOOL bOK = TRUE; for (bOK = Thread32First(hThreadSnap, &th32); bOK; bOK = Thread32Next(hThreadSnap, &th32)) { if (th32.th32OwnerProcessID == dwProcID) { HANDLE hThread = OpenThread(THREAD_QUERY_INFORMATION, TRUE, th32.th32ThreadID); if (hThread) { FILETIME afTimes[4] = { 0 }; if (GetThreadTimes(hThread, &afTimes[0], &afTimes[1], &afTimes[2], &afTimes[3])) { ULONGLONG ullTest = MAKEULONGLONG(afTimes[0].dwLowDateTime, afTimes[0].dwHighDateTime); if (ullTest && ullTest < ullMinCreateTime) { ullMinCreateTime = ullTest; dwMainThreadID = th32.th32ThreadID; // let it be main... :) } } CloseHandle(hThread); } } } CloseHandle(hThreadSnap); } return (dwMainThreadID); }
/* This is the fastpoll function which gathers up info by calling various api's */ BOOL FastPoll (void) { int nOriginalRandIndex = nRandIndex; static BOOL addedFixedItems = FALSE; FILETIME creationTime, exitTime, kernelTime, userTime; SIZE_T minimumWorkingSetSize, maximumWorkingSetSize; LARGE_INTEGER performanceCount; MEMORYSTATUS memoryStatus; HANDLE handle; POINT point; /* Get various basic pieces of system information */ RandaddIntPtr (GetActiveWindow ()); /* Handle of active window */ RandaddIntPtr (GetCapture ()); /* Handle of window with mouse capture */ RandaddIntPtr (GetClipboardOwner ()); /* Handle of clipboard owner */ RandaddIntPtr (GetClipboardViewer ()); /* Handle of start of clpbd.viewer list */ RandaddIntPtr (GetCurrentProcess ()); /* Pseudohandle of current process */ RandaddInt32 (GetCurrentProcessId ()); /* Current process ID */ RandaddIntPtr (GetCurrentThread ()); /* Pseudohandle of current thread */ RandaddInt32 (GetCurrentThreadId ()); /* Current thread ID */ RandaddInt32 (GetCurrentTime ()); /* Milliseconds since Windows started */ RandaddIntPtr (GetDesktopWindow ()); /* Handle of desktop window */ RandaddIntPtr (GetFocus ()); /* Handle of window with kb.focus */ RandaddInt32 (GetInputState ()); /* Whether sys.queue has any events */ RandaddInt32 (GetMessagePos ()); /* Cursor pos.for last message */ RandaddInt32 (GetMessageTime ()); /* 1 ms time for last message */ RandaddIntPtr (GetOpenClipboardWindow ()); /* Handle of window with clpbd.open */ RandaddIntPtr (GetProcessHeap ()); /* Handle of process heap */ RandaddIntPtr (GetProcessWindowStation ()); /* Handle of procs window station */ RandaddInt32 (GetQueueStatus (QS_ALLEVENTS)); /* Types of events in input queue */ /* Get multiword system information */ GetCaretPos (&point); /* Current caret position */ RandaddBuf ((unsigned char *) &point, sizeof (POINT)); GetCursorPos (&point); /* Current mouse cursor position */ RandaddBuf ((unsigned char *) &point, sizeof (POINT)); /* Get percent of memory in use, bytes of physical memory, bytes of free physical memory, bytes in paging file, free bytes in paging file, user bytes of address space, and free user bytes */ memoryStatus.dwLength = sizeof (MEMORYSTATUS); GlobalMemoryStatus (&memoryStatus); RandaddBuf ((unsigned char *) &memoryStatus, sizeof (MEMORYSTATUS)); /* Get thread and process creation time, exit time, time in kernel mode, and time in user mode in 100ns intervals */ handle = GetCurrentThread (); GetThreadTimes (handle, &creationTime, &exitTime, &kernelTime, &userTime); RandaddBuf ((unsigned char *) &creationTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &exitTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &kernelTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &userTime, sizeof (FILETIME)); handle = GetCurrentProcess (); GetProcessTimes (handle, &creationTime, &exitTime, &kernelTime, &userTime); RandaddBuf ((unsigned char *) &creationTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &exitTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &kernelTime, sizeof (FILETIME)); RandaddBuf ((unsigned char *) &userTime, sizeof (FILETIME)); /* Get the minimum and maximum working set size for the current process */ GetProcessWorkingSetSize (handle, &minimumWorkingSetSize, &maximumWorkingSetSize); RandaddIntPtr (minimumWorkingSetSize); RandaddIntPtr (maximumWorkingSetSize); /* The following are fixed for the lifetime of the process so we only add them once */ if (addedFixedItems == 0) { STARTUPINFO startupInfo; /* Get name of desktop, console window title, new window position and size, window flags, and handles for stdin, stdout, and stderr */ startupInfo.cb = sizeof (STARTUPINFO); GetStartupInfo (&startupInfo); RandaddBuf ((unsigned char *) &startupInfo, sizeof (STARTUPINFO)); addedFixedItems = TRUE; } /* The docs say QPC can fail if appropriate hardware is not available. It works on 486 & Pentium boxes, but hasn't been tested for 386 or RISC boxes */ if (QueryPerformanceCounter (&performanceCount)) RandaddBuf ((unsigned char *) &performanceCount, sizeof (LARGE_INTEGER)); else { /* Millisecond accuracy at best... */ DWORD dwTicks = GetTickCount (); RandaddBuf ((unsigned char *) &dwTicks, sizeof (dwTicks)); } // CryptoAPI: We always have a valid CryptoAPI context when we arrive here but // we keep the check for clarity purpose if ( !CryptoAPIAvailable ) return FALSE; if (CryptGenRandom (hCryptProv, sizeof (buffer), buffer)) { RandaddBuf (buffer, sizeof (buffer)); burn (buffer, sizeof(buffer)); } else { /* return error in case CryptGenRandom fails */ CryptoAPILastError = GetLastError (); return FALSE; } /* Apply the pool mixing function */ Randmix(); /* Restore the original pool cursor position. If this wasn't done, mouse coordinates could be written to a limited area of the pool, especially when moving the mouse uninterruptedly. The severity of the problem would depend on the length of data written by FastPoll (if it was equal to the size of the pool, mouse coordinates would be written only to a particular 4-byte area, whenever moving the mouse uninterruptedly). */ nRandIndex = nOriginalRandIndex; return TRUE; }
void Run(void) override { WaitForStateUpdate([this] { return m_continue; }); while(m_spinCount--); GetThreadTimes(m_kernelTime, m_userTime); }
DWORD CalculationThread (LPVOID lpvoid) { (void)lpvoid; bool needcalculationsslow; NMEA_INFO tmpGPS; DERIVED_INFO tmpCALCULATED; FILETIME CreationTime, ExitTime, StartKernelTime, EndKernelTime, StartUserTime, EndUserTime ; needcalculationsslow = false; // let's not create a deadlock here, setting the go after another race condition goCalculationThread=true; // 091119 CHECK // wait for proper startup signal while (!MapWindow::IsDisplayRunning()) { Sleep(100); } // while (!goCalculating) Sleep(100); Sleep(1000); // 091213 BUGFIX need to syncronize !!! TOFIX02 TODO while (!MapWindow::CLOSETHREAD) { WaitForSingleObject(dataTriggerEvent, 5000); ResetEvent(dataTriggerEvent); if (MapWindow::CLOSETHREAD) break; // drop out on exit GetThreadTimes( hCalculationThread, &CreationTime, &ExitTime,&StartKernelTime,&StartUserTime); // make local copy before editing... LockFlightData(); FLARM_RefreshSlots(&GPS_INFO); memcpy(&tmpGPS,&GPS_INFO,sizeof(NMEA_INFO)); memcpy(&tmpCALCULATED,&CALCULATED_INFO,sizeof(DERIVED_INFO)); UnlockFlightData(); DoCalculationsVario(&tmpGPS,&tmpCALCULATED); if (!tmpGPS.VarioAvailable) { TriggerVarioUpdate(); // emulate vario update } if(DoCalculations(&tmpGPS,&tmpCALCULATED)){ #if (WINDOWSPC>0) && !TESTBENCH #else if (!INPAN) #endif { MapWindow::MapDirty = true; } needcalculationsslow = true; if (tmpCALCULATED.Circling) MapWindow::mode.Fly(MapWindow::Mode::MODE_FLY_CIRCLING); else if (tmpCALCULATED.FinalGlide) MapWindow::mode.Fly(MapWindow::Mode::MODE_FLY_FINAL_GLIDE); else MapWindow::mode.Fly(MapWindow::Mode::MODE_FLY_CRUISE); } if (MapWindow::CLOSETHREAD) break; // drop out on exit // This is activating another run for Thread Draw TriggerRedraws(&tmpGPS, &tmpCALCULATED); if (MapWindow::CLOSETHREAD) break; // drop out on exit if (SIMMODE) { if (needcalculationsslow || ( ReplayLogger::IsEnabled() ) ) { DoCalculationsSlow(&tmpGPS,&tmpCALCULATED); needcalculationsslow = false; } } else { if (needcalculationsslow) { DoCalculationsSlow(&tmpGPS,&tmpCALCULATED); needcalculationsslow = false; } } if (MapWindow::CLOSETHREAD) break; // drop out on exit // values changed, so copy them back now: ONLY CALCULATED INFO // should be changed in DoCalculations, so we only need to write // that one back (otherwise we may write over new data) LockFlightData(); memcpy(&CALCULATED_INFO,&tmpCALCULATED,sizeof(DERIVED_INFO)); UnlockFlightData(); // update live tracker with new values // this is a nonblocking call, live tracker runs on different thread LiveTrackerUpdate(&tmpGPS, &tmpCALCULATED); if (FlightDataRecorderActive) UpdateFlightDataRecorder(&tmpGPS,&tmpCALCULATED); if ( (GetThreadTimes( hCalculationThread, &CreationTime, &ExitTime,&EndKernelTime,&EndUserTime)) == 0) { Cpu_Calc=9999; } else { Cpustats(&Cpu_Calc,&StartKernelTime, &EndKernelTime, &StartUserTime, &EndUserTime); } } return 0; }
extern "C" int clock_gettime(clockid_t clock_id, struct timespec* tp) { if (!tp) { errno = EFAULT; return -1; } const auto unanosToTimespec = [](timespec* tp, unsigned_nanos t) -> int { static constexpr unsigned_nanos one_sec(std::chrono::seconds(1)); tp->tv_sec = time_t(std::chrono::duration_cast<std::chrono::seconds>(t).count()); tp->tv_nsec = long((t % one_sec).count()); return 0; }; FILETIME createTime, exitTime, kernalTime, userTime; switch (clock_id) { case CLOCK_REALTIME: { auto now = std::chrono::system_clock::now().time_since_epoch(); duration_to_ts(now, tp); return 0; } case CLOCK_MONOTONIC: { auto now = std::chrono::steady_clock::now().time_since_epoch(); duration_to_ts(now, tp); return 0; } case CLOCK_PROCESS_CPUTIME_ID: { if (!GetProcessTimes( GetCurrentProcess(), &createTime, &exitTime, &kernalTime, &userTime)) { errno = EINVAL; return -1; } return unanosToTimespec( tp, filetimeToUnsignedNanos(kernalTime) + filetimeToUnsignedNanos(userTime)); } case CLOCK_THREAD_CPUTIME_ID: { if (!GetThreadTimes( GetCurrentThread(), &createTime, &exitTime, &kernalTime, &userTime)) { errno = EINVAL; return -1; } return unanosToTimespec( tp, filetimeToUnsignedNanos(kernalTime) + filetimeToUnsignedNanos(userTime)); } default: errno = EINVAL; return -1; } }
DWORD SerialPort::RxThread() { #if ( (WINDOWSPC == 0)) && !NEWCOMM // 100222 DWORD dwCommModemStatus = 0; // Specify a set of events to be monitored for the port. #endif DWORD dwBytesTransferred = 0; // 091117 initialized variables _Buff_t szString; FILETIME CreationTime, ExitTime, StartKernelTime, EndKernelTime, StartUserTime, EndUserTime; Purge(); #if TRACETHREAD StartupStore(_T("############## PORT=%d threadid=%d\n"), GetPortIndex(), GetCurrentThreadId()); if (GetPortIndex() = 0) _THREADID_PORT1 = GetCurrentThreadId(); if (GetPortIndex() = 1) _THREADID_PORT2 = GetCurrentThreadId(); if (GetPortIndex() != 1 && GetPortIndex() != 2) _THREADID_UNKNOWNPORT = GetCurrentThreadId(); #endif // Specify a set of events to be monitored for the port. _dwMask = EV_RXFLAG | EV_CTS | EV_DSR | EV_RING | EV_RXCHAR; #if ( (WINDOWSPC == 0)) && !NEWCOMM SetCommMask(hPort, _dwMask); #endif #if (WINDOWSPC<1) if (!_PollingMode) SetCommMask(hPort, _dwMask); #endif while ((hPort != INVALID_HANDLE_VALUE) && (::WaitForSingleObject(hStop, 0) == WAIT_TIMEOUT)) { GetThreadTimes(hReadThread, &CreationTime, &ExitTime, &StartKernelTime, &StartUserTime); UpdateStatus(); #if (WINDOWSPC>0) || NEWCOMM // 091206 // PC version does BUSY WAIT Sleep(50); // ToDo rewrite the whole driver to use overlaped IO on W2K or higher #else if (_PollingMode) Sleep(100); else // Wait for an event to occur for the port. if (!WaitCommEvent(hPort, &dwCommModemStatus, 0)) { // error reading from port Sleep(100); } #endif // Re-specify the set of events to be monitored for the port. // SetCommMask(hPort, dwMask1); // #if (WINDOWSPC == 0) 091206 #if ( (WINDOWSPC == 0)) && !NEWCOMM if (_PollingMode || (dwCommModemStatus & EV_RXFLAG) || (dwCommModemStatus & EV_RXCHAR)) // Do this only for non-PC #endif { // Loop for waiting for the data. do { // Read the data from the serial port. dwBytesTransferred = ReadData(szString); if (dwBytesTransferred > 0) { if (ProgramStarted >= psNormalOp) { // ignore everything until started std::for_each(begin(szString), begin(szString) + dwBytesTransferred, std::bind1st(std::mem_fun(&SerialPort::ProcessChar), this)); } } else { dwBytesTransferred = 0; } Sleep(50); // JMW20070515: give port some time to // fill... prevents ReadFile from causing the // thread to take up too much CPU if ((GetThreadTimes(hReadThread, &CreationTime, &ExitTime, &EndKernelTime, &EndUserTime)) == 0) { if (GetPortIndex() == 0) Cpu_PortA = 9999; else Cpu_PortB = 9999; } else { Cpustats((GetPortIndex() == 0) ? &Cpu_PortA : &Cpu_PortB, &StartKernelTime, &EndKernelTime, &StartUserTime, &EndUserTime); } if (::WaitForSingleObject(hStop, 0) != WAIT_TIMEOUT) { dwBytesTransferred = 0; } } while (dwBytesTransferred != 0); } // give port some time to fill Sleep(5); // Retrieve modem control-register values. #if ((WINDOWSPC == 0)) if (!_PollingMode) { // this is causing problems on PC BT, apparently. Setting Polling will not call this, but it is a bug GetCommModemStatus(hPort, &dwCommModemStatus); } #endif } DirtyPurge(); return 0; }