Test8086:测试CPU型号{ Will always be 2 (386 or later) }
Test8087:测试协处理器{ Will always be 3 (387 or later) }
TestFDIV: 测试奔腾芯片是否有缺陷{ -1: 有缺陷, 0: 不能决定, 1: OK }Q:  How do I detect for a co-processor?
Q:  How can I tell which CPU is being used?A:  Here is the short version.  The problem here is that it doesn't detect the pentium.var winFlags: LongInt;
begin
  winFlags := GetWinFlags;
  { Get math coprocessor status }
  If winFlags And WF_80x87 > 0 Then Caption := 'Present'
  Else Caption := 'Not Present';  { Get CPU type }
  If winFlags And WF_CPU486 > 0 Then edit1.text := '486' {also pentium}
  else If winFlags And WF_CPU386 > 0 Then edit1.text := '386'  else If winFlags And WF_CPU286 > 0 Then edit1.text := '286';
end;
Here is a version that will work with the pentium:{ This code comes from Intel, and has been modified for Delphi's
  inline assembler.
}unit Cpu;interfaceuses
  SysUtils, WinTypes, WinProcs, Messages, Classes, Graphics, Controls,
  Forms, Dialogs, StdCtrls, Buttons;type
  { All the types currently known.  As new types are created,
    add suitable names, and extend the case statement in    the GetCpuType function.
  }
  TCPUType = (i8086CPU, i286CPU, i386CPU, i486CPU, iPentiumCPU);  TForm1 = class(TForm)
    Edit1: TEdit;
    Label1: TLabel;
    BitBtn1: TBitBtn;
    procedure FormCreate(Sender: TObject);
    procedure BitBtn1Click(Sender: TObject);
  private
    { Return the type of the current CPU }
    function CpuType: TCPUType;
    { Return the type as a string }
    function GetCPUType: String;
  public
  end;var
  Form1: TForm1;  { Define the winFlags variable for 286 check }
  winFlags: Longint;implementation{$R *.DFM}
{ Get CPU type }
function TForm1.GetCPUType: String;
var
  kind: TCPUType;
begin
  if winFlags and WF_CPU286 > 0 then
     Result := '80286'
  else
    begin
      kind := CpuType;
      case kind of
      i8086CPU:
        Result := '8086';
      i386CPU:
        Result := '80386';
      i486CPU:
        Result := '80486';
      iPentiumCPU:
        Result := 'Pentium';      else
        { Try to be flexible for future cpu types, e.g., P6. }
        Result := Format('P%d', [Ord(kind)]);
      end;
    end;
