How to get CPU frequency and usage rate?

Source: Internet
Author: User
Tags sleep function volatile

Recently saw the forum someone needs to read the system in the Java CPU frequency and usage rate, search the Internet for a while, found some useful things, summed up in this.

First, get the CPU frequency

1, read from the registry

The key Hklm/hardware/description/system/centralprocessor/0/~mhz in the registry corresponds to the CPU's central frequency.

But this method has certain limitations, that is, some systems do not have this key value.

2, by writing JNI invoke assembly code to obtain

Cpuid.h class declaration #ifndef _cpuid_h #define _CPUID_H #include <string> #include <windows.h> using namespace std; typedef unsigned long DWORD; typedef __int64 Longlong; Class CPUID {public:cpuid (); virtual ~cpuid (); string Getvid ();//Get CPU manufacturer string Getbrand ();//Get CPU model Longlong Getfreq Uency (DWORD sleeptime = 1000);//Get CPU Frequency Private:void Executecpuid (DWORD veax); Used to execute CPUID instruction DWORD m_eax; Store the returned eax DWORD m_ebx; Store the returned EBX DWORD m_ecx; Store the returned ECX DWORD M_edx; Store the returned edx}; #endif//cpuid.cpp class implementation #include "Cpuid.h" static const int S = sizeof (DWORD); Cpuid::cpuid (): M_eax (0), M_EBX (0), m_ecx (0), M_edx (0) {} cpuid::~cpuid () {} void Cpuid::executecpuid (DWORD veax) {//Because embedded -Type assembly code cannot recognize class member variables//So define four temporary variables as transitional DWORD Deax; DWORD DEBX; DWORD decx; DWORD Dedx; __asm {mov eax, veax cpuid mov deax, eax mov debx, ebx mov decx, ECX mov dedx, edx} m_eax = Deax; Put the contents of the temporary variable into the class member variable M_EBX = DEBX; M_ECX = DECX; M_edx = Dedx; } string Cpuid::getvid () {char cvid[s*3+1];//string, used to store manufacturer information memset (cvid, 0, sizeof (cvid)); Put the array clear 0 executecpuid (0); Executes the CPUID instruction using the input parameter EAX = 0 memcpy (cvid+s*0, &AMP;M_EBX, S); Copy the first four characters to the array memcpy (cvid+s*1, &m_edx, S); Copy intermediate four characters to array memcpy (cvid+s*2, &AMP;M_ECX, S); Copies the last four characters to the array return string (Cvid); Returns} string Cpuid::getbrand () {const DWORD brandid = 0x80000002; start from 0x80000002 to 0x80000004 end Char cbrand[ S*4*3+1]; Used to store trademark strings, 48 characters memset (cbrand, 0, sizeof (Cbrand)); Initialize to 0 for (DWORD i = 0; i < 3; i++)//execute 3 instructions in sequence {executecpuid (brandid + i);/////////////////////////////////////// nd + i*s*4 + s*0, &m_eax, S); memcpy (Cbrand + i*s*4 + s*1, &AMP;M_EBX, S); memcpy (Cbrand + i*s*4 + s*2, &m_ecx, S); memcpy (Cbrand + i*s*4 + s*3, &m_edx, S); return string (Cbrand); Return as String} longlong CPUID:: Getfrequency (DWORD sleeptime) {HANDLE hp =:: GetCurrentProcess ();//Get current process HANDLE HT = :: GetCurrentThread (); Get current thread DWORD PC =:: Getpriorityclass (HP); Gets the current process priority DWORD TP =:: GetThreadPriority (HT); Get Current lineProcess precedence BOOL Flag1 = False, Flag2 = false; DWORD low1 = 0, high1 = 0, Low2 = 0, high2 = 0; Flag1 =:: Setpriorityclass (HP, Realtime_priority_class); Sets the current process priority to the highest FLAG2 =:: SetThreadPriority (HT, thread_priority_highest); Set the current thread priority to the highest:: Sleep (10); Large_integer fq,st,ed; :: QueryPerformanceFrequency (&AMP;FQ); Precise timing:: QueryPerformanceCounter (&AMP;ST); Get start time __asm//Get current CPU number of time periods {RDTSC mov low1, eax mov high1, edx}:: Sleep (Sleeptime); Suspend thread for a moment:: QueryPerformanceCounter (&ed); Get end time __asm//Get current CPU number of time periods {RDTSC mov low2, eax mov high2, edx} if (Flag1):: Setpriorityclass (HP, PC); Restores the current process priority as if (FLAG2):: SetThreadPriority (HT, TP); Restores the current thread priority to:: CloseHandle (HP); :: CloseHandle (HT); Converts a CPU's time period number to a 64-bit integer longlong begin = (longlong) high1<<32 | Low1; Longlong end = (longlong) high2<<32 | Low2; Divides the number of CPU cycles that are obtained two times by the interval, that is, the frequency of the CPU. Because Windows ' sleep function has an error of about 15 milliseconds, the precise timing of Windows is the Quasi return (End-begin) *fq. quadpart/(ed. Quadpart-st.quadpart); }//CPU.cpp main cpp #include <iostream> #include "Cpuid.h" #define GHZ_UNIT (1000*1000*1000) #define MHZ_UNIT (1000*1000) int Main () {CPUID cpu; string vid = CPU. Getvid (); cout<<vid<<endl; String brand = CPU. Getbrand (); cout<<brand<<endl; Longlong freq = CPU. Getfrequency (); if (Freq > Ghz_unit) {double Freqghz = (double) freq/ghz_unit; printf ("%.2fghz/n", Freqghz);///left two-bit output after decimal point} else {cout& lt;<freq/mhz_unit<< "MHZ" <<endl; } cin.get (); return 0; }

