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

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

[复制链接]
发表于 2005-5-22 17:04:00 | 显示全部楼层 |阅读模式
  Victor Chen, (C++ 爱好者)8 w$ @8 `( }% Y3 G, G4 b
7 G* e) q* B, z8 e2 l/ b

/ c" X4 W' ?* ^  z1 B6 g--------------------------------------------------------------------------------) K( S9 V! w0 B# W; E4 p
WMI: Windows Management Instrumentation (Windows 管理工具)
0 [+ r6 G3 q6 h7 L; w. h   通过 WMI 可以获取主板、BIOS、磁盘、显卡、网络等几乎所有的系统信息。
5 j  O9 t6 W6 S) Y   利用这个工具可以管理本地或客户端系统中几乎所有的信息。$ q8 L, \- L( T# X, v7 Y2 f
  很多网络管理工具都是基于WMI开发的。在 Windows NT/2000/XP/2003 都有这个工具, 在 Windows 98 里面可以选择安装这个工具。
$ o( u$ b8 P0 |6 n# Y
1 b8 G" e$ G" T) {--------------------------------------------------------------------------------
3 b9 l+ n: v) ]. ?6 o# ^1 LBCB 的 WMI 库文件 wbemuuid.lib 由本站提供, 包含在本页下面的程序源码下载里面4 B% @- j  D+ J: I& D9 k. k6 X

9 ~4 ^1 t  o6 u, I2 q6 J--------------------------------------------------------------------------------
1 a0 W# l! r9 }1 H5 U① 初始化 COM 接口:
/ J1 u, O& ]5 }" m0 s   访问 WMI, 必须先初始化 COM 接口, 在程序的一开始调用 CoInitialize(NULL); 初始化, 在结束时调用 CoUninitialize(); 释放资源。7 T$ }1 j. c1 P" o% H( I
  这两个函数在 #include <comdef.h> 里面定义。
& ?' o* ]7 l# t  Z; i5 l4 I3 f: ~$ X$ _* J; S( S
② 获取访问 WMI 权限:& a* K+ e6 N- l) }2 b. ^
  CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_PKT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, 0);0 W* E2 H0 H$ M$ U5 X" ]$ V% Z
  如果这个函数返回 S_OK 获取权限成功, 否则为失败。, m. Z% q) z$ b) `% P( u' z- A* {. L
6 N3 Y9 X" Q+ y
③ 通过 IWbemLocator 和 IWbemServices 这两个 COM 接口访问 WMI, 获取系统信息:
' A0 H* Q, w" o: b7 {   这个函数的参数: lpList 返回信息, wsClass 为要查找的系统信息类, 这些 COM 接口在 #include <wbemidl.h> 里定义。# N. q. k$ C0 C8 T: k7 F% v

  E2 g! g* e% R7 i8 ~' ?void GetWmiInfo(TStrings *lpList, WideString wsClass)( C9 t  P/ u1 ]: n' I- v
{
5 D/ @  ]1 n! \" F  IWbemLocator *pWbemLocator = NULL;- n; Y/ l& j: v) E. ]6 X0 f
  if(CoCreateInstance(CLSID_WbemAdministrativeLocator, NULL, CLSCTX_INPROC_SERVER|CLSCTX_LOCAL_SERVER, IID_IUnknown, (void**)&pWbemLocator) == S_OK)* F* r6 ^( m. c+ l& E* C
  {6 f5 `- b5 v. A5 n, A; j! m
    IWbemServices *pWbemServices = NULL;# n! t6 g; }& K) _
    WideString wsNamespace = (L"root\\cimv2");1 J% d3 E: u+ d) }+ |% ]
    if(pWbemLocator->ConnectServer(wsNamespace, NULL, NULL, NULL, 0, NULL, NULL, &pWbemServices) == S_OK)4 x7 Y2 w0 h/ \) z
     {1 r. ]: E$ d9 O8 j5 a1 l
       IEnumWbemClassObject *pEnumClassObject = NULL;1 Y) x/ p6 L5 A! b
       WideString wsWQL=L"WQL", wsQuery=WideString(L"Select * from ")+wsClass;6 Z9 H% S9 D% t# V  k1 j: C, i
       if(pWbemServices->ExecQuery(wsWQL, wsQuery, WBEM_FLAG_RETURN_IMMEDIATELY,NULL, &pEnumClassObject) == S_OK)! q; R% x2 F* G) c$ y' ~+ [" T
        {
0 p5 z- J. [4 C) D& f: t& T9 e           IWbemClassObject *pClassObject = NULL;
8 ]( P1 m, a  g& S           ULONG uCount = 1, uReturned;
: Q/ ^) m/ d2 a, H1 y9 ~+ z/ e           if(pEnumClassObject->Reset() == S_OK)
9 ]: w. L' i, d  |; U$ q' M            {3 A) k/ ~" M* N: ?4 w# \$ c
             int iEnumIdx = 0;
5 l+ d" p6 ]9 \: T' n              while(pEnumClassObject->Next(WBEM_INFINITE, uCount, &pClassObject, &uReturned) == S_OK)% b1 ?& h7 e  Z# P7 D
              {& F4 t2 C$ E+ g6 G! s* B8 K
                lpList->Add("---------------- ["+IntToStr(iEnumIdx)+"] -----------------");
( z9 f% y% T) ?; q% o
$ Y/ H# u5 n9 X* t                 SAFEARRAY *pvNames = NULL;- e# p5 T6 |7 `: F9 X- h7 T8 C/ C
                if(pClassObject->GetNames(NULL, WBEM_FLAG_ALWAYS | WBEM_MASK_CONDITION_ORIGIN, NULL, &pvNames) == S_OK)( ^7 N1 V; }+ k% z0 r  `
                 {
0 {2 a; ?/ |4 Z) r% d                    long vbl, vbu;' A. o1 i4 A3 W0 L2 c4 t
                   SafeArrayGetLBound(pvNames, 1, &vbl);& G& T, F0 F/ O! H3 e
                   SafeArrayGetUBound(pvNames, 1, &vbu);. q  }: T2 k% \* G
                   for(long idx=vbl; idx<=vbu; idx++)
1 Y* ]+ _! e& ~+ d# t5 N( n                     {
- U  L& V/ p, h9 A/ ^" C                       long aidx = idx;
" O8 L. {1 E# D& Q# X  i3 L                       wchar_t *wsName = 0;8 p" t8 A4 F4 u$ C$ t; \" T; ?" N' B
                      VARIANT vValue;
9 v& |( o! Z9 m, K1 E( ]# R. W* B& ^4 v                       VariantInit(&vValue);& W  N# I7 T6 k2 y( z4 C7 d
                      SafeArrayGetElement(pvNames, &aidx, &wsName);
  ]# u. {) \8 D# P4 B9 a. t0 e/ G/ a- {; X1 q7 [
                      BSTR bs = SysAllocString(wsName);
* z7 |* I% w5 A/ @                       HRESULT hRes = pClassObject->Get(bs, 0, &vValue, NULL, 0);- W2 H+ m8 V! G
                      SysFreeString(bs);
; T" O8 r; l0 X  ~$ c* b' k; n4 l" S
/ k' f* O) U. N0 i9 h                       if(hRes == S_OK)
7 A% C6 J4 K0 o+ I                        {* ~. i" b6 X; l8 W1 N2 X- v
                         AnsiString s;
; |: U; T, L3 V) o* w3 z' e                          Variant v = *(Variant*)&vValue;# K! X: p/ l; b0 ^
                         if(v.IsArray())
3 G8 [- ?  N9 H( C0 l$ x) x                           {/ U0 \1 q& m; N, ^; Q
                            for(int i=v.ArrayLowBound(); i<=v.ArrayHighBound(); i++)( @1 K; S- G$ q6 v/ x' q
                             {
# n$ W( |( u& K5 W4 v, n: Z) o                                Variant a = v.GetElement(i);2 X- k8 C, l$ P+ Q9 L, j
                               if(!s.IsEmpty())
$ t& j' {1 W1 Z& E. j2 B                                  s+=", ";
2 E7 c3 \1 p9 x: T5 B! y                                s+=VarToStr(a);( S% t0 @6 F; b3 B: J  J
                             }3 x" x" B4 n: Z# G5 D; A" t
                          }& _) P5 B: g/ w/ K
                         else
& R2 _* \$ f0 H8 H& p                           {/ H9 a4 |3 \, o/ U; S
                            s = VarToStr(v);# ~" S" R( V0 t
                          }5 ?9 P6 Q( P8 c# F6 `8 T
                         lpList->Add(AnsiString(wsName)+"="+s);
+ a( m: w! |1 H, i' d; B3 K                        }
6 n$ N6 S& v6 R6 O- \. ]4 Z' }: v7 Y4 X
                      VariantClear(&vValue);& b/ j! ]3 D. a6 @, D: |& O; K
                      SysFreeString(wsName);
; w. J$ Q3 B2 V                     }6 i8 A1 e) T% f3 S% C
                 }
