[Java] ¿Qué significa BufferBlob :: Intérprete en el registro de bloqueo de JVM?


Answers

Esta pregunta ahora ha sido respondida por Tom Rodríguez en la lista de distribución hotspot-runtime-dev.

http://mail.openjdk.java.net/pipermail/hotspot-runtime-dev/2011-November/002592.html

Question

Estoy investigando un bloqueo de JVM que ocurre ocasionalmente en mi aplicación. El archivo hs_err contiene los siguientes detalles sobre el bloqueo.

#  SIGSEGV (0xb) at pc=0x065e68f4, pid=20208, tid=570166160
#
# Java VM: Java HotSpot(TM) Server VM (10.0-b23 mixed mode linux-x86)

...

# Problematic frame:
# V  [libjvm.so+0x5e68f4]

...

Current thread (0x099ea800):  JavaThread "Thread-315" daemon [_thread_in_vm, id=25782, stack(0x21fa3000,0x21fc1000)]

...

vm_info: Java HotSpot(TM) Server VM (10.0-b23) for linux-x86 JRE (1.6.0_07-b06), built on Jun 10 2008 01:20:15 by "java_re" with gcc 3.2.1-7a (J2SE release)

Así que esto me dice que la JVM golpeó un segfault cuando se ejecuta un código de Java. El registro de errores también contiene información sobre la pila del hilo que se colgó.

Native frames: (J=compiled Java code, j=interpreted, Vv=VM code, C=native code)
V  [libjvm.so+0x5e68f4]
V  [libjvm.so+0x1c054f]
V  [libjvm.so+0x1bfef2]
V  [libjvm.so+0x1bf57f]
V  [libjvm.so+0x592495]
V  [libjvm.so+0x365c4e]
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter

Java frames: (J=compiled Java code, j=interpreted, Vv=VM code)
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
v  ~BufferBlob::Interpreter
J  org.myapp.AppClass.getBytes()Lorg/myapp/ByteHolder;

He usado GDB para conectarme al archivo central del accidente y obtener más detalles sobre la pila. Esto me da la siguiente salida.

#5  <signal handler called>
#6  0x065e68f4 in interpretedVFrame::monitors() const ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so
#7  0x061c054f in get_or_compute_monitor_info(JavaThread*) ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so
#8  0x061bfef2 in revoke_bias(oopDesc*, bool, bool, JavaThread*) ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so
#9  0x061bf57f in BiasedLocking::revoke_and_rebias(Handle, bool, Thread*) ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so
#10 0x06592495 in ObjectSynchronizer::fast_enter(Handle, BasicLock*, bool, Thread*) ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so
#11 0x06365c4e in InterpreterRuntime::monitorenter(JavaThread*, BasicObjectLock*) ()
   from /usr/java/jdk1.6.0_07/jre/lib/i386/server/libjvm.so

Esto muestra que los seis marcos libjvm.so enumerados en el informe de errores original estaban relacionados con la captura de un bloqueo de Java. Sin embargo, no puedo encontrar ningún código dentro de org.myapp.AppClass.getBytes () que use bloqueos.

¿Qué significan las líneas BufferBlob :: Interpreter en la pila? ¿Son estos marcos de pila de Java? Marcos de pila JVM? ¿Es posible resolver lo que se llamó en estos marcos de pila?

NOTA: No sugiera que intente cambiar a una JVM de Hotspot más nueva. Confío en el recopilador CMS y ninguna de las JVM Hotspot V1.6 más recientes es lo suficientemente estable con el recopilador CMS.

EDITAR: Este documento (http://www.oracle.com/technetwork/java/javase/tsg-vm-149989.pdf) establece que un marco "v" es un "marco de tallo generado por VM". Alguna idea de lo que esto significa?

EDIT2: org.myapp.AppClass.getBytes () lee desde un DataInputStream. Esto podría implicar el siguiente seguimiento de pila:

AppClass.getBytes()
AppClass.readByte()
DataInputStream.readByte()
SocketInputStream.read()
SocketInputStream.read(byte[],int,int)
PlainSocketImpl.aquireFD()

Este método final toma un bloqueo. Esta podría ser la fuente de la eventual llamada al código JVM enumerado anteriormente. Esta pila de arriba tiene la clara característica de que hay 5 marcos de pila de Java debajo de getBytes (). Esto coincidiría perfectamente con las 5 líneas de BufferBlob :: Interpreter en la lista de "marcos de Java".

Esto plantea un par de preguntas nuevas:

  • ¿Es posible que las 5 líneas de BufferBlob :: Interpreter en la sección "Cuadros nativos" sean solo duplicados de las mismas líneas en la sección "Cuadros de Java"?
  • ¿Por qué el registro de errores no muestra los detalles de estos 5 marcos de pila?

EDIT3 - Este error de Oracle parece ser el mismo / similar: http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6676175

La traza de la pila que se muestra no es idéntica, pero menciona una condición de carrera rara en revoke_and_rebias que se corrigió en 6u14.

EDIT4 - El mensaje de recompensa debería decir "familiarizado con la implementación de Hotspot"