Path: blob/master/src/hotspot/cpu/arm/interpreterRT_arm.cpp
40930 views
/*1* Copyright (c) 2008, 2021, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*22*/2324#include "precompiled.hpp"25#include "asm/macroAssembler.inline.hpp"26#include "interpreter/interp_masm.hpp"27#include "interpreter/interpreter.hpp"28#include "interpreter/interpreterRuntime.hpp"29#include "memory/allocation.inline.hpp"30#include "oops/method.hpp"31#include "oops/oop.inline.hpp"32#include "runtime/handles.inline.hpp"33#include "runtime/icache.hpp"34#include "runtime/interfaceSupport.inline.hpp"35#include "runtime/signature.hpp"3637#define __ _masm->3839InterpreterRuntime::SignatureHandlerGenerator::SignatureHandlerGenerator(40const methodHandle& method, CodeBuffer* buffer) : NativeSignatureIterator(method) {41_masm = new MacroAssembler(buffer);42_abi_offset = 0;43_ireg = is_static() ? 2 : 1;44#ifdef __ABI_HARD__45_fp_slot = 0;46_single_fpr_slot = 0;47#endif48}4950#ifdef SHARING_FAST_NATIVE_FINGERPRINTS51// mapping from SignatureIterator param to (common) type of parsing52static const BasicType shared_type[] = {53T_INT, // bool54T_INT, // char55#ifndef __ABI_HARD__56T_INT, // float, passed as int57T_LONG, // double, passed as long58#else59T_FLOAT, // float60T_DOUBLE, // double61#endif62T_INT, // byte63T_INT, // short64T_INT, // int65T_LONG, // long66T_OBJECT, // obj67T_OBJECT, // array68};6970uint64_t InterpreterRuntime::normalize_fast_native_fingerprint(uint64_t fingerprint) {71if (fingerprint == UCONST64(-1)) {72// special signature used when the argument list cannot be encoded in a 64 bits value73return fingerprint;74}75int shift = SignatureIterator::fp_static_feature_size;76SignatureIterator::fingerprint_t result = fingerprint & ((1 << shift) - 1);7778BasicType ret_type = SignatureIterator::fp_return_type(fingerprint);79// For ARM, the fast signature handler only needs to know whether80// the return value must be unboxed. T_OBJECT and T_ARRAY need not81// be distinguished from each other and all other return values82// behave like integers with respect to the handler except T_BOOLEAN83// which must be mapped to the range 0..1.84if (is_reference_type(ret_type)) {85ret_type = T_OBJECT;86} else if (ret_type != T_BOOLEAN) {87ret_type = T_INT;88}89result |= ((SignatureIterator::fingerprint_t) ret_type) << shift;90shift += SignatureIterator::fp_result_feature_size;9192SignatureIterator::fingerprint_t unaccumulator = SignatureIterator::fp_start_parameters(fingerprint);93while (true) {94BasicType type = SignatureIterator::fp_next_parameter(unaccumulator);95if (type == (BasicType)SignatureIterator::fp_parameters_done) {96return result;97}98assert(SignatureIterator::fp_is_valid_type(type), "garbled fingerprint");99BasicType shared = shared_type[type - T_BOOLEAN];100result |= ((SignatureIterator::fingerprint_t) shared) << shift;101shift += SignatureIterator::fp_parameter_feature_size;102}103}104#endif // SHARING_FAST_NATIVE_FINGERPRINTS105106// Implementation of SignatureHandlerGenerator107void InterpreterRuntime::SignatureHandlerGenerator::pass_int() {108if (_ireg < GPR_PARAMS) {109Register dst = as_Register(_ireg);110__ ldr_s32(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));111_ireg++;112} else {113__ ldr_s32(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));114__ str_32(Rtemp, Address(SP, _abi_offset * wordSize));115_abi_offset++;116}117}118119void InterpreterRuntime::SignatureHandlerGenerator::pass_long() {120if (_ireg <= 2) {121#if (ALIGN_WIDE_ARGUMENTS == 1)122if ((_ireg & 1) != 0) {123// 64-bit values should be 8-byte aligned124_ireg++;125}126#endif127Register dst1 = as_Register(_ireg);128Register dst2 = as_Register(_ireg+1);129__ ldr(dst1, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));130__ ldr(dst2, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));131_ireg += 2;132#if (ALIGN_WIDE_ARGUMENTS == 0)133} else if (_ireg == 3) {134// uses R3 + one stack slot135Register dst1 = as_Register(_ireg);136__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));137__ ldr(dst1, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));138__ str(Rtemp, Address(SP, _abi_offset * wordSize));139_ireg += 1;140_abi_offset += 1;141#endif142} else {143#if (ALIGN_WIDE_ARGUMENTS == 1)144if(_abi_offset & 1) _abi_offset++;145#endif146__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));147__ str(Rtemp, Address(SP, (_abi_offset) * wordSize));148__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));149__ str(Rtemp, Address(SP, (_abi_offset+1) * wordSize));150_abi_offset += 2;151_ireg = 4;152}153}154155void InterpreterRuntime::SignatureHandlerGenerator::pass_object() {156if (_ireg < 4) {157Register dst = as_Register(_ireg);158__ ldr(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));159__ cmp(dst, 0);160__ sub(dst, Rlocals, -Interpreter::local_offset_in_bytes(offset()), ne);161_ireg++;162} else {163__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));164__ cmp(Rtemp, 0);165__ sub(Rtemp, Rlocals, -Interpreter::local_offset_in_bytes(offset()), ne);166__ str(Rtemp, Address(SP, _abi_offset * wordSize));167_abi_offset++;168}169}170171#ifndef __ABI_HARD__172void InterpreterRuntime::SignatureHandlerGenerator::pass_float() {173if (_ireg < 4) {174Register dst = as_Register(_ireg);175__ ldr(dst, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));176_ireg++;177} else {178__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));179__ str(Rtemp, Address(SP, _abi_offset * wordSize));180_abi_offset++;181}182}183184#else185#ifndef __SOFTFP__186void InterpreterRuntime::SignatureHandlerGenerator::pass_float() {187if((_fp_slot < 16) || (_single_fpr_slot & 1)) {188if ((_single_fpr_slot & 1) == 0) {189_single_fpr_slot = _fp_slot;190_fp_slot += 2;191}192__ flds(as_FloatRegister(_single_fpr_slot), Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));193_single_fpr_slot++;194} else {195__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));196__ str(Rtemp, Address(SP, _abi_offset * wordSize));197_abi_offset++;198}199}200201void InterpreterRuntime::SignatureHandlerGenerator::pass_double() {202if(_fp_slot <= 14) {203__ fldd(as_FloatRegister(_fp_slot), Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));204_fp_slot += 2;205} else {206__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset()+1)));207__ str(Rtemp, Address(SP, (_abi_offset) * wordSize));208__ ldr(Rtemp, Address(Rlocals, Interpreter::local_offset_in_bytes(offset())));209__ str(Rtemp, Address(SP, (_abi_offset+1) * wordSize));210_abi_offset += 2;211_single_fpr_slot = 16;212}213}214#endif // __SOFTFP__215#endif // __ABI_HARD__216217void InterpreterRuntime::SignatureHandlerGenerator::generate(uint64_t fingerprint) {218iterate(fingerprint);219220BasicType result_type = SignatureIterator::fp_return_type(fingerprint);221222address result_handler = Interpreter::result_handler(result_type);223224__ mov_slow(R0, (intptr_t)result_handler);225226__ ret();227}228229230// Implementation of SignatureHandlerLibrary231232void SignatureHandlerLibrary::pd_set_handler(address handler) {}233234class SlowSignatureHandler: public NativeSignatureIterator {235private:236address _from;237intptr_t* _to;238239#ifndef __ABI_HARD__240virtual void pass_int() {241*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));242_from -= Interpreter::stackElementSize;243}244245virtual void pass_float() {246*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));247_from -= Interpreter::stackElementSize;248}249250virtual void pass_long() {251#if (ALIGN_WIDE_ARGUMENTS == 1)252if (((intptr_t)_to & 7) != 0) {253// 64-bit values should be 8-byte aligned254_to++;255}256#endif257_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));258_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));259_to += 2;260_from -= 2*Interpreter::stackElementSize;261}262263virtual void pass_object() {264intptr_t from_addr = (intptr_t)(_from + Interpreter::local_offset_in_bytes(0));265*_to++ = (*(intptr_t*)from_addr == 0) ? (intptr_t)NULL : from_addr;266_from -= Interpreter::stackElementSize;267}268269#else270271intptr_t* _toFP;272intptr_t* _toGP;273int _last_gp;274int _last_fp;275int _last_single_fp;276277virtual void pass_int() {278if(_last_gp < GPR_PARAMS) {279_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));280} else {281*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));282}283_from -= Interpreter::stackElementSize;284}285286virtual void pass_long() {287assert(ALIGN_WIDE_ARGUMENTS == 1, "ABI_HARD not supported with unaligned wide arguments");288if (_last_gp <= 2) {289if(_last_gp & 1) _last_gp++;290_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(1));291_toGP[_last_gp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));292} else {293if (((intptr_t)_to & 7) != 0) {294// 64-bit values should be 8-byte aligned295_to++;296}297_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));298_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));299_to += 2;300_last_gp = 4;301}302_from -= 2*Interpreter::stackElementSize;303}304305virtual void pass_object() {306intptr_t from_addr = (intptr_t)(_from + Interpreter::local_offset_in_bytes(0));307if(_last_gp < GPR_PARAMS) {308_toGP[_last_gp++] = (*(intptr_t*)from_addr == 0) ? NULL : from_addr;309} else {310*_to++ = (*(intptr_t*)from_addr == 0) ? NULL : from_addr;311}312_from -= Interpreter::stackElementSize;313}314315virtual void pass_float() {316if((_last_fp < 16) || (_last_single_fp & 1)) {317if ((_last_single_fp & 1) == 0) {318_last_single_fp = _last_fp;319_last_fp += 2;320}321322_toFP[_last_single_fp++] = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));323} else {324*_to++ = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));325}326_from -= Interpreter::stackElementSize;327}328329virtual void pass_double() {330assert(ALIGN_WIDE_ARGUMENTS == 1, "ABI_HARD not supported with unaligned wide arguments");331if(_last_fp <= 14) {332_toFP[_last_fp++] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));333_toFP[_last_fp++] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));334} else {335if (((intptr_t)_to & 7) != 0) { // 64-bit values should be 8-byte aligned336_to++;337}338_to[0] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));339_to[1] = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(0));340_to += 2;341_last_single_fp = 16;342}343_from -= 2*Interpreter::stackElementSize;344}345346#endif // !__ABI_HARD__347348public:349SlowSignatureHandler(const methodHandle& method, address from, intptr_t* to) :350NativeSignatureIterator(method) {351_from = from;352353#ifdef __ABI_HARD__354_toGP = to;355_toFP = _toGP + GPR_PARAMS;356_to = _toFP + (8*2);357_last_gp = (is_static() ? 2 : 1);358_last_fp = 0;359_last_single_fp = 0;360#else361_to = to + (is_static() ? 2 : 1);362#endif // __ABI_HARD__363}364};365366JRT_ENTRY(address, InterpreterRuntime::slow_signature_handler(JavaThread* current, Method* method, intptr_t* from, intptr_t* to))367methodHandle m(current, (Method*)method);368assert(m->is_native(), "sanity check");369SlowSignatureHandler(m, (address)from, to).iterate(UCONST64(-1));370return Interpreter::result_handler(m->result_type());371JRT_END372373374