diff -r 4ebc2e2fb97c -r 71c04702a3d5 src/hotspot/cpu/ppc/frame_ppc.hpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/hotspot/cpu/ppc/frame_ppc.hpp Tue Sep 12 19:03:39 2017 +0200 @@ -0,0 +1,428 @@ +/* + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2012, 2015 SAP SE. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + * + */ + +#ifndef CPU_PPC_VM_FRAME_PPC_HPP +#define CPU_PPC_VM_FRAME_PPC_HPP + +#include "runtime/synchronizer.hpp" + + // C frame layout on PPC-64. + // + // In this figure the stack grows upwards, while memory grows + // downwards. See "64-bit PowerPC ELF ABI Supplement Version 1.7", + // IBM Corp. (2003-10-29) + // (http://math-atlas.sourceforge.net/devel/assembly/PPC-elf64abi-1.7.pdf). + // + // Square brackets denote stack regions possibly larger + // than a single 64 bit slot. + // + // STACK: + // 0 [C_FRAME] <-- SP after prolog (mod 16 = 0) + // [C_FRAME] <-- SP before prolog + // ... + // [C_FRAME] + // + // C_FRAME: + // 0 [ABI_REG_ARGS] + // 112 CARG_9: outgoing arg 9 (arg_1 ... arg_8 via gpr_3 ... gpr_{10}) + // ... + // 40+M*8 CARG_M: outgoing arg M (M is the maximum of outgoing args taken over all call sites in the procedure) + // local 1 + // ... + // local N + // spill slot for vector reg (16 bytes aligned) + // ... + // spill slot for vector reg + // alignment (4 or 12 bytes) + // V SR_VRSAVE + // V+4 spill slot for GR + // ... ... + // spill slot for GR + // spill slot for FR + // ... + // spill slot for FR + // + // ABI_48: + // 0 caller's SP + // 8 space for condition register (CR) for next call + // 16 space for link register (LR) for next call + // 24 reserved + // 32 reserved + // 40 space for TOC (=R2) register for next call + // + // ABI_REG_ARGS: + // 0 [ABI_48] + // 48 CARG_1: spill slot for outgoing arg 1. used by next callee. + // ... ... + // 104 CARG_8: spill slot for outgoing arg 8. used by next callee. + // + + public: + + // C frame layout + static const int alignment_in_bytes = 16; + + // ABI_MINFRAME: + struct abi_minframe { + uint64_t callers_sp; + uint64_t cr; //_16 + uint64_t lr; +#if !defined(ABI_ELFv2) + uint64_t reserved1; //_16 + uint64_t reserved2; +#endif + uint64_t toc; //_16 + // nothing to add here! + // aligned to frame::alignment_in_bytes (16) + }; + + enum { + abi_minframe_size = sizeof(abi_minframe) + }; + + struct abi_reg_args : abi_minframe { + uint64_t carg_1; + uint64_t carg_2; //_16 + uint64_t carg_3; + uint64_t carg_4; //_16 + uint64_t carg_5; + uint64_t carg_6; //_16 + uint64_t carg_7; + uint64_t carg_8; //_16 + // aligned to frame::alignment_in_bytes (16) + }; + + enum { + abi_reg_args_size = sizeof(abi_reg_args) + }; + + #define _abi(_component) \ + (offset_of(frame::abi_reg_args, _component)) + + struct abi_reg_args_spill : abi_reg_args { + // additional spill slots + uint64_t spill_ret; + uint64_t spill_fret; //_16 + // aligned to frame::alignment_in_bytes (16) + }; + + enum { + abi_reg_args_spill_size = sizeof(abi_reg_args_spill) + }; + + #define _abi_reg_args_spill(_component) \ + (offset_of(frame::abi_reg_args_spill, _component)) + + // non-volatile GPRs: + + struct spill_nonvolatiles { + uint64_t r14; + uint64_t r15; //_16 + uint64_t r16; + uint64_t r17; //_16 + uint64_t r18; + uint64_t r19; //_16 + uint64_t r20; + uint64_t r21; //_16 + uint64_t r22; + uint64_t r23; //_16 + uint64_t r24; + uint64_t r25; //_16 + uint64_t r26; + uint64_t r27; //_16 + uint64_t r28; + uint64_t r29; //_16 + uint64_t r30; + uint64_t r31; //_16 + + double f14; + double f15; + double f16; + double f17; + double f18; + double f19; + double f20; + double f21; + double f22; + double f23; + double f24; + double f25; + double f26; + double f27; + double f28; + double f29; + double f30; + double f31; + + // aligned to frame::alignment_in_bytes (16) + }; + + enum { + spill_nonvolatiles_size = sizeof(spill_nonvolatiles) + }; + + #define _spill_nonvolatiles_neg(_component) \ + (int)(-frame::spill_nonvolatiles_size + offset_of(frame::spill_nonvolatiles, _component)) + + // Frame layout for the Java template interpreter on PPC64. + // + // In these figures the stack grows upwards, while memory grows + // downwards. Square brackets denote regions possibly larger than + // single 64 bit slots. + // + // STACK (interpreter is active): + // 0 [TOP_IJAVA_FRAME] + // [PARENT_IJAVA_FRAME] + // ... + // [PARENT_IJAVA_FRAME] + // [ENTRY_FRAME] + // [C_FRAME] + // ... + // [C_FRAME] + // + // With the following frame layouts: + // TOP_IJAVA_FRAME: + // 0 [TOP_IJAVA_FRAME_ABI] + // alignment (optional) + // [operand stack] + // [monitors] (optional) + // [IJAVA_STATE] + // note: own locals are located in the caller frame. + // + // PARENT_IJAVA_FRAME: + // 0 [PARENT_IJAVA_FRAME_ABI] + // alignment (optional) + // [callee's Java result] + // [callee's locals w/o arguments] + // [outgoing arguments] + // [used part of operand stack w/o arguments] + // [monitors] (optional) + // [IJAVA_STATE] + // + // ENTRY_FRAME: + // 0 [PARENT_IJAVA_FRAME_ABI] + // alignment (optional) + // [callee's Java result] + // [callee's locals w/o arguments] + // [outgoing arguments] + // [ENTRY_FRAME_LOCALS] + + struct parent_ijava_frame_abi : abi_minframe { + }; + + enum { + parent_ijava_frame_abi_size = sizeof(parent_ijava_frame_abi) + }; + +#define _parent_ijava_frame_abi(_component) \ + (offset_of(frame::parent_ijava_frame_abi, _component)) + + struct top_ijava_frame_abi : abi_reg_args { + }; + + enum { + top_ijava_frame_abi_size = sizeof(top_ijava_frame_abi) + }; + +#define _top_ijava_frame_abi(_component) \ + (offset_of(frame::top_ijava_frame_abi, _component)) + + struct ijava_state { +#ifdef ASSERT + uint64_t ijava_reserved; // Used for assertion. +#endif + uint64_t method; + uint64_t mirror; + uint64_t locals; + uint64_t monitors; + uint64_t cpoolCache; + uint64_t bcp; + uint64_t esp; + uint64_t mdx; + uint64_t top_frame_sp; // Maybe define parent_frame_abi and move there. + uint64_t sender_sp; + // Slots only needed for native calls. Maybe better to move elsewhere. + uint64_t oop_tmp; + uint64_t lresult; + uint64_t fresult; + }; + + enum { + ijava_state_size = sizeof(ijava_state) + }; + +#define _ijava_state_neg(_component) \ + (int) (-frame::ijava_state_size + offset_of(frame::ijava_state, _component)) + + // ENTRY_FRAME + + struct entry_frame_locals { + uint64_t call_wrapper_address; + uint64_t result_address; //_16 + uint64_t result_type; + uint64_t arguments_tos_address; //_16 + // aligned to frame::alignment_in_bytes (16) + uint64_t r[spill_nonvolatiles_size/sizeof(uint64_t)]; + }; + + enum { + entry_frame_locals_size = sizeof(entry_frame_locals) + }; + + #define _entry_frame_locals_neg(_component) \ + (int)(-frame::entry_frame_locals_size + offset_of(frame::entry_frame_locals, _component)) + + + // Frame layout for JIT generated methods + // + // In these figures the stack grows upwards, while memory grows + // downwards. Square brackets denote regions possibly larger than single + // 64 bit slots. + // + // STACK (interpreted Java calls JIT generated Java): + // [JIT_FRAME] <-- SP (mod 16 = 0) + // [TOP_IJAVA_FRAME] + // ... + // + // JIT_FRAME (is a C frame according to PPC-64 ABI): + // [out_preserve] + // [out_args] + // [spills] + // [pad_1] + // [monitor] (optional) + // ... + // [monitor] (optional) + // [pad_2] + // [in_preserve] added / removed by prolog / epilog + // + + // JIT_ABI (TOP and PARENT) + + struct jit_abi { + uint64_t callers_sp; + uint64_t cr; + uint64_t lr; + uint64_t toc; + // Nothing to add here! + // NOT ALIGNED to frame::alignment_in_bytes (16). + }; + + struct jit_out_preserve : jit_abi { + // Nothing to add here! + }; + + struct jit_in_preserve { + // Nothing to add here! + }; + + enum { + jit_out_preserve_size = sizeof(jit_out_preserve), + jit_in_preserve_size = sizeof(jit_in_preserve) + }; + + struct jit_monitor { + uint64_t monitor[1]; + }; + + enum { + jit_monitor_size = sizeof(jit_monitor), + }; + + private: + + // STACK: + // ... + // [THIS_FRAME] <-- this._sp (stack pointer for this frame) + // [CALLER_FRAME] <-- this.fp() (_sp of caller's frame) + // ... + // + + // frame pointer for this frame + intptr_t* _fp; + + // The frame's stack pointer before it has been extended by a c2i adapter; + // needed by deoptimization + intptr_t* _unextended_sp; + + public: + + // Accessors for fields + intptr_t* fp() const { return _fp; } + + // Accessors for ABIs + inline abi_minframe* own_abi() const { return (abi_minframe*) _sp; } + inline abi_minframe* callers_abi() const { return (abi_minframe*) _fp; } + + private: + + // Find codeblob and set deopt_state. + inline void find_codeblob_and_set_pc_and_deopt_state(address pc); + + public: + + // Constructors + inline frame(intptr_t* sp); + frame(intptr_t* sp, address pc); + inline frame(intptr_t* sp, address pc, intptr_t* unextended_sp); + + private: + + intptr_t* compiled_sender_sp(CodeBlob* cb) const; + address* compiled_sender_pc_addr(CodeBlob* cb) const; + address* sender_pc_addr(void) const; + + public: + + inline ijava_state* get_ijava_state() const; + // Some convenient register frame setters/getters for deoptimization. + inline intptr_t* interpreter_frame_esp() const; + inline void interpreter_frame_set_cpcache(ConstantPoolCache* cp); + inline void interpreter_frame_set_esp(intptr_t* esp); + inline void interpreter_frame_set_top_frame_sp(intptr_t* top_frame_sp); + inline void interpreter_frame_set_sender_sp(intptr_t* sender_sp); + + // Size of a monitor in bytes. + static int interpreter_frame_monitor_size_in_bytes(); + + // The size of a cInterpreter object. + static inline int interpreter_frame_cinterpreterstate_size_in_bytes(); + + private: + + ConstantPoolCache** interpreter_frame_cpoolcache_addr() const; + + public: + + // Additional interface for entry frames: + inline entry_frame_locals* get_entry_frame_locals() const { + return (entry_frame_locals*) (((address) fp()) - entry_frame_locals_size); + } + + enum { + // normal return address is 1 bundle past PC + pc_return_offset = 0 + }; + +#endif // CPU_PPC_VM_FRAME_PPC_HPP