您的位置:首页 > 其它

【WMI-2】使用WMI获取系统信息过程

2008-11-26 11:25 507 查看
我们以获取本机系统为例,获取系统信息的过程如下:
1)初始化COM库
        由于用C++编写WMI应用是基于COM技术的,所以必须初始化COM库,这时调用函数CoInitializeEx用于初始化COM库。


    HRESULT hres;


    hres =  CoInitializeEx(0, COINIT_MULTITHREADED); 


    if (FAILED(hres))




    ...{


        cout << "Failed to initialize COM library. Error code = 0x" 


            << hex << hres << endl;


        return 1;                  // Program has failed.


    }

2)初始化COM库安全级别
        调用函数CoInitializeSecurity用于初始化COM安全级别。


    hres =  CoInitializeSecurity(


        NULL, 


        -1,                          // COM authentication


        NULL,                        // Authentication services


        NULL,                        // Reserved


        RPC_C_AUTHN_LEVEL_DEFAULT,   // Default authentication 


        RPC_C_IMP_LEVEL_IMPERSONATE, // Default Impersonation  


        NULL,                        // Authentication info


        EOAC_NONE,                   // Additional capabilities 


        NULL                         // Reserved


        );




    if (FAILED(hres))




    ...{


        cout << "Failed to initialize security. Error code = 0x" 


            << hex << hres << endl;


        CoUninitialize();


        return 1;                    // Program has failed.


    }

3)连接到WMI命名空间
        通过调用CoCreateInstance初始化WMI的定位器(IWbemLocator类型的实例)。


    hres = CoCreateInstance(


        CLSID_WbemLocator,             


        0, 


        CLSCTX_INPROC_SERVER, 


        IID_IWbemLocator, (LPVOID *) &pLoc);




    if (FAILED(hres))




    ...{


        cout << "Failed to create IWbemLocator object."


            << " Err code = 0x"


            << hex << hres << endl;


        CoUninitialize();


        return 1;                 // Program has failed.


    }

4)创建WMI服务
        调用IWbemLocator::ConnectServer方法,通过这个定位器连接到WMI的命名空间,通过把一个IWbemServices的实例以参数形式传递给ConnectServer方法,就会创建这个服务。如我们需要一些BIOS信息,那么需要使用的WMI提供程序是Win32_BIOS,则需要连接到ROOT//CIMV2命名空间中。


    IWbemServices *pSvc = NULL;


    hres = pLoc->ConnectServer(


        _bstr_t(L"ROOT/CIMV2"), // Object path of WMI namespace


        NULL,                    // User name. NULL = current user


        NULL,                    // User password. NULL = current


        0,                       // Locale. NULL indicates current


        NULL,                    // Security flags.


        0,                       // Authority (e.g. Kerberos)


        0,                       // Context object 


        &pSvc                    // pointer to IWbemServices proxy


        );




    if (FAILED(hres))




    ...{


        cout << "Could not connect. Error code = 0x" 


            << hex << hres << endl;


        pLoc->Release();     


        CoUninitialize();


        return 1;                // Program has failed.


    }


5)设置WMI服务的安全级别
        根据上一步得到的服务,设置相应的服务安全级别。通常来说,如果我们没有设置适当的安全属性,COM安全方案不允许一个进程去访问另一个进程,因此如果我们要访问一个外部进程的对象,那么我们应该设置适当的IWbemServices的安全级别。


hres = CoSetProxyBlanket(


        pSvc,                        // Indicates the proxy to set


        RPC_C_AUTHN_WINNT,           // RPC_C_AUTHN_xxx


        RPC_C_AUTHZ_NONE,            // RPC_C_AUTHZ_xxx


        NULL,                        // Server principal name 


        RPC_C_AUTHN_LEVEL_CALL,      // RPC_C_AUTHN_LEVEL_xxx 


        RPC_C_IMP_LEVEL_IMPERSONATE, // RPC_C_IMP_LEVEL_xxx


        NULL,                        // client identity


        EOAC_NONE                    // proxy capabilities 


        );




    if (FAILED(hres))




    ...{


        cout << "Could not set proxy blanket. Error code = 0x" 


            << hex << hres << endl;


        pSvc->Release();


        pLoc->Release();     


        CoUninitialize();


        return 1;               // Program has failed.


    }6)使用WMI服务
        使用之前得到的服务,可以进行一些操作,如查询、调用方法和其他一些操作。之后详细介绍
7)释放资源,关闭服务与连接,关闭COM库
        在用完资源后,释放资源,关闭连接,关闭COM库等一些善后操作。


    //可能在第六步还申请了其他资源,也要释放掉


    pSvc->Release();


    pLoc->Release();


    pEnumerator->Release();


    pclsObj->Release();


    CoUninitialize();
如何使用WMI服务
        前五步是申请服务,那么如何使用WMI提供的服务呢?
        像优化大师或超级兔子那样,主要的操作是查询!即从Windows提供的WMI Provider中查询到我们想要的信息,比如多种多样的硬件/软件信息;有的时候,信息是动态的,或者某种元素的状态是可设置的,那就用到了调用方法;再或者,我们可以自己做一个提供程序,收集我们关心的信息,然后提供给用户......
        WMI允许我们做的操作很多,查询同样信息的方法和途径也很多,包括同步、异步、半同步等。以后的几篇文章,我将blog下使用WMI服务的几种常用方式。也许,在学会了这种那种技术后,我们也能写出像优化大师或超级兔子一样的优秀软件。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  c 优化 windows server blog null