end;{ Assembly function to get CPU type including Pentium and later }
function TForm1.CpuType: TCPUType; assembler;
asm
  push DS
  { First check for an 8086 CPU }
  { Bits 12-15 of the FLAGS register are always set on the }
  { 8086 processor. }
  pushf                          { save EFLAGS }
  pop bx               { store EFLAGS in BX }  mov ax,0fffh         { clear bits 12-15 }
  and ax,bx            { in EFLAGS }
  push ax                       { store new EFLAGS value on stack }
  popf                           { replace current EFLAGS value }
  pushf                          { set new EFLAGS }
  pop ax               { store new EFLAGS in AX }
  and ax,0f000h        { if bits 12-15 are set, then CPU }
  cmp ax,0f000h        { is an 8086/8088 }
  mov  ax, i8086CPU             { turn on 8086/8088 flag }  je @@End_CpuType  { 80286 CPU check }
  { Bits 12-15 of the FLAGS register are always clear on the }
  { 80286 processor. }
  { Commented out because 'pop ax' crashes it to the DOS prompt when running }
  { with a Delphi form on some Machines.}
  {  or bx,0f000h  }   { try to set bits 12-15 }
  {  push  bx               }
  {  popf                          }
  {  pushf                         }
  {  pop ax               }     { This crashes Delphi programs on some machines }  {  and ax,0f000h  }     { if bits 12-15 are cleared, CPU=80286 }
  {  mov  ax, i286CPU              }     { turn on 80286 flag }
  {  jz @@End_CpuType    }  { To test for 386 or better, we need to use 32 bit instructions,
    but the 16-bit Delphi assembler does not recognize the 32 bit opcodes
    or operands.  Instead, use the 66H operand size prefix to change
    each instruction to its 32-bit equivalent. For 32-bit immediate
    operands, we also need to store the high word of the operand immediately    following the instruction.  The 32-bit instruction is shown in a comment
    after the 66H instruction.
  }  { i386 CPU check }
  { The AC bit, bit #18, is a new bit introduced in the EFLAGS }
  { register on the i486 DX CPU to generate alignment faults. }
  { This bit can not be set on the i386 CPU. }  db 66h                    { pushfd }
  pushf
  db 66h                    { pop eax }
  pop ax                  { get original EFLAGS }
  db 66h                    { mov ecx, eax }  mov cx,ax     { save original EFLAGS }
  db 66h                    { xor eax,40000h }
  xor ax,0h             { flip AC bit in EFLAGS }
  dw 0004h
  db 66h                    { push eax }
  push ax     { save for EFLAGS }
  db 66h                    { popfd }
  popf     { copy to EFLAGS }
  db 66h                    { pushfd }
  pushf     { push EFLAGS }
  db 66h                    { pop eax }
  pop ax     { get new EFLAGS value }
  db 66h                    { xor eax,ecx }  xor ax,cx     { can't toggle AC bit, CPU=Intel386 }
  mov ax, i386CPU           { turn on 386 flag }
  je @@End_CpuType  { i486 DX CPU / i487 SX MCP and i486 SX CPU checking }
  { Checking for ability to set/clear ID flag (Bit 21) in EFLAGS }
  { which indicates the presence of a processor }
  { with the ability to use the CPUID instruction. }
  db 66h                    { pushfd }
  pushf     { push original EFLAGS }
  db 66h                    { pop eax }  pop ax     { get original EFLAGS in eax }
  db 66h                    { mov ecx, eax }
  mov cx,ax     { save original EFLAGS in ecx }
  db 66h                    { xor eax,200000h }
  xor ax,0h             { flip ID bit in EFLAGS }
  dw 0020h
  db 66h                    { push eax }
  push ax     { save for EFLAGS }
  db 66h                    { popfd }
  popf     { copy to EFLAGS }
  db 66h                    { pushfd }
  pushf                     { push EFLAGS }  db 66h                    { pop eax }
  pop ax     { get new EFLAGS value }
  db 66h                    { xor eax, ecx }
  xor ax, cx
  mov ax, i486CPU           { turn on i486 flag }
  je @@End_CpuType     { if ID bit cannot be changed, CPU=486 }
    { without CPUID instruction functionality }  { Execute CPUID instruction to determine vendor, family, }
  { model and stepping.  The use of the CPUID instruction used }
  { in this program can be used for B0 and later steppings }  { of the P5 processor. }
  db 66h                   { mov eax, 1 }
  mov ax, 1            { set up for CPUID instruction }
  dw 0
  db 66h                   { cpuid }
  db 0Fh            { Hardcoded opcode for CPUID instruction }
  db 0a2h
  db 66h                   { and eax, 0F00H }
  and ax, 0F00H            { mask everything but family }
  dw 0
  db 66h                   { shr eax, 8 }
  shr ax, 8                { shift the cpu type down to the low byte }  sub ax, 1                { subtract 1 to map to TCpuType }@@End_CpuType:
  pop ds
end;
{ Get the Windows Flags to check for 286.  The 286 assembly code
  crashes due to a problem when using with Delphi Forms on some machines.  This
  method is safer.
}
procedure TForm1.FormCreate(Sender: TObject);
begin
  winFlags := GetWinFlags;
end;{ Call the CPU function and assign it to the Edit box }
procedure TForm1.BitBtn1Click(Sender: TObject);
begin
  Edit1.Text := GetCPUType;end;end.{This code came from Lloyd's help file!}

解决方案 »

  1.   

    to lin513(东方求救) :
    我把getcputype直接写成:kind   := CpuType;
                           Result := Format('P%d', [Ord(kind)]);
    其他照抄;
    可是运行以后,发现不仅AMD的Athlon芯片认不出来,且P4也认不出?好象所有的芯片都认为是P2,是我搞错了吗?请继续指教!
      

  2.   

    获得cpu的使用率
    procedure TForm1.Timer1Timer(Sender: TObject);
    Var
    TMS : TMemoryStatus;
    begin
         TMS.dwLength := SizeOf (TMS);
         GlobalMemoryStatus (TMS);
         Gauge1.Progress := TMS.dwMemoryLoad;
         Gauge2.Progress := (100*TMS.dwAvailPhys) Div TMS.dwTotalPhys;
         Gauge3.Progress := (100*TMS.dwAvailPageFile) Div TMS.dwTotalPageFile;
    end;
      

  3.   

    获得cpu的使用率procedure TForm1.Timer1Timer(Sender: TObject);
    varTMS : TMemoryStatus;
    begin
         TMS.dwLength := SizeOf (TMS);
         GlobalMemoryStatus (TMS);
         Gauge1.Progress := TMS.dwMemoryLoad;
         Gauge2.Progress := (100*TMS.dwAvailPhys) Div TMS.dwTotalPhys;
         Gauge3.Progress := (100*TMS.dwAvailPageFile) Div TMS.dwTotalPageFile;
    end;
      

  4.   

    cpuid & cpuspeedtype   *TCPUID*= array[1..4] of Longint;   *TVendor*= array [0..11] of char;       function GetCPUID : TCPUID; assembler; register;   asm     PUSH    EBX         {Save affected register}     PUSH    EDI     MOV     EDI,EAX     {@Result}         POP     EBX   end;       function GetCPUVendor : TVendor; assembler; register;   asm     PUSH    EBX*   {Save affected register}     PUSH    EDI     MOV     EDI,EAX*   {@Result (TVendor)}     MOV     EAX,0     DW      $A20F*   {CPUID Command}         LOOP    @2     MOV     EAX,EBX     MOV***ECX,4   @3:     STOSB     SHR     EAX,8     LOOP    @3     POP     EDI* {Restore registers}     POP     EBX   end;        MyReg.RootKey:=HKEY_LOCAL_MACHINE;    TRY    if MyReg.OpenKey('\HARDWARE\DESCRIPTION\System\CentralProcessor\0',FALSE) then     Begin      B:=MyReg.ReadInteger('~MHz');      if B > 0 Then Mhz:=B else       B:=MyReg.ReadInteger('~Mhz');       if B > 0 Then Mhz:=B else       B:=MyReg.ReadInteger('~mhz');       if B > 0 Then Mhz:=B; :   PUSH    EBX         {Save affected register}           -- ※ 来源:·BBS 水木清华站 smth.org·[FROM: 202.120.99.140] 发信人: dyfu (windwolf), 信区: Delphi 标  题: Re: re:cpuid & cpu speed 发信站: BBS 水木清华站 (Wed Nov  8 10:17:40 2000)       在\HARDWARE\DESCRIPTION\System\CentralProcessor\0'下根本就没有 'Mhz'这个键值,CPU速度还是得不到   【 在 zenganiu (zenganiu) 的大作中提到: 】 : type :       TCPUID  = array[1..4] of Longint; :       TVendor = array [0..11] of char; :   :   PUSH    EDI :   MOV     EDI,EAX     {@Result} :   MOV     EAX,1 :   DW      $A20F       {CPUID Command} : ...................   --   ※ 来源:·BBS 水木清华站 smth.org·[FROM: 202.201.3.58] 发信人: zenganiu (zenganiu), 信区: Delphi 标  题: Re: re:cpuid & cpu speed 发信站: BBS 水木清华站 (Wed Nov  8 14:28:41 2000) WWW-POST   【 在 dyfu (windwolf) 的大作中提到: 】   : 在\HARDWARE\DESCRIPTION\System\CentralProcessor\0'下根本就没有   : 'Mhz'这个键值,CPU速度还是得不到           function GetCPUSpeed: Double;   const     DelayTime = 500; // measure time in ms   var     TimerHi, TimerLo: DWORD;     PriorityClass, Priority: Integer;   begin     PriorityClass := GetPriorityClass(GetCurrentProcess);     Priority := GetThreadPriority(GetCurrentThread);       ※ 来源:·BBS 水木清华站 smth.org·[FROM: 202.120.8.172]     end;     Sleep(DelayTime);     asm       dw 310Fh // rdtsc       sub eax, TimerLo       sbb edx, TimerHi       mov TimerLo, eax       mov TimerHi, edx     end;