3, through the CPUID to obtain

#include <stdio.h> int main () {unsigned int eflags1, EFLAGS2 = 0; unsigned int eax = 0; unsigned int ebx,ecx,edx; * * * Test whether the CPU supports CPUID instructions. * The 21st bit of the EFlags register, if the program can clear/set it, then the CPU support CPUID instructions. Otherwise do not support *////* First Take eflags * * ASM volatile ("pushf/n/t" "Popl%%eax": "=a" (EFLAGS1):: "Memory"); printf ("Original eflags is%p/n", EFLAGS1); /* To reverse the 21st bit of eflags, write back to the Register/ASM volatile ("PUSHL%0/n/t" "Popf":: "G" (Eflags1 & ~ (EFLAGS1 & (1&LT;&LT;21))) ; /* Check the current eflags to confirm that the 21st position is the opposite of the original value */ASM volatile ("pushf/n/t" "Popl%%eax": "=a" (EFLAGS2): "Memory"); printf ("Modified eflags is%p/n", EFLAGS2); /* Set the original EFlags value back/ASM volatile ("PUSHL%0/n/t" "Popf":: "G" (EFLAGS1)); The/** * Fixme:intel document does not say that if CPUID is not supported, the Clear/set EFlags's 21st place will be wrong. * It only says that on CPUs that do not support CPUID instructions, such as 80386, executing cpuid will produce invalid opcode error * * So, here we do not deal with read/write EFlags 21st bit failure situation * * */** * eax = 1, then return F in eax amily/model/stepping information * [0:3] Stepping * [4:7] Model * [8:11] family * [12:13] Processor type * [16:19] Extended Model I D * [20:] Extended family ID */ASM volatile ("CPUID": "=a" (EAX): "0" (1)); printf ("EAX is%p/n", eax); printf ("Extended family/t:%d/n", (0xff00000 & eax) >> 20); printf ("Extended model/t:%d/n", (0xf0000 & EAX) >> 16); printf ("Processor type/t:%d/n", (0x3000 & EAX) >> 12); printf ("family/t/t:%d/n", (0xf00 & EAX) >> 8); printf ("model/t/t:%d/n", (0xf0 & EAX) >> 4); printf ("stepping:/t:%d/n", (0xf & EAX)); printf ("n"); /** * EAX = = 0x800000000 * If the CPU supports brand String, the EAX >= value is returned in 0x80000004. * * ASM volatile ("CPUID": "=a" (EAX): "0" (0x80000000)); printf ("is CPU support Brand String?") %s/n ", eax >= 0x80000004? "Yes": "No"); printf ("n"); /** * If Brand string is supported, then EAX from 0x80000002 to 0x80000004, each increment 1,cpuid instruction returns: * eax:processor Brand String * ebx:processor Brand S Tring continued * Ecx:processor Brand String continued * Edx:processor Brand string continued/if (EAX >= 0x800000 (a) {unsigned int brands[4];//each time eax, ebx, ECX, edx unsigned int i; printf ("Brand string/t:"); for (i = 0x80000002 i <= 0x80000004 i++) {asm volatile ("CPUID": "=a" (brands[0)), "=b" (brands[1), "=c" (brands[2)), "=d" (Brands[3]): "0" (i)); printf ("%s", (char *) brands); //fixme: The string to be typed is: In^htel (R) Pentium (r^h) D CPU 2.80GHz///Where ^h is an invisible character, it will be eaten in front of printf ("n"); }/** * EAX = = 0 * Eax:cpuid maximum allowable eax input value * ebx: "genu" * ecx: "Ntel" * edx: "inel" */ASM volatile ("CPUID": "=a" (E AX), "=b" (EBX), "=c" (ecx), "=d" (edx): "0" (0)); printf ("Maximum CPUID Input EAX:%p/n", EAX); Char string[128]; snprintf (String, 5, "%s", (char *) &AMP;EBX); snprintf (String + 4, 5, "%s", (char *) &edx); snprintf (String + 8, 5, "%s", (char *) &AMP;ECX); printf ("vendor/t/t:%s/n", string); printf ("n"); /** * EAX = = 1, * EdX's 18th bit is 1, the CPU support serial number * is 0, it is not supported, or is disabled * serial numbers have 96 digits, of which the highest 32 is the output value of the EAX. It should be preserved and then * set eax==3, taking the remaining 64-bit/ASM volatile ("CPUID": "=a" (EAX), "=d" (edx): "A" (1)); if (EdX & (1 <<)) {/* serial number Supported/* edx output the middle 32-bit serial number, ECX output the lowest 32-bit serial number * * ASM volatile ("CPUID": "=c" (ecx), "=d" (edx): "A" (3)); printf ("Serial number/t:%x-%x-%x-%x-%x-%x/n", eax >>, eax <<, edx >>, edx <<, ecx &G t;>, ECX << 16); else printf ("Serial number not supported./n"); printf ("n"); /** * eax = 80000006h, return L2 cache information * * ECX[31:16]: L2 cache size, in Kbytes * Ecx[15:12]: L2 Cache associativity * 00h Disabled * 01H Direct mapped * 02h 2-way * 04h 4-way * 06h 8-way * 08h 16-way * 0Fh fully associative * ecx[7:0]: L2 Cac He line size in bytes/ASM volatile ("CPUID": "=c" (ECX): "A" (0x80000006)); printf ("L2 Cache size/t:%dkbytes/n", (ecx >> 16)); printf ("L2 Cache line size/t:%dbytes/n", (ECX & 0xFF)); printf ("L2 Cache associativity/t:"); Switch ((ECX & 0xf000) >>) {case 0x00:printf ("%s/n", "disabled"); a break; case 0x01:printf ("%s/n", "Direc T mapped "); Break Case 0x02:printf ("%s/n", "2-way"); Break Case 0x04:priNTF ("%s/n", "4-way"); Break Case 0x06:printf ("%s/n", "8-way"); Break Case 0x08:printf ("%s/n", "16-way"); Break Case 0x0f:printf ("fully associative"); Break default:printf ("No such entry.../n"); printf ("n"); /** * Input:eax = = 4 && ecx = 0 * * (eax[31:26] + 1) is the number of core package implemented on this physical processor CPUs * * ASM volatile ("CPUID": " =a "(EAX)," =b "(EBX)," =c "(ecx)," =d "(edx):" 0 "(4)," 2 "(0)); printf ("Number of cores on this physical package/t:%d/n", (eax >> 27) + 1); printf ("n"); /** * Input:eax = = 1, then edx return feature Flag * * * * * * */0; }

Second, obtain the CPU utilization rate

Reference http://www.java2000.net/p11161

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.