United StatesChange Country, Oracle Worldwide Web Sites Communities I am a... I want to...
Bug ID: JDK-6186722 Signal 11 in countStackFrames() by libjvm.so
JDK-6186722 : Signal 11 in countStackFrames() by libjvm.so

Details
Type:
Bug
Submit Date:
2004-10-29
Status:
Closed
Updated Date:
2011-04-23
Project Name:
JDK
Resolved Date:
2011-04-23
Component:
hotspot
OS:
linux
Sub-Component:
runtime
CPU:
x86
Priority:
P4
Resolution:
Fixed
Affected Versions:
1.4.2_01
Fixed Versions:
hs10 (b03)

Related Reports
Backport:
Backport:

Sub Tasks

Description
FULL PRODUCT VERSION :
java version "1.4.2_01"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_01-b06)
Java HotSpot(TM) Client VM (build 1.4.2_01-b06, mixed mode)


ADDITIONAL OS VERSION INFORMATION :
Slackware 9.1.0: Linux tyre 2.4.25 #3 SMP Fri Mar 26 01:19:27 CET 2004 i686 unknown unknown GNU/Linux
Microsoft Windows 2000 (in vmware) also gives the problem

A DESCRIPTION OF THE PROBLEM :
With Threads, it is possible to use countStackFrames().  However, that may cause the JRE to crash in libjvm.so.  I suspect that this occures when using the method on threads which are already disposed.

I think the bug exists in all JRE's from the beginning of java.
(I use code like this for debugging purposes, and have been using it from java 1.0.2.  Sometimes I saw the crash, sometimes not.  But the supplied code will demonstrate it much more easy.)

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
  To reproduce, compile and run the supplied code and it will crash.  Notice that it will not crash on every call to countStackFrames, but surely the test will show the problem.
Notice that the problem also occures on Microsoft Windows 2000 (in a vmware session) with jre (1.4.2_04).
(I am pretty sure I've had the same problem on Windows NT4.0 with older jvm's (1.2/1.3 etc) and was expecting that it should have been fixed by now...)


EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
A lot of (not very interresting) output on a console.
ACTUAL -
Just a crash of the JRE.

ERROR MESSAGES/STACK TRACES THAT OCCUR :

Unexpected Signal : 11 occurred at PC=0x403B0EA5
Function=JVM_CountStackFrames+0xE9
Library=/usr/lib/j2sdk1.4.2_01/jre/lib/i386/client/libjvm.so

Current Java thread:
        at java.lang.Thread.countStackFrames(Native Method)
        at t.main(t.java:16)

