Estoy tratando de escribir una aplicación de Windows que me da de nuevo de todas las subclaves y valores dada una cierta clave. He escrito el código que aparece a trabajar como subclaves de la clave, pero no funciona correctamente en la enumeración de los valores; con éxito enumera las subclaves sin valores y devuelve los resultados en una especie de pestañas árbol disposición. Sin embargo, cuando la enumeración de los valores, el programa devuelve un valor aleatorio para cada valor presente (el mismo valor aleatorio cada vez), y a continuación, se bloquea después con un error de depuración.

Es la intención de salida es básicamente:

(1) KEY
    (1) SUBKEY
    (1) SUBKEYWITHINSUBKEY
        Code: value1data
        Code: value2data
        Code: value3data
(2) SUBKEY
    (1) SUBKEYWITHINSUBKEY
(3) SUBKEY

…y así sucesivamente.

La salida I lugar es algo así como:

(1) KEY
(1) SUBKEY
    (1) SUBKEYWITHINSUBKEY
        Code: someValue
        Code: someValue
        Code: someValue

(…y después del accidente)

Esto es seguido con el siguiente error:

«Error De Depuración! «Run-Time Error de Comprobación de #2 – Pila alrededor de la variable ‘valNameLen’ fue dañado.»

El código es un poco desordenado en la actualidad (soy un API de Windows novato), pero si alguien podría enseñarme lo que estoy haciendo mal, o criticar mi estilo de codificación en todo lo que siento en forma, eso sería genial.

Gracias!

-R

/*
Windows Registry Subkey Enumeration Example
Based on example found at code-blue.org
*/
#include <windows.h>
#include <stdio.h>
void EnumerateValues(HKEY hKey, DWORD numValues)
{
DWORD dwIndex = 0;
LPSTR valueName = new CHAR[64];
DWORD valNameLen;
DWORD dataType;
DWORD data;
DWORD dataSize;
for (int i = 0; i < numValues; i++)
{
RegEnumValue(hKey,
dwIndex,
valueName,
&valNameLen,
NULL,
&dataType,
(BYTE*)&data,
&dataSize);
dwIndex++;
printf("Code: 0x%08X\n", data);
}
}
void EnumerateSubKeys(HKEY RootKey, char* subKey, unsigned int tabs = 0) 
{
HKEY hKey;
DWORD cSubKeys;        //Used to store the number of Subkeys
DWORD maxSubkeyLen;    //Longest Subkey name length
DWORD cValues;        //Used to store the number of Subkeys
DWORD maxValueLen;    //Longest Subkey name length
DWORD retCode;        //Return values of calls
RegOpenKeyEx(RootKey, subKey, 0, KEY_ALL_ACCESS, &hKey);
RegQueryInfoKey(hKey,            //key handle
NULL,            //buffer for class name
NULL,            //size of class string
NULL,            //reserved
&cSubKeys,        //number of subkeys
&maxSubkeyLen,    //longest subkey length
NULL,            //longest class string 
&cValues,        //number of values for this key 
&maxValueLen,    //longest value name 
NULL,            //longest value data 
NULL,            //security descriptor 
NULL);            //last write time
if(cSubKeys>0)
{
char currentSubkey[MAX_PATH];
for(int i=0;i < cSubKeys;i++){
DWORD currentSubLen=MAX_PATH;
retCode=RegEnumKeyEx(hKey,    //Handle to an open/predefined key
i,                //Index of the subkey to retrieve.
currentSubkey,            //buffer to receives the name of the subkey
&currentSubLen,            //size of that buffer
NULL,                //Reserved
NULL,                //buffer for class string 
NULL,                //size of that buffer
NULL);                //last write time
if(retCode==ERROR_SUCCESS)
{
for (int i = 0; i < tabs; i++)
printf("\t");
printf("(%d) %s\n", i+1, currentSubkey);
char* subKeyPath = new char[currentSubLen + strlen(subKey)];
sprintf(subKeyPath, "%s\\%s", subKey, currentSubkey);
EnumerateSubKeys(RootKey, subKeyPath, (tabs + 1));
}
}
}
else
{
EnumerateValues(hKey, cValues);
}
RegCloseKey(hKey); 
}
int main()
{
EnumerateSubKeys(HKEY_CURRENT_USER,"SOFTWARE\\MyKeyToSearchIn");
return 0;
}

2 Comentarios

  1. 2

    La enumeración de las claves de esta manera es una exageración. Esto sería sólo una pérdida de los recursos del sistema, la memoria, la pila de llamadas y poner presión sobre registro sub-sistema. No lo hagas a menos que sea necesario.

    Vas a tener «registro de búsqueda» en su aplicación? Si, sí, por enumerar sólo cuando el usuario así lo exija. O, si usted es el desarrollo de «Registro de Visor/Editor», ¿ expandir y abrir sub-claves sólo cuando sea necesario.

    Si es absolutamente necesario para recuperar y almacenar todas las claves/valores, puede hacer uso de múltiples hilos para enumerar las claves. El número de hilos que inicialmente podría ser el HKEY-grandes teclas y, a continuación, usted puede tener más hilos, dependiendo del número de claves de sub y tiempo de ejecución de la heurística de realizar mientras se enumeran las teclas.

    La recursividad puede o no puede ser una buena aproximación para «recursivo-enumeración» de la sub-claves – usted debe mantener el número de argumentos a la implementación recursiva de mínimos poner los argumentos en uno struct o exponerlos en clase. También puede utilizar std::stack para el mismo.

    • He reescrito el código desde cero y hace todo lo que necesites. El algoritmo debe estar bien yo creo – el punto entero de la utilidad es para obtener esta información y algunas otras cosas y las claves de búsqueda son específicos y no contienen todos los que mucho subclaves o valores. Gracias por los consejos!
  2. 2

    Parece que te están llamando RegEnumValue() sin establecer la lpcchValueName parámetro a un valor apropiado. Este parámetro es un parámetro [in] así como un parámetro [out]. Intente esto:

    for (int i = 0; i < numValues; i++)
     {
    DWORD valNameLen = 64; //added this line to match valueName buffer size
      RegEnumValue(hKey,
         dwIndex,
         valueName,
         &valNameLen,
         NULL,
         &dataType,
         (BYTE*)&data,
         &dataSize);

    Documentación para RegEnumValue() : http://msdn.microsoft.com/en-us/library/ms724865(v=vs 85).aspx

Dejar respuesta

Please enter your comment!
Please enter your name here