8049632: JDK 1.8.0 b132 :Linux x64 : Crash in ClassFileParser::copy_localvariable_table(..)
Summary: Use resource allocated hashtable for local variable table checking
Reviewed-by: kamg, sspitsyn
--- a/hotspot/src/share/vm/classfile/classFileParser.cpp Thu Jan 29 03:11:01 2015 -0800
+++ b/hotspot/src/share/vm/classfile/classFileParser.cpp Thu Jan 29 14:37:14 2015 -0500
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2015, 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
@@ -62,6 +62,7 @@
#include "utilities/globalDefinitions.hpp"
#include "utilities/macros.hpp"
#include "utilities/ostream.hpp"
+#include "utilities/resourceHash.hpp"
#if INCLUDE_CDS
#include "classfile/systemDictionaryShared.hpp"
#endif
@@ -693,7 +694,6 @@
}
-
class NameSigHash: public ResourceObj {
public:
Symbol* _name; // name
@@ -1370,6 +1370,33 @@
}
+class LVT_Hash : public AllStatic {
+ public:
+
+ static bool equals(LocalVariableTableElement const& e0, LocalVariableTableElement const& e1) {
+ /*
+ * 3-tuple start_bci/length/slot has to be unique key,
+ * so the following comparison seems to be redundant:
+ * && elem->name_cp_index == entry->_elem->name_cp_index
+ */
+ return (e0.start_bci == e1.start_bci &&
+ e0.length == e1.length &&
+ e0.name_cp_index == e1.name_cp_index &&
+ e0.slot == e1.slot);
+ }
+
+ static unsigned int hash(LocalVariableTableElement const& e0) {
+ unsigned int raw_hash = e0.start_bci;
+
+ raw_hash = e0.length + raw_hash * 37;
+ raw_hash = e0.name_cp_index + raw_hash * 37;
+ raw_hash = e0.slot + raw_hash * 37;
+
+ return raw_hash;
+ }
+};
+
+
// Class file LocalVariableTable elements.
class Classfile_LVT_Element VALUE_OBJ_CLASS_SPEC {
public:
@@ -1380,88 +1407,6 @@
u2 slot;
};
-
-class LVT_Hash: public CHeapObj<mtClass> {
- public:
- LocalVariableTableElement *_elem; // element
- LVT_Hash* _next; // Next entry in hash table
-};
-
-unsigned int hash(LocalVariableTableElement *elem) {
- unsigned int raw_hash = elem->start_bci;
-
- raw_hash = elem->length + raw_hash * 37;
- raw_hash = elem->name_cp_index + raw_hash * 37;
- raw_hash = elem->slot + raw_hash * 37;
-
- return raw_hash % HASH_ROW_SIZE;
-}
-
-void initialize_hashtable(LVT_Hash** table) {
- for (int i = 0; i < HASH_ROW_SIZE; i++) {
- table[i] = NULL;
- }
-}
-
-void clear_hashtable(LVT_Hash** table) {
- for (int i = 0; i < HASH_ROW_SIZE; i++) {
- LVT_Hash* current = table[i];
- LVT_Hash* next;
- while (current != NULL) {
- next = current->_next;
- current->_next = NULL;
- delete(current);
- current = next;
- }
- table[i] = NULL;
- }
-}
-
-LVT_Hash* LVT_lookup(LocalVariableTableElement *elem, int index, LVT_Hash** table) {
- LVT_Hash* entry = table[index];
-
- /*
- * 3-tuple start_bci/length/slot has to be unique key,
- * so the following comparison seems to be redundant:
- * && elem->name_cp_index == entry->_elem->name_cp_index
- */
- while (entry != NULL) {
- if (elem->start_bci == entry->_elem->start_bci
- && elem->length == entry->_elem->length
- && elem->name_cp_index == entry->_elem->name_cp_index
- && elem->slot == entry->_elem->slot
- ) {
- return entry;
- }
- entry = entry->_next;
- }
- return NULL;
-}
-
-// Return false if the local variable is found in table.
-// Return true if no duplicate is found.
-// And local variable is added as a new entry in table.
-bool LVT_put_after_lookup(LocalVariableTableElement *elem, LVT_Hash** table) {
- // First lookup for duplicates
- int index = hash(elem);
- LVT_Hash* entry = LVT_lookup(elem, index, table);
-
- if (entry != NULL) {
- return false;
- }
- // No duplicate is found, allocate a new entry and fill it.
- if ((entry = new LVT_Hash()) == NULL) {
- return false;
- }
- entry->_elem = elem;
-
- // Insert into hash table
- entry->_next = table[index];
- table[index] = entry;
-
- return true;
-}
-
void copy_lvt_element(Classfile_LVT_Element *src, LocalVariableTableElement *lvt) {
lvt->start_bci = Bytes::get_Java_u2((u1*) &src->start_bci);
lvt->length = Bytes::get_Java_u2((u1*) &src->length);
@@ -1861,8 +1806,12 @@
u2** localvariable_type_table_start,
TRAPS) {
- LVT_Hash** lvt_Hash = NEW_RESOURCE_ARRAY(LVT_Hash*, HASH_ROW_SIZE);
- initialize_hashtable(lvt_Hash);
+ ResourceMark rm(THREAD);
+
+ typedef ResourceHashtable<LocalVariableTableElement, LocalVariableTableElement*,
+ &LVT_Hash::hash, &LVT_Hash::equals> LVT_HashTable;
+
+ LVT_HashTable* table = new LVT_HashTable();
// To fill LocalVariableTable in
Classfile_LVT_Element* cf_lvt;
@@ -1872,11 +1821,10 @@
cf_lvt = (Classfile_LVT_Element *) localvariable_table_start[tbl_no];
for (int idx = 0; idx < localvariable_table_length[tbl_no]; idx++, lvt++) {
copy_lvt_element(&cf_lvt[idx], lvt);
- // If no duplicates, add LVT elem in hashtable lvt_Hash.
- if (LVT_put_after_lookup(lvt, lvt_Hash) == false
+ // If no duplicates, add LVT elem in hashtable.
+ if (table->put(*lvt, lvt) == false
&& _need_verify
&& _major_version >= JAVA_1_5_VERSION) {
- clear_hashtable(lvt_Hash);
classfile_parse_error("Duplicated LocalVariableTable attribute "
"entry for '%s' in class file %s",
_cp->symbol_at(lvt->name_cp_index)->as_utf8(),
@@ -1893,29 +1841,25 @@
cf_lvtt = (Classfile_LVT_Element *) localvariable_type_table_start[tbl_no];
for (int idx = 0; idx < localvariable_type_table_length[tbl_no]; idx++) {
copy_lvt_element(&cf_lvtt[idx], &lvtt_elem);
- int index = hash(&lvtt_elem);
- LVT_Hash* entry = LVT_lookup(&lvtt_elem, index, lvt_Hash);
+ LocalVariableTableElement** entry = table->get(lvtt_elem);
if (entry == NULL) {
if (_need_verify) {
- clear_hashtable(lvt_Hash);
classfile_parse_error("LVTT entry for '%s' in class file %s "
"does not match any LVT entry",
_cp->symbol_at(lvtt_elem.name_cp_index)->as_utf8(),
CHECK);
}
- } else if (entry->_elem->signature_cp_index != 0 && _need_verify) {
- clear_hashtable(lvt_Hash);
+ } else if ((*entry)->signature_cp_index != 0 && _need_verify) {
classfile_parse_error("Duplicated LocalVariableTypeTable attribute "
"entry for '%s' in class file %s",
_cp->symbol_at(lvtt_elem.name_cp_index)->as_utf8(),
CHECK);
} else {
// to add generic signatures into LocalVariableTable
- entry->_elem->signature_cp_index = lvtt_elem.descriptor_cp_index;
+ (*entry)->signature_cp_index = lvtt_elem.descriptor_cp_index;
}
}
}
- clear_hashtable(lvt_Hash);
}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/LocalVariableTable/DuplicateLVT.cod Thu Jan 29 14:37:14 2015 -0500
@@ -0,0 +1,293 @@
+/*
+ * Copyright (c) 2015, 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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+// This creates a duplicate LVT entry
+
+class DuplicateLVT {
+ 0xCAFEBABE;
+ 0; // minor version
+ 52; // version
+ [] { // Constant Pool
+ ; // first element is empty
+ Method #34 #68; // #1
+ double 0x3FF199999999999A;; // #2
+ float 0x3F99999A; // #4
+ long 0xFFFFFFFFCAFEBABE;; // #5
+ class #69; // #7
+ Method #7 #68; // #8
+ String #70; // #9
+ Method #7 #71; // #10
+ Field #72 #73; // #11
+ class #74; // #12
+ Method #12 #68; // #13
+ String #75; // #14
+ Method #12 #76; // #15
+ Method #12 #77; // #16
+ Method #12 #78; // #17
+ Method #79 #80; // #18
+ String #81; // #19
+ Method #12 #82; // #20
+ String #83; // #21
+ Method #12 #84; // #22
+ String #85; // #23
+ Method #12 #86; // #24
+ String #87; // #25
+ Method #12 #88; // #26
+ String #89; // #27
+ String #90; // #28
+ Method #12 #91; // #29
+ String #92; // #30
+ String #93; // #31
+ Method #12 #94; // #32
+ class #95; // #33
+ class #96; // #34
+ Utf8 "<init>"; // #35
+ Utf8 "()V"; // #36
+ Utf8 "Code"; // #37
+ Utf8 "LineNumberTable"; // #38
+ Utf8 "LocalVariableTable"; // #39
+ Utf8 "this"; // #40
+ Utf8 "LDuplicateLVT;"; // #41
+ Utf8 "main"; // #42
+ Utf8 "([Ljava/lang/String;)V"; // #43
+ Utf8 "args"; // #44
+ Utf8 "[Ljava/lang/String;"; // #45
+ Utf8 "b"; // #46
+ Utf8 "Z"; // #47
+ Utf8 "by"; // #48
+ Utf8 "B"; // #49
+ Utf8 "c"; // #50
+ Utf8 "C"; // #51
+ Utf8 "d"; // #52
+ Utf8 "D"; // #53
+ Utf8 "f"; // #54
+ Utf8 "F"; // #55
+ Utf8 "i"; // #56
+ Utf8 "I"; // #57
+ Utf8 "l"; // #58
+ Utf8 "J"; // #59
+ Utf8 "s"; // #60
+ Utf8 "S"; // #61
+ Utf8 "list"; // #62
+ Utf8 "Ljava/util/ArrayList;"; // #63
+ Utf8 "LocalVariableTypeTable"; // #64
+ Utf8 "Ljava/util/ArrayList<Ljava/lang/String;>;"; // #65
+ Utf8 "SourceFile"; // #66
+ Utf8 "DuplicateLVT.java"; // #67
+ NameAndType #35 #36; // #68
+ Utf8 "java/util/ArrayList"; // #69
+ Utf8 "me"; // #70
+ NameAndType #97 #98; // #71
+ class #99; // #72
+ NameAndType #100 #101; // #73
+ Utf8 "java/lang/StringBuilder"; // #74
+ Utf8 "b="; // #75
+ NameAndType #102 #103; // #76
+ NameAndType #102 #104; // #77
+ NameAndType #105 #106; // #78
+ class #107; // #79
+ NameAndType #108 #109; // #80
+ Utf8 "by="; // #81
+ NameAndType #102 #110; // #82
+ Utf8 "c="; // #83
+ NameAndType #102 #111; // #84
+ Utf8 "d="; // #85
+ NameAndType #102 #112; // #86
+ Utf8 "f="; // #87
+ NameAndType #102 #113; // #88
+ Utf8 "i="; // #89
+ Utf8 "l="; // #90
+ NameAndType #102 #114; // #91
+ Utf8 "s="; // #92
+ Utf8 "ArrayList<String>="; // #93
+ NameAndType #102 #115; // #94
+ Utf8 "DuplicateLVT"; // #95
+ Utf8 "java/lang/Object"; // #96
+ Utf8 "add"; // #97
+ Utf8 "(Ljava/lang/Object;)Z"; // #98
+ Utf8 "java/lang/System"; // #99
+ Utf8 "out"; // #100
+ Utf8 "Ljava/io/PrintStream;"; // #101
+ Utf8 "append"; // #102
+ Utf8 "(Ljava/lang/String;)Ljava/lang/StringBuilder;"; // #103
+ Utf8 "(Z)Ljava/lang/StringBuilder;"; // #104
+ Utf8 "toString"; // #105
+ Utf8 "()Ljava/lang/String;"; // #106
+ Utf8 "java/io/PrintStream"; // #107
+ Utf8 "println"; // #108
+ Utf8 "(Ljava/lang/String;)V"; // #109
+ Utf8 "(I)Ljava/lang/StringBuilder;"; // #110
+ Utf8 "(C)Ljava/lang/StringBuilder;"; // #111
+ Utf8 "(D)Ljava/lang/StringBuilder;"; // #112
+ Utf8 "(F)Ljava/lang/StringBuilder;"; // #113
+ Utf8 "(J)Ljava/lang/StringBuilder;"; // #114
+ Utf8 "(Ljava/lang/Object;)Ljava/lang/StringBuilder;"; // #115
+ } // Constant Pool
+
+ 0x0021; // access
+ #33;// this_cpx
+ #34;// super_cpx
+
+ [] { // Interfaces
+ } // Interfaces
+
+ [] { // fields
+ } // fields
+
+ [] { // methods
+ { // Member
+ 0x0001; // access
+ #35; // name_cpx
+ #36; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 1; // max_stack
+ 1; // max_locals
+ Bytes[]{
+ 0x2AB70001B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 26;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 5 40 41 0;
+ }
+ } // end LocalVariableTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ ;
+ { // Member
+ 0x0009; // access
+ #42; // name_cpx
+ #43; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 4; // max_stack
+ 12; // max_locals
+ Bytes[]{
+ 0x043C10423D10583E;
+ 0x1400023904120438;
+ 0x06102A3607140005;
+ 0x37081058360ABB00;
+ 0x0759B700083A0B19;
+ 0x0B1209B6000A57B2;
+ 0x000BBB000C59B700;
+ 0x0D120EB6000F1BB6;
+ 0x0010B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D1213B6000F1C;
+ 0xB60014B60011B600;
+ 0x12B2000BBB000C59;
+ 0xB7000D1215B6000F;
+ 0x1DB60016B60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D1217B600;
+ 0x0F1804B60018B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D1219;
+ 0xB6000F1706B6001A;
+ 0xB60011B60012B200;
+ 0x0BBB000C59B7000D;
+ 0x121BB6000F1507B6;
+ 0x0014B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D121CB6000F16;
+ 0x08B6001DB60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D121EB600;
+ 0x0F150AB60014B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D121F;
+ 0xB6000F190BB60020;
+ 0xB60011B60012B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 28;
+ 2 29;
+ 5 30;
+ 8 31;
+ 13 32;
+ 17 33;
+ 21 34;
+ 26 35;
+ 30 36;
+ 39 37;
+ 47 39;
+ 72 40;
+ 97 41;
+ 122 42;
+ 148 43;
+ 174 44;
+ 200 45;
+ 226 46;
+ 252 47;
+ 278 48;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 279 44 45 0;
+ 2 277 46 47 1;
+ 5 274 48 49 2;
+ 5 274 48 49 2;
+ 8 271 50 51 3;
+ 13 266 52 53 4;
+ 17 262 54 55 6;
+ 21 258 56 57 7;
+ 26 253 58 59 8;
+ 30 249 60 61 10;
+ 39 240 62 63 11;
+ }
+ } // end LocalVariableTable
+ ;
+ Attr(#64) { // LocalVariableTypeTable
+ [] { // LocalVariableTypeTable
+ 39 240 62 65 11;
+ }
+ } // end LocalVariableTypeTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ } // methods
+
+ [] { // Attributes
+ Attr(#66) { // SourceFile
+ #67;
+ } // end SourceFile
+ } // Attributes
+} // end class DuplicateLVT
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/LocalVariableTable/DuplicateLVTT.cod Thu Jan 29 14:37:14 2015 -0500
@@ -0,0 +1,293 @@
+/*
+ * Copyright (c) 2015, 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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+// There's a duplicate LVTT entry below.
+
+class DuplicateLVTT {
+ 0xCAFEBABE;
+ 0; // minor version
+ 52; // version
+ [] { // Constant Pool
+ ; // first element is empty
+ Method #34 #68; // #1
+ double 0x3FF199999999999A;; // #2
+ float 0x3F99999A; // #4
+ long 0xFFFFFFFFCAFEBABE;; // #5
+ class #69; // #7
+ Method #7 #68; // #8
+ String #70; // #9
+ Method #7 #71; // #10
+ Field #72 #73; // #11
+ class #74; // #12
+ Method #12 #68; // #13
+ String #75; // #14
+ Method #12 #76; // #15
+ Method #12 #77; // #16
+ Method #12 #78; // #17
+ Method #79 #80; // #18
+ String #81; // #19
+ Method #12 #82; // #20
+ String #83; // #21
+ Method #12 #84; // #22
+ String #85; // #23
+ Method #12 #86; // #24
+ String #87; // #25
+ Method #12 #88; // #26
+ String #89; // #27
+ String #90; // #28
+ Method #12 #91; // #29
+ String #92; // #30
+ String #93; // #31
+ Method #12 #94; // #32
+ class #95; // #33
+ class #96; // #34
+ Utf8 "<init>"; // #35
+ Utf8 "()V"; // #36
+ Utf8 "Code"; // #37
+ Utf8 "LineNumberTable"; // #38
+ Utf8 "LocalVariableTable"; // #39
+ Utf8 "this"; // #40
+ Utf8 "LDuplicateLVTT;"; // #41
+ Utf8 "main"; // #42
+ Utf8 "([Ljava/lang/String;)V"; // #43
+ Utf8 "args"; // #44
+ Utf8 "[Ljava/lang/String;"; // #45
+ Utf8 "b"; // #46
+ Utf8 "Z"; // #47
+ Utf8 "by"; // #48
+ Utf8 "B"; // #49
+ Utf8 "c"; // #50
+ Utf8 "C"; // #51
+ Utf8 "d"; // #52
+ Utf8 "D"; // #53
+ Utf8 "f"; // #54
+ Utf8 "F"; // #55
+ Utf8 "i"; // #56
+ Utf8 "I"; // #57
+ Utf8 "l"; // #58
+ Utf8 "J"; // #59
+ Utf8 "s"; // #60
+ Utf8 "S"; // #61
+ Utf8 "list"; // #62
+ Utf8 "Ljava/util/ArrayList;"; // #63
+ Utf8 "LocalVariableTypeTable"; // #64
+ Utf8 "Ljava/util/ArrayList<Ljava/lang/String;>;"; // #65
+ Utf8 "SourceFile"; // #66
+ Utf8 "DuplicateLVTT.java"; // #67
+ NameAndType #35 #36; // #68
+ Utf8 "java/util/ArrayList"; // #69
+ Utf8 "me"; // #70
+ NameAndType #97 #98; // #71
+ class #99; // #72
+ NameAndType #100 #101; // #73
+ Utf8 "java/lang/StringBuilder"; // #74
+ Utf8 "b="; // #75
+ NameAndType #102 #103; // #76
+ NameAndType #102 #104; // #77
+ NameAndType #105 #106; // #78
+ class #107; // #79
+ NameAndType #108 #109; // #80
+ Utf8 "by="; // #81
+ NameAndType #102 #110; // #82
+ Utf8 "c="; // #83
+ NameAndType #102 #111; // #84
+ Utf8 "d="; // #85
+ NameAndType #102 #112; // #86
+ Utf8 "f="; // #87
+ NameAndType #102 #113; // #88
+ Utf8 "i="; // #89
+ Utf8 "l="; // #90
+ NameAndType #102 #114; // #91
+ Utf8 "s="; // #92
+ Utf8 "ArrayList<String>="; // #93
+ NameAndType #102 #115; // #94
+ Utf8 "DuplicateLVTT"; // #95
+ Utf8 "java/lang/Object"; // #96
+ Utf8 "add"; // #97
+ Utf8 "(Ljava/lang/Object;)Z"; // #98
+ Utf8 "java/lang/System"; // #99
+ Utf8 "out"; // #100
+ Utf8 "Ljava/io/PrintStream;"; // #101
+ Utf8 "append"; // #102
+ Utf8 "(Ljava/lang/String;)Ljava/lang/StringBuilder;"; // #103
+ Utf8 "(Z)Ljava/lang/StringBuilder;"; // #104
+ Utf8 "toString"; // #105
+ Utf8 "()Ljava/lang/String;"; // #106
+ Utf8 "java/io/PrintStream"; // #107
+ Utf8 "println"; // #108
+ Utf8 "(Ljava/lang/String;)V"; // #109
+ Utf8 "(I)Ljava/lang/StringBuilder;"; // #110
+ Utf8 "(C)Ljava/lang/StringBuilder;"; // #111
+ Utf8 "(D)Ljava/lang/StringBuilder;"; // #112
+ Utf8 "(F)Ljava/lang/StringBuilder;"; // #113
+ Utf8 "(J)Ljava/lang/StringBuilder;"; // #114
+ Utf8 "(Ljava/lang/Object;)Ljava/lang/StringBuilder;"; // #115
+ } // Constant Pool
+
+ 0x0021; // access
+ #33;// this_cpx
+ #34;// super_cpx
+
+ [] { // Interfaces
+ } // Interfaces
+
+ [] { // fields
+ } // fields
+
+ [] { // methods
+ { // Member
+ 0x0001; // access
+ #35; // name_cpx
+ #36; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 1; // max_stack
+ 1; // max_locals
+ Bytes[]{
+ 0x2AB70001B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 26;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 5 40 41 0;
+ }
+ } // end LocalVariableTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ ;
+ { // Member
+ 0x0009; // access
+ #42; // name_cpx
+ #43; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 4; // max_stack
+ 12; // max_locals
+ Bytes[]{
+ 0x043C10423D10583E;
+ 0x1400023904120438;
+ 0x06102A3607140005;
+ 0x37081058360ABB00;
+ 0x0759B700083A0B19;
+ 0x0B1209B6000A57B2;
+ 0x000BBB000C59B700;
+ 0x0D120EB6000F1BB6;
+ 0x0010B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D1213B6000F1C;
+ 0xB60014B60011B600;
+ 0x12B2000BBB000C59;
+ 0xB7000D1215B6000F;
+ 0x1DB60016B60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D1217B600;
+ 0x0F1804B60018B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D1219;
+ 0xB6000F1706B6001A;
+ 0xB60011B60012B200;
+ 0x0BBB000C59B7000D;
+ 0x121BB6000F1507B6;
+ 0x0014B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D121CB6000F16;
+ 0x08B6001DB60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D121EB600;
+ 0x0F150AB60014B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D121F;
+ 0xB6000F190BB60020;
+ 0xB60011B60012B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 28;
+ 2 29;
+ 5 30;
+ 8 31;
+ 13 32;
+ 17 33;
+ 21 34;
+ 26 35;
+ 30 36;
+ 39 37;
+ 47 39;
+ 72 40;
+ 97 41;
+ 122 42;
+ 148 43;
+ 174 44;
+ 200 45;
+ 226 46;
+ 252 47;
+ 278 48;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 279 44 45 0;
+ 2 277 46 47 1;
+ 5 274 48 49 2;
+ 8 271 50 51 3;
+ 13 266 52 53 4;
+ 17 262 54 55 6;
+ 21 258 56 57 7;
+ 26 253 58 59 8;
+ 30 249 60 61 10;
+ 39 240 62 63 11;
+ }
+ } // end LocalVariableTable
+ ;
+ Attr(#64) { // LocalVariableTypeTable
+ [] { // LocalVariableTypeTable
+ 39 240 62 65 11;
+ 39 240 62 65 11;
+ }
+ } // end LocalVariableTypeTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ } // methods
+
+ [] { // Attributes
+ Attr(#66) { // SourceFile
+ #67;
+ } // end SourceFile
+ } // Attributes
+} // end class DuplicateLVTT
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/LocalVariableTable/NotFoundLVTT.cod Thu Jan 29 14:37:14 2015 -0500
@@ -0,0 +1,292 @@
+/*
+ * Copyright (c) 2015, 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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+// The LVTT entry points to a non-existant LVT entry
+
+class NotFoundLVTT {
+ 0xCAFEBABE;
+ 0; // minor version
+ 52; // version
+ [] { // Constant Pool
+ ; // first element is empty
+ Method #34 #68; // #1
+ double 0x3FF199999999999A;; // #2
+ float 0x3F99999A; // #4
+ long 0xFFFFFFFFCAFEBABE;; // #5
+ class #69; // #7
+ Method #7 #68; // #8
+ String #70; // #9
+ Method #7 #71; // #10
+ Field #72 #73; // #11
+ class #74; // #12
+ Method #12 #68; // #13
+ String #75; // #14
+ Method #12 #76; // #15
+ Method #12 #77; // #16
+ Method #12 #78; // #17
+ Method #79 #80; // #18
+ String #81; // #19
+ Method #12 #82; // #20
+ String #83; // #21
+ Method #12 #84; // #22
+ String #85; // #23
+ Method #12 #86; // #24
+ String #87; // #25
+ Method #12 #88; // #26
+ String #89; // #27
+ String #90; // #28
+ Method #12 #91; // #29
+ String #92; // #30
+ String #93; // #31
+ Method #12 #94; // #32
+ class #95; // #33
+ class #96; // #34
+ Utf8 "<init>"; // #35
+ Utf8 "()V"; // #36
+ Utf8 "Code"; // #37
+ Utf8 "LineNumberTable"; // #38
+ Utf8 "LocalVariableTable"; // #39
+ Utf8 "this"; // #40
+ Utf8 "LNotFoundLVTT;"; // #41
+ Utf8 "main"; // #42
+ Utf8 "([Ljava/lang/String;)V"; // #43
+ Utf8 "args"; // #44
+ Utf8 "[Ljava/lang/String;"; // #45
+ Utf8 "b"; // #46
+ Utf8 "Z"; // #47
+ Utf8 "by"; // #48
+ Utf8 "B"; // #49
+ Utf8 "c"; // #50
+ Utf8 "C"; // #51
+ Utf8 "d"; // #52
+ Utf8 "D"; // #53
+ Utf8 "f"; // #54
+ Utf8 "F"; // #55
+ Utf8 "i"; // #56
+ Utf8 "I"; // #57
+ Utf8 "l"; // #58
+ Utf8 "J"; // #59
+ Utf8 "s"; // #60
+ Utf8 "S"; // #61
+ Utf8 "list"; // #62
+ Utf8 "Ljava/util/ArrayList;"; // #63
+ Utf8 "LocalVariableTypeTable"; // #64
+ Utf8 "Ljava/util/ArrayList<Ljava/lang/String;>;"; // #65
+ Utf8 "SourceFile"; // #66
+ Utf8 "NotFoundLVTT.java"; // #67
+ NameAndType #35 #36; // #68
+ Utf8 "java/util/ArrayList"; // #69
+ Utf8 "me"; // #70
+ NameAndType #97 #98; // #71
+ class #99; // #72
+ NameAndType #100 #101; // #73
+ Utf8 "java/lang/StringBuilder"; // #74
+ Utf8 "b="; // #75
+ NameAndType #102 #103; // #76
+ NameAndType #102 #104; // #77
+ NameAndType #105 #106; // #78
+ class #107; // #79
+ NameAndType #108 #109; // #80
+ Utf8 "by="; // #81
+ NameAndType #102 #110; // #82
+ Utf8 "c="; // #83
+ NameAndType #102 #111; // #84
+ Utf8 "d="; // #85
+ NameAndType #102 #112; // #86
+ Utf8 "f="; // #87
+ NameAndType #102 #113; // #88
+ Utf8 "i="; // #89
+ Utf8 "l="; // #90
+ NameAndType #102 #114; // #91
+ Utf8 "s="; // #92
+ Utf8 "ArrayList<String>="; // #93
+ NameAndType #102 #115; // #94
+ Utf8 "NotFoundLVTT"; // #95
+ Utf8 "java/lang/Object"; // #96
+ Utf8 "add"; // #97
+ Utf8 "(Ljava/lang/Object;)Z"; // #98
+ Utf8 "java/lang/System"; // #99
+ Utf8 "out"; // #100
+ Utf8 "Ljava/io/PrintStream;"; // #101
+ Utf8 "append"; // #102
+ Utf8 "(Ljava/lang/String;)Ljava/lang/StringBuilder;"; // #103
+ Utf8 "(Z)Ljava/lang/StringBuilder;"; // #104
+ Utf8 "toString"; // #105
+ Utf8 "()Ljava/lang/String;"; // #106
+ Utf8 "java/io/PrintStream"; // #107
+ Utf8 "println"; // #108
+ Utf8 "(Ljava/lang/String;)V"; // #109
+ Utf8 "(I)Ljava/lang/StringBuilder;"; // #110
+ Utf8 "(C)Ljava/lang/StringBuilder;"; // #111
+ Utf8 "(D)Ljava/lang/StringBuilder;"; // #112
+ Utf8 "(F)Ljava/lang/StringBuilder;"; // #113
+ Utf8 "(J)Ljava/lang/StringBuilder;"; // #114
+ Utf8 "(Ljava/lang/Object;)Ljava/lang/StringBuilder;"; // #115
+ } // Constant Pool
+
+ 0x0021; // access
+ #33;// this_cpx
+ #34;// super_cpx
+
+ [] { // Interfaces
+ } // Interfaces
+
+ [] { // fields
+ } // fields
+
+ [] { // methods
+ { // Member
+ 0x0001; // access
+ #35; // name_cpx
+ #36; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 1; // max_stack
+ 1; // max_locals
+ Bytes[]{
+ 0x2AB70001B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 26;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 5 40 41 0;
+ }
+ } // end LocalVariableTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ ;
+ { // Member
+ 0x0009; // access
+ #42; // name_cpx
+ #43; // sig_cpx
+ [] { // Attributes
+ Attr(#37) { // Code
+ 4; // max_stack
+ 12; // max_locals
+ Bytes[]{
+ 0x043C10423D10583E;
+ 0x1400023904120438;
+ 0x06102A3607140005;
+ 0x37081058360ABB00;
+ 0x0759B700083A0B19;
+ 0x0B1209B6000A57B2;
+ 0x000BBB000C59B700;
+ 0x0D120EB6000F1BB6;
+ 0x0010B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D1213B6000F1C;
+ 0xB60014B60011B600;
+ 0x12B2000BBB000C59;
+ 0xB7000D1215B6000F;
+ 0x1DB60016B60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D1217B600;
+ 0x0F1804B60018B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D1219;
+ 0xB6000F1706B6001A;
+ 0xB60011B60012B200;
+ 0x0BBB000C59B7000D;
+ 0x121BB6000F1507B6;
+ 0x0014B60011B60012;
+ 0xB2000BBB000C59B7;
+ 0x000D121CB6000F16;
+ 0x08B6001DB60011B6;
+ 0x0012B2000BBB000C;
+ 0x59B7000D121EB600;
+ 0x0F150AB60014B600;
+ 0x11B60012B2000BBB;
+ 0x000C59B7000D121F;
+ 0xB6000F190BB60020;
+ 0xB60011B60012B1;
+ };
+ [] { // Traps
+ } // end Traps
+ [] { // Attributes
+ Attr(#38) { // LineNumberTable
+ [] { // LineNumberTable
+ 0 28;
+ 2 29;
+ 5 30;
+ 8 31;
+ 13 32;
+ 17 33;
+ 21 34;
+ 26 35;
+ 30 36;
+ 39 37;
+ 47 39;
+ 72 40;
+ 97 41;
+ 122 42;
+ 148 43;
+ 174 44;
+ 200 45;
+ 226 46;
+ 252 47;
+ 278 48;
+ }
+ } // end LineNumberTable
+ ;
+ Attr(#39) { // LocalVariableTable
+ [] { // LocalVariableTable
+ 0 279 44 45 0;
+ 2 277 46 47 1;
+ 5 274 48 49 2;
+ 8 271 50 51 3;
+ 13 266 52 53 4;
+ 17 262 54 55 6;
+ 21 258 56 57 7;
+ 26 253 58 59 8;
+ 30 249 60 61 10;
+ 39 240 62 63 11;
+ }
+ } // end LocalVariableTable
+ ;
+ Attr(#64) { // LocalVariableTypeTable
+ [] { // LocalVariableTypeTable
+ 38 240 62 65 11;
+ }
+ } // end LocalVariableTypeTable
+ } // Attributes
+ } // end Code
+ } // Attributes
+ } // Member
+ } // methods
+
+ [] { // Attributes
+ Attr(#66) { // SourceFile
+ #67;
+ } // end SourceFile
+ } // Attributes
+} // end class NotFoundLVTT
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/LocalVariableTable/TestLVT.java Thu Jan 29 14:37:14 2015 -0500
@@ -0,0 +1,83 @@
+/*
+ * Copyright (c) 2015, 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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @bug 8049632
+ * @summary Test ClassFileParser::copy_localvariable_table cases
+ * @library /testlibrary
+ * @compile -g -XDignore.symbol.file TestLVT.java
+ * @run main TestLVT
+ */
+
+import com.oracle.java.testlibrary.*;
+import java.util.*;
+
+public class TestLVT {
+ public static void main(String[] args) throws Exception {
+ test(); // Test good LVT in this test
+
+ String jarFile = System.getProperty("test.src") + "/testcase.jar";
+
+ // java -cp $testSrc/testcase.jar DuplicateLVT
+ ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-cp", jarFile, "DuplicateLVT");
+ new OutputAnalyzer(pb.start())
+ .shouldContain("Duplicated LocalVariableTable attribute entry for 'by' in class file DuplicateLVT")
+ .shouldHaveExitValue(1);
+
+ // java -cp $testclasses/testcase.jar DuplicateLVTT
+ pb = ProcessTools.createJavaProcessBuilder("-cp", jarFile, "DuplicateLVTT");
+ new OutputAnalyzer(pb.start())
+ .shouldContain("Duplicated LocalVariableTypeTable attribute entry for 'list' in class file DuplicateLVTT")
+ .shouldHaveExitValue(1);
+
+ // java -cp $testclasses/testcase.jar NotFoundLVTT
+ pb = ProcessTools.createJavaProcessBuilder("-cp", jarFile, "NotFoundLVTT");
+ new OutputAnalyzer(pb.start())
+ .shouldContain("LVTT entry for 'list' in class file NotFoundLVTT does not match any LVT entry")
+ .shouldHaveExitValue(1);
+ }
+
+ public static void test() {
+ boolean b = true;
+ byte by = 0x42;
+ char c = 'X';
+ double d = 1.1;
+ float f = (float) 1.2;
+ int i = 42;
+ long l = 0xCAFEBABE;
+ short s = 88;
+ ArrayList<String> list = new ArrayList<String>();
+ list.add("me");
+
+ System.out.println("b=" + b);
+ System.out.println("by=" + by);
+ System.out.println("c=" + c);
+ System.out.println("d=" + d);
+ System.out.println("f=" + f);
+ System.out.println("i=" + i);
+ System.out.println("l=" + l);
+ System.out.println("s=" + s);
+ System.out.println("ArrayList<String>=" + list);
+ }
+}
Binary file hotspot/test/runtime/LocalVariableTable/testcase.jar has changed