mirror of
https://github.com/openjdk/jdk.git
synced 2025-09-21 19:44:41 +02:00
8028347: Rewriter::scan_method asserts with array oob in RT_Baseline
Fix reversing rewriting for invokespecial Reviewed-by: jrose, hseigel
This commit is contained in:
parent
689cc9ddb7
commit
3e62155fec
2 changed files with 29 additions and 27 deletions
|
@ -70,12 +70,14 @@ void Rewriter::compute_index_maps() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Unrewrite the bytecodes if an error occurs.
|
// Unrewrite the bytecodes if an error occurs.
|
||||||
void Rewriter::restore_bytecodes(TRAPS) {
|
void Rewriter::restore_bytecodes() {
|
||||||
int len = _methods->length();
|
int len = _methods->length();
|
||||||
|
bool invokespecial_error = false;
|
||||||
|
|
||||||
for (int i = len-1; i >= 0; i--) {
|
for (int i = len-1; i >= 0; i--) {
|
||||||
Method* method = _methods->at(i);
|
Method* method = _methods->at(i);
|
||||||
scan_method(method, true, CHECK);
|
scan_method(method, true, &invokespecial_error);
|
||||||
|
assert(!invokespecial_error, "reversing should not get an invokespecial error");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -160,22 +162,21 @@ void Rewriter::rewrite_member_reference(address bcp, int offset, bool reverse) {
|
||||||
// These cannot share cpCache entries. It's unclear if all invokespecial to
|
// These cannot share cpCache entries. It's unclear if all invokespecial to
|
||||||
// InterfaceMethodrefs would resolve to the same thing so a new cpCache entry
|
// InterfaceMethodrefs would resolve to the same thing so a new cpCache entry
|
||||||
// is created for each one. This was added with lambda.
|
// is created for each one. This was added with lambda.
|
||||||
void Rewriter::rewrite_invokespecial(address bcp, int offset, bool reverse, TRAPS) {
|
void Rewriter::rewrite_invokespecial(address bcp, int offset, bool reverse, bool* invokespecial_error) {
|
||||||
static int count = 0;
|
|
||||||
address p = bcp + offset;
|
address p = bcp + offset;
|
||||||
if (!reverse) {
|
if (!reverse) {
|
||||||
int cp_index = Bytes::get_Java_u2(p);
|
int cp_index = Bytes::get_Java_u2(p);
|
||||||
|
if (_pool->tag_at(cp_index).is_interface_method()) {
|
||||||
int cache_index = add_invokespecial_cp_cache_entry(cp_index);
|
int cache_index = add_invokespecial_cp_cache_entry(cp_index);
|
||||||
if (cache_index != (int)(jushort) cache_index) {
|
if (cache_index != (int)(jushort) cache_index) {
|
||||||
THROW_MSG(vmSymbols::java_lang_InternalError(),
|
*invokespecial_error = true;
|
||||||
"This classfile overflows invokespecial for interfaces "
|
|
||||||
"and cannot be loaded");
|
|
||||||
}
|
}
|
||||||
Bytes::put_native_u2(p, cache_index);
|
Bytes::put_native_u2(p, cache_index);
|
||||||
} else {
|
} else {
|
||||||
int cache_index = Bytes::get_native_u2(p);
|
rewrite_member_reference(bcp, offset, reverse);
|
||||||
int cp_index = cp_cache_entry_pool_index(cache_index);
|
}
|
||||||
Bytes::put_Java_u2(p, cp_index);
|
} else {
|
||||||
|
rewrite_member_reference(bcp, offset, reverse);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -329,7 +330,7 @@ void Rewriter::maybe_rewrite_ldc(address bcp, int offset, bool is_wide,
|
||||||
|
|
||||||
|
|
||||||
// Rewrites a method given the index_map information
|
// Rewrites a method given the index_map information
|
||||||
void Rewriter::scan_method(Method* method, bool reverse, TRAPS) {
|
void Rewriter::scan_method(Method* method, bool reverse, bool* invokespecial_error) {
|
||||||
|
|
||||||
int nof_jsrs = 0;
|
int nof_jsrs = 0;
|
||||||
bool has_monitor_bytecodes = false;
|
bool has_monitor_bytecodes = false;
|
||||||
|
@ -391,15 +392,7 @@ void Rewriter::scan_method(Method* method, bool reverse, TRAPS) {
|
||||||
}
|
}
|
||||||
|
|
||||||
case Bytecodes::_invokespecial : {
|
case Bytecodes::_invokespecial : {
|
||||||
int offset = prefix_length + 1;
|
rewrite_invokespecial(bcp, prefix_length+1, reverse, invokespecial_error);
|
||||||
address p = bcp + offset;
|
|
||||||
int cp_index = Bytes::get_Java_u2(p);
|
|
||||||
// InterfaceMethodref
|
|
||||||
if (_pool->tag_at(cp_index).is_interface_method()) {
|
|
||||||
rewrite_invokespecial(bcp, offset, reverse, CHECK);
|
|
||||||
} else {
|
|
||||||
rewrite_member_reference(bcp, offset, reverse);
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -496,11 +489,20 @@ Rewriter::Rewriter(instanceKlassHandle klass, constantPoolHandle cpool, Array<Me
|
||||||
|
|
||||||
// rewrite methods, in two passes
|
// rewrite methods, in two passes
|
||||||
int len = _methods->length();
|
int len = _methods->length();
|
||||||
|
bool invokespecial_error = false;
|
||||||
|
|
||||||
for (int i = len-1; i >= 0; i--) {
|
for (int i = len-1; i >= 0; i--) {
|
||||||
Method* method = _methods->at(i);
|
Method* method = _methods->at(i);
|
||||||
scan_method(method, false, CHECK); // If you get an error here,
|
scan_method(method, false, &invokespecial_error);
|
||||||
// there is no reversing bytecodes
|
if (invokespecial_error) {
|
||||||
|
// If you get an error here, there is no reversing bytecodes
|
||||||
|
// This exception is stored for this class and no further attempt is
|
||||||
|
// made at verifying or rewriting.
|
||||||
|
THROW_MSG(vmSymbols::java_lang_InternalError(),
|
||||||
|
"This classfile overflows invokespecial for interfaces "
|
||||||
|
"and cannot be loaded");
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// May have to fix invokedynamic bytecodes if invokestatic/InterfaceMethodref
|
// May have to fix invokedynamic bytecodes if invokestatic/InterfaceMethodref
|
||||||
|
@ -513,7 +515,7 @@ Rewriter::Rewriter(instanceKlassHandle klass, constantPoolHandle cpool, Array<Me
|
||||||
// Restore bytecodes to their unrewritten state if there are exceptions
|
// Restore bytecodes to their unrewritten state if there are exceptions
|
||||||
// rewriting bytecodes or allocating the cpCache
|
// rewriting bytecodes or allocating the cpCache
|
||||||
if (HAS_PENDING_EXCEPTION) {
|
if (HAS_PENDING_EXCEPTION) {
|
||||||
restore_bytecodes(CATCH);
|
restore_bytecodes();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -530,7 +532,7 @@ Rewriter::Rewriter(instanceKlassHandle klass, constantPoolHandle cpool, Array<Me
|
||||||
// relocating bytecodes. If some are relocated, that is ok because that
|
// relocating bytecodes. If some are relocated, that is ok because that
|
||||||
// doesn't affect constant pool to cpCache rewriting.
|
// doesn't affect constant pool to cpCache rewriting.
|
||||||
if (HAS_PENDING_EXCEPTION) {
|
if (HAS_PENDING_EXCEPTION) {
|
||||||
restore_bytecodes(CATCH);
|
restore_bytecodes();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Method might have gotten rewritten.
|
// Method might have gotten rewritten.
|
||||||
|
|
|
@ -189,18 +189,18 @@ class Rewriter: public StackObj {
|
||||||
|
|
||||||
void compute_index_maps();
|
void compute_index_maps();
|
||||||
void make_constant_pool_cache(TRAPS);
|
void make_constant_pool_cache(TRAPS);
|
||||||
void scan_method(Method* m, bool reverse, TRAPS);
|
void scan_method(Method* m, bool reverse, bool* invokespecial_error);
|
||||||
void rewrite_Object_init(methodHandle m, TRAPS);
|
void rewrite_Object_init(methodHandle m, TRAPS);
|
||||||
void rewrite_member_reference(address bcp, int offset, bool reverse);
|
void rewrite_member_reference(address bcp, int offset, bool reverse);
|
||||||
void maybe_rewrite_invokehandle(address opc, int cp_index, int cache_index, bool reverse);
|
void maybe_rewrite_invokehandle(address opc, int cp_index, int cache_index, bool reverse);
|
||||||
void rewrite_invokedynamic(address bcp, int offset, bool reverse);
|
void rewrite_invokedynamic(address bcp, int offset, bool reverse);
|
||||||
void maybe_rewrite_ldc(address bcp, int offset, bool is_wide, bool reverse);
|
void maybe_rewrite_ldc(address bcp, int offset, bool is_wide, bool reverse);
|
||||||
void rewrite_invokespecial(address bcp, int offset, bool reverse, TRAPS);
|
void rewrite_invokespecial(address bcp, int offset, bool reverse, bool* invokespecial_error);
|
||||||
|
|
||||||
void patch_invokedynamic_bytecodes();
|
void patch_invokedynamic_bytecodes();
|
||||||
|
|
||||||
// Revert bytecodes in case of an exception.
|
// Revert bytecodes in case of an exception.
|
||||||
void restore_bytecodes(TRAPS);
|
void restore_bytecodes();
|
||||||
|
|
||||||
static methodHandle rewrite_jsrs(methodHandle m, TRAPS);
|
static methodHandle rewrite_jsrs(methodHandle m, TRAPS);
|
||||||
public:
|
public:
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue