CPU信息获取 (一)

author:辟邪马甲

介绍下在VC下获取CPU各项信息的方法,并附部分参考代码 

MS的升级包屏蔽了很多底层的访问,真是黑手!

本节介绍下,CPU主频的获得方法,当然很多信息是可以从注册表读的,但是总感觉没那么安全,

这个安全也是相对的,不是还有背后的黑手在嘛....

 

其实SDK中也有些API跟CPU相关的

void GetSystemInfo(
  LPSYSTEM_INFO lpSystemInfo
);
typedef struct _SYSTEM_INFO {
union {
DWORD dwOemId;
struct {
WORD wProcessorArchitecture;
WORD wReserved;
};
};
DWORD dwPageSize;
LPVOID lpMinimumApplicationAddress;
LPVOID lpMaximumApplicationAddress;
DWORD_PTR dwActiveProcessorMask;
DWORD dwNumberOfProcessors;
DWORD dwProcessorType;
DWORD dwAllocationGranularity;
WORD wProcessorLevel;
WORD wProcessorRevision; } SYSTEM_INFO;
 
呵呵,我们看怎么获得CPU主频
 
  
  
typedef  struct
{
    unsigned 
long in_cycles;    // Internal clock cycles during
                                
//   test
    unsigned long ex_ticks;        // Microseconds elapsed during 
                                
//   test
    unsigned long raw_freq;        // Raw frequency of CPU in MHz

    unsigned 
long norm_freq;    // Normalized frequency of CPU
                                
//   in MHz.
    
}
FREQ_INFO;

