ACUConfig с исправленной ошибкой вывода логов
ACUConfig всегда раздражал своими логами, в которых постоянно фигурировали "процентики": %1, %2, %3, %4 и т.д. Например, самый популярный вариант:
2012-06-06 10:56:37: Thread:5500(ERROR) : ACU Configurator, Category: Exit Source: Src\ActivatorMain.cpp : wmain Line: 957: ***********Exit with code 33 - Failed to configure this Intel(R) AMT device. Details: Intel(R) AMT %1 failed. Failed to connect to the Intel(R) AMT device (possible reasons - the system does not have Intel(R) AMT or is not responding; user access to it is denied).
Оказалось, что разработчики изначально предусмотревшие возможность перевода на другие языки ошиблись, в результате чего для английской дефолтной страницы (т.е. english-Windows) всё нормально (т.е. у них в логах не "%1", а правильная строка). Чтобы исправить эту ошибку нужно в файле из Intel AMT SDK 7.1.5.19 (последняя доступная версия с исходниками на данный момент):
\7.1.5.19\IntelAMTSCS\Source_Kit\Source_Code\ConfigurationCode\Configuration_Sources\Messages\Src\MessageTable.cpp
в строчках 88, 94-95,124-125 сделать следующие изменения (--- убрать, +++ добавить):
/****************************************************************
Copyright © 2003-2011, Intel Corporation. All rights reserved.
*****************************************************************/
#include "MessageTable.h"
#include "StringUtils.h"
#include <iostream>
#include <string>
#include <sstream>
using namespace std;
using namespace MessageTable;
HMODULE _hModule;
#ifdef _MANAGED
#pragma managed(push, off)
#endif
#define DEFAULT_LANG 0x409
BOOL APIENTRY DllMain( HANDLE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
_hModule = (HMODULE)hModule;
return TRUE;
}
#ifdef _MANAGED
#pragma managed(pop)
#endif
wstring MessageTable::GetSCSMessageEx( unsigned int errCode,unsigned int paramNumber,...)
{
va_list argList;
va_start( argList, paramNumber );
wstring message;
GetSCSMessage(errCode,message,paramNumber,argList);
va_end( argList );
return message;
}
wstring MessageTable::GetSCSMessage(unsigned int errCode, unsigned int paramNumber,va_list argList)
{
wstring message;
GetSCSMessage(errCode,message,paramNumber,argList);
return message;
}
bool MessageTable::GetSCSMessage(unsigned int errCode, wstring& message,unsigned int paramNumber, va_list argList)
{
HLOCAL msg;
DWORD ret;
LANGID lang = GetUserDefaultLangID();
try
{
#ifdef _DEBUG
#ifdef RCS
const TCHAR* dll = L"RCSServerD.exe";
#else // RCS
const TCHAR* dll = L"ACUD.dll";
#endif // RCS
#else //_DEBUG
#ifdef RCS
const TCHAR* dll = L"RCSServer.exe";
#else // RCS
const TCHAR* dll = L"ACU.dll";
#endif // RCS
#endif // _DEBUG
_hModule = GetModuleHandle(dll);
ret =::FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_HMODULE|FORMAT_MESSAGE_IGNORE_INSERTS,
_hModule,
errCode,
lang,
(LPTSTR) &msg,
0,
&argList );
// if there is not string for the OS language format get English(US) string
if ((0 == ret)&& (DEFAULT_LANG !=lang))
{
+++ lang = DEFAULT_LANG;
ret =::FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_HMODULE|FORMAT_MESSAGE_IGNORE_INSERTS,
_hModule,
errCode,
--- DEFAULT_LANG,
+++ lang,
(LPTSTR) &msg,
0,
&argList );
}
if ( 0 != ret )
{
unsigned int count = 0 ;
message = StrUtl::cleanNonPrintable((LPTSTR)msg);
if (paramNumber>0)
{
wstring::const_iterator iter;
for (iter = message.begin();iter!=message.end();iter++)
{
wchar_t xx = *iter;
if (xx ==L'%')
count++;
}
}
if ((count == paramNumber) && (count >0))
{
::LocalFree( msg );
ret =::FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_HMODULE,
_hModule,
errCode,
--- GetUserDefaultLangID(),
+++ lang,
(LPTSTR) &msg,
0,
&argList );
if ( 0 != ret )
{
message = StrUtl::cleanNonPrintable((LPTSTR)msg);
}
}
else if (count != paramNumber)
{
wstringstream tmp;
wstring messNumber;
tmp << (errCode & 0xFFFF);
tmp >> messNumber;
message = L"SCS Code: " + message +L"("+ messNumber + L"). Bad Format String. ";
}
}
else
{
wstringstream tmp;
tmp << (errCode & 0xFFFF);
message = tmp.str();
}
::LocalFree( msg );
}
catch (...)
{
return false;
}
return (0 != ret);
}
Собранный с такими изменениями ACUConfig можно использовать на любой Windows и логи будут полными.

Comments
Реальный пример работы.
Реальный пример работы. Получаем ошибку (с оригинальным ACUConfig7):
Что произошло понять крайне сложно. Меняем на пропатченный:
Совсем другое дело, всё становится ясно - UserConsent выставлен в Enabled, при этом стоит значение для False (потому 0).
Add new comment