如何检测CPU的主频

  概述:  说到检测CPU速度般是测试在单位时间内运算指令条数但用这种思路方法有太大局限性由于受到很多原因影响准确度比较低特别是在Windows环境下你不知道在你外别占用了多少时间片其实在586及以上档次处理器中已经有了条专用指令来测试主频那就是 RDTSC指令意思是读取时间标记计数器(Read Time-Stamp Counter)Time-stamp counter 是处理器内部个64位MSR (model specic register)它每个时钟增加个记数在处理器复位时候值为0RDTSC 指令把 TSC值低32位装入EAX中高32位装入EDX中如果CPU主频是200MHz那么在秒钟内TSC值增加 200,000,000 次所以在计算时候把两次TSC差值除以两次时间差值就是CPU主频

  结构如下: 时候设置个定时器定时时间为1秒然后在定时器消息中利用 RDTSC 取得 TSC计数再和上次保留值相减然后除以时间差即可

  这里是本文中所有

  源:

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  Programmed by 罗云彬, [email protected]
;  Website: http://asm.yeah.net
;  LuoYunBin's Win32 ASM page (罗云彬编程乐园)
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  版本信息
;  CPU 频率 - 利用586指令 rdtsc 计算CPU频率
;    V1.0 ------  2000年6月21日
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .586
    .model flat, stdcall
    option map :none  ; sensitive
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  Include 数据
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    windows.inc
    user32.inc
    kernel32.inc
    comctl32.inc
    comdlg32.inc
lib  user32.lib
lib  kernel32.lib
lib  comctl32.lib
lib  comdlg32.lib
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  Equ 数据
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
DLG_MAIN  equ    1000
ID_SPEED  equ    1001
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  数据段
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .data?
dwTickCount  dd  ?
dwTSC    dd  ?,?
hInstance  dd  ?
szBuffer  db  256 dup  (?)
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  子声明
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
_ProcDlgMain  PROTO  :DWORD,:DWORD,:DWORD,:DWORD
    .data
szSpeed    db  "你CPU主频为 %d MHz",0
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
;  代码段
;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
    .code
    Win.asm
;********************************************************************
_ProcDlgMain  proc  uses ebx edi esi,
    hWnd:DWORD,wMsg:DWORD,wParam:DWORD,lParam:DWORD
    local  @stPo:POINT
    local  @hWindow
    mov  eax,wMsg
    .  eax WM_CLOSE
      invoke  EndDialog,hWnd,NULL
      invoke  KillTimer,hWnd,1
    .  eax WM_INITDIALOG
      invoke  _CenterWindow,hWnd
      invoke  GetTickCount    ;TSC
      mov  dwTickCount,eax
      rdtsc
      mov  dwTSC,eax
      mov  dwTSC+4,edx
      invoke  SetTimer,hWnd,1,1000,NULL
    .  eax WM_TIMER
      invoke  GetTickCount
      push  eax
      sub  eax,dwTickCount
      pop  dwTickCount
      push  eax
      rdtsc
      push  edx
      push  eax
      sub  eax,dwTSC
      sbb  edx,dwTSC+4
      pop  dwTSC
      pop  dwTSC+4
      mov  ecx,1000000
      div  ecx      ;除以1Mhz=1000000hz
      .  edx >= 500000h    ; 4舍 5入
        inc  eax
      .end
      mov  ecx,1000
      mul  ecx      ;1秒=1000毫秒
      pop  ecx      ;pop出经过毫秒数
      div  ecx
      invoke  wsprf,off szBuffer,off szSpeed,eax
      invoke  SendDlgItemMessage,hWnd,ID_SPEED,
        WM_SETTEXT,0,off szBuffer
    .
;********************************************************************
;  注意:对话框消息处理后要返回 TRUE,对没有处理消息
;  要返回 FALSE
;********************************************************************
      mov  eax,FALSE
      ret
    .end     
    mov  eax,TRUE
    ret
    
_ProcDlgMain  endp
;********************************************************************
start:
    invoke  GetModuleHandle,NULL
    mov  hInstance,eax
    invoke  DialogBoxParam,hInstance,
DLG_MAIN,NULL,off _ProcDlgMain,0
    invoke  ExitProcess,NULL
    end  start


Tags: 

延伸阅读

最新评论

发表评论