2010-09-17 36 views
9

Tengo una aplicación multiproceso. Varios mensajes vienen a la aplicación y se procesan en hilos separados. Para esto estoy usando las clases ThreadPoolExecutor y FutureTask del paquete java.util.concurrent.Cómo obtener el seguimiento de la pila de un hilo

De vez en cuando tengo algunos bloqueos en la aplicación. Cuando se produce un interbloqueo, quiero interrumpir el hilo de bloqueo y quiero registrar el seguimiento de la pila de este hilo para poder resolverlo más tarde.

¿Hay alguna manera de cómo podemos encontrar el rastro de pila de un hilo fuera de ese hilo en Java?

+0

¿Quiere decir que quiere detectar un punto muerto y recuperarse? Nunca he hecho eso, pero usar un seguimiento de la pila no me parece el correcto ... –

+0

Necesito el seguimiento de la pila para saber dónde quedó el hilo y puedo solucionar el problema para que la aplicación funcione bien después reiniciar. Sin embargo, quiero interrumpir el hilo de bloqueo para que la aplicación funcione hasta que encuentre algo de tiempo para solucionar el problema y liberarlo. – Palo

Respuesta

5

Consulte here para saber cómo generar seguimientos de pila, incluido cómo hacerlo de forma programática. Desde la consola, Ctrl + Break volcará los rastreos de pila a stdout. Vea también this SO question para más detalles.

+5

En entornos UNIX, el envío de una señal "QUIT" ('kill -QUIT ') al proceso java también generará el seguimiento de la pila en la salida estándar. – Bombe

5

Puede registrar los rastreos de la pila de todos los subprocesos de vez en cuando (o antes de matar el proceso) desde su aplicación. Para hacer eso, use:

Map<Thread, StackTraceElement[]> m = Thread.getAllStackTraces(); 
for(Map.Entry<Thread, StackTraceElement[]> e : m.entrySet()) { 
    log(e.getKey().toString()); 
    for (StackTraceElement s : e.getValue()) { 
     log(" " + s); 
    } 
} 

Cuando se ejecutan pruebas automáticas nocturnas, a veces algunos de los casos de prueba se estancan. Agregué un hilo daemon "TimeBomb" que espera 30 minutos, y si luego registra todos los rastreos de la pila como se indica arriba.

0

no estaba seguro si desea obtener el StackTrace desde dentro de la misma JVM o externamente, pero si desea obtener el seguimiento de la pila con herramientas externas, lo siguiente ayuda:

  • The Java VisualVM herramienta se puede usar para conectarse a la JVM en ejecución, donde se puede descargar la pila de subprocesos. Este suele ser el enfoque preferido para la mayoría de las personas que usan Java 6. Una vez que se inicia VisualVM, se puede obtener el volcado de subprocesos del proceso seleccionando el proceso en la pestaña Aplicación. Ahora está disponible una pestaña Temas para ver los hilos en el proceso en ejecución, y en la misma pestaña encontrará el botón "Volcado de subprocesos" para extraer la información requerida.
  • La utilidad jstack dentro del JDK también se puede usar para producir registros de pila de hilos.
2

Utiliza JStack. Aquí hay un buen blog entry que detalla cómo obtener los rastros de la pila.

4

Antes de entrar en la región de estancamiento, defina un campo como,

thread = Thread.currentThread(); 

En el subproceso de supervisión puede realizar thread.getStackTrace(); para obtener el seguimiento de la pila de ese hilo en cualquier momento.

0

Cuando se produce un estancamiento quiero interrumpir el hilo de bloqueo ...

Usted podría implementar una tarea periódica para comprobar si hay puntos muertos (donde los puntos muertos son java intrínseco o Lock con base) y la llamada interrupt en todos los hilos implicados en el escenario. Sin embargo, esto no tiene garantías de que resolverá su problema. Es probable que el escenario vuelva a suceder. Vea Dr Heinz's article on a deadlock detector para más detalles.

De hecho, no hay garantía de que interrupt libere incluso un proceso bloqueado como este. Es un enfoque mucho mejor para evitar el escenario de interbloqueo en primer lugar, por ejemplo, mediante el uso de bloqueos con tiempos de espera y estrategias de reintento o enfoques 'probar antes de comprar'.

y quiero registrar el seguimiento de la pila de este hilo ...

Si quieres hacer esto mediante programación, una vez más, seguir el ejemplo del Dr. Heinz. Si no, solo genera el volcado de hilo cuando hayas detectado el problema.

¿Hay alguna manera de cómo podemos encontrar el rastro de pila de un hilo fuera de ese hilo en Java?

Sí y no. Puede volcar los subprocesos de otras máquinas virtuales, pero sus seguimientos de pila pueden no ser tan útiles como podría pensar para determinar las causas de su interbloqueo. Si se ha detectado un punto muerto genuino (por la propia JVM en el volcado de subprocesos de su VM de aplicaciones), debe tener todo lo que necesita para depurar la causa (más o menos).

Cuestiones relacionadas