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

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

[复制链接]
发表于 2005-5-22 17:04:00 | 显示全部楼层 |阅读模式
  Victor Chen, (C++ 爱好者)! o+ a* H2 R' a$ u9 B
8 \% X% U1 L9 Z9 J/ r
7 C6 m( ]4 w4 d& `% h3 G
--------------------------------------------------------------------------------4 Z. {/ e& U# P% i
WMI: Windows Management Instrumentation (Windows 管理工具)
; {# c/ y# [/ e) L   通过 WMI 可以获取主板、BIOS、磁盘、显卡、网络等几乎所有的系统信息。 / L( e( A) J* _9 O% m2 Q0 m
  利用这个工具可以管理本地或客户端系统中几乎所有的信息。7 @/ B. f, _4 ?" w# S) k6 l
  很多网络管理工具都是基于WMI开发的。在 Windows NT/2000/XP/2003 都有这个工具, 在 Windows 98 里面可以选择安装这个工具。 / C8 u2 g7 V# A& \& k% i$ G
3 Q% ?! T5 w6 b& }7 i6 K  D
--------------------------------------------------------------------------------. G3 f% ]( ^: r1 \; z, v$ ~
BCB 的 WMI 库文件 wbemuuid.lib 由本站提供, 包含在本页下面的程序源码下载里面
' a6 ?% A: P6 K8 B! n6 }- B; B
1 V4 W' B6 u6 J( [$ O7 c" g--------------------------------------------------------------------------------2 D. W( h. X: P4 ?. W5 \+ B
① 初始化 COM 接口:/ J5 s2 y. Y( ~. H
  访问 WMI, 必须先初始化 COM 接口, 在程序的一开始调用 CoInitialize(NULL); 初始化, 在结束时调用 CoUninitialize(); 释放资源。
$ T4 D4 i+ y' y5 ^   这两个函数在 #include <comdef.h> 里面定义。! n# x# G7 s/ L" q3 J) W( s
( w& q- @8 R; N9 i
② 获取访问 WMI 权限:
3 X2 D: J3 r) C# [7 z2 \1 G   CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_PKT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, 0);' S& M  k& P3 p' {: _, ]% P0 A7 h
  如果这个函数返回 S_OK 获取权限成功, 否则为失败。
3 ~9 \5 P0 }$ X9 i: ]( r5 M. _9 v) \! S2 D% b1 `- T
③ 通过 IWbemLocator 和 IWbemServices 这两个 COM 接口访问 WMI, 获取系统信息:
* b# d1 B/ n) j" j5 q$ p1 F" p   这个函数的参数: lpList 返回信息, wsClass 为要查找的系统信息类, 这些 COM 接口在 #include <wbemidl.h> 里定义。$ M1 F, L# j+ ~9 l" R" Z

