--- a/src/hotspot/share/runtime/stubRoutines.cpp Thu Jun 20 14:09:22 2019 +0100
+++ b/src/hotspot/share/runtime/stubRoutines.cpp Mon Jun 24 11:37:56 2019 -0700
@@ -38,6 +38,10 @@
#include "opto/runtime.hpp"
#endif
+UnsafeCopyMemory* UnsafeCopyMemory::_table = NULL;
+int UnsafeCopyMemory::_table_length = 0;
+int UnsafeCopyMemory::_table_max_length = 0;
+address UnsafeCopyMemory::_common_exit_stub_pc = NULL;
// Implementation of StubRoutines - for a description
// of how to extend it, see the header file.
@@ -113,7 +117,6 @@
address StubRoutines::_unsafe_arraycopy = NULL;
address StubRoutines::_generic_arraycopy = NULL;
-
address StubRoutines::_jbyte_fill;
address StubRoutines::_jshort_fill;
address StubRoutines::_jint_fill;
@@ -177,6 +180,31 @@
extern void StubGenerator_generate(CodeBuffer* code, bool all); // only interface to generators
+void UnsafeCopyMemory::create_table(int max_size) {
+ UnsafeCopyMemory::_table = new UnsafeCopyMemory[max_size];
+ UnsafeCopyMemory::_table_max_length = max_size;
+}
+
+bool UnsafeCopyMemory::contains_pc(address pc) {
+ for (int i = 0; i < UnsafeCopyMemory::_table_length; i++) {
+ UnsafeCopyMemory* entry = &UnsafeCopyMemory::_table[i];
+ if (pc >= entry->start_pc() && pc < entry->end_pc()) {
+ return true;
+ }
+ }
+ return false;
+}
+
+address UnsafeCopyMemory::page_error_continue_pc(address pc) {
+ for (int i = 0; i < UnsafeCopyMemory::_table_length; i++) {
+ UnsafeCopyMemory* entry = &UnsafeCopyMemory::_table[i];
+ if (pc >= entry->start_pc() && pc < entry->end_pc()) {
+ return entry->error_exit_pc();
+ }
+ }
+ return NULL;
+}
+
void StubRoutines::initialize1() {
if (_code1 == NULL) {
ResourceMark rm;
@@ -569,3 +597,25 @@
#undef RETURN_STUB
#undef RETURN_STUB_PARM
}
+
+UnsafeCopyMemoryMark::UnsafeCopyMemoryMark(StubCodeGenerator* cgen, bool add_entry, bool continue_at_scope_end, address error_exit_pc) {
+ _cgen = cgen;
+ _ucm_entry = NULL;
+ if (add_entry) {
+ address err_exit_pc = NULL;
+ if (!continue_at_scope_end) {
+ err_exit_pc = error_exit_pc != NULL ? error_exit_pc : UnsafeCopyMemory::common_exit_stub_pc();
+ }
+ assert(err_exit_pc != NULL || continue_at_scope_end, "error exit not set");
+ _ucm_entry = UnsafeCopyMemory::add_to_table(_cgen->assembler()->pc(), NULL, err_exit_pc);
+ }
+}
+
+UnsafeCopyMemoryMark::~UnsafeCopyMemoryMark() {
+ if (_ucm_entry != NULL) {
+ _ucm_entry->set_end_pc(_cgen->assembler()->pc());
+ if (_ucm_entry->error_exit_pc() == NULL) {
+ _ucm_entry->set_error_exit_pc(_cgen->assembler()->pc());
+ }
+ }
+}