找回密码
 注册
搜索
查看: 12670|回复: 0

[收藏]C++ Builder 通过 WMI 获取系统信息

[复制链接]
发表于 2005-5-22 17:04:00 | 显示全部楼层 |阅读模式
  Victor Chen, (C++ 爱好者)
/ A$ q. H7 a' V6 ^. M5 [
9 [' X9 k3 w5 V: e/ S% D# \5 G3 W( K' r' }: n' S
--------------------------------------------------------------------------------2 c7 n/ ^# H' s
WMI: Windows Management Instrumentation (Windows 管理工具)' d9 d0 O( h: L' s5 Q/ W
  通过 WMI 可以获取主板、BIOS、磁盘、显卡、网络等几乎所有的系统信息。
; Z" L9 b  U2 N/ h& k; q1 @   利用这个工具可以管理本地或客户端系统中几乎所有的信息。
7 Y4 i# V, g7 N6 W1 N: x$ |! E   很多网络管理工具都是基于WMI开发的。在 Windows NT/2000/XP/2003 都有这个工具, 在 Windows 98 里面可以选择安装这个工具。
6 _: y! f3 n" b* x6 J3 u0 ?  I* W+ D0 q8 [, ~
--------------------------------------------------------------------------------- A' \, D  K9 K  T) j/ A; ?
BCB 的 WMI 库文件 wbemuuid.lib 由本站提供, 包含在本页下面的程序源码下载里面; V+ |, H! ]4 d8 H
$ h: A1 `8 K! W: P# E1 k0 D4 S
--------------------------------------------------------------------------------& D9 U  Z! m% s1 g
① 初始化 COM 接口:
; ]1 k% t- N. @- E# |   访问 WMI, 必须先初始化 COM 接口, 在程序的一开始调用 CoInitialize(NULL); 初始化, 在结束时调用 CoUninitialize(); 释放资源。8 w9 Y- A% M/ i/ w
  这两个函数在 #include <comdef.h> 里面定义。
$ E. N  ?" O- x) D9 y' u7 R3 t" V7 Q, A' {8 Y9 m, m
② 获取访问 WMI 权限:# z, x0 _# W7 `6 [
  CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_PKT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, 0);& e# b& d) t! c$ {. U: z- ~: ~! a
  如果这个函数返回 S_OK 获取权限成功, 否则为失败。" I7 k/ d. \' |) S

. y. j# t4 l7 N% _8 B9 ?! s③ 通过 IWbemLocator 和 IWbemServices 这两个 COM 接口访问 WMI, 获取系统信息:, `: F* R- m( [$ K
  这个函数的参数: lpList 返回信息, wsClass 为要查找的系统信息类, 这些 COM 接口在 #include <wbemidl.h> 里定义。* F# K: b- m0 t4 r3 ?; s