5 b/ D  c* t! L% M% ], Y2 Nvoid GetWmiInfo(TStrings *lpList, WideString wsClass)
  U1 S8 ?0 Q, k{4 F6 B# p. \7 _. I
  IWbemLocator *pWbemLocator = NULL;' ?' Q+ r7 G% x
  if(CoCreateInstance(CLSID_WbemAdministrativeLocator, NULL, CLSCTX_INPROC_SERVER|CLSCTX_LOCAL_SERVER, IID_IUnknown, (void**)&pWbemLocator) == S_OK)
6 H6 N- ?0 y  L2 N& p* [   {) q$ _2 k2 K5 \1 l9 B6 R4 q
    IWbemServices *pWbemServices = NULL;9 `. e3 c+ ^1 Y0 z
    WideString wsNamespace = (L"root\\cimv2");7 }% m. M: g8 ]5 t
    if(pWbemLocator->ConnectServer(wsNamespace, NULL, NULL, NULL, 0, NULL, NULL, &pWbemServices) == S_OK)
$ S8 B. z* e7 h( i$ u% {) M      {" ?/ m# S3 T* R8 D- C' ~* Y, z
       IEnumWbemClassObject *pEnumClassObject = NULL;6 B' s) _4 z8 D" k# }: V' O6 a  D
       WideString wsWQL=L"WQL", wsQuery=WideString(L"Select * from ")+wsClass;
: N; L- |% y& G9 ]$ A4 [        if(pWbemServices->ExecQuery(wsWQL, wsQuery, WBEM_FLAG_RETURN_IMMEDIATELY,NULL, &pEnumClassObject) == S_OK)
1 r9 n+ K( R! C$ K( f1 a+ y         {" W* P2 P  w" F7 e* h! a1 A
          IWbemClassObject *pClassObject = NULL;
% |( q1 _  ]" Z& n7 @! B' j           ULONG uCount = 1, uReturned;0 \+ Z* A* N4 W
          if(pEnumClassObject->Reset() == S_OK)0 i. K6 |% t9 x+ K- P
           {
: @0 T$ }+ e- w5 {              int iEnumIdx = 0;
1 H' x: z' V+ U- U4 m8 q              while(pEnumClassObject->Next(WBEM_INFINITE, uCount, &pClassObject, &uReturned) == S_OK)
8 @% v; i) n( T& W! c) ?+ `               {
2 G( v" }( Q. @9 _! _  D0 P: y) w                 lpList->Add("---------------- ["+IntToStr(iEnumIdx)+"] -----------------");
( B* P$ ~4 q' N" D  X* a1 x( A' m; c$ M
                SAFEARRAY *pvNames = NULL;
; U: o+ L. C! @. s5 d3 a9 N4 {                 if(pClassObject->GetNames(NULL, WBEM_FLAG_ALWAYS | WBEM_MASK_CONDITION_ORIGIN, NULL, &pvNames) == S_OK)" [' |& \" H# N9 r+ ?. W
                 {
7 M7 o  _8 H1 c& y1 n" P                    long vbl, vbu;
0 ]1 m  G* S) `  `5 ]# x% a& v2 e                    SafeArrayGetLBound(pvNames, 1, &vbl);
( C( L; I8 _5 f/ `% T                    SafeArrayGetUBound(pvNames, 1, &vbu);3 u0 V; h; K0 \# {) `+ m; x
                   for(long idx=vbl; idx<=vbu; idx++)
" I( Y- z7 c9 ~- f- H; |/ W                     {
: N$ J8 M5 h$ T1 Y: F1 \4 D                       long aidx = idx;
8 \/ u' S* Q" B' b/ M: E* \" _7 t4 M                       wchar_t *wsName = 0;
( Y/ x, ?; K9 \  P" M, C. ~: G! D& o                       VARIANT vValue;
0 K& D; O! Q% l$ U5 E1 ?: z! ~                       VariantInit(&vValue);4 @# r2 _* ~$ ?. i
                      SafeArrayGetElement(pvNames, &aidx, &wsName);
; ?1 D3 [7 a+ P5 E% }. P
, n) G+ ^$ F4 u                       BSTR bs = SysAllocString(wsName);
; K% m2 T# o* D6 s$ ]* K                       HRESULT hRes = pClassObject->Get(bs, 0, &vValue, NULL, 0);/ Q2 ?8 [* R" m. ^( f
                      SysFreeString(bs);0 ?7 P8 }! G1 Z: E4 t3 [) k

8 P# _) A8 Z8 a* Z                       if(hRes == S_OK)
1 d' [) D) a9 r5 I  O7 l8 p                        {
/ A  h8 }# X8 R* s                          AnsiString s;
) A% L+ a# H8 d# o                          Variant v = *(Variant*)&vValue;0 ^$ g5 _. x% T( R5 P* Z8 n
                         if(v.IsArray())* q+ }4 s: g% I" V- C9 T
                          {
5 K- F5 m$ C- R8 ^! i                             for(int i=v.ArrayLowBound(); i<=v.ArrayHighBound(); i++)
. l' u: q5 p1 T' s& c7 b! e+ q                              {
; F$ s' z& _+ c/ `4 K                                Variant a = v.GetElement(i);( @" L( |0 _. A5 ~5 `
                               if(!s.IsEmpty())3 s1 f# F5 U8 e7 [+ j0 G* l6 \& }
                                 s+=", ";4 s2 {# k. C% z& z, X1 M$ r$ Q
                               s+=VarToStr(a);; @( R0 ~7 i4 T, M/ F. B: {
                             }
4 P& C' H1 N! f5 t% t4 I1 S                           }0 X" G) N6 b$ v3 r4 S3 @/ ]; q
                         else$ k; k2 ]: C; H* h2 n
                          {
) T& u$ p* d3 h0 @( I; @% @1 k                             s = VarToStr(v);
0 @3 B; ?' @7 V9 C! ^" v6 ]( y                           }- S" ?9 T; U) i. L( `
                         lpList->Add(AnsiString(wsName)+"="+s);8 t; u4 V2 x9 ^8 @  M: W1 x
                       }
) F! s, G8 @* d8 g/ \8 r5 m1 Y
/ U0 O1 E$ t5 V! ~  V+ F5 W                       VariantClear(&vValue);" `' Q( Y$ P0 M; {4 |
                      SysFreeString(wsName);
! Q8 F4 v' g% R1 p6 m* ^                     }
5 V6 i! M; ~% k; x2 q9 r                  }
( L) f, D6 }6 H4 |                 if(pvNames)SafeArrayDestroy(pvNames);+ G4 y* z$ S) U) F% m/ F
                iEnumIdx++;
