Программная регистрация счетчика производительности в реестре

Я пытаюсь зарегистрировать счетчик производительности, и часть этого процесса включает добавление некоторых текстовых описаний к определенному разделу реестра. Для английского языка этот ключ - HKEY_LOCAL_MACHINE \ SOFTWARE \ Microsoft \ Windows NT \ CurrentVersion \ Perflib \ 009, который также известен как HKEY_PERFORMANCE_TEXT. Там есть пара значений (Counter, Help), которые имеют данные REG_MULTI_SZ, и мне нужно изменить их для достижения моей цели.

Официальный способ сделать это с помощьюинструмент под названием lodctr вместе с файлами .h и .ini, Также естьфункция для этого программно, но я понимаю, что это просто оболочка для вызова программы lodctr. Перспектива сохранения, распространения и хранения синхронизированных трех отдельных файлов была несколько обременительной, поэтому ранее я писал для этого код, и он прекрасно работал в Windows XP (и, возможно, в Vista, хотя я точно не помню).

Сейчас я пытаюсь использовать тот же код в Windows 7, и он не работает. Проблема в том, что всякий раз, когда я пытаюсь установить значения реестра, происходит сбой с ERROR_BADKEY; даже regedit не может изменить значения, так что это не проблема с моим кодом. Я запустил Process Monitor и заметил, что на уровне драйвера не было никаких действий, поэтому кажется, что этот доступ должен быть заблокирован в коде пользовательского режима (например, advapi32.dll или где-либо еще). Я понимаю, почему Microsoft пытается запретить людям делать это, поскольку это очень легко испортить, и это приведет к повреждению всей коллекции счетчиков производительности на машине.

Я собираюсь отладить lodctr и посмотреть, что за волшебство чисто из любопытства, но мне интересно, сталкивался ли кто-нибудь с этим раньше? Есть ли альтернативы, кроме утилиты lodctr? Возможно, вызов API реестра NT напрямую? Я действительно предпочел бы избежать хлопот метода lodctr, если это возможно.

Минимальный пример для воспроизведения проблемы:

HKEY hKey = NULL;
LONG nResult = RegOpenKeyEx(HKEY_LOCAL_MACHINE, _T("SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Perflib\\009"), 0, KEY_ALL_ACCESS, &hKey);
if(ERROR_SUCCESS == nResult)
{
    LPCTSTR lpData = _T("bar");
    DWORD cbData = (_tcsclen(lpData) + 1) * sizeof(TCHAR);
    nResult = RegSetValueEx(hKey, _T("foo"), 0, REG_SZ, (const BYTE*)lpData, cbData);
    // here nResult == ERROR_BADKEY
    RegCloseKey(hKey);
    hKey = NULL;
}

РЕДАКТИРОВАТЬ 1:

Я потратил около часа или около того, пытаясь отладить официальные API, и не мог понять это, поэтому я попробовал еще немного Google. Через некоторое время я наткнулсяэта статья KB который объясняет поведение RegSetValueEx. Поскольку в нем упоминалось изменение системных файлов, я подумал, что, возможно, именно эти данные реестра поддерживаются сопоставленным файлом. Потом наткнулсядругая статья KB это упоминает Perfc009.dat и Perfh009.dat в папке system32. Открыл их в шестнадцатеричном редакторе и, конечно же, это необработанные данные REG_MULTI_SZ, которые я пытаюсь изменить. Теперь, когда я знаю, что, может быть, я смогу еще раз взглянуть и разобраться, хотя сейчас мне это надоело.

Ответы на вопрос(1)

Ваш ответ на вопрос