Intereting Posts
Почему я получаю странные результаты при чтении массива целых чисел из сокета TCP? sizeof single struct member в C Вызовите функцию без аргумента, хотя для этого нужен один Пользовательский распределитель памяти / менеджер в C? какой подход? Как разобрать HTTP-заголовки с libcurl? Мы теряем данные в буфере после realloc’ing? Почему для sqlite3_open мы используем двойной указатель **, а для sqlite3_prepare мы используем указатель * Malloc внутри вызова функции, кажется, освобождается по возвращении? Как изменить компилятор VS? Промывка streamов сокетов в программировании сокета C Максимальное количество файлов, которые можно открыть с помощью c “fopen” в linux Обрабатывать память при чтении длинных строк из файла в C Невозможно заблокировать чтение из именованного канала (FIFO) в Linux В чем разница между нулевым указателем и указателем void? Бит четности для нечетного числа бит

Как получить данные из WMI с помощью приложения C?

У меня есть приложение с чистым C, которое выдает вызовы IOCTL на мой драйвер адаптера и отображает информацию, однако это скомпилировано с помощью Visual Developer Studio 5 (не управляемый код) … Мне нужно получить некоторую информацию, однако, из моего адаптера с использованием WMI .. .. Мои усилия по поиску в Google показывают, что мне нужно будет написать приложение C ++ с помощью COM для достижения любой формы связи с wMI или C # с .NET-приложением. A) Это действительно так? НЕТ работать для моего приложения C? б) Если выше верно, каковы минимальные изменения уровня, которые мне потребуются для настройки моего проекта / wp / workspace?

Благодаря Som

Вы можете вызывать COM из C. Синтаксис несколько менее дружелюбен, чем у C ++, но он работает. COM первоначально был разработан для работы с C или C ++, а встроенная поддержка языка C включена в файлы заголовков COM и WMI. Это будет долго, но … ваша программа будет отвечать за выделение всех необходимых объектов, проверку условий ошибок от каждого COM-вызова и освобождение созданных им объектов.

При использовании документации, написанной с учетом C ++, конвертируйте COM-вызовы формы:

pSomething->Method(arg1, ...); // C++ 

чтобы:

 pSomething->lpVtbl->Method(pSomething, arg1, ...); // C 

Ниже приведен самый короткий fragment кода C, который я мог бы получить, чтобы на самом деле вытащить некоторую информацию из WMI. В случае успеха он должен перечислить процессоры на вашем компьютере, а также их тактовую частоту в МГц. Программа заботится об утилизации ресурсов, которые она выделяет, но она не проверяет ошибки вообще (вы должны смотреть на эти значения hr перед продолжением каждого шага).