Dynamic libraries:
08048000-0804e000 r-xp 00000000 08:02 61761      /usr/lib/j2sdk1.4.2_01/bin/java
0804e000-0804f000 rw-p 00005000 08:02 61761      /usr/lib/j2sdk1.4.2_01/bin/java
40000000-40015000 r-xp 00000000 08:02 13080      /lib/ld-2.3.2.so
40015000-40016000 rw-p 00014000 08:02 13080      /lib/ld-2.3.2.so
40016000-4001e000 r-xp 00000000 08:02 62243      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/native_threads/libhpi.so
4001e000-4001f000 rw-p 00007000 08:02 62243      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/native_threads/libhpi.so
4001f000-40023000 rw-s 00000000 00:07 5005544    /dev/shm/tmp/hsperfdata_bklip/22503
40023000-40026000 r--s 00000000 08:02 62226      /usr/lib/j2sdk1.4.2_01/jre/lib/ext/dnsns.jar
40028000-40036000 r-xp 00000000 08:02 13118      /lib/libpthread-0.10.so
40036000-40039000 rw-p 0000e000 08:02 13118      /lib/libpthread-0.10.so
40079000-4007b000 r-xp 00000000 08:02 13105      /lib/libdl-2.3.2.so
4007b000-4007c000 rw-p 00001000 08:02 13105      /lib/libdl-2.3.2.so
4007c000-401ab000 r-xp 00000000 08:02 13098      /lib/libc-2.3.2.so
401ab000-401b0000 rw-p 0012f000 08:02 13098      /lib/libc-2.3.2.so
401b2000-405ac000 r-xp 00000000 08:02 62247      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/client/libjvm.so
405ac000-405c8000 rw-p 003f9000 08:02 62247      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/client/libjvm.so
405da000-405ec000 r-xp 00000000 08:02 13113      /lib/libnsl-2.3.2.so
405ec000-405ed000 rw-p 00011000 08:02 13113      /lib/libnsl-2.3.2.so
405ef000-40611000 r-xp 00000000 08:02 12877      /lib/libm-2.3.2.so
40611000-40612000 rw-p 00021000 08:02 12877      /lib/libm-2.3.2.so
40612000-40623000 r--s 00000000 08:02 62363      /usr/lib/j2sdk1.4.2_01/jre/lib/jce.jar
40623000-4062e000 r-xp 00000000 08:02 13104      /lib/libnss_compat-2.3.2.so
4062e000-4062f000 rw-p 0000a000 08:02 13104      /lib/libnss_compat-2.3.2.so
4062f000-4063f000 r-xp 00000000 08:02 62236      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libverify.so
4063f000-40641000 rw-p 0000f000 08:02 62236      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libverify.so
40641000-40661000 r-xp 00000000 08:02 62252      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libjava.so
40661000-40663000 rw-p 0001f000 08:02 62252      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libjava.so
40663000-40677000 r-xp 00000000 08:02 62241      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libzip.so
40677000-4067a000 rw-p 00013000 08:02 62241      /usr/lib/j2sdk1.4.2_01/jre/lib/i386/libzip.so
4067a000-42012000 r--s 00000000 08:02 62357      /usr/lib/j2sdk1.4.2_01/jre/lib/rt.jar
4205c000-42072000 r--s 00000000 08:02 62316      /usr/lib/j2sdk1.4.2_01/jre/lib/sunrsasign.jar
42072000-4214d000 r--s 00000000 08:02 62292      /usr/lib/j2sdk1.4.2_01/jre/lib/jsse.jar
4214d000-426a6000 r--s 00000000 08:02 62355      /usr/lib/j2sdk1.4.2_01/jre/lib/charsets.jar4c7d0000-4c7ec000 r--s 00000000 08:02 62227      /usr/lib/j2sdk1.4.2_01/jre/lib/ext/sunjce_provider.jar
4c7ec000-4c7f9000 r--s 00000000 08:02 62228      /usr/lib/j2sdk1.4.2_01/jre/lib/ext/ldapsec.jar
4c7f9000-4c8b5000 r--s 00000000 08:02 62229      /usr/lib/j2sdk1.4.2_01/jre/lib/ext/localedata.jar

Heap at VM Abort:
Heap
 def new generation   total 576K, used 384K [0x44750000, 0x447f0000, 0x44c30000)
  eden space 512K,  62% used [0x44750000, 0x447a0338, 0x447d0000)
  from space 64K, 100% used [0x447e0000, 0x447f0000, 0x447f0000)
  to   space 64K,   0% used [0x447d0000, 0x447d0000, 0x447e0000)
 tenured generation   total 1408K, used 21K [0x44c30000, 0x44d90000, 0x48750000)
   the space 1408K,   1% used [0x44c30000, 0x44c35628, 0x44c35800, 0x44d90000)
 compacting perm gen  total 4096K, used 966K [0x48750000, 0x48b50000, 0x4c750000)
   the space 4096K,  23% used [0x48750000, 0x48841a00, 0x48841a00, 0x48b50000)

Local Time = Fri Oct 29 11:34:43 2004
Elapsed Time = 0
#
# HotSpot Virtual Machine Error : 11
# Error ID : 4F530E43505002EF
# Please report this error at
# http://java.sun.com/cgi-bin/bugreport.cgi
#
# Java VM: Java HotSpot(TM) Client VM (1.4.2_01-b06 mixed mode)
#



REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
public class t
{
   static public void main(String[] args) {
      while (true) {
         new tt();

         ThreadGroup rootGrp = Thread.currentThread().getThreadGroup();
         while (rootGrp.getParent() != null)
            rootGrp = rootGrp.getParent();
   
         Thread[] threads = new Thread[rootGrp.activeCount() + 8];
         int count = rootGrp.enumerate(threads, true);
         System.err.print("count="+count);
         for (int i = 0; i < count; ++i) {
            Thread t = threads[i];
            int tmp = t.countStackFrames();     // ************ causes the crash
            System.err.print(tmp+" ");
         }
         System.err.println();
      }
   }
}

class tt implements Runnable
{
        private Thread runner;

