Path: blob/master/src/hotspot/share/code/relocInfo.hpp
40931 views
/*1* Copyright (c) 1997, 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#ifndef SHARE_CODE_RELOCINFO_HPP25#define SHARE_CODE_RELOCINFO_HPP2627#include "runtime/os.hpp"28#include "utilities/macros.hpp"2930class nmethod;31class CodeBlob;32class CompiledMethod;33class Metadata;34class NativeMovConstReg;3536// Types in this file:37// relocInfo38// One element of an array of halfwords encoding compressed relocations.39// Also, the source of relocation types (relocInfo::oop_type, ...).40// Relocation41// A flyweight object representing a single relocation.42// It is fully unpacked from the compressed relocation array.43// metadata_Relocation, ... (subclasses of Relocation)44// The location of some type-specific operations (metadata_addr, ...).45// Also, the source of relocation specs (metadata_Relocation::spec, ...).46// oop_Relocation, ... (subclasses of Relocation)47// oops in the code stream (strings, class loaders)48// Also, the source of relocation specs (oop_Relocation::spec, ...).49// RelocationHolder50// A value type which acts as a union holding a Relocation object.51// Represents a relocation spec passed into a CodeBuffer during assembly.52// RelocIterator53// A StackObj which iterates over the relocations associated with54// a range of code addresses. Can be used to operate a copy of code.555657// Notes on relocType:58//59// These hold enough information to read or write a value embedded in60// the instructions of an CodeBlob. They're used to update:61//62// 1) embedded oops (isOop() == true)63// 2) inline caches (isIC() == true)64// 3) runtime calls (isRuntimeCall() == true)65// 4) internal word ref (isInternalWord() == true)66// 5) external word ref (isExternalWord() == true)67//68// when objects move (GC) or if code moves (compacting the code heap).69// They are also used to patch the code (if a call site must change)70//71// A relocInfo is represented in 16 bits:72// 4 bits indicating the relocation type73// 12 bits indicating the offset from the previous relocInfo address74//75// The offsets accumulate along the relocInfo stream to encode the76// address within the CodeBlob, which is named RelocIterator::addr().77// The address of a particular relocInfo always points to the first78// byte of the relevant instruction (and not to any of its subfields79// or embedded immediate constants).80//81// The offset value is scaled appropriately for the target machine.82// (See relocInfo_<arch>.hpp for the offset scaling.)83//84// On some machines, there may also be a "format" field which may provide85// additional information about the format of the instruction stream86// at the corresponding code address. The format value is usually zero.87// Any machine (such as Intel) whose instructions can sometimes contain88// more than one relocatable constant needs format codes to distinguish89// which operand goes with a given relocation.90//91// If the target machine needs N format bits, the offset has 12-N bits,92// the format is encoded between the offset and the type, and the93// relocInfo_<arch>.hpp file has manifest constants for the format codes.94//95// If the type is "data_prefix_tag" then the offset bits are further encoded,96// and in fact represent not a code-stream offset but some inline data.97// The data takes the form of a counted sequence of halfwords, which98// precedes the actual relocation record. (Clients never see it directly.)99// The interpetation of this extra data depends on the relocation type.100//101// On machines that have 32-bit immediate fields, there is usually102// little need for relocation "prefix" data, because the instruction stream103// is a perfectly reasonable place to store the value. On machines in104// which 32-bit values must be "split" across instructions, the relocation105// data is the "true" specification of the value, which is then applied106// to some field of the instruction (22 or 13 bits, on SPARC).107//108// Whenever the location of the CodeBlob changes, any PC-relative109// relocations, and any internal_word_type relocations, must be reapplied.110// After the GC runs, oop_type relocations must be reapplied.111//112//113// Here are meanings of the types:114//115// relocInfo::none -- a filler record116// Value: none117// Instruction: The corresponding code address is ignored118// Data: Any data prefix and format code are ignored119// (This means that any relocInfo can be disabled by setting120// its type to none. See relocInfo::remove.)121//122// relocInfo::oop_type, relocInfo::metadata_type -- a reference to an oop or meta data123// Value: an oop, or else the address (handle) of an oop124// Instruction types: memory (load), set (load address)125// Data: [] an oop stored in 4 bytes of instruction126// [n] n is the index of an oop in the CodeBlob's oop pool127// [[N]n l] and l is a byte offset to be applied to the oop128// [Nn Ll] both index and offset may be 32 bits if necessary129// Here is a special hack, used only by the old compiler:130// [[N]n 00] the value is the __address__ of the nth oop in the pool131// (Note that the offset allows optimal references to class variables.)132//133// relocInfo::internal_word_type -- an address within the same CodeBlob134// relocInfo::section_word_type -- same, but can refer to another section135// Value: an address in the CodeBlob's code or constants section136// Instruction types: memory (load), set (load address)137// Data: [] stored in 4 bytes of instruction138// [[L]l] a relative offset (see [About Offsets] below)139// In the case of section_word_type, the offset is relative to a section140// base address, and the section number (e.g., SECT_INSTS) is encoded141// into the low two bits of the offset L.142//143// relocInfo::external_word_type -- a fixed address in the runtime system144// Value: an address145// Instruction types: memory (load), set (load address)146// Data: [] stored in 4 bytes of instruction147// [n] the index of a "well-known" stub (usual case on RISC)148// [Ll] a 32-bit address149//150// relocInfo::runtime_call_type -- a fixed subroutine in the runtime system151// Value: an address152// Instruction types: PC-relative call (or a PC-relative branch)153// Data: [] stored in 4 bytes of instruction154//155// relocInfo::static_call_type -- a static call156// Value: an CodeBlob, a stub, or a fixup routine157// Instruction types: a call158// Data: []159// The identity of the callee is extracted from debugging information.160// //%note reloc_3161//162// relocInfo::virtual_call_type -- a virtual call site (which includes an inline163// cache)164// Value: an CodeBlob, a stub, the interpreter, or a fixup routine165// Instruction types: a call, plus some associated set-oop instructions166// Data: [] the associated set-oops are adjacent to the call167// [n] n is a relative offset to the first set-oop168// [[N]n l] and l is a limit within which the set-oops occur169// [Nn Ll] both n and l may be 32 bits if necessary170// The identity of the callee is extracted from debugging information.171//172// relocInfo::opt_virtual_call_type -- a virtual call site that is statically bound173//174// Same info as a static_call_type. We use a special type, so the handling of175// virtuals and statics are separated.176//177//178// The offset n points to the first set-oop. (See [About Offsets] below.)179// In turn, the set-oop instruction specifies or contains an oop cell devoted180// exclusively to the IC call, which can be patched along with the call.181//182// The locations of any other set-oops are found by searching the relocation183// information starting at the first set-oop, and continuing until all184// relocations up through l have been inspected. The value l is another185// relative offset. (Both n and l are relative to the call's first byte.)186//187// The limit l of the search is exclusive. However, if it points within188// the call (e.g., offset zero), it is adjusted to point after the call and189// any associated machine-specific delay slot.190//191// Since the offsets could be as wide as 32-bits, these conventions192// put no restrictions whatever upon code reorganization.193//194// The compiler is responsible for ensuring that transition from a clean195// state to a monomorphic compiled state is MP-safe. This implies that196// the system must respond well to intermediate states where a random197// subset of the set-oops has been correctly from the clean state198// upon entry to the VEP of the compiled method. In the case of a199// machine (Intel) with a single set-oop instruction, the 32-bit200// immediate field must not straddle a unit of memory coherence.201// //%note reloc_3202//203// relocInfo::static_stub_type -- an extra stub for each static_call_type204// Value: none205// Instruction types: a virtual call: { set_oop; jump; }206// Data: [[N]n] the offset of the associated static_call reloc207// This stub becomes the target of a static call which must be upgraded208// to a virtual call (because the callee is interpreted).209// See [About Offsets] below.210// //%note reloc_2211//212// relocInfo::poll_[return_]type -- a safepoint poll213// Value: none214// Instruction types: memory load or test215// Data: none216//217// For example:218//219// INSTRUCTIONS RELOC: TYPE PREFIX DATA220// ------------ ---- -----------221// sethi %hi(myObject), R oop_type [n(myObject)]222// ld [R+%lo(myObject)+fldOffset], R2 oop_type [n(myObject) fldOffset]223// add R2, 1, R2224// st R2, [R+%lo(myObject)+fldOffset] oop_type [n(myObject) fldOffset]225//%note reloc_1226//227// This uses 4 instruction words, 8 relocation halfwords,228// and an entry (which is sharable) in the CodeBlob's oop pool,229// for a total of 36 bytes.230//231// Note that the compiler is responsible for ensuring the "fldOffset" when232// added to "%lo(myObject)" does not overflow the immediate fields of the233// memory instructions.234//235//236// [About Offsets] Relative offsets are supplied to this module as237// positive byte offsets, but they may be internally stored scaled238// and/or negated, depending on what is most compact for the target239// system. Since the object pointed to by the offset typically240// precedes the relocation address, it is profitable to store241// these negative offsets as positive numbers, but this decision242// is internal to the relocation information abstractions.243//244245class Relocation;246class CodeBuffer;247class CodeSection;248class RelocIterator;249250class relocInfo {251friend class RelocIterator;252public:253enum relocType {254none = 0, // Used when no relocation should be generated255oop_type = 1, // embedded oop256virtual_call_type = 2, // a standard inline cache call for a virtual send257opt_virtual_call_type = 3, // a virtual call that has been statically bound (i.e., no IC cache)258static_call_type = 4, // a static send259static_stub_type = 5, // stub-entry for static send (takes care of interpreter case)260runtime_call_type = 6, // call to fixed external routine261external_word_type = 7, // reference to fixed external address262internal_word_type = 8, // reference within the current code blob263section_word_type = 9, // internal, but a cross-section reference264poll_type = 10, // polling instruction for safepoints265poll_return_type = 11, // polling instruction for safepoints at return266metadata_type = 12, // metadata that used to be oops267trampoline_stub_type = 13, // stub-entry for trampoline268runtime_call_w_cp_type = 14, // Runtime call which may load its target from the constant pool269data_prefix_tag = 15, // tag for a prefix (carries data arguments)270type_mask = 15 // A mask which selects only the above values271};272273private:274unsigned short _value;275276static const enum class RawBitsToken {} RAW_BITS{};277278relocInfo(relocType type, RawBitsToken, int bits)279: _value((type << nontype_width) + bits) { }280281static relocType check_relocType(relocType type) NOT_DEBUG({ return type; });282283static void check_offset_and_format(int offset, int format) NOT_DEBUG_RETURN;284285static int compute_bits(int offset, int format) {286check_offset_and_format(offset, format);287return (offset / offset_unit) + (format << offset_width);288}289290public:291relocInfo(relocType type, int offset, int format = 0)292: relocInfo(check_relocType(type), RAW_BITS, compute_bits(offset, format)) {}293294#define APPLY_TO_RELOCATIONS(visitor) \295visitor(oop) \296visitor(metadata) \297visitor(virtual_call) \298visitor(opt_virtual_call) \299visitor(static_call) \300visitor(static_stub) \301visitor(runtime_call) \302visitor(runtime_call_w_cp) \303visitor(external_word) \304visitor(internal_word) \305visitor(poll) \306visitor(poll_return) \307visitor(section_word) \308visitor(trampoline_stub) \309310311public:312enum {313value_width = sizeof(unsigned short) * BitsPerByte,314type_width = 4, // == log2(type_mask+1)315nontype_width = value_width - type_width,316datalen_width = nontype_width-1,317datalen_tag = 1 << datalen_width, // or-ed into _value318datalen_limit = 1 << datalen_width,319datalen_mask = (1 << datalen_width)-1320};321322// accessors323public:324relocType type() const { return (relocType)((unsigned)_value >> nontype_width); }325int format() const { return format_mask==0? 0: format_mask &326((unsigned)_value >> offset_width); }327int addr_offset() const { assert(!is_prefix(), "must have offset");328return (_value & offset_mask)*offset_unit; }329330protected:331const short* data() const { assert(is_datalen(), "must have data");332return (const short*)(this + 1); }333int datalen() const { assert(is_datalen(), "must have data");334return (_value & datalen_mask); }335int immediate() const { assert(is_immediate(), "must have immed");336return (_value & datalen_mask); }337public:338static int addr_unit() { return offset_unit; }339static int offset_limit() { return (1 << offset_width) * offset_unit; }340341void set_type(relocType type);342343void remove() { set_type(none); }344345protected:346bool is_none() const { return type() == none; }347bool is_prefix() const { return type() == data_prefix_tag; }348bool is_datalen() const { assert(is_prefix(), "must be prefix");349return (_value & datalen_tag) != 0; }350bool is_immediate() const { assert(is_prefix(), "must be prefix");351return (_value & datalen_tag) == 0; }352353public:354// Occasionally records of type relocInfo::none will appear in the stream.355// We do not bother to filter these out, but clients should ignore them.356// These records serve as "filler" in three ways:357// - to skip large spans of unrelocated code (this is rare)358// - to pad out the relocInfo array to the required oop alignment359// - to disable old relocation information which is no longer applicable360361inline friend relocInfo filler_relocInfo();362363// Every non-prefix relocation may be preceded by at most one prefix,364// which supplies 1 or more halfwords of associated data. Conventionally,365// an int is represented by 0, 1, or 2 halfwords, depending on how366// many bits are required to represent the value. (In addition,367// if the sole halfword is a 10-bit unsigned number, it is made368// "immediate" in the prefix header word itself. This optimization369// is invisible outside this module.)370371inline friend relocInfo prefix_relocInfo(int datalen);372373private:374// an immediate relocInfo optimizes a prefix with one 10-bit unsigned value375static relocInfo immediate_relocInfo(int data0) {376assert(fits_into_immediate(data0), "data0 in limits");377return relocInfo(relocInfo::data_prefix_tag, RAW_BITS, data0);378}379static bool fits_into_immediate(int data0) {380return (data0 >= 0 && data0 < datalen_limit);381}382383public:384// Support routines for compilers.385386// This routine takes an infant relocInfo (unprefixed) and387// edits in its prefix, if any. It also updates dest.locs_end.388void initialize(CodeSection* dest, Relocation* reloc);389390// This routine updates a prefix and returns the limit pointer.391// It tries to compress the prefix from 32 to 16 bits, and if392// successful returns a reduced "prefix_limit" pointer.393relocInfo* finish_prefix(short* prefix_limit);394395// bit-packers for the data array:396397// As it happens, the bytes within the shorts are ordered natively,398// but the shorts within the word are ordered big-endian.399// This is an arbitrary choice, made this way mainly to ease debugging.400static int data0_from_int(jint x) { return x >> value_width; }401static int data1_from_int(jint x) { return (short)x; }402static jint jint_from_data(short* data) {403return (data[0] << value_width) + (unsigned short)data[1];404}405406static jint short_data_at(int n, short* data, int datalen) {407return datalen > n ? data[n] : 0;408}409410static jint jint_data_at(int n, short* data, int datalen) {411return datalen > n+1 ? jint_from_data(&data[n]) : short_data_at(n, data, datalen);412}413414// Update methods for relocation information415// (since code is dynamically patched, we also need to dynamically update the relocation info)416// Both methods takes old_type, so it is able to performe sanity checks on the information removed.417static void change_reloc_info_for_address(RelocIterator *itr, address pc, relocType old_type, relocType new_type);418419// Machine dependent stuff420#include CPU_HEADER(relocInfo)421422protected:423// Derived constant, based on format_width which is PD:424enum {425offset_width = nontype_width - format_width,426offset_mask = (1<<offset_width) - 1,427format_mask = (1<<format_width) - 1428};429public:430enum {431#ifdef _LP64432// for use in format433// format_width must be at least 1 on _LP64434narrow_oop_in_const = 1,435#endif436// Conservatively large estimate of maximum length (in shorts)437// of any relocation record.438// Extended format is length prefix, data words, and tag/offset suffix.439length_limit = 1 + 1 + (3*BytesPerWord/BytesPerShort) + 1,440have_format = format_width > 0441};442};443444#define FORWARD_DECLARE_EACH_CLASS(name) \445class name##_Relocation;446APPLY_TO_RELOCATIONS(FORWARD_DECLARE_EACH_CLASS)447#undef FORWARD_DECLARE_EACH_CLASS448449450451inline relocInfo filler_relocInfo() {452return relocInfo(relocInfo::none, relocInfo::offset_limit() - relocInfo::offset_unit);453}454455inline relocInfo prefix_relocInfo(int datalen = 0) {456assert(relocInfo::fits_into_immediate(datalen), "datalen in limits");457return relocInfo(relocInfo::data_prefix_tag, relocInfo::RAW_BITS, relocInfo::datalen_tag | datalen);458}459460461// Holder for flyweight relocation objects.462// Although the flyweight subclasses are of varying sizes,463// the holder is "one size fits all".464class RelocationHolder {465friend class Relocation;466friend class CodeSection;467468private:469// this preallocated memory must accommodate all subclasses of Relocation470// (this number is assertion-checked in Relocation::operator new)471enum { _relocbuf_size = 5 };472void* _relocbuf[ _relocbuf_size ];473474public:475Relocation* reloc() const { return (Relocation*) &_relocbuf[0]; }476inline relocInfo::relocType type() const;477478// Add a constant offset to a relocation. Helper for class Address.479RelocationHolder plus(int offset) const;480481inline RelocationHolder(); // initializes type to none482483inline RelocationHolder(Relocation* r); // make a copy484485static const RelocationHolder none;486};487488// A RelocIterator iterates through the relocation information of a CodeBlob.489// It provides access to successive relocations as it is advanced through a490// code stream.491// Usage:492// RelocIterator iter(nm);493// while (iter.next()) {494// iter.reloc()->some_operation();495// }496// or:497// RelocIterator iter(nm);498// while (iter.next()) {499// switch (iter.type()) {500// case relocInfo::oop_type :501// case relocInfo::ic_type :502// case relocInfo::prim_type :503// case relocInfo::uncommon_type :504// case relocInfo::runtime_call_type :505// case relocInfo::internal_word_type:506// case relocInfo::external_word_type:507// ...508// }509// }510511class RelocIterator : public StackObj {512friend class section_word_Relocation; // for section verification513enum { SECT_LIMIT = 3 }; // must be equal to CodeBuffer::SECT_LIMIT, checked in ctor514friend class Relocation;515friend class relocInfo; // for change_reloc_info_for_address only516typedef relocInfo::relocType relocType;517518private:519address _limit; // stop producing relocations after this _addr520relocInfo* _current; // the current relocation information521relocInfo* _end; // end marker; we're done iterating when _current == _end522CompiledMethod* _code; // compiled method containing _addr523address _addr; // instruction to which the relocation applies524short _databuf; // spare buffer for compressed data525short* _data; // pointer to the relocation's data526short _datalen; // number of halfwords in _data527528// Base addresses needed to compute targets of section_word_type relocs.529address _section_start[SECT_LIMIT];530address _section_end [SECT_LIMIT];531532void set_has_current(bool b) {533_datalen = !b ? -1 : 0;534debug_only(_data = NULL);535}536void set_current(relocInfo& ri) {537_current = &ri;538set_has_current(true);539}540541RelocationHolder _rh; // where the current relocation is allocated542543relocInfo* current() const { assert(has_current(), "must have current");544return _current; }545546void set_limits(address begin, address limit);547548void advance_over_prefix(); // helper method549550void initialize_misc();551552void initialize(CompiledMethod* nm, address begin, address limit);553554RelocIterator() { initialize_misc(); }555556public:557// constructor558RelocIterator(CompiledMethod* nm, address begin = NULL, address limit = NULL);559RelocIterator(CodeSection* cb, address begin = NULL, address limit = NULL);560561// get next reloc info, return !eos562bool next() {563_current++;564assert(_current <= _end, "must not overrun relocInfo");565if (_current == _end) {566set_has_current(false);567return false;568}569set_has_current(true);570571if (_current->is_prefix()) {572advance_over_prefix();573assert(!current()->is_prefix(), "only one prefix at a time");574}575576_addr += _current->addr_offset();577578if (_limit != NULL && _addr >= _limit) {579set_has_current(false);580return false;581}582583return true;584}585586// accessors587address limit() const { return _limit; }588relocType type() const { return current()->type(); }589int format() const { return (relocInfo::have_format) ? current()->format() : 0; }590address addr() const { return _addr; }591CompiledMethod* code() const { return _code; }592short* data() const { return _data; }593int datalen() const { return _datalen; }594bool has_current() const { return _datalen >= 0; }595bool addr_in_const() const;596597address section_start(int n) const {598assert(_section_start[n], "must be initialized");599return _section_start[n];600}601address section_end(int n) const {602assert(_section_end[n], "must be initialized");603return _section_end[n];604}605606// The address points to the affected displacement part of the instruction.607// For RISC, this is just the whole instruction.608// For Intel, this is an unaligned 32-bit word.609610// type-specific relocation accessors: oop_Relocation* oop_reloc(), etc.611#define EACH_TYPE(name) \612inline name##_Relocation* name##_reloc();613APPLY_TO_RELOCATIONS(EACH_TYPE)614#undef EACH_TYPE615// generic relocation accessor; switches on type to call the above616Relocation* reloc();617618#ifndef PRODUCT619public:620void print();621void print_current();622#endif623};624625626// A Relocation is a flyweight object allocated within a RelocationHolder.627// It represents the relocation data of relocation record.628// So, the RelocIterator unpacks relocInfos into Relocations.629630class Relocation {631friend class RelocationHolder;632friend class RelocIterator;633634private:635// When a relocation has been created by a RelocIterator,636// this field is non-null. It allows the relocation to know637// its context, such as the address to which it applies.638RelocIterator* _binding;639640relocInfo::relocType _rtype;641642protected:643RelocIterator* binding() const {644assert(_binding != NULL, "must be bound");645return _binding;646}647void set_binding(RelocIterator* b) {648assert(_binding == NULL, "must be unbound");649_binding = b;650assert(_binding != NULL, "must now be bound");651}652653Relocation(relocInfo::relocType rtype) : _binding(NULL), _rtype(rtype) { }654655static RelocationHolder newHolder() {656return RelocationHolder();657}658659public:660void* operator new(size_t size, const RelocationHolder& holder) throw() {661assert(size <= sizeof(holder._relocbuf), "Make _relocbuf bigger!");662assert((void* const *)holder.reloc() == &holder._relocbuf[0], "ptrs must agree");663return holder.reloc();664}665666// make a generic relocation for a given type (if possible)667static RelocationHolder spec_simple(relocInfo::relocType rtype);668669// here is the type-specific hook which writes relocation data:670virtual void pack_data_to(CodeSection* dest) { }671672// here is the type-specific hook which reads (unpacks) relocation data:673virtual void unpack_data() {674assert(datalen()==0 || type()==relocInfo::none, "no data here");675}676677protected:678// Helper functions for pack_data_to() and unpack_data().679680// Most of the compression logic is confined here.681// (The "immediate data" mechanism of relocInfo works independently682// of this stuff, and acts to further compress most 1-word data prefixes.)683684// A variable-width int is encoded as a short if it will fit in 16 bits.685// The decoder looks at datalen to decide whether to unpack short or jint.686// Most relocation records are quite simple, containing at most two ints.687688static bool is_short(jint x) { return x == (short)x; }689static short* add_short(short* p, int x) { *p++ = x; return p; }690static short* add_jint (short* p, jint x) {691*p++ = relocInfo::data0_from_int(x); *p++ = relocInfo::data1_from_int(x);692return p;693}694static short* add_var_int(short* p, jint x) { // add a variable-width int695if (is_short(x)) p = add_short(p, x);696else p = add_jint (p, x);697return p;698}699700static short* pack_1_int_to(short* p, jint x0) {701// Format is one of: [] [x] [Xx]702if (x0 != 0) p = add_var_int(p, x0);703return p;704}705int unpack_1_int() {706assert(datalen() <= 2, "too much data");707return relocInfo::jint_data_at(0, data(), datalen());708}709710// With two ints, the short form is used only if both ints are short.711short* pack_2_ints_to(short* p, jint x0, jint x1) {712// Format is one of: [] [x y?] [Xx Y?y]713if (x0 == 0 && x1 == 0) {714// no halfwords needed to store zeroes715} else if (is_short(x0) && is_short(x1)) {716// 1-2 halfwords needed to store shorts717p = add_short(p, x0); if (x1!=0) p = add_short(p, x1);718} else {719// 3-4 halfwords needed to store jints720p = add_jint(p, x0); p = add_var_int(p, x1);721}722return p;723}724void unpack_2_ints(jint& x0, jint& x1) {725int dlen = datalen();726short* dp = data();727if (dlen <= 2) {728x0 = relocInfo::short_data_at(0, dp, dlen);729x1 = relocInfo::short_data_at(1, dp, dlen);730} else {731assert(dlen <= 4, "too much data");732x0 = relocInfo::jint_data_at(0, dp, dlen);733x1 = relocInfo::jint_data_at(2, dp, dlen);734}735}736737protected:738// platform-independent utility for patching constant section739void const_set_data_value (address x);740void const_verify_data_value (address x);741// platform-dependent utilities for decoding and patching instructions742void pd_set_data_value (address x, intptr_t off, bool verify_only = false); // a set or mem-ref743void pd_verify_data_value (address x, intptr_t off) { pd_set_data_value(x, off, true); }744address pd_call_destination (address orig_addr = NULL);745void pd_set_call_destination (address x);746747// this extracts the address of an address in the code stream instead of the reloc data748address* pd_address_in_code ();749750// this extracts an address from the code stream instead of the reloc data751address pd_get_address_from_code ();752753// these convert from byte offsets, to scaled offsets, to addresses754static jint scaled_offset(address x, address base) {755int byte_offset = x - base;756int offset = -byte_offset / relocInfo::addr_unit();757assert(address_from_scaled_offset(offset, base) == x, "just checkin'");758return offset;759}760static jint scaled_offset_null_special(address x, address base) {761// Some relocations treat offset=0 as meaning NULL.762// Handle this extra convention carefully.763if (x == NULL) return 0;764assert(x != base, "offset must not be zero");765return scaled_offset(x, base);766}767static address address_from_scaled_offset(jint offset, address base) {768int byte_offset = -( offset * relocInfo::addr_unit() );769return base + byte_offset;770}771772// helpers for mapping between old and new addresses after a move or resize773address old_addr_for(address newa, const CodeBuffer* src, CodeBuffer* dest);774address new_addr_for(address olda, const CodeBuffer* src, CodeBuffer* dest);775void normalize_address(address& addr, const CodeSection* dest, bool allow_other_sections = false);776777public:778// accessors which only make sense for a bound Relocation779address addr() const { return binding()->addr(); }780CompiledMethod* code() const { return binding()->code(); }781bool addr_in_const() const { return binding()->addr_in_const(); }782protected:783short* data() const { return binding()->data(); }784int datalen() const { return binding()->datalen(); }785int format() const { return binding()->format(); }786787public:788relocInfo::relocType type() const { return _rtype; }789790// is it a call instruction?791virtual bool is_call() { return false; }792793// is it a data movement instruction?794virtual bool is_data() { return false; }795796// some relocations can compute their own values797virtual address value();798799// all relocations are able to reassert their values800virtual void set_value(address x);801802virtual bool clear_inline_cache() { return true; }803804// This method assumes that all virtual/static (inline) caches are cleared (since for static_call_type and805// ic_call_type is not always posisition dependent (depending on the state of the cache)). However, this is806// probably a reasonable assumption, since empty caches simplifies code reloacation.807virtual void fix_relocation_after_move(const CodeBuffer* src, CodeBuffer* dest) { }808};809810811// certain inlines must be deferred until class Relocation is defined:812813inline RelocationHolder::RelocationHolder() {814// initialize the vtbl, just to keep things type-safe815new(*this) Relocation(relocInfo::none);816}817818819inline RelocationHolder::RelocationHolder(Relocation* r) {820// wordwise copy from r (ok if it copies garbage after r)821for (int i = 0; i < _relocbuf_size; i++) {822_relocbuf[i] = ((void**)r)[i];823}824}825826relocInfo::relocType RelocationHolder::type() const {827return reloc()->type();828}829830// A DataRelocation always points at a memory or load-constant instruction..831// It is absolute on most machines, and the constant is split on RISCs.832// The specific subtypes are oop, external_word, and internal_word.833// By convention, the "value" does not include a separately reckoned "offset".834class DataRelocation : public Relocation {835public:836DataRelocation(relocInfo::relocType type) : Relocation(type) {}837838bool is_data() { return true; }839840// both target and offset must be computed somehow from relocation data841virtual int offset() { return 0; }842address value() = 0;843void set_value(address x) { set_value(x, offset()); }844void set_value(address x, intptr_t o) {845if (addr_in_const())846const_set_data_value(x);847else848pd_set_data_value(x, o);849}850void verify_value(address x) {851if (addr_in_const())852const_verify_data_value(x);853else854pd_verify_data_value(x, offset());855}856857// The "o" (displacement) argument is relevant only to split relocations858// on RISC machines. In some CPUs (SPARC), the set-hi and set-lo ins'ns859// can encode more than 32 bits between them. This allows compilers to860// share set-hi instructions between addresses that differ by a small861// offset (e.g., different static variables in the same class).862// On such machines, the "x" argument to set_value on all set-lo863// instructions must be the same as the "x" argument for the864// corresponding set-hi instructions. The "o" arguments for the865// set-hi instructions are ignored, and must not affect the high-half866// immediate constant. The "o" arguments for the set-lo instructions are867// added into the low-half immediate constant, and must not overflow it.868};869870// A CallRelocation always points at a call instruction.871// It is PC-relative on most machines.872class CallRelocation : public Relocation {873public:874CallRelocation(relocInfo::relocType type) : Relocation(type) { }875876bool is_call() { return true; }877878address destination() { return pd_call_destination(); }879void set_destination(address x); // pd_set_call_destination880881void fix_relocation_after_move(const CodeBuffer* src, CodeBuffer* dest);882address value() { return destination(); }883void set_value(address x) { set_destination(x); }884};885886class oop_Relocation : public DataRelocation {887public:888// encode in one of these formats: [] [n] [n l] [Nn l] [Nn Ll]889// an oop in the CodeBlob's oop pool890static RelocationHolder spec(int oop_index, int offset = 0) {891assert(oop_index > 0, "must be a pool-resident oop");892RelocationHolder rh = newHolder();893new(rh) oop_Relocation(oop_index, offset);894return rh;895}896// an oop in the instruction stream897static RelocationHolder spec_for_immediate() {898// If no immediate oops are generated, we can skip some walks over nmethods.899// Assert that they don't get generated accidently!900assert(relocInfo::mustIterateImmediateOopsInCode(),901"Must return true so we will search for oops as roots etc. in the code.");902const int oop_index = 0;903const int offset = 0; // if you want an offset, use the oop pool904RelocationHolder rh = newHolder();905new(rh) oop_Relocation(oop_index, offset);906return rh;907}908909private:910jint _oop_index; // if > 0, index into CodeBlob::oop_at911jint _offset; // byte offset to apply to the oop itself912913oop_Relocation(int oop_index, int offset)914: DataRelocation(relocInfo::oop_type), _oop_index(oop_index), _offset(offset) { }915916friend class RelocIterator;917oop_Relocation() : DataRelocation(relocInfo::oop_type) {}918919public:920int oop_index() { return _oop_index; }921int offset() { return _offset; }922923// data is packed in "2_ints" format: [i o] or [Ii Oo]924void pack_data_to(CodeSection* dest);925void unpack_data();926927void fix_oop_relocation(); // reasserts oop value928929void verify_oop_relocation();930931address value() { return cast_from_oop<address>(*oop_addr()); }932933bool oop_is_immediate() { return oop_index() == 0; }934935oop* oop_addr(); // addr or &pool[jint_data]936oop oop_value(); // *oop_addr937// Note: oop_value transparently converts Universe::non_oop_word to NULL.938};939940941// copy of oop_Relocation for now but may delete stuff in both/either942class metadata_Relocation : public DataRelocation {943944public:945// encode in one of these formats: [] [n] [n l] [Nn l] [Nn Ll]946// an metadata in the CodeBlob's metadata pool947static RelocationHolder spec(int metadata_index, int offset = 0) {948assert(metadata_index > 0, "must be a pool-resident metadata");949RelocationHolder rh = newHolder();950new(rh) metadata_Relocation(metadata_index, offset);951return rh;952}953// an metadata in the instruction stream954static RelocationHolder spec_for_immediate() {955const int metadata_index = 0;956const int offset = 0; // if you want an offset, use the metadata pool957RelocationHolder rh = newHolder();958new(rh) metadata_Relocation(metadata_index, offset);959return rh;960}961962private:963jint _metadata_index; // if > 0, index into nmethod::metadata_at964jint _offset; // byte offset to apply to the metadata itself965966metadata_Relocation(int metadata_index, int offset)967: DataRelocation(relocInfo::metadata_type), _metadata_index(metadata_index), _offset(offset) { }968969friend class RelocIterator;970metadata_Relocation() : DataRelocation(relocInfo::metadata_type) { }971972// Fixes a Metadata pointer in the code. Most platforms embeds the973// Metadata pointer in the code at compile time so this is empty974// for them.975void pd_fix_value(address x);976977public:978int metadata_index() { return _metadata_index; }979int offset() { return _offset; }980981// data is packed in "2_ints" format: [i o] or [Ii Oo]982void pack_data_to(CodeSection* dest);983void unpack_data();984985void fix_metadata_relocation(); // reasserts metadata value986987address value() { return (address) *metadata_addr(); }988989bool metadata_is_immediate() { return metadata_index() == 0; }990991Metadata** metadata_addr(); // addr or &pool[jint_data]992Metadata* metadata_value(); // *metadata_addr993// Note: metadata_value transparently converts Universe::non_metadata_word to NULL.994};995996997class virtual_call_Relocation : public CallRelocation {998999public:1000// "cached_value" points to the first associated set-oop.1001// The oop_limit helps find the last associated set-oop.1002// (See comments at the top of this file.)1003static RelocationHolder spec(address cached_value, jint method_index = 0) {1004RelocationHolder rh = newHolder();1005new(rh) virtual_call_Relocation(cached_value, method_index);1006return rh;1007}10081009private:1010address _cached_value; // location of set-value instruction1011jint _method_index; // resolved method for a Java call10121013virtual_call_Relocation(address cached_value, int method_index)1014: CallRelocation(relocInfo::virtual_call_type),1015_cached_value(cached_value),1016_method_index(method_index) {1017assert(cached_value != NULL, "first oop address must be specified");1018}10191020friend class RelocIterator;1021virtual_call_Relocation() : CallRelocation(relocInfo::virtual_call_type) { }10221023public:1024address cached_value();10251026int method_index() { return _method_index; }1027Method* method_value();10281029// data is packed as scaled offsets in "2_ints" format: [f l] or [Ff Ll]1030// oop_limit is set to 0 if the limit falls somewhere within the call.1031// When unpacking, a zero oop_limit is taken to refer to the end of the call.1032// (This has the effect of bringing in the call's delay slot on SPARC.)1033void pack_data_to(CodeSection* dest);1034void unpack_data();10351036bool clear_inline_cache();1037};103810391040class opt_virtual_call_Relocation : public CallRelocation {1041public:1042static RelocationHolder spec(int method_index = 0) {1043RelocationHolder rh = newHolder();1044new(rh) opt_virtual_call_Relocation(method_index);1045return rh;1046}10471048private:1049jint _method_index; // resolved method for a Java call10501051opt_virtual_call_Relocation(int method_index)1052: CallRelocation(relocInfo::opt_virtual_call_type),1053_method_index(method_index) { }10541055friend class RelocIterator;1056opt_virtual_call_Relocation() : CallRelocation(relocInfo::opt_virtual_call_type) {}10571058public:1059int method_index() { return _method_index; }1060Method* method_value();10611062void pack_data_to(CodeSection* dest);1063void unpack_data();10641065bool clear_inline_cache();10661067// find the matching static_stub1068address static_stub();1069};107010711072class static_call_Relocation : public CallRelocation {1073public:1074static RelocationHolder spec(int method_index = 0) {1075RelocationHolder rh = newHolder();1076new(rh) static_call_Relocation(method_index);1077return rh;1078}10791080private:1081jint _method_index; // resolved method for a Java call10821083static_call_Relocation(int method_index)1084: CallRelocation(relocInfo::static_call_type),1085_method_index(method_index) { }10861087friend class RelocIterator;1088static_call_Relocation() : CallRelocation(relocInfo::static_call_type) {}10891090public:1091int method_index() { return _method_index; }1092Method* method_value();10931094void pack_data_to(CodeSection* dest);1095void unpack_data();10961097bool clear_inline_cache();10981099// find the matching static_stub1100address static_stub();1101};11021103class static_stub_Relocation : public Relocation {1104public:1105static RelocationHolder spec(address static_call) {1106RelocationHolder rh = newHolder();1107new(rh) static_stub_Relocation(static_call);1108return rh;1109}11101111private:1112address _static_call; // location of corresponding static_call11131114static_stub_Relocation(address static_call)1115: Relocation(relocInfo::static_stub_type),1116_static_call(static_call) { }11171118friend class RelocIterator;1119static_stub_Relocation() : Relocation(relocInfo::static_stub_type) { }11201121public:1122bool clear_inline_cache();11231124address static_call() { return _static_call; }11251126// data is packed as a scaled offset in "1_int" format: [c] or [Cc]1127void pack_data_to(CodeSection* dest);1128void unpack_data();1129};11301131class runtime_call_Relocation : public CallRelocation {11321133public:1134static RelocationHolder spec() {1135RelocationHolder rh = newHolder();1136new(rh) runtime_call_Relocation();1137return rh;1138}11391140private:1141friend class RelocIterator;1142runtime_call_Relocation() : CallRelocation(relocInfo::runtime_call_type) { }11431144public:1145};114611471148class runtime_call_w_cp_Relocation : public CallRelocation {1149public:1150static RelocationHolder spec() {1151RelocationHolder rh = newHolder();1152new(rh) runtime_call_w_cp_Relocation();1153return rh;1154}11551156private:1157friend class RelocIterator;1158runtime_call_w_cp_Relocation()1159: CallRelocation(relocInfo::runtime_call_w_cp_type),1160_offset(-4) /* <0 = invalid */ { }11611162// On z/Architecture, runtime calls are either a sequence1163// of two instructions (load destination of call from constant pool + do call)1164// or a pc-relative call. The pc-relative call is faster, but it can only1165// be used if the destination of the call is not too far away.1166// In order to be able to patch a pc-relative call back into one using1167// the constant pool, we have to remember the location of the call's destination1168// in the constant pool.1169int _offset;11701171public:1172void set_constant_pool_offset(int offset) { _offset = offset; }1173int get_constant_pool_offset() { return _offset; }1174void pack_data_to(CodeSection * dest);1175void unpack_data();1176};11771178// Trampoline Relocations.1179// A trampoline allows to encode a small branch in the code, even if there1180// is the chance that this branch can not reach all possible code locations.1181// If the relocation finds that a branch is too far for the instruction1182// in the code, it can patch it to jump to the trampoline where is1183// sufficient space for a far branch. Needed on PPC.1184class trampoline_stub_Relocation : public Relocation {1185public:1186static RelocationHolder spec(address static_call) {1187RelocationHolder rh = newHolder();1188return (new (rh) trampoline_stub_Relocation(static_call));1189}11901191private:1192address _owner; // Address of the NativeCall that owns the trampoline.11931194trampoline_stub_Relocation(address owner)1195: Relocation(relocInfo::trampoline_stub_type),1196_owner(owner) { }11971198friend class RelocIterator;1199trampoline_stub_Relocation() : Relocation(relocInfo::trampoline_stub_type) { }12001201public:12021203// Return the address of the NativeCall that owns the trampoline.1204address owner() { return _owner; }12051206void pack_data_to(CodeSection * dest);1207void unpack_data();12081209// Find the trampoline stub for a call.1210static address get_trampoline_for(address call, nmethod* code);1211};12121213class external_word_Relocation : public DataRelocation {1214public:1215static RelocationHolder spec(address target) {1216assert(target != NULL, "must not be null");1217RelocationHolder rh = newHolder();1218new(rh) external_word_Relocation(target);1219return rh;1220}12211222// Use this one where all 32/64 bits of the target live in the code stream.1223// The target must be an intptr_t, and must be absolute (not relative).1224static RelocationHolder spec_for_immediate() {1225RelocationHolder rh = newHolder();1226new(rh) external_word_Relocation(NULL);1227return rh;1228}12291230// Some address looking values aren't safe to treat as relocations1231// and should just be treated as constants.1232static bool can_be_relocated(address target) {1233assert(target == NULL || (uintptr_t)target >= (uintptr_t)os::vm_page_size(), INTPTR_FORMAT, (intptr_t)target);1234return target != NULL;1235}12361237private:1238address _target; // address in runtime12391240external_word_Relocation(address target)1241: DataRelocation(relocInfo::external_word_type), _target(target) { }12421243friend class RelocIterator;1244external_word_Relocation() : DataRelocation(relocInfo::external_word_type) { }12451246public:1247// data is packed as a well-known address in "1_int" format: [a] or [Aa]1248// The function runtime_address_to_index is used to turn full addresses1249// to short indexes, if they are pre-registered by the stub mechanism.1250// If the "a" value is 0 (i.e., _target is NULL), the address is stored1251// in the code stream. See external_word_Relocation::target().1252void pack_data_to(CodeSection* dest);1253void unpack_data();12541255void fix_relocation_after_move(const CodeBuffer* src, CodeBuffer* dest);1256address target(); // if _target==NULL, fetch addr from code stream1257address value() { return target(); }1258};12591260class internal_word_Relocation : public DataRelocation {12611262public:1263static RelocationHolder spec(address target) {1264assert(target != NULL, "must not be null");1265RelocationHolder rh = newHolder();1266new(rh) internal_word_Relocation(target);1267return rh;1268}12691270// use this one where all the bits of the target can fit in the code stream:1271static RelocationHolder spec_for_immediate() {1272RelocationHolder rh = newHolder();1273new(rh) internal_word_Relocation(NULL);1274return rh;1275}12761277// default section -1 means self-relative1278internal_word_Relocation(address target, int section = -1,1279relocInfo::relocType type = relocInfo::internal_word_type)1280: DataRelocation(type), _target(target), _section(section) { }12811282protected:1283address _target; // address in CodeBlob1284int _section; // section providing base address, if any12851286friend class RelocIterator;1287internal_word_Relocation(relocInfo::relocType type = relocInfo::internal_word_type)1288: DataRelocation(type) { }12891290// bit-width of LSB field in packed offset, if section >= 01291enum { section_width = 2 }; // must equal CodeBuffer::sect_bits12921293public:1294// data is packed as a scaled offset in "1_int" format: [o] or [Oo]1295// If the "o" value is 0 (i.e., _target is NULL), the offset is stored1296// in the code stream. See internal_word_Relocation::target().1297// If _section is not -1, it is appended to the low bits of the offset.1298void pack_data_to(CodeSection* dest);1299void unpack_data();13001301void fix_relocation_after_move(const CodeBuffer* src, CodeBuffer* dest);1302address target(); // if _target==NULL, fetch addr from code stream1303int section() { return _section; }1304address value() { return target(); }1305};13061307class section_word_Relocation : public internal_word_Relocation {1308public:1309static RelocationHolder spec(address target, int section) {1310RelocationHolder rh = newHolder();1311new(rh) section_word_Relocation(target, section);1312return rh;1313}13141315section_word_Relocation(address target, int section)1316: internal_word_Relocation(target, section, relocInfo::section_word_type) {1317assert(target != NULL, "must not be null");1318assert(section >= 0 && section < RelocIterator::SECT_LIMIT, "must be a valid section");1319}13201321//void pack_data_to -- inherited1322void unpack_data();13231324private:1325friend class RelocIterator;1326section_word_Relocation() : internal_word_Relocation(relocInfo::section_word_type) { }1327};132813291330class poll_Relocation : public Relocation {1331bool is_data() { return true; }1332void fix_relocation_after_move(const CodeBuffer* src, CodeBuffer* dest);1333public:1334poll_Relocation(relocInfo::relocType type = relocInfo::poll_type) : Relocation(type) { }1335};13361337class poll_return_Relocation : public poll_Relocation {1338public:1339poll_return_Relocation() : poll_Relocation(relocInfo::relocInfo::poll_return_type) { }1340};13411342// We know all the xxx_Relocation classes, so now we can define these:1343#define EACH_CASE(name) \1344inline name##_Relocation* RelocIterator::name##_reloc() { \1345assert(type() == relocInfo::name##_type, "type must agree"); \1346/* The purpose of the placed "new" is to re-use the same */ \1347/* stack storage for each new iteration. */ \1348name##_Relocation* r = new(_rh) name##_Relocation(); \1349r->set_binding(this); \1350r->name##_Relocation::unpack_data(); \1351return r; \1352}1353APPLY_TO_RELOCATIONS(EACH_CASE);1354#undef EACH_CASE13551356inline RelocIterator::RelocIterator(CompiledMethod* nm, address begin, address limit) {1357initialize(nm, begin, limit);1358}13591360#endif // SHARE_CODE_RELOCINFO_HPP136113621363