Merge
authorcoleenp
Fri, 12 Dec 2014 02:51:07 +0000
changeset 28164 cb7b36c43fac
parent 28163 322d55d167be (current diff)
parent 28162 cf13d6e8e46f (diff)
child 28165 ffeee11192a9
Merge
--- a/hotspot/agent/src/os/win32/windbg/sawindbg.cpp	Thu Dec 11 21:34:43 2014 -0500
+++ b/hotspot/agent/src/os/win32/windbg/sawindbg.cpp	Fri Dec 12 02:51:07 2014 +0000
@@ -22,6 +22,9 @@
  *
  */
 
+// Disable CRT security warning against strcpy/strcat
+#pragma warning(disable: 4996)
+
 // this is source code windbg based SA debugger agent to debug
 // Dr. Watson dump files and process snapshots.
 
--- a/hotspot/agent/src/share/native/sadis.c	Thu Dec 11 21:34:43 2014 -0500
+++ b/hotspot/agent/src/share/native/sadis.c	Fri Dec 12 02:51:07 2014 +0000
@@ -33,6 +33,8 @@
  */
 
 #ifdef _WINDOWS
+// Disable CRT security warning against _snprintf
+#pragma warning (disable : 4996)
 
 #define snprintf  _snprintf
 #define vsnprintf _vsnprintf
@@ -90,12 +92,8 @@
     if (errno != 0)
     {
       /* C runtime error that has no corresponding DOS error code */
-      const char *s = strerror(errno);
-      size_t n = strlen(s);
-      if (n >= len) n = len - 1;
-      strncpy(buf, s, n);
-      buf[n] = '\0';
-      return (int)n;
+      strerror_s(buf, len, errno);
+      return strlen(buf);
     }
     return 0;
 }