        public tt() {
                runner = new Thread(this, "tt");
                runner.setDaemon(true);
                runner.start();
        }

        public void run() {
                if (Thread.currentThread() == runner) {
                        try {
                                Thread.sleep(10);
                        } catch (InterruptedException e) {}
                }
        }
}

---------- END SOURCE ----------

CUSTOMER SUBMITTED WORKAROUND :
I haven't found any.
###@###.### 10/29/04 16:31 GMT

                                    

Comments
EVALUATION

int 	countStackFrames()
          Deprecated. The definition of this call depends on suspend(), which is deprecated. Further, the results of this call were never well-defined.

void 	suspend()
          Deprecated. This method has been deprecated, as it is inherently deadlock-prone. If the target thread holds a lock on the monitor protecting a critical system resource when it is suspended, no thread can access this resource until the target thread is resumed. If the thread that would resume the target thread attempts to lock this monitor prior to calling resume, deadlock results. Such deadlocks typically manifest themselves as "frozen" processes. For more information, see
http://java.sun.com/j2se/1.5.0/docs/guide/misc/threadPrimitiveDeprecation.html  
I think this issue is not going to get fixed since the methods in question are deprecated.

###@###.### 10/29/04 17:40 GMT

The fix for this bug would be to throw IllegalStateException
since the thread on which the countStackFrames is called
has not been suspended. If it were suspended this should
work - so the caller will want to fix the test case as
well to suspend and resume those threads. 
###@###.### 10/29/04 19:22 GMT
###@###.### 10/29/04 19:28 GMT
                                     
2004-10-29
WORK AROUND

The fix will be to throw IllegalThreadStateException if
the thread on which the call to countThreadState is made
has not been suspended. This should fix the VM crash.

The workaround is to change the code to suspend/ call
countThreadState/resume the thread in question. That
fix will also be needed when the fixed vm is available.
###@###.### 10/29/04 19:29 GMT
                                     
2004-10-29
EVALUATION

Are going to implement the exception and close this bug out?
                                     
2005-08-04
EVALUATION

Retarget to Dolphin.
                                     
2005-10-11
SUGGESTED FIX

Here is the suggested fix based on the comments made by ###@###.###.

------- jvm.cpp -------
2571c2571,2578
<   oop java_thread = JNIHandles::resolve_non_null(jthread);  
---
>   oop java_thread = JNIHandles::resolve_non_null(jthread);
>   JavaThread* thr = java_lang_Thread::thread(java_thread);
>   // Ensure this thread is suspended before counting the frames, see details at bug 
>   // 6186722
>   if (thr != NULL && !thr->is_external_suspend()) {
>     THROW_MSG_0(vmSymbols::java_lang_IllegalThreadStateException(), 
> 		"This thread is not suspended");
>   }
2575c2582
<   JavaThread* thr = java_lang_Thread::thread(JNIHandles::resolve_non_null(jthread));
---
>   JNIHandles::resolve_non_null(jthread);

I've tested the fix on both Windows and Solaris sparc and it worked fine with the original testcase. It now throws IllegalThreadStateException when Thread.countStackFrames() is called.

I recommend to modify the testcase as below in order to work properly.

public class t
{
   static public void main(String[] args) {
      
      while (true) {
         new tt();

         ThreadGroup rootGrp = Thread.currentThread().getThreadGroup();
         while (rootGrp.getParent() != null)
            rootGrp = rootGrp.getParent();

         Thread[] threads = new Thread[rootGrp.activeCount() + 8];
         int count = rootGrp.enumerate(threads, true);
          System.err.print("count=" + count + " ");
         for (int i = 0; i < count; ++i) {
            Thread t = threads[i];
	    
	    if (t != Thread.currentThread()) {
		try {
                    t.suspend();
		    /* countStackFrames() SHOULD NOT cause crash. */
		    int tmp = t.countStackFrames();    
		    System.err.print(tmp+" ");
		    t.resume();
		} catch(IllegalThreadStateException ex) {
		   /* Ignore the exception since "suspend()" does not guaranteet
                      this thread will be suspended, so potentially countStackFrames()                       will still throw IllegalThreadStateException
                    */
		}
		
	    }
         }
         System.err.println();
      }
   }
}

*** (#1 of 1): [ UNSAVED ] ###@###.###
                                     
2005-12-20



Hardware and Software, Engineered to Work Together