. i- G( j' `6 X/ @' g5 w$ `               }
: f, C" a7 w8 p' N( {' F# k' l5 Y            }
9 X5 Y$ x! ]. K# v9 v2 Y4 m" `           if(pClassObject)pClassObject->Release();
/ y0 h! ]" L  N         }  I4 Q/ @2 y4 w3 `! F% Y
       if(pEnumClassObject)pEnumClassObject->Release();; x! W- h( I4 P' H
     }
  m( A1 ^! ~& q; J: p1 V% G     if(pWbemServices)pWbemServices->Release();# r7 @! F6 N" R* a
  }
# I  l9 n  I6 D5 Q, Q2 [  if(pWbemLocator)pWbemLocator->Release();
/ J' Z  X: S) c}2 o$ l) H/ M$ q+ q  v! F5 i" X6 V
//---------------------------------------------------------------------------
: ]; q" O- X& g: Q# p" Y4 |: X) o; M: X1 T. G
// 通过 WIN32_bios 获取 BIOS 信息:
" V2 W1 {  T3 D0 Z8 g: @9 Bvoid __fastcall TForm1::Button1Click(TObject *Sender). R4 q: u9 p) C% L
{
* S! u, ]& S8 u    Memo1->Lines->Add("================== [WIN32_bios] =================");
8 v$ ~# {' R# A) q    GetWmiInfo(Memo1->Lines, "WIN32_bios");! U) G, Y0 W: w4 ~* J& A) v' Q; j8 U
   Memo1->Lines->Add("");3 t3 E% i& e$ Y# k' w" f
}3 r& R" t! p8 o, Y9 {$ K( c

  M, X4 ~4 X6 W--------------------------------------------------------------------------------
