src/share/vm/classfile/verifier.cpp

Print this page

        

@@ -1,7 +1,7 @@
 /*
- * Copyright (c) 1998, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
  * under the terms of the GNU General Public License version 2 only, as
  * published by the Free Software Foundation.

@@ -1366,18 +1366,19 @@
 
   return code_data;
 }
 
 void ClassVerifier::verify_exception_handler_table(u4 code_length, char* code_data, int& min, int& max, TRAPS) {
-  typeArrayHandle exhandlers (THREAD, _method->exception_table());
+  ExceptionTable exhandlers(_method());
   constantPoolHandle cp (THREAD, _method->constants());
 
-  if (exhandlers() != NULL) {
-    for(int i = 0; i < exhandlers->length();) {
-      u2 start_pc = exhandlers->int_at(i++);
-      u2 end_pc = exhandlers->int_at(i++);
-      u2 handler_pc = exhandlers->int_at(i++);
+  for(int i = 0; i < exhandlers.length(); i++) {
+    //reacquire the table in case a GC happened
+    ExceptionTable exhandlers(_method());
+    u2 start_pc = exhandlers.start_pc(i);
+    u2 end_pc = exhandlers.end_pc(i);
+    u2 handler_pc = exhandlers.handler_pc(i);
       if (start_pc >= code_length || code_data[start_pc] == 0) {
         class_format_error("Illegal exception table start_pc %d", start_pc);
         return;
       }
       if (end_pc != code_length) {   // special case: end_pc == code_length

@@ -1388,11 +1389,11 @@
       }
       if (handler_pc >= code_length || code_data[handler_pc] == 0) {
         class_format_error("Illegal exception table handler_pc %d", handler_pc);
         return;
       }
-      int catch_type_index = exhandlers->int_at(i++);
+    int catch_type_index = exhandlers.catch_type_index(i);
       if (catch_type_index != 0) {
         VerificationType catch_type = cp_index_to_type(
           catch_type_index, cp, CHECK_VERIFY(this));
         VerificationType throwable =
           VerificationType::reference_type(vmSymbols::java_lang_Throwable());

@@ -1407,11 +1408,10 @@
         }
       }
       if (start_pc < min) min = start_pc;
       if (end_pc > max) max = end_pc;
     }
-  }
 }
 
 void ClassVerifier::verify_local_variable_table(u4 code_length, char* code_data, TRAPS) {
   int localvariable_table_length = _method()->localvariable_table_length();
   if (localvariable_table_length > 0) {

@@ -1472,17 +1472,18 @@
 }
 
 void ClassVerifier::verify_exception_handler_targets(u2 bci, bool this_uninit, StackMapFrame* current_frame,
                                                      StackMapTable* stackmap_table, TRAPS) {
   constantPoolHandle cp (THREAD, _method->constants());
-  typeArrayHandle exhandlers (THREAD, _method->exception_table());
-  if (exhandlers() != NULL) {
-    for(int i = 0; i < exhandlers->length();) {
-      u2 start_pc = exhandlers->int_at(i++);
-      u2 end_pc = exhandlers->int_at(i++);
-      u2 handler_pc = exhandlers->int_at(i++);
-      int catch_type_index = exhandlers->int_at(i++);
+  ExceptionTable exhandlers(_method());
+  for(int i = 0; i < exhandlers.length(); i++) {
+    //reacquire the table in case a GC happened
+    ExceptionTable exhandlers(_method());
+    u2 start_pc = exhandlers.start_pc(i);
+    u2 end_pc = exhandlers.end_pc(i);
+    u2 handler_pc = exhandlers.handler_pc(i);
+    int catch_type_index = exhandlers.catch_type_index(i);
       if(bci >= start_pc && bci < end_pc) {
         u1 flags = current_frame->flags();
         if (this_uninit) {  flags |= FLAG_THIS_UNINIT; }
         StackMapFrame* new_frame = current_frame->frame_in_exception_handler(flags);
         if (catch_type_index != 0) {

@@ -1503,11 +1504,10 @@
             handler_pc);
           return;
         }
       }
     }
-  }
 }
 
 void ClassVerifier::verify_cp_index(constantPoolHandle cp, int index, TRAPS) {
   int nconstants = cp->length();
   if ((index <= 0) || (index >= nconstants)) {