; H4 `+ u+ b, n9 i
void GetWmiInfo(TStrings *lpList, WideString wsClass)' @* ?. M0 o* n9 @* N
{3 j7 a, u. {7 G* x0 g, p2 e2 a
  IWbemLocator *pWbemLocator = NULL;, W+ [% K- ?' Q$ h
  if(CoCreateInstance(CLSID_WbemAdministrativeLocator, NULL, CLSCTX_INPROC_SERVER|CLSCTX_LOCAL_SERVER, IID_IUnknown, (void**)&pWbemLocator) == S_OK)# P8 V& l! M/ c, P
  {: T) v+ Y# D# v" q
    IWbemServices *pWbemServices = NULL;1 z9 f% I  Q1 |. Q1 n& r0 m9 l+ e! _
    WideString wsNamespace = (L"root\\cimv2");
4 t3 r3 _* l# }+ @     if(pWbemLocator->ConnectServer(wsNamespace, NULL, NULL, NULL, 0, NULL, NULL, &pWbemServices) == S_OK)
0 R& E  {+ A: O, Y      {
$ r3 l8 L% k$ P" S2 W9 ]        IEnumWbemClassObject *pEnumClassObject = NULL;
6 p. p  J) ~# e        WideString wsWQL=L"WQL", wsQuery=WideString(L"Select * from ")+wsClass;
: G% P! D& t4 O- |, v3 T2 R        if(pWbemServices->ExecQuery(wsWQL, wsQuery, WBEM_FLAG_RETURN_IMMEDIATELY,NULL, &pEnumClassObject) == S_OK)
* z: ~( U' T  `: l6 E- L5 X         {
& @; _$ i# a) p, P           IWbemClassObject *pClassObject = NULL;2 [% H6 R, Z- N9 G7 M! o8 h
          ULONG uCount = 1, uReturned;9 h( [$ w, T8 y( U; O# C+ k
          if(pEnumClassObject->Reset() == S_OK)! U. E6 b- A& t8 ?$ \! `
           {+ _. N- e* n- z
             int iEnumIdx = 0;2 U# X! p) M1 x6 A9 G5 r2 y
             while(pEnumClassObject->Next(WBEM_INFINITE, uCount, &pClassObject, &uReturned) == S_OK)
+ i7 _0 @0 M5 s' C) ]5 T7 g               {1 a* n9 O* m7 r! \# u5 g* C
                lpList->Add("---------------- ["+IntToStr(iEnumIdx)+"] -----------------");+ J7 T9 e' `) z" Q) K* C9 H+ u4 E4 `& A

* q- }  {* y" @  p- r                 SAFEARRAY *pvNames = NULL;* v% n9 b: N& Q. q9 R3 ]" q6 |
                if(pClassObject->GetNames(NULL, WBEM_FLAG_ALWAYS | WBEM_MASK_CONDITION_ORIGIN, NULL, &pvNames) == S_OK)
+ q3 n, w! _, w: ]: n                  {
+ i+ t, h9 D# p7 u2 z                    long vbl, vbu;1 E8 f; b& u# f# Z3 v5 H1 {
                   SafeArrayGetLBound(pvNames, 1, &vbl);
2 S' G$ O9 N2 H                    SafeArrayGetUBound(pvNames, 1, &vbu);
5 @% D* T2 |4 e) d, Y8 F                    for(long idx=vbl; idx<=vbu; idx++)3 Z: R- D- z! X, i2 E
                    {
8 Q( A6 \" P) R: m                       long aidx = idx;& Y$ T9 I6 V1 O4 r  z, F
                      wchar_t *wsName = 0;
+ h8 K6 g" s; p                       VARIANT vValue;
' v4 X; |5 ~& k. q7 Y9 S                       VariantInit(&vValue);
. Y& f* d! A/ b" V& t# I7 p: b                       SafeArrayGetElement(pvNames, &aidx, &wsName);
0 I' A7 s' x( s) u5 Z7 B* p8 f
7 d0 @! q" f- B9 x: _" y$ W                       BSTR bs = SysAllocString(wsName);
  Q( Z' y7 u# f% V3 @                       HRESULT hRes = pClassObject->Get(bs, 0, &vValue, NULL, 0);
7 T! n; I, R6 n( f% Y1 N                       SysFreeString(bs);
& D  e- ?: @& L' H
8 }5 ^7 _, n' G2 D; I% B7 C- g                       if(hRes == S_OK)- Z7 Z, N9 j+ R  i0 U) Q
                       {  \1 n$ B' `3 b1 k( O
                         AnsiString s;
0 Y0 u; w" W$ t) }                          Variant v = *(Variant*)&vValue;; \* a$ Q9 E# o* w0 ]1 k  `. q% C
                         if(v.IsArray())
2 z: N# {0 f; T) a6 z, x3 W! S, T                           {8 [% T/ S9 C8 L; V% g, T) ^/ _
                            for(int i=v.ArrayLowBound(); i<=v.ArrayHighBound(); i++)
1 y, G8 j; G& r4 }+ R  ]& \) |                              {
+ j( D2 e" R- I$ H4 z2 }' A- \                                Variant a = v.GetElement(i);+ a5 j. `, r0 m" e, O
                               if(!s.IsEmpty())
5 n, o1 V$ `1 B+ [* T$ S' e; e                                  s+=", ";
6 [" O1 a7 }$ @' C3 n" U, ~$ Q                                s+=VarToStr(a);  r; ?* p. f& m2 l1 l
                             }
# p& U: C0 w8 d, r2 P* ^2 P                           }
  p$ @0 g2 t4 r+ ~( _2 q8 ]                          else
, p9 n0 K0 A, e! i                           {# u( c& c* E) [4 Q% p
                            s = VarToStr(v);$ D- j  A, n7 ?. ~4 `& `* ]1 g. f
                          }
* u+ {4 I* c5 E                          lpList->Add(AnsiString(wsName)+"="+s);, F! h" e; M+ r0 \2 E- n
                       }
% Q! o! q, c" _" ]$ S8 P' f4 |9 P3 z% _7 Q& q
                      VariantClear(&vValue);% }5 Z% M' w% u% B! r$ r. A
                      SysFreeString(wsName);
5 Y4 t5 d- M7 }* A( p                     }
# @- V& x2 Z! {5 P# C                  }; }4 ?$ j- n8 W" w. M* ^( v1 j
                if(pvNames)SafeArrayDestroy(pvNames);' u3 \) q1 _) X& u9 L$ E
                iEnumIdx++;
, c1 g" |5 M  `" p2 w               }
2 T; U# e1 m/ f, a            }
2 ?5 C- J1 W6 x           if(pClassObject)pClassObject->Release();- t" s  W2 `2 n. ^7 ~
        }2 A7 u  o' ~( ]- y. F" @4 O& @3 a
       if(pEnumClassObject)pEnumClassObject->Release();& v& b% T: V% O; a$ Y) T4 O. X/ v$ A
     }" d/ M1 r* q/ J' x1 K- h
    if(pWbemServices)pWbemServices->Release();
9 N4 Z' [/ D* |1 u) q! A9 m% [$ d  v$ c( E   }! A5 |& H. J' E. E% w
  if(pWbemLocator)pWbemLocator->Release();
& a- ^0 {; D* W5 t' a7 J1 u}" F. d8 f! X6 o! j! o1 ^* M$ H7 @
//---------------------------------------------------------------------------
$ C) T, S1 O, P# M  k8 g8 {( C; @5 Y
// 通过 WIN32_bios 获取 BIOS 信息:
" H2 E$ S2 Y0 K; L. evoid __fastcall TForm1::Button1Click(TObject *Sender)
% F6 J. e. p" Z; v{% b. k2 R0 D* v' L& B5 h
   Memo1->Lines->Add("================== [WIN32_bios] =================");) `. S0 X) b, T, ^  S3 ~" j
   GetWmiInfo(Memo1->Lines, "WIN32_bios");9 ?% A* f0 M' g9 p
   Memo1->Lines->Add("");
! s% T: W: d# c8 R8 [}# L: _4 j* g$ g- s, A- u

; w& D2 O0 s5 s* ]# O/ u" i--------------------------------------------------------------------------------
- U3 ~- I3 o+ P7 A& V) ?* a! Q8 b# D1 W5 M4 {, V' B
WMI 可以访问的信息类型有:
( b: C" n! U1 V; a+ I   Win32_1394Controller
) ~/ Z) b: c+ l5 _5 C   Win32_BaseBoard' G0 r$ O2 [8 v0 l) u  v9 N+ b6 G
  Win32_Battery
+ m- \, ?" \* o( ^+ [( f0 |   Win32_BIOS
# b4 N5 p* {9 z: D6 Y5 e  I   Win32_Bus* u" c; N" {* W' Y# c* M% ]5 E
  Win32_CacheMemory5 l1 t3 ^/ V0 T: D
  Win32_CDROMDrive
& \! r: c; S2 M+ s8 [; B   Win32_CurrentProbe
1 D4 H$ _" N; M$ i1 [& M5 [   Win32_DesktopMonitor
  X) S9 [/ h8 }/ a   Win32_DeviceMemoryAddress* c- B& `6 A) n5 L- v
  Win32_DiskDrive
