提交 473329eb 编写于 作者: S sspitsyn

8005128: JSR 292: the mlvm redefineClassInBootstrap test crashes in ConstantPool::compare_entry_to

Summary: When constant pool is copied in merge_constant_pools the invokedynamic operands must be copied before.
Reviewed-by: coleenp, twisti
Contributed-by: serguei.spitsyn@oracle.com
上级 7dc0d7c0
......@@ -1098,32 +1098,9 @@ bool ConstantPool::compare_entry_to(int index1, constantPoolHandle cp2,
} // end compare_entry_to()
// Copy this constant pool's entries at start_i to end_i (inclusive)
// to the constant pool to_cp's entries starting at to_i. A total of
// (end_i - start_i) + 1 entries are copied.
void ConstantPool::copy_cp_to_impl(constantPoolHandle from_cp, int start_i, int end_i,
constantPoolHandle to_cp, int to_i, TRAPS) {
int dest_i = to_i; // leave original alone for debug purposes
for (int src_i = start_i; src_i <= end_i; /* see loop bottom */ ) {
copy_entry_to(from_cp, src_i, to_cp, dest_i, CHECK);
switch (from_cp->tag_at(src_i).value()) {
case JVM_CONSTANT_Double:
case JVM_CONSTANT_Long:
// double and long take two constant pool entries
src_i += 2;
dest_i += 2;
break;
default:
// all others take one constant pool entry
src_i++;
dest_i++;
break;
}
}
void ConstantPool::copy_operands(constantPoolHandle from_cp,
constantPoolHandle to_cp,
TRAPS) {
int from_oplen = operand_array_length(from_cp->operands());
int old_oplen = operand_array_length(to_cp->operands());
......@@ -1179,8 +1156,39 @@ void ConstantPool::copy_cp_to_impl(constantPoolHandle from_cp, int start_i, int
to_cp->set_operands(new_operands);
}
}
} // end copy_operands()
// Copy this constant pool's entries at start_i to end_i (inclusive)
// to the constant pool to_cp's entries starting at to_i. A total of
// (end_i - start_i) + 1 entries are copied.
void ConstantPool::copy_cp_to_impl(constantPoolHandle from_cp, int start_i, int end_i,
constantPoolHandle to_cp, int to_i, TRAPS) {
int dest_i = to_i; // leave original alone for debug purposes
for (int src_i = start_i; src_i <= end_i; /* see loop bottom */ ) {
copy_entry_to(from_cp, src_i, to_cp, dest_i, CHECK);
switch (from_cp->tag_at(src_i).value()) {
case JVM_CONSTANT_Double:
case JVM_CONSTANT_Long:
// double and long take two constant pool entries
src_i += 2;
dest_i += 2;
break;
default:
// all others take one constant pool entry
src_i++;
dest_i++;
break;
}
}
copy_operands(from_cp, to_cp, CHECK);
} // end copy_cp_to()
} // end copy_cp_to_impl()
// Copy this constant pool's entry at from_i to the constant pool
......
......@@ -781,6 +781,7 @@ class ConstantPool : public Metadata {
}
static void copy_cp_to_impl(constantPoolHandle from_cp, int start_i, int end_i, constantPoolHandle to_cp, int to_i, TRAPS);
static void copy_entry_to(constantPoolHandle from_cp, int from_i, constantPoolHandle to_cp, int to_i, TRAPS);
static void copy_operands(constantPoolHandle from_cp, constantPoolHandle to_cp, TRAPS);
int find_matching_entry(int pattern_i, constantPoolHandle search_cp, TRAPS);
int version() const { return _saved._version; }
void set_version(int version) { _saved._version = version; }
......
......@@ -1122,6 +1122,8 @@ bool VM_RedefineClasses::merge_constant_pools(constantPoolHandle old_cp,
}
} // end for each old_cp entry
ConstantPool::copy_operands(old_cp, *merge_cp_p, CHECK_0);
// We don't need to sanity check that *merge_cp_length_p is within
// *merge_cp_p bounds since we have the minimum on-entry check above.
(*merge_cp_length_p) = old_i;
......@@ -1305,8 +1307,12 @@ jvmtiError VM_RedefineClasses::merge_cp_and_rewrite(
_index_map_count = 0;
_index_map_p = new intArray(scratch_cp->length(), -1);
// reference to the cp holder is needed for copy_operands()
merge_cp->set_pool_holder(scratch_class());
bool result = merge_constant_pools(old_cp, scratch_cp, &merge_cp,
&merge_cp_length, THREAD);
merge_cp->set_pool_holder(NULL);
if (!result) {
// The merge can fail due to memory allocation failure or due
// to robustness checks.
......@@ -2380,13 +2386,14 @@ void VM_RedefineClasses::set_new_constant_pool(
assert(version != 0, "sanity check");
smaller_cp->set_version(version);
// attach klass to new constant pool
// reference to the cp holder is needed for copy_operands()
smaller_cp->set_pool_holder(scratch_class());
scratch_cp->copy_cp_to(1, scratch_cp_length - 1, smaller_cp, 1, THREAD);
scratch_cp = smaller_cp;
// attach new constant pool to klass
scratch_cp->set_pool_holder(scratch_class());
// attach klass to new constant pool
scratch_class->set_constants(scratch_cp());
int i; // for portability
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册