Проблема с реестром - удаление ключа / значений с помощью C ++ - PullRequest
1 голос
/ 27 августа 2010

Кажется, что следующий фрагмент кода выполняется ненадежно, и по истечении неопределенного времени произойдет сбой с кодом ошибки 234 при функции RegEnumValue.

Я не написал этот код, я просто пытаюсь его отладить. Я знаю, что есть проблема с выполнением RegEnumValue и последующим удалением ключей в цикле while.

Сначала я пытаюсь выяснить, почему он генерирует эту ошибку 234 в кажущихся случайными точках, как, например, никогда после последовательного числа итераций цикла или чего-то подобного.

Из того, что я видел, он не заполняет свой буфер имен, но этот буфер ни в коем случае не слишком мал для своей цели, поэтому я не понимаю, как он мог потерпеть неудачу ??

Может, кто-нибудь посоветует, как избавиться от этой ошибки 234, выдаваемой функцией RegEnumValue?

    HKEY key;
    DWORD dw;
    int idx;
    char name[8192];
    DWORD namesize=4096;
    std::string m_path = "SOFTWARE\\Company\\Server 4.0";

    if (RegOpenKeyEx(HKEY_LOCAL_MACHINE,m_path.c_str(),0,KEY_ALL_ACCESS,&key) == ERROR_SUCCESS)
    {
        bool error=false;
        idx=0;
        long result;
        long delresult;
        while (true)
        {
            result = RegEnumValue(key,idx,(char*)name,&namesize,NULL,NULL,NULL,NULL);

            if (result == ERROR_SUCCESS && !error){

                delresult = RegDeleteValue(key,name);
                if (delresult != ERROR_SUCCESS)
                    error = true;

                idx++;
            }
            else
            {
                break;
            }
        }
        RegCloseKey(key);
    }

Ответы [ 3 ]

3 голосов
/ 27 августа 2010

В вашем коде есть некоторые ошибки:

  1. 4-й параметр RegEnumValue (namesize) является параметром in-out.Таким образом, вы должны сбросить namesize на sizeof(name)/sizeof(name[0]) (в случае использования char type это просто sizeof(name)) внутри while loop перед каждым вызовом из RegEnumValue .Это основная ошибка в вашей программе.
  2. Если вы не хотите, чтобы ошибка ERROR_MORE_DATA была в любое время, когда у вас есть буфер, содержащий 32 767 символов.Это максимальный размер имени значения regitry (см. Документацию RegEnumValue ).
  3. Использование KEY_ALL_ACCESS в RegOpenKeyEx нецелесообразно.Я рекомендую вам изменить его на KEY_QUERY_VALUE | KEY_SET_VALUE.Это не настоящая ошибка, но может зависеть от вашей среды.
  4. Лучше использовать UNICODE-версию всех этих функций, чтобы немного ускорить код.

ОБНОВЛЕНО : Небольшой комментарий об использовании версии UNICODE.Стажер Windows работает с символами UNICODE.Таким образом, использование не-Unicode версии RegEnumValue si медленнее, поскольку при вызове evry будет выделен новый блок памяти UICODE, который будет преобразован в ANSI / многобайтовый.Более того, если у вас есть имя значения, написанное на языке, который не может быть преобразован в вашей кодовой странице Windows ANSI (китайский, японский и т. Д.), А некоторые символы будут заменены на «?»(см. WC_DEFAULTCHAR флаг WideCharToMultiByte ), тогда может случиться так, что функция RegDeleteValue завершится с ошибкой с кодом ошибки типа «значение с именем не существует».

1 голос
/ 05 июля 2012

просто измените значение вашего четвертого параметра, то есть nameses с 4096 до 8192. Всегда следите за тем, чтобы оно всегда было равно размеру буфера.

0 голосов
/ 27 августа 2010

Ответ находится внизу этой страницы: http://msdn.microsoft.com/en-us/library/ms724865(VS.85).aspx

Пожалуйста, прочитайте ответ "ERROR_MORE_DATA: lpData слишком мала или lpValueName слишком мала?"вопрос.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...