7 i6 O2 q' m* B   Win32_DisplayConfiguration
3 F5 O4 z6 S$ ~   Win32_DisplayControllerConfiguration+ L7 W# m3 k* S; R$ o/ `
  Win32_DMAChannel
) s. p! ~+ h1 o8 o# t% S   Win32_Fan
; c* k8 M$ g5 L" |, w- |  c   Win32_FloppyController
+ j$ U( |  W6 ~) R5 Y) O$ o! S   Win32_FloppyDrive
% t8 i9 E1 \" E. _  d' H# V   Win32_HeatPipe  v% @! U0 g" N
  Win32_IDEController  _$ ~/ y, T1 t6 b) A3 X
  Win32_InfraredDevice
2 H! U; W7 R8 ]7 l   Win32_IRQResource+ Z4 ^! D- Y% I6 p& V
  Win32_Keyboard/ V. o6 j5 `1 I7 S, s
  Win32_MemoryArray
4 r" S$ c) T( Z( Y/ n, v   Win32_MemoryDevice
' Z- d$ e- O5 r: ]4 r4 e   Win32_MotherboardDevice
, W% o0 v6 I5 f* n   Win32_NetworkAdapter0 W, ^5 c9 p" f% T$ U
  Win32_NetworkAdapterConfiguration% j3 `0 I7 y: A  W4 u
  Win32_OnBoardDevice, q5 Q9 w, y. c. |" W% U2 k
  Win32_ParallelPort