@@ -111,16 +109,30 @@
                                                                            jstring jrepath_s,
                                                                            jstring libname_s) {
   uintptr_t func = 0;
-  const char* error_message = NULL;
-  jboolean isCopy;
+  const char *error_message = NULL;
+  const char *jrepath = NULL;
+  const char *libname = NULL;
+  char buffer[128];
+
+#ifdef _WINDOWS
+  HINSTANCE hsdis_handle = (HINSTANCE) NULL;
+#else
+  void* hsdis_handle = NULL;
+#endif
 
-  const char * jrepath = (*env)->GetStringUTFChars(env, jrepath_s, &isCopy); // like $JAVA_HOME/jre/lib/sparc/
-  const char * libname = (*env)->GetStringUTFChars(env, libname_s, &isCopy);
-  char buffer[128];
+  jrepath = (*env)->GetStringUTFChars(env, jrepath_s, NULL); // like $JAVA_HOME/jre/lib/sparc/
+  if (jrepath == NULL || (*env)->ExceptionOccurred(env)) {
+    return 0;
+  }
+
+  libname = (*env)->GetStringUTFChars(env, libname_s, NULL);
+  if (libname == NULL || (*env)->ExceptionOccurred(env)) {
+    (*env)->ReleaseStringUTFChars(env, jrepath_s, jrepath);
+    return 0;
+  }
 
   /* Load the hsdis library */
 #ifdef _WINDOWS
-  HINSTANCE hsdis_handle;
   hsdis_handle = LoadLibrary(libname);
   if (hsdis_handle == NULL) {
     snprintf(buffer, sizeof(buffer), "%s%s", jrepath, libname);
@@ -134,7 +146,6 @@
     error_message = buffer;
   }
 #else
-  void* hsdis_handle;
   hsdis_handle = dlopen(libname, RTLD_LAZY | RTLD_GLOBAL);
   if (hsdis_handle == NULL) {
     snprintf(buffer, sizeof(buffer), "%s%s", jrepath, libname);
@@ -156,6 +167,11 @@
      * platform dependent error message.
      */
     jclass eclass = (*env)->FindClass(env, "sun/jvm/hotspot/debugger/DebuggerException");
+    if ((*env)->ExceptionOccurred(env)) {
+      /* Can't throw exception, probably OOM, so silently return 0 */
+      return (jlong) 0;
+    }
+
     (*env)->ThrowNew(env, eclass, error_message);
   }
   return (jlong)func;
@@ -184,16 +200,22 @@
 
 /* event callback binding to Disassembler.handleEvent */
 static void* event_to_env(void* env_pv, const char* event, void* arg) {
+  jlong result = 0;
   decode_env* denv = (decode_env*)env_pv;
   JNIEnv* env = denv->env;
   jstring event_string = (*env)->NewStringUTF(env, event);
-  jlong result = (*env)->CallLongMethod(env, denv->dis, denv->handle_event, denv->visitor,
-                                        event_string, (jlong) (uintptr_t)arg);
-  if ((*env)->ExceptionOccurred(env) != NULL) {
+  if ((*env)->ExceptionOccurred(env)) {
+    return NULL;
+  }
+
+  result = (*env)->CallLongMethod(env, denv->dis, denv->handle_event, denv->visitor,
+                                  event_string, (jlong) (uintptr_t)arg);
+  if ((*env)->ExceptionOccurred(env)) {
     /* ignore exceptions for now */
     (*env)->ExceptionClear(env);
-    result = 0;
+    return NULL;
   }
+
   return (void*)(uintptr_t)result;
 }
 
@@ -219,10 +241,13 @@
   }
   if (raw != NULL) {
     jstring output = (*env)->NewStringUTF(env, raw);
-    (*env)->CallVoidMethod(env, denv->dis, denv->raw_print, denv->visitor, output);
-    if ((*env)->ExceptionOccurred(env) != NULL) {
+    if (!(*env)->ExceptionOccurred(env)) {
+      /* make sure that UTF allocation doesn't cause OOM */
+      (*env)->CallVoidMethod(env, denv->dis, denv->raw_print, denv->visitor, output);
+    }
+    if ((*env)->ExceptionOccurred(env)) {
       /* ignore exceptions for now */
-      (*env)->ExceptionClear(env);
+        (*env)->ExceptionClear(env);
     }
     return (int) flen;
   }
@@ -231,11 +256,16 @@
   va_end(ap);
 
   output = (*env)->NewStringUTF(env, denv->buffer);
-  (*env)->CallVoidMethod(env, denv->dis, denv->raw_print, denv->visitor, output);
-  if ((*env)->ExceptionOccurred(env) != NULL) {
+  if (!(*env)->ExceptionOccurred(env)) {
+    /* make sure that UTF allocation doesn't cause OOM */
+    (*env)->CallVoidMethod(env, denv->dis, denv->raw_print, denv->visitor, output);
+  }
+
+  if ((*env)->ExceptionOccurred(env)) {
     /* ignore exceptions for now */
     (*env)->ExceptionClear(env);
   }
+
   return cnt;
 }
 
@@ -251,13 +281,24 @@
                                                                     jbyteArray code,
                                                                     jstring options_s,
                                                                     jlong decode_instructions_virtual) {
-  jboolean isCopy;
-  jbyte* start = (*env)->GetByteArrayElements(env, code, &isCopy);
-  jbyte* end = start + (*env)->GetArrayLength(env, code);
-  const char * options = (*env)->GetStringUTFChars(env, options_s, &isCopy);
-  jclass disclass = (*env)->GetObjectClass(env, dis);
+  jbyte *start = NULL;
+  jbyte *end = NULL;
+  jclass disclass = NULL;
+  const char *options = NULL;
+  decode_env denv;
 
-  decode_env denv;
+  start = (*env)->GetByteArrayElements(env, code, NULL);
+  if ((*env)->ExceptionOccurred(env)) {
+    return;
+  }
+  end = start + (*env)->GetArrayLength(env, code);
+  options = (*env)->GetStringUTFChars(env, options_s, NULL);
+  if ((*env)->ExceptionOccurred(env)) {
+    (*env)->ReleaseByteArrayElements(env, code, start, JNI_ABORT);
+    return;
+  }
+  disclass = (*env)->GetObjectClass(env, dis);
+
   denv.env = env;
   denv.dis = dis;
   denv.visitor = visitor;
@@ -266,6 +307,8 @@
   denv.handle_event = (*env)->GetMethodID(env, disclass, "handleEvent",
                                           "(Lsun/jvm/hotspot/asm/InstructionVisitor;Ljava/lang/String;J)J");
   if ((*env)->ExceptionOccurred(env)) {
+    (*env)->ReleaseByteArrayElements(env, code, start, JNI_ABORT);
+    (*env)->ReleaseStringUTFChars(env, options_s, options);
     return;
   }
 
@@ -273,11 +316,13 @@
   denv.raw_print = (*env)->GetMethodID(env, disclass, "rawPrint",
                                        "(Lsun/jvm/hotspot/asm/InstructionVisitor;Ljava/lang/String;)V");
   if ((*env)->ExceptionOccurred(env)) {
+    (*env)->ReleaseByteArrayElements(env, code, start, JNI_ABORT);
+    (*env)->ReleaseStringUTFChars(env, options_s, options);
     return;
   }
 
   /* decode the buffer */
-  (*(decode_func)(uintptr_t)decode_instructions_virtual)(startPc,
+  (*(decode_func)(uintptr_t)decode_instructions_virtual)((uintptr_t) startPc,
                                                          startPc + end - start,
                                                          (unsigned char*)start,
                                                          end - start,