.net - pila - ¿Cómo uso un archivo de volcado para diagnosticar una fuga de memoria?
volcado de pila (4)
Tengo un servicio .NET con un conjunto de trabajo privado normal de aproximadamente 80 MB. Durante una prueba de carga reciente, el proceso alcanzó un consumo de memoria de 3,5 GB, lo que provocó que toda la máquina tuviera poca memoria física (se utilizaron 3,9 de 4 GB) y la memoria no se liberó mucho después de que se detuviera la prueba de carga. Utilizando el administrador de tareas, tomé un archivo de volcado del proceso y lo abrí en Visual Studio 2010 SP1, y puedo comenzar a depurarlo.
¿Cómo diagnostico el problema de memoria? Tengo dotTrace Memory 3.x a mi disposición, ¿admite perfiles de memoria en archivos de volcado? De lo contrario, ¿las funciones de creación de perfiles de memoria de Visual Studio 2010 Premium serán de ayuda (actualmente tengo Professional)? ¿Puede WinDbg ayudarme?
ACTUALIZACIÓN: el nuevo Visual Studio 2013 Ultimate ahora puede diagnosticar de forma nativa problemas de memoria utilizando archivos de volcado. Vea esta publicación en el blog para más detalles.
Desde la versión 2017.2 JetBrains dotMemory admite el análisis de volcados de memoria de Windows con toda su potencia y elegante GUI.
En general, si tiene una fuga en una aplicación administrada, significa que algo no se está recopilando. Las fuentes comunes incluyen
Controladores de eventos: si el suscriptor no se elimina, el editor se aferrará a él.
Estática
Finalizadores: un finalizador bloqueado evitará que el hilo del finalizador ejecute cualquier otro finalizador y, por lo tanto, evitará que se recopilen estas instancias.
De manera similar, un hilo estancado se mantendrá a cualquier raíz que contenga. Por supuesto, si tienes hilos bloqueados que probablemente afectarán a la aplicación en varios niveles.
Para solucionar este problema, debe inspeccionar el montón administrado. WinDbg + SOS (o PSSCOR) te permitirá hacer esto. El comando !dumpheap -stat
enumera todo el montón administrado.
Debe tener una idea del número de instancias de cada tipo que se espera en el montón. Una vez que encuentre algo que parece extraño, puede usar el !dumpheap -mt <METHOD TABLE>
para listar todas las instancias de un tipo dado.
El siguiente paso es analizar la raíz de estas instancias. Elige uno al azar y haz un !gcroot
sobre eso. Eso mostrará cómo está enraizada esa instancia particular. Busque controladores de eventos y objetos anclados (generalmente representan referencias estáticas). Si ve la cola del finalizador allí, necesita examinar qué está haciendo el hilo del finalizador. Use los comandos !clrstack
y !clrstack
para eso.
Si todo se ve bien para esa instancia, pasará a otra instancia. Si eso no produce nada, es posible que deba volver a mirar el montón nuevamente y repetir desde allí.
Otras fuentes de filtraciones incluyen: ensamblados que no están descargados y fragmentación del gran montón de objetos. SOS / PSSCOR puede ayudarlo a localizar estos también, pero omitiré los detalles por el momento.
Si quieres saber más, recomiendo el blog de Tess . También hice un par de videos sobre cómo usar WinDbg + SOS ( here y here ).
Si tiene la opción de depurar el proceso mientras se ejecuta, le recomiendo usar PSSCOR lugar de SOS. PSSCOR es esencialmente una rama privada de las fuentes SOS que se ha mejorado con comandos adicionales y muchos de los comandos SOS existentes también se han mejorado. Por ejemplo, la versión PSSCOR del comando !dumpheap
tiene una columna delta muy útil, lo que hace que la solución de problemas de pérdida de memoria sea mucho más fácil.
Para usarlo, necesita iniciar su proceso, conectar WinDbg y cargar PSSCOR y hacer un !dumpheap -stat
Dumpheap -stat. Luego, permite que el proceso vuelva a ejecutarse para que se realicen asignaciones. Rompe la ejecución y repite el comando. Ahora PSSCOR le mostrará el número de instancias que se agregaron / eliminaron desde la inspección anterior.
Instalar WinDbg. Debe asegurarse de obtener la versión correcta x86 o x64 según su volcado. Aquí hay un enlace directo a la download de x86.
En eso, debes asegurarte de que tomaste el basurero correcto. Puede usar el Administrador de tareas para crear el archivo de volcado (haga clic derecho en proceso -> Crear archivo volcado). Si está en 64 bits y su proceso es x86, use la versión de 32 bits del Administrador de tareas (C: / Windows / SysWOW64 / taskmgr.exe) para tomar el archivo de volcado. Consulte mi artículo para obtener más información sobre cómo tomar archivos de volcado, por ejemplo, si tiene XP y necesita usar windbg para crear el archivo de volcado.
advirtiendo que hay una curva de aprendizaje bastante empinada y es posible que las cosas no funcionen exactamente como se describe aquí, así que vuelva con cualquier problema.
Supongo que está usando .NET4 dado que puede abrir el volcado en Visual Studio. Aquí hay una guía muy rápida para ayudarlo a trabajar con su archivo dmp:
1) Ejecute WinDbg, configure la ruta de símbolos (Archivo -> Ruta de búsqueda de símbolos) a
SRV*c:/symbols*http://msdl.microsoft.com/download/symbols
2) Abra el volcado de Crash o arrastre su archivo .DMP a WinDbg.
3) escribe esto en la ventana de comandos
.loadby sos clr
(Para su información, para .NET 2, el comando debe ser .loadby sos mscorwks
)
4) luego escribe esto
!dumpheap -stat
que enumera el tipo de objetos y su recuento. se ve algo como esto:
Deberá analizar esto en el contexto de su aplicación y ver si algo parece inusual.
Hay mucho más para windbg, google es tu amigo.
http://msdn.microsoft.com/en-us/library/ee817660.aspx
Microsoft tiene una guía aquí. Sin embargo, es demasiado difícil para principiantes.
dotTrace puede generar gráficos de memoria visual (mejor que WinDbg), pero nunca los use para volcados.