4 [3 m5 c( O' _% T) l/ L5 m5 W7 ^/ P                 if(pvNames)SafeArrayDestroy(pvNames);
  X$ ~6 p5 i) ^1 h* ^                 iEnumIdx++;
& ^2 h3 p- \" B( s# M               }
- U# B3 p* p+ k5 r            }
. {/ s  k- G2 h2 M$ B. o           if(pClassObject)pClassObject->Release();* g/ d. B# F( Y0 z
        }
3 s: H( ~9 D6 Q. }  R        if(pEnumClassObject)pEnumClassObject->Release();* O! T6 b8 b% y1 X9 W) Q8 `
     }
' T& @' b* t- `6 w) R% V     if(pWbemServices)pWbemServices->Release();7 l6 ~* o9 w, o$ d* B+ [. m" ^
  }
7 w4 f0 n* E% F% s( u$ a$ d$ k  if(pWbemLocator)pWbemLocator->Release();( C7 I% c1 W0 [& c
}
% J" `$ y: p9 p: u6 Q//---------------------------------------------------------------------------0 `' v* `9 ^' t
8 U3 E, t4 G0 ?. k8 K
// 通过 WIN32_bios 获取 BIOS 信息:4 x+ o1 U( D4 a7 f( P9 y9 m1 i
void __fastcall TForm1::Button1Click(TObject *Sender)/ o8 X' ^1 j! C* F$ G
{5 G) ~  t# T3 D+ k9 I) O: z
   Memo1->Lines->Add("================== [WIN32_bios] =================");
( `8 |5 @5 N4 [% k/ ^& k( S5 u+ Y    GetWmiInfo(Memo1->Lines, "WIN32_bios");' y% @/ \9 d: z9 u* n, ]
   Memo1->Lines->Add("");/ d: K; Z/ [6 i" U" {& O: o
}
4 p* s8 F! u4 }
) k* b5 J  e# ~8 b+ z. T4 l--------------------------------------------------------------------------------
' S9 v& P8 O, r4 }: G: ?7 `
1 a! |. m5 O8 B, ^WMI 可以访问的信息类型有:1 ]7 A! F% B* j) q
  Win32_1394Controller
7 ]1 g' U5 i' U7 G   Win32_BaseBoard! m' C& J$ c. G0 ~. @; }
  Win32_Battery