int  _stdcall GetCPUSpeed()
{
    FREQ_INFO cpu_speed;
    LARGE_INTEGER t0,t1;            
// Variables for High-
                                    
// Resolution Performance
                                    
// Counter reads

    unsigned 
long freq  =0;            // Most current frequ. calculation
    unsigned long freq2 =0;            // 2nd most current frequ. calc.
    unsigned long freq3 =0;            // 3rd most current frequ. calc.
    
    unsigned 
long total;            // Sum of previous three frequency
                                    
// calculations

    
int tries=0;                    // Number of times a calculation has
                                    
// been made on this call to 
                                    
// cpuspeed

    unsigned 
long  total_cycles=0, cycles;    // Clock cycles elapsed 
                                            
// during test
    
    unsigned 
long  stamp0, stamp1;            // Time Stamp Variable 
                                            
// for beginning and end 
                                            
// of test
    unsigned long  total_ticks=0, ticks;    // Microseconds elapsed 
                                    
// during test
    
    LARGE_INTEGER count_freq;        
// High Resolution 
                                    
// Performance Counter 
                                    
// frequency

#ifdef WIN32
    
int iPriority;
    HANDLE hThread 
= GetCurrentThread();
#endif // WIN32;
    memset(
&cpu_speed, 0x00sizeof(cpu_speed));

//        return cpu_speed;
    QueryPerformanceFrequency ( &count_freq );
    
// On processors supporting the Read 
    
// Time Stamp opcode, compare elapsed
    
// time on the High-Resolution Counter
    
// with elapsed cycles on the Time 
    
// Stamp Register.
    
    
do {            // This do loop runs up to 20 times or
                       
//   until the average of the previous 
                       
//   three calculated frequencies is 
                       
//   within 1 MHz of each of the 
                       
//   individual calculated frequencies. 
                    
//   This resampling increases the 
                    
//   accuracy of the results since
                    
//   outside factors could affect this
                    
//   calculation
            
        tries
++;                            // Increment number of times sampled
                                            
// on this call to cpuspeed
            
        freq3 
= freq2;                        // Shift frequencies back to make
        freq2 = freq;                        // room for new frequency 
                                            
// measurement

        QueryPerformanceCounter(
&t0);    
                                            
// Get high-resolution performance 
                                            
// counter time
            
        t1.LowPart 
= t0.LowPart;            // Set Initial time
        t1.HighPart = t0.HighPart;

#ifdef WIN32
        iPriority 
= GetThreadPriority(hThread);
        
if ( iPriority != THREAD_PRIORITY_ERROR_RETURN )
        
{
            SetThreadPriority(hThread, THREAD_PRIORITY_TIME_CRITICAL);
        }

#endif // WIN32
        
while ( (unsigned long)t1.LowPart - (unsigned long)t0.LowPart<50{      
                           
// Loop until 50 ticks have 
                           
//   passed    since last read of hi-
                        
//     res counter. This accounts for
                        
//   overhead later.

            QueryPerformanceCounter(
&t1);
            _asm 
{
                RDTSC                        
// Read Time Stamp
                MOV stamp0, EAX
            }

        }

        t0.LowPart 
= t1.LowPart;        // Reset Initial 
        t0.HighPart = t1.HighPart;        //   Time

        
while ((unsigned long)t1.LowPart-(unsigned long)t0.LowPart<1000 ) {
                           
// Loop until 1000 ticks have 
                           
//   passed    since last read of hi-
                           
//   res counter. This allows for
                        
//   elapsed time for sampling.
            QueryPerformanceCounter(&t1);
            __asm 
{
                RDTSC                    
// Read Time Stamp
                MOV stamp1, EAX
            }

        }

#ifdef WIN32
        
// Reset priority
        if ( iPriority != THREAD_PRIORITY_ERROR_RETURN )
        
{
            SetThreadPriority(hThread, iPriority);
        }

#endif // WIN32
        cycles 
= stamp1 - stamp0;    // Number of internal 
                                    
//   clock cycles is 
                                    
//   difference between 
                                    
//   two time stamp 
                                    
//   readings.
           ticks = (unsigned long) t1.LowPart - (unsigned long) t0.LowPart;    
                                
// Number of external ticks is
                                
// difference between two
                                
// hi-res counter reads.
                                
// Note that some seemingly arbitrary mulitplies and
                                
// divides are done below. This is to maintain a 
                                
// high level of precision without truncating the 
                                
// most significant data. According to what value 
                                
// ITERATIIONS is set to, these multiplies and
                                
// divides might need to be shifted for optimal
                                
// precision.

        ticks 
= ticks * 100000;
                                
// Convert ticks to hundred
                                
// thousandths of a tick
            
        ticks 
= ticks / ( count_freq.LowPart/10 );        
                                
// Hundred Thousandths of a 
                                
//   Ticks / ( 10 ticks/second )
                                
//   = microseconds (us)
        total_ticks += ticks;
        total_cycles 
+= cycles;

        
if ( ticks%count_freq.LowPart > count_freq.LowPart/2 )
            ticks
++;            // Round up if necessary
                
        freq 
= cycles/ticks;    // Cycles / us  = MHz
                                                    
           
if ( cycles%ticks > ticks/2 )
            freq
++;                // Round up if necessary
                  
        total 
= ( freq + freq2 + freq3 );
                                
// Total last three frequency 
                                
//   calculations
    }
while ( (tries < 3 ) ||
              (tries 
< 20)&&
              ((abs(
3 * freq -total) > 3*TOLERANCE )||
               (abs(
3 * freq2-total) > 3*TOLERANCE )||
               (abs(
3 * freq3-total) > 3*TOLERANCE )));    
                    
// Compare last three calculations to 
                      
//   average of last three calculations.        
    
// Try one more significant digit.
    freq3 = ( total_cycles * 10 ) / total_ticks;
    freq2 
= ( total_cycles * 100 ) / total_ticks;

    
if ( freq2 - (freq3 * 10>= ROUND_THRESHOLD )
        freq3
++;

    cpu_speed.raw_freq 
= total_cycles / total_ticks;
    cpu_speed.norm_freq 
= cpu_speed.raw_freq;

    freq 
= cpu_speed.raw_freq * 10;
    
if( (freq3 - freq) >= ROUND_THRESHOLD )
        cpu_speed.norm_freq
++;

    cpu_speed.ex_ticks 
= total_ticks;
    cpu_speed.in_cycles 
= total_cycles;
    
    
return (int)cpu_speed.norm_freq;
}
http://blog.youkuaiyun.com/Pregunta/
 
从注册表获得这些信息的方法就不介绍了.下节探讨CPU的技术参数规格.
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值