Это визуальная студия 2008 «Консольное приложение Win32» с основным файлом, переименованным в расширение .c, и дополнительные файлы stdafx удалены. Чтобы связать программу, обязательно включите wbemuuid.lib в свойства проекта в разделе «Свойства конфигурации» / «Linker / Input / Additional Dependencies». Он успешно работал в моей папке Vista.

 #define _WIN32_WINNT 0x0400 #define _WIN32_DCOM #include  #include  #include  #include  void _tmain(int argc, _TCHAR* argv[]) { // result code from COM calls HRESULT hr = 0; // COM interface pointers IWbemLocator *locator = NULL; IWbemServices *services = NULL; IEnumWbemClassObject *results = NULL; // BSTR strings we'll use (http://msdn.microsoft.com/en-us/library/ms221069.aspx) BSTR resource = SysAllocString(L"ROOT\\CIMV2"); BSTR language = SysAllocString(L"WQL"); BSTR query = SysAllocString(L"SELECT * FROM Win32_Processor"); // initialize COM hr = CoInitializeEx(0, COINIT_MULTITHREADED); hr = CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_DEFAULT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, NULL); // connect to WMI hr = CoCreateInstance(&CLSID_WbemLocator, 0, CLSCTX_INPROC_SERVER, &IID_IWbemLocator, (LPVOID *) &locator); hr = locator->lpVtbl->ConnectServer(locator, resource, NULL, NULL, NULL, 0, NULL, NULL, &services); // issue a WMI query hr = services->lpVtbl->ExecQuery(services, language, query, WBEM_FLAG_BIDIRECTIONAL, NULL, &results); // list the query results if (results != NULL) { IWbemClassObject *result = NULL; ULONG returnedCount = 0; // enumerate the retrieved objects while((hr = results->lpVtbl->Next(results, WBEM_INFINITE, 1, &result, &returnedCount)) == S_OK) { VARIANT name; VARIANT speed; // obtain the desired properties of the next result and print them out hr = result->lpVtbl->Get(result, L"Name", 0, &name, 0, 0); hr = result->lpVtbl->Get(result, L"MaxClockSpeed", 0, &speed, 0, 0); wprintf(L"%s, %dMHz\r\n", name.bstrVal, speed.intVal); // release the current result object result->lpVtbl->Release(result); } } // release WMI COM interfaces results->lpVtbl->Release(results); services->lpVtbl->Release(services); locator->lpVtbl->Release(locator); // unwind everything else we've allocated CoUninitialize(); SysFreeString(query); SysFreeString(language); SysFreeString(resource); } конечные #define _WIN32_WINNT 0x0400 #define _WIN32_DCOM #include  #include  #include  #include  void _tmain(int argc, _TCHAR* argv[]) { // result code from COM calls HRESULT hr = 0; // COM interface pointers IWbemLocator *locator = NULL; IWbemServices *services = NULL; IEnumWbemClassObject *results = NULL; // BSTR strings we'll use (http://msdn.microsoft.com/en-us/library/ms221069.aspx) BSTR resource = SysAllocString(L"ROOT\\CIMV2"); BSTR language = SysAllocString(L"WQL"); BSTR query = SysAllocString(L"SELECT * FROM Win32_Processor"); // initialize COM hr = CoInitializeEx(0, COINIT_MULTITHREADED); hr = CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_DEFAULT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, NULL); // connect to WMI hr = CoCreateInstance(&CLSID_WbemLocator, 0, CLSCTX_INPROC_SERVER, &IID_IWbemLocator, (LPVOID *) &locator); hr = locator->lpVtbl->ConnectServer(locator, resource, NULL, NULL, NULL, 0, NULL, NULL, &services); // issue a WMI query hr = services->lpVtbl->ExecQuery(services, language, query, WBEM_FLAG_BIDIRECTIONAL, NULL, &results); // list the query results if (results != NULL) { IWbemClassObject *result = NULL; ULONG returnedCount = 0; // enumerate the retrieved objects while((hr = results->lpVtbl->Next(results, WBEM_INFINITE, 1, &result, &returnedCount)) == S_OK) { VARIANT name; VARIANT speed; // obtain the desired properties of the next result and print them out hr = result->lpVtbl->Get(result, L"Name", 0, &name, 0, 0); hr = result->lpVtbl->Get(result, L"MaxClockSpeed", 0, &speed, 0, 0); wprintf(L"%s, %dMHz\r\n", name.bstrVal, speed.intVal); // release the current result object result->lpVtbl->Release(result); } } // release WMI COM interfaces results->lpVtbl->Release(results); services->lpVtbl->Release(services); locator->lpVtbl->Release(locator); // unwind everything else we've allocated CoUninitialize(); SysFreeString(query); SysFreeString(language); SysFreeString(resource); } 

Другой вариант, если вы хотите сохранить влияние на существующее существующее приложение C, – это написать DLL, которая внутренне может использовать classы оболочки C ++ и COM для запроса необходимой информации WMI.

Эта DLL может обеспечить простой интерфейс C для адаптации к вашему приложению. То, как я поеду.