: j3 r, ?3 ^) t# b/ t   Win32_BIOS
" u9 Y& U6 m* x$ D* K4 _4 Z8 U   Win32_Bus% s8 ^# M0 G6 O( K
  Win32_CacheMemory8 ~6 t$ j% I7 Z- `1 n
  Win32_CDROMDrive3 H, i4 N6 N6 O" I
  Win32_CurrentProbe; _9 m3 y' P9 y2 I! p
  Win32_DesktopMonitor; V) X& B$ k, J
  Win32_DeviceMemoryAddress) R9 l* K; H& r5 G
  Win32_DiskDrive
9 Q; r& Z5 B7 A0 Z   Win32_DisplayConfiguration
- p0 D' l( E3 p! a9 {* T* V   Win32_DisplayControllerConfiguration+ @5 r! t5 p! \9 N( u2 A' \) `
  Win32_DMAChannel
; m2 Q! p( q3 ~+ m   Win32_Fan" q( d2 r7 N- `3 b) v. {+ P
  Win32_FloppyController
5 W5 v9 P, L5 w( ^- F" q' M9 [: {& ]   Win32_FloppyDrive
) ^& }' m; V3 M9 ~8 Q) V' j6 P7 B7 }   Win32_HeatPipe1 ~" L0 G) q/ p. c5 r
  Win32_IDEController; Y8 [2 A8 G  J7 |  m
  Win32_InfraredDevice+ \% y% e% F$ d+ G6 j
  Win32_IRQResource) ~: b, d2 d5 n& ~; ?4 v. }" m
  Win32_Keyboard+ ~/ ^) m/ d* [! }. M& O
  Win32_MemoryArray& _2 W$ h/ S- i  i# w& n6 Q
  Win32_MemoryDevice