1 Q8 i( m8 |/ p$ K/ y  u. a' ]: i- G   Win32_PCMCIAController5 v# H1 q* O3 Z" F/ P5 H
  Win32_PhysicalMemory( ]" Q2 Q7 J# D/ v( [* J7 K
  Win32_PhysicalMemoryArray( M- K$ @5 q9 Q( s4 L
  Win32_PnPEntity
  Q, X% _5 x) d" i$ S+ O# e6 l$ H   Win32_PointingDevice! {6 Y: c6 G5 @$ `, N- g& Q
  Win32_PortableBattery& O$ q* u6 {/ H# ^0 Q0 |0 w
  Win32_PortConnector6 a! G+ q( r& R' D/ I/ B
  Win32_PortResource
4 v/ U3 a( t6 \2 `9 m& ?   Win32_POTSModem4 W  W) h: ^! l( A# o
  Win32_PowerManagementEvent
6 ~" {" b8 v: Q7 _0 w   Win32_Printer4 f0 N) }( [: ?
  Win32_PrinterConfiguration9 `8 e1 {( J1 c' T" `! i
  Win32_PrintJob: }. I( b& y% E$ i' I- y. V
  Win32_Processor# z( ^- P! X7 ^# E
  Win32_Refrigeration& d( G& L4 Z! r+ o
  Win32_SerialPort  V# R* {! C' S# L# }( ]: P: }$ L
  Win32_SerialPortConfiguration! \1 v/ s0 y  F2 ~3 i8 C& }
  Win32_SMBIOSMemory# B9 K- e3 e" i
  Win32_SoundDevice! w; x: J; j, q# l7 |; a
  Win32_SystemEnclosure4 e; P: \  S- y7 X! U+ i$ @
  Win32_SystemMemoryResource  T& R5 b. t" y! e+ \1 O
  Win32_SystemSlot
0 B/ G5 B+ L0 C! z+ s9 c   Win32_TapeDrive* O) s4 _% }6 {- j) h6 ^6 z3 N
  Win32_TemperatureProbe
1 n2 ?6 i- {. x  X: n0 V- c   Win32_UninterruptiblePowerSupply. ~# d2 w6 M7 A# I6 l
  Win32_USBController& f8 n2 ~. p% I1 Y! z+ g
  Win32_VideoConfiguration5 W# ^) |+ C/ S$ ~* E
  Win32_VideoController* `2 F( `5 j- r) S. j
  Win32_VoltageProbe; M% R) @0 C1 V3 o

  o' T0 Z/ z0 b以上类型(字符串值)通过前面写的函数 GetWmiInfo 可以得到相应的信息, 例如 GetWmiInfo(Memo1->Lines, "WIN32_bios");
您需要登录后才可以回帖 登录 | 注册

本版积分规则

Archiver|手机版|小黑屋|宁德市腾云网络科技有限公司 ( 闽ICP备2022007940号-5|闽公网安备 35092202000206号 )

GMT+8, 2026-1-8 22:11 , Processed in 0.020151 second(s), 14 queries .

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

快速回复 返回顶部 返回列表