/ s0 s' [$ ~! b4 f6 l2 D; z7 L2 t% P1 x. h5 J
WMI 可以访问的信息类型有:
2 T# e  D# H- n& W! |   Win32_1394Controller
% f' q' s$ }* k- I3 g+ y   Win32_BaseBoard9 _- H& z( X" {: O3 j; \/ k; f
  Win32_Battery
+ d( u  H1 s8 @9 @$ y/ x   Win32_BIOS8 }- J. p8 c" ^7 Q$ [! i2 y
  Win32_Bus, L4 V# A, M" Z2 u3 _* h8 q. Q% s
  Win32_CacheMemory/ W3 B, }8 T/ u9 l: f; i7 M
  Win32_CDROMDrive9 h8 l: [, U" g+ e
  Win32_CurrentProbe
; m3 c2 H" P% ~; c3 |% k# J- q+ i   Win32_DesktopMonitor
7 A$ j% ~8 z- E   Win32_DeviceMemoryAddress! g; j/ S4 k: C  Q
  Win32_DiskDrive9 c  d0 ^4 q/ ?1 r2 i7 \
  Win32_DisplayConfiguration% D; T( E: k* a/ J% g! K& _6 Q" `
  Win32_DisplayControllerConfiguration* `! d% J& X& x% D8 B5 a. a  Z0 f* X. ^
  Win32_DMAChannel1 Z" B: h' _3 O4 s5 s
  Win32_Fan  R0 k/ i( k8 O
  Win32_FloppyController: H; H: N( q# s& j( H' R, b
  Win32_FloppyDrive% z' q7 I7 ^3 d6 O" ~% E
  Win32_HeatPipe8 r( Z# o" Y3 l9 R2 p) T3 G
  Win32_IDEController& N6 u4 y/ \+ K6 d3 N! d
  Win32_InfraredDevice
. ~# L6 S8 t3 s+ j6 [   Win32_IRQResource* ?! q" T: }0 m  o+ X
  Win32_Keyboard  R' B) H' P- V/ r- u# \; C
  Win32_MemoryArray* N7 @8 r1 z, ]
  Win32_MemoryDevice
% F8 T- `6 L; q* B   Win32_MotherboardDevice4 D9 S) [- m6 s: Z# `; [
  Win32_NetworkAdapter1 [" O, ^  T/ z" a( ~  l" i
  Win32_NetworkAdapterConfiguration
2 t& A2 p; a7 U4 z+ W' z+ V. q   Win32_OnBoardDevice8 W+ U- m# E, h& S* N/ b
  Win32_ParallelPort
5 P2 c8 [  O) m/ H' ~0 S" B   Win32_PCMCIAController
  c8 b( i+ P9 N. z9 s, `( O6 f   Win32_PhysicalMemory
8 {; t- m# _+ `  ~' ~& _6 D9 i5 K   Win32_PhysicalMemoryArray
& _" W  A2 q) B  c8 S   Win32_PnPEntity, K% l: h5 f$ Q
  Win32_PointingDevice) ], i; A8 S0 z, ?4 w
  Win32_PortableBattery0 `$ X& P' S; m) o: n
  Win32_PortConnector
* I9 Q6 H2 G  g   Win32_PortResource
2 t+ ]5 ~/ W+ y, q0 ?   Win32_POTSModem
( M9 J: G2 p) A2 n$ N! V: x5 l) |   Win32_PowerManagementEvent
& K$ ]4 v9 U  i* o: g% l0 y   Win32_Printer0 s9 c. [1 H6 ^8 }& |$ x8 j4 [
  Win32_PrinterConfiguration9 J* m# y' y, m" H
  Win32_PrintJob8 F. T; r6 s  B
  Win32_Processor
7 W3 b. s% B, }   Win32_Refrigeration, n- p7 X1 W$ X3 X
  Win32_SerialPort
% D9 Y* k+ B3 y6 w1 f   Win32_SerialPortConfiguration
$ z" l/ i- B% v9 Y0 X   Win32_SMBIOSMemory
3 G* }( M$ K5 v1 \+ F. p   Win32_SoundDevice
  M2 {+ E) ]4 W" _' y   Win32_SystemEnclosure  l' h5 x3 z: o: Q1 ~+ M
  Win32_SystemMemoryResource1 i/ m3 W6 L% o
  Win32_SystemSlot# P/ G; b7 U! H7 Y' T5 N
  Win32_TapeDrive! c2 J8 Z; \0 Y$ h% z/ e, L+ V
  Win32_TemperatureProbe
9 e% L' T, W1 t5 O- A1 j  R   Win32_UninterruptiblePowerSupply, Q' W) N5 w4 d: s! d
  Win32_USBController6 R: z7 @. D5 B
  Win32_VideoConfiguration0 |+ h( D: P2 P+ t- ~4 P; N- m
  Win32_VideoController
1 q2 m  g& D9 W. x$ ^   Win32_VoltageProbe
+ D* n. D! ?) D  \  ?9 K
( G8 y7 x* s0 }# G" {% ]* [9 K以上类型(字符串值)通过前面写的函数 GetWmiInfo 可以得到相应的信息, 例如 GetWmiInfo(Memo1->Lines, "WIN32_bios");
您需要登录后才可以回帖 登录 | 注册

本版积分规则

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

GMT+8, 2026-2-5 06:40 , Processed in 0.019590 second(s), 15 queries .

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

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