$ f' L& O* q; ^0 d" Q6 w   Win32_MotherboardDevice0 M4 y5 p$ W( C0 Q  ]
  Win32_NetworkAdapter
. D7 v3 C8 m5 g# T$ e" M$ k5 {) W   Win32_NetworkAdapterConfiguration
) _/ h: e8 b$ P% P" Q9 d; @( ?   Win32_OnBoardDevice
8 y  G8 t6 U. X* U8 s( |   Win32_ParallelPort) i. M8 m, U# [6 x
  Win32_PCMCIAController$ j/ Y' [+ t  V) G* H% n1 v
  Win32_PhysicalMemory/ q2 m# G: y5 U
  Win32_PhysicalMemoryArray2 v2 p0 }5 Z) ]0 D: j- E$ ~
  Win32_PnPEntity
+ b( F' x3 V& s6 b3 _   Win32_PointingDevice
8 B, A$ _' g+ G' g! K9 T5 R# X: @   Win32_PortableBattery+ Y1 E3 o1 F; D9 }0 ?. M3 _) J
  Win32_PortConnector0 O$ X% d) d9 O) r7 ^; A; A
  Win32_PortResource9 x5 D2 r5 e$ X7 N& R
  Win32_POTSModem
- a. b  B2 N5 f' m. n   Win32_PowerManagementEvent8 ^3 ]7 e$ W) S4 z) I
  Win32_Printer
5 u3 @# g7 ^3 ~% g! V% l   Win32_PrinterConfiguration
/ P9 N* j7 m  l6 M* }) ]: h   Win32_PrintJob
) W& ^5 V! d* ~+ b5 J   Win32_Processor
- p* x' p2 V& {5 r6 I  M   Win32_Refrigeration7 i6 M3 N: l" W2 f: K& q
  Win32_SerialPort: B% A$ e$ q" d5 q* w; M+ s1 T
  Win32_SerialPortConfiguration; |, s3 L; U  o+ H
  Win32_SMBIOSMemory, x  k: B; s1 ]) V. S8 k
  Win32_SoundDevice# k) |; S; z! d" \/ |. q0 J
  Win32_SystemEnclosure
$ e+ O/ p  C5 H4 ]3 \/ t1 g   Win32_SystemMemoryResource
; `# x5 i" h' H) m, Q: |: R   Win32_SystemSlot5 d+ v! C* }  u) A: {
  Win32_TapeDrive
/ i/ m7 @. ^( q& V" s: T   Win32_TemperatureProbe. m5 {. }: X. X7 `" M. A7 P
  Win32_UninterruptiblePowerSupply
# o& F0 L# P: N   Win32_USBController' _( ?% a4 s$ @. F6 k8 O
  Win32_VideoConfiguration
" i, a; ]* g0 V* D7 E" F; V3 b* v   Win32_VideoController
* Y) y4 g) Q# g( g8 n   Win32_VoltageProbe
: d. n8 X- _1 h3 z+ x7 H* A. i5 y1 o$ [+ p7 n" Y+ ~5 R0 N
以上类型(字符串值)通过前面写的函数 GetWmiInfo 可以得到相应的信息, 例如 GetWmiInfo(Memo1->Lines, "WIN32_bios");
您需要登录后才可以回帖 登录 | 注册

本版积分规则

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

GMT+8, 2026-2-7 13:34 , Processed in 0.017606 second(s), 14 queries .

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

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