# HG changeset patch # User Joshua Zhu # Date 1573548993 0 # Tue Nov 12 08:56:33 2019 +0000 # Node ID ef067cd5d943f691649215f01ff8ed2edf9e0870 # Parent cfc7bb9a5a92605c1ed0dbdbdba082ea1c3528be 8233948: AArch64: Incorrect mapping between OptoReg and VMReg for high 64 bits of Vector Register Reviewed-by: duke diff --git a/src/hotspot/cpu/aarch64/aarch64.ad b/src/hotspot/cpu/aarch64/aarch64.ad --- a/src/hotspot/cpu/aarch64/aarch64.ad +++ b/src/hotspot/cpu/aarch64/aarch64.ad @@ -1888,8 +1888,8 @@ return rc_int; } - // we have 32 float register * 2 halves - if (reg < 60 + 128) { + // we have 32 float register * 4 halves + if (reg < 60 + FloatRegisterImpl::max_slots_per_register * FloatRegisterImpl::number_of_registers) { return rc_float; } diff --git a/src/hotspot/cpu/aarch64/register_aarch64.cpp b/src/hotspot/cpu/aarch64/register_aarch64.cpp --- a/src/hotspot/cpu/aarch64/register_aarch64.cpp +++ b/src/hotspot/cpu/aarch64/register_aarch64.cpp @@ -26,10 +26,12 @@ #include "precompiled.hpp" #include "register_aarch64.hpp" -const int ConcreteRegisterImpl::max_gpr = RegisterImpl::number_of_registers << 1; +const int ConcreteRegisterImpl::max_gpr = RegisterImpl::number_of_registers * + RegisterImpl::max_slots_per_register; const int ConcreteRegisterImpl::max_fpr - = ConcreteRegisterImpl::max_gpr + (FloatRegisterImpl::number_of_registers << 1); + = ConcreteRegisterImpl::max_gpr + + FloatRegisterImpl::number_of_registers * FloatRegisterImpl::max_slots_per_register; const char* RegisterImpl::name() const { const char* names[number_of_registers] = { diff --git a/src/hotspot/cpu/aarch64/register_aarch64.hpp b/src/hotspot/cpu/aarch64/register_aarch64.hpp --- a/src/hotspot/cpu/aarch64/register_aarch64.hpp +++ b/src/hotspot/cpu/aarch64/register_aarch64.hpp @@ -44,7 +44,8 @@ enum { number_of_registers = 32, number_of_byte_registers = 32, - number_of_registers_for_jvmci = 34 // Including SP and ZR. + number_of_registers_for_jvmci = 34, // Including SP and ZR. + max_slots_per_register = 2 }; // derived registers, offsets, and addresses @@ -127,7 +128,8 @@ class FloatRegisterImpl: public AbstractRegisterImpl { public: enum { - number_of_registers = 32 + number_of_registers = 32, + max_slots_per_register = 4 }; // construction @@ -193,8 +195,8 @@ // There is no requirement that any ordering here matches any ordering c2 gives // it's optoregs. - number_of_registers = (2 * RegisterImpl::number_of_registers + - 4 * FloatRegisterImpl::number_of_registers + + number_of_registers = (RegisterImpl::max_slots_per_register * RegisterImpl::number_of_registers + + FloatRegisterImpl::max_slots_per_register * FloatRegisterImpl::number_of_registers + 1) // flags }; diff --git a/src/hotspot/cpu/aarch64/sharedRuntime_aarch64.cpp b/src/hotspot/cpu/aarch64/sharedRuntime_aarch64.cpp --- a/src/hotspot/cpu/aarch64/sharedRuntime_aarch64.cpp +++ b/src/hotspot/cpu/aarch64/sharedRuntime_aarch64.cpp @@ -115,7 +115,7 @@ #if COMPILER2_OR_JVMCI if (save_vectors) { // Save upper half of vector registers - int vect_words = 32 * 8 / wordSize; + int vect_words = FloatRegisterImpl::number_of_registers * 8 / wordSize; additional_frame_words += vect_words; } #else @@ -147,10 +147,10 @@ for (int i = 0; i < RegisterImpl::number_of_registers; i++) { Register r = as_Register(i); if (r < rheapbase && r != rscratch1 && r != rscratch2) { - int sp_offset = 2 * (i + 32); // SP offsets are in 4-byte words, - // register slots are 8 bytes - // wide, 32 floating-point - // registers + int sp_offset = 2 * (i + FloatRegisterImpl::number_of_registers); // SP offsets are in 4-byte words, + // register slots are 8 bytes + // wide, 32 floating-point + // registers oop_map->set_callee_saved(VMRegImpl::stack2reg(sp_offset + additional_frame_slots), r->as_VMReg()); } diff --git a/src/hotspot/cpu/aarch64/vmreg_aarch64.cpp b/src/hotspot/cpu/aarch64/vmreg_aarch64.cpp --- a/src/hotspot/cpu/aarch64/vmreg_aarch64.cpp +++ b/src/hotspot/cpu/aarch64/vmreg_aarch64.cpp @@ -33,15 +33,17 @@ Register reg = ::as_Register(0); int i; for (i = 0; i < ConcreteRegisterImpl::max_gpr ; ) { - regName[i++] = reg->name(); - regName[i++] = reg->name(); + for (int j = 0 ; j < RegisterImpl::max_slots_per_register ; j++) { + regName[i++] = reg->name(); + } reg = reg->successor(); } FloatRegister freg = ::as_FloatRegister(0); for ( ; i < ConcreteRegisterImpl::max_fpr ; ) { - regName[i++] = freg->name(); - regName[i++] = freg->name(); + for (int j = 0 ; j < FloatRegisterImpl::max_slots_per_register ; j++) { + regName[i++] = freg->name(); + } freg = freg->successor(); } diff --git a/src/hotspot/cpu/aarch64/vmreg_aarch64.hpp b/src/hotspot/cpu/aarch64/vmreg_aarch64.hpp --- a/src/hotspot/cpu/aarch64/vmreg_aarch64.hpp +++ b/src/hotspot/cpu/aarch64/vmreg_aarch64.hpp @@ -38,13 +38,14 @@ assert( is_Register(), "must be"); // Yuk - return ::as_Register(value() >> 1); + return ::as_Register(value() / RegisterImpl::max_slots_per_register); } inline FloatRegister as_FloatRegister() { assert( is_FloatRegister() && is_even(value()), "must be" ); // Yuk - return ::as_FloatRegister((value() - ConcreteRegisterImpl::max_gpr) >> 1); + return ::as_FloatRegister((value() - ConcreteRegisterImpl::max_gpr) / + FloatRegisterImpl::max_slots_per_register); } inline bool is_concrete() { diff --git a/src/hotspot/cpu/aarch64/vmreg_aarch64.inline.hpp b/src/hotspot/cpu/aarch64/vmreg_aarch64.inline.hpp --- a/src/hotspot/cpu/aarch64/vmreg_aarch64.inline.hpp +++ b/src/hotspot/cpu/aarch64/vmreg_aarch64.inline.hpp @@ -28,11 +28,12 @@ inline VMReg RegisterImpl::as_VMReg() { if( this==noreg ) return VMRegImpl::Bad(); - return VMRegImpl::as_VMReg(encoding() << 1 ); + return VMRegImpl::as_VMReg(encoding() * RegisterImpl::max_slots_per_register); } inline VMReg FloatRegisterImpl::as_VMReg() { - return VMRegImpl::as_VMReg((encoding() << 1) + ConcreteRegisterImpl::max_gpr); + return VMRegImpl::as_VMReg((encoding() * FloatRegisterImpl::max_slots_per_register) + + ConcreteRegisterImpl::max_gpr); } #endif // CPU_AARCH64_VMREG_AARCH64_INLINE_HPP