Compartir a través de


Usar el depurador de kernel para buscar una pérdida de memoria Kernel-Mode

El depurador de kernel determina la ubicación precisa de una fuga de memoria en modo kernel.

Habilitación del etiquetado de grupos

Primero debe usar GFlags para habilitar el etiquetado de grupos. GFlags se incluye en Herramientas de depuración para Windows. Inicie GFlags, elija la pestaña Registro del sistema , active la casilla Habilitar etiquetado de grupos y, a continuación, seleccione Aplicar. Debe reiniciar Windows para que esta configuración surta efecto.

En Windows Server 2003 y versiones posteriores de Windows, el etiquetado de grupos siempre está habilitado.

Determinar la etiqueta de grupo de la fuga

Para determinar qué etiqueta de grupo está asociada a la fuga, normalmente es más fácil usar la herramienta PoolMon para este paso. Para más información, consulte Uso de PoolMon para buscar Kernel-Mode fugas de memoria.

Como alternativa, puede usar el depurador de kernel para buscar etiquetas asociadas a asignaciones de grupos grandes. Para ello, siga este procedimiento:

  1. Vuelva a cargar todos los módulos mediante el comando .reload (Módulo de recarga).

  2. Use la extensión !poolused . Incluya la marca "4" para ordenar la salida por uso de memoria paginada:

    kd> !poolused 4 
    Sorting by Paged Pool Consumed
    
    Pool Used:
                NonPaged            Paged     
    Tag    Allocs     Used    Allocs     Used 
    Abc         0        0     36405 33930272 
    Tron        0        0       552  7863232 
    IoN7        0        0     10939   998432 
    Gla5        1      128      2222   924352 
    Ggb         0        0        22   828384 
    
  3. Determine qué etiqueta de grupo está asociada al mayor uso de memoria. En este ejemplo, el controlador que usa la etiqueta "Abc" usa la mayoría de memoria,casi 34 MB. Por lo tanto, es más probable que la pérdida de memoria esté en este controlador.

Búsqueda de la fuga

Después de determinar la etiqueta de grupo asociada a la fuga, siga este procedimiento para localizar la propia fuga:

  1. Use el comando ed (Enter Values) para modificar el valor de la variable global del sistema PoolHitTag. Esta variable global hace que el depurador interrumpa cada vez que se usa una etiqueta de grupo que coincida con su valor.

  2. Establezca PoolHitTag igual a la etiqueta que sospecha que es el origen de la fuga de memoria. El nombre del módulo "nt" debe especificarse para una resolución de símbolos más rápida. El valor de etiqueta debe especificarse en formato little-endian (es decir, hacia atrás). Dado que las etiquetas de grupo siempre son cuatro caracteres, esta etiqueta es realmente A-b-c-space, no solo A-b-c. Por lo tanto, use el siguiente comando:

    kd> ed nt!poolhittag ' cbA' 
    
  3. Para comprobar el valor actual de PoolHitTag, use el comando db (Memoria para mostrar):

    kd> db nt!poolhittag L4 
    820f2ba4  41 62 63 20           Abc  
    
  4. El depurador se interrumpirá cada vez que el grupo se asigne o libere con la etiqueta Abc. Cada vez que el depurador se interrumpe en una de estas asignaciones o operaciones gratuitas, use el comando kb (Display Stack Backtrace) para ver el seguimiento de la pila.

Con este procedimiento, puede determinar qué código residente en memoria está sobreasignando el grupo con la etiqueta Abc.

Para borrar el punto de interrupción, establezca PoolHitTag en cero:

kd> ed nt!poolhittag 0 

Si hay varios lugares diferentes en los que se asigna memoria con esta etiqueta y se encuentran en una aplicación o controlador que ha escrito, puede modificar el código fuente para usar etiquetas únicas para cada una de estas asignaciones.

Si no puede volver a compilar el programa, pero desea determinar cuál de las distintas ubicaciones posibles del código está causando la fuga, puede anular el ensamblado del código en cada ubicación y usar el depurador para editar este código residente en la memoria para que cada instancia use una etiqueta de grupo distinta (y no usada anteriormente). A continuación, permita que el sistema se ejecute durante varios minutos o más. Una vez transcurrido algún tiempo, vuelva a iniciar sesión con el depurador y use la extensión !poolfind para buscar todas las asignaciones de grupo asociadas a cada una de las nuevas etiquetas.