Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-4712793

JNI : Failure in JNI_CreateJavaVM() after calling DestroyJavaVM()

XMLWordPrintable

    • Icon: Bug Bug
    • Resolution: Duplicate
    • Icon: P4 P4
    • None
    • 1.3.1, 1.4.0
    • hotspot
    • x86
    • windows_98, windows_nt, windows_2000

      Name: gm110360 Date: 07/10/2002


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

      FULL OPERATING SYSTEM VERSION :
      Microsoft Windows 2000 [Version 5.00.2195]

      A DESCRIPTION OF THE PROBLEM :
      In order to give C++ access to some Java code, we provide
      an intermediate class that :
      - creates a JVM (JNI_CreateJavaVM()),
      - passes appropriate arguments to Java classes
      - calls DestroyJavaVM() to destroy the JavaVM.

      All goes well the first time, but when trying to call the
      function again from the same application, we get the as
      listed in the Error Messages section.

      ERROR MESSAGES/STACK TRACES THAT OCCUR :
      #
      # HotSpot Virtual Machine Error, Internal Error
      # Please report this error at
      # http://java.sun.com/cgi-bin/bugreport.cgi
      #
      # Java VM: Java HotSpot(TM) Client VM (1.4.0-b92 interpreted mode)
      #
      # Error ID: 455843455054494F4E530E43505000DF
      #
      # Problematic Thread: prio=183470880 tid=0x0AEF8B20 nid=0x1e0700 runnable
      #

      This bug can be reproduced always.

      ---------- BEGIN SOURCE ----------
      C++ source code for function

      int CALLBACK compareImages(const char ** compareString, string& results, int&
      results_count) {
      JavaVMOption options[4];
      JavaVMInitArgs vm_args;
      JavaVM *jvm = NULL;
      JNIEnv *env;
      long result = 0;
      jmethodID mid;
      jclass jcls;
      _jobjectArray *compareResult;
      jsize rSize;

      //Set JVM options
      options[0].optionString = "-Djava.class.path=.";
      options[1].optionString = "-Djava.compiler=NONE";
      options[2].optionString = "-Djava.library.path=.";
      options[3].optionString = "-verbose:jni";

      vm_args.version = JNI_VERSION_1_2;

      vm_args.options = options;
      vm_args.nOptions = 4;
      vm_args.ignoreUnrecognized = JNI_FALSE;

      //Create the JVM
      result = JNI_CreateJavaVM(&jvm, (void **)&env, &vm_args);

      if (result == JNI_ERR) {
      results = "Error invoking the JVM\n";
      jvm->DestroyJavaVM();
      return -1;
      }

      //Find class IksneWrapper
      jcls = env->FindClass("IksneWrapper");
      if (jcls == 0 || jcls == NULL) {
      results = "Cannot find class IksneWrapper\n";
      jvm->DestroyJavaVM();
      return -1;
      }

      env->ExceptionClear();

      //Find public static String[] compare(String compareString);
      mid = env->GetStaticMethodID(jcls, "compare", "(Ljava/lang/String;)
      [Ljava/lang/String;");

      if (mid == 0) {
      results = "Cannot find IksneWrapper.compare function\n";
      jvm->DestroyJavaVM();
              return -1;
          }

      //Call method and compare
      compareResult = (jobjectArray)((jarray) env->CallStaticObjectMethod
      (jcls, mid, env->NewStringUTF(*compareString)));
      rSize = env->GetArrayLength(compareResult);

      // If an error occured, only one result is returned with error message
      if (rSize == 1) {
      results = env->GetStringUTFChars(
      (jstring) env->GetObjectArrayElement(compareResult, 0),
      JNI_FALSE);
      results_count = 0;
      jvm->DestroyJavaVM();
      return 0;
      }
      // If only one test was executed, only test result is returned
      else if (rSize == 2) {
      results = env->GetStringUTFChars(
      (jstring) env->GetObjectArrayElement(compareResult, 1),
      JNI_FALSE);
      results_count = 1;
      }
      // Test results of all executed tests are returned
      else {
      int i;
      results = "";
      for (i=1; i < rSize; i++) {
      results = results.append(env->GetStringUTFChars
      ((jstring) env->GetObjectArrayElement(compareResult, i), JNI_FALSE));
      if (i != (rSize - 1))
      results = results.append("\n");
      }
      results_count = rSize - 1;
      }

      //delete [] vmBuf;
      jvm->DetachCurrentThread();
      jvm->DestroyJavaVM();
      return 1;
      }

      --------------------------------------------------------------------------------

      C++ Test application

      #include "windows.h"

      #include <iostream>
      #include <string>
      //#include <stdio.h>

      using namespace std;

      typedef int (CALLBACK* PCOMPIMAGE) (const char**, string&, int&);

      int func() {
      HINSTANCE hDLL; // Handle to DLL
      PCOMPIMAGE pComImg; // Function pointer

      /*sample compare string call of format :
      <base image> <test image> <comparison command>
      */
      const char *compareString
      = "\\\\jayant\\testImages\\testColors\\blank.bmp
      \\\\jayant\\testImages\\testColors\\bmp.bmp COMPARE_PIXELBYPIXEL true 0
      OPERATE_COMPAREBYRGB COMPARE_PIXELBYPIXEL true 25";
      //string compareString = "\\\\jayant\\testImages\\testColors\\blank.bmp
      \\\\jayant\\testImages\\testColors\\bmp.bmp COMPARE_PIXELBYPIXEL true 0
      OPERATE_COMPAREBYRGB COMPARE_PIXELBYPIXEL true 25";
      string result;
      int i; //number

      hDLL = LoadLibrary("IksneCpp");
      if (hDLL != NULL)
      {
      pComImg = (PCOMPIMAGE) GetProcAddress(hDLL,"compareImages");
      if (!pComImg)
      {
      // handle the error
      FreeLibrary(hDLL);
      return -1;
      }
      else
      {
      // call the function
      if (pComImg(&compareString, result, i) == 1) {
      //printf("For %s,\ntotal results = %d,\nresult
      = %s\n", compareString, i, result);
      cout << "For " << compareString << endl
      << "total results = " << i << endl;
      cout << "(\\n seperated results)" << endl <<
      result << endl;
      }
      else
      cout << "Error : " << result << endl;
      //printf("Error : '%s'\n", result);
      }
      }

      FreeLibrary(hDLL);

      hDLL = LoadLibrary("IksneCpp");
      if (hDLL != NULL)
      {
      pComImg = (PCOMPIMAGE) GetProcAddress(hDLL,"compareImages");
      if (!pComImg)
      {
      // handle the error
      FreeLibrary(hDLL);
      return -1;
      }
      else
      {
      // call the function
      if (pComImg(&compareString, result, i) == 1) {
      //printf("For %s,\ntotal results = %d,\nresult
      = %s\n", compareString, i, result);
      cout << "For " << compareString << endl
      << "total results = " << i << endl;
      cout << "(\\n seperated results)" << endl <<
      result << endl;
      }
      else
      cout << "Error : " << result << endl;
      //printf("Error : '%s'\n", result);
      }
      }

      FreeLibrary(hDLL);
      GlobalFree((void *) compareString);

      return 0;
      }

      int main()
      {
      int res;
      res = func();
      res = func();
      return 0;
      }

      ---------- END SOURCE ----------
      (Review ID: 147214)
      ======================================================================

      Name: rmT116609 Date: 10/10/2002


      FULL PRODUCT VERSION :
      java version "1.4.0_02"
      Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0_02-b02)
      Java HotSpot(TM) Client VM (build 1.4.0_02-b02, mixed mode)

      FULL OPERATING SYSTEM VERSION :
      Windows NT Version 4.0 Service Pack 6a Numerous hot fixes for security issues


      A DESCRIPTION OF THE PROBLEM :
      The environment is a C++ application using the Invocation API to launch a Java VM.

      The C++ code does the following (in pseudocode):

      =======On Initialization========
      JNI_CreateJavaVM() <<-- crashes here 2nd time
      FindClass()/GetMethodID() for classes used
      Create NewGlobalRef() for classIDs

      =======On Shutdown========
      DeleteGlobalRef for classID references
      DetachCurrentThread
      DestroyJavaVM <<-- returns 0!

      Our code repeatedly attempts to shutdown and restart. The
      second restart, the code crashes.
      Here is the output from stderr when the JVM crashes:
      #
      # HotSpot Virtual Machine Error, Internal Error
      # Please report this error at
      # http://java.sun.com/cgi-bin/bugreport.cgi
      #
      # Java VM: Java HotSpot(TM) Client VM (1.4.0_02-b02 mixed
      mode)
      #
      # Error ID: 455843455054494F4E530E43505000DF
      #
      # Problematic Thread: prio=10821120 tid=0x00A51E00 nid=0xf1
      runnable
      #

      EXPECTED VERSUS ACTUAL BEHAVIOR :
      The JNI_CreateJavaVM function should succeed (or barring that, fail with a return code).


      REPRODUCIBILITY :
      This bug can be reproduced always.

      CUSTOMER WORKAROUND :
      Comment out the DestroyJavaVM call.
      This however leads to a memory leak that causes the application to crash after several days running.
      (Review ID: 165185)
      ======================================================================

            ksrini Kumar Srinivasan
            gmanwanisunw Girish Manwani (Inactive)
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

              Created:
              Updated:
              Resolved:
              Imported:
              Indexed: