Wed, 03 Jul 2019 20:42:37 +0800
Merge
aoqi@0 | 1 | /* |
aoqi@0 | 2 | * Copyright (c) 1999, 2013, Oracle and/or its affiliates. All rights reserved. |
aoqi@0 | 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
aoqi@0 | 4 | * |
aoqi@0 | 5 | * This code is free software; you can redistribute it and/or modify it |
aoqi@0 | 6 | * under the terms of the GNU General Public License version 2 only, as |
aoqi@0 | 7 | * published by the Free Software Foundation. |
aoqi@0 | 8 | * |
aoqi@0 | 9 | * This code is distributed in the hope that it will be useful, but WITHOUT |
aoqi@0 | 10 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
aoqi@0 | 11 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
aoqi@0 | 12 | * version 2 for more details (a copy is included in the LICENSE file that |
aoqi@0 | 13 | * accompanied this code). |
aoqi@0 | 14 | * |
aoqi@0 | 15 | * You should have received a copy of the GNU General Public License version |
aoqi@0 | 16 | * 2 along with this work; if not, write to the Free Software Foundation, |
aoqi@0 | 17 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. |
aoqi@0 | 18 | * |
aoqi@0 | 19 | * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
aoqi@0 | 20 | * or visit www.oracle.com if you need additional information or have any |
aoqi@0 | 21 | * questions. |
aoqi@0 | 22 | * |
aoqi@0 | 23 | */ |
aoqi@0 | 24 | |
aoqi@0 | 25 | #ifndef SHARE_VM_CI_CIFIELD_HPP |
aoqi@0 | 26 | #define SHARE_VM_CI_CIFIELD_HPP |
aoqi@0 | 27 | |
aoqi@0 | 28 | #include "ci/ciClassList.hpp" |
aoqi@0 | 29 | #include "ci/ciConstant.hpp" |
aoqi@0 | 30 | #include "ci/ciFlags.hpp" |
aoqi@0 | 31 | #include "ci/ciInstance.hpp" |
aoqi@0 | 32 | |
aoqi@0 | 33 | // ciField |
aoqi@0 | 34 | // |
aoqi@0 | 35 | // This class represents the result of a field lookup in the VM. |
aoqi@0 | 36 | // The lookup may not succeed, in which case the information in |
aoqi@0 | 37 | // the ciField will be incomplete. |
aoqi@0 | 38 | class ciField : public ResourceObj { |
aoqi@0 | 39 | CI_PACKAGE_ACCESS |
aoqi@0 | 40 | friend class ciEnv; |
aoqi@0 | 41 | friend class ciInstanceKlass; |
aoqi@0 | 42 | friend class NonStaticFieldFiller; |
aoqi@0 | 43 | |
aoqi@0 | 44 | private: |
aoqi@0 | 45 | ciFlags _flags; |
aoqi@0 | 46 | ciInstanceKlass* _holder; |
aoqi@0 | 47 | ciSymbol* _name; |
aoqi@0 | 48 | ciSymbol* _signature; |
aoqi@0 | 49 | ciType* _type; |
aoqi@0 | 50 | int _offset; |
aoqi@0 | 51 | bool _is_constant; |
aoqi@0 | 52 | ciInstanceKlass* _known_to_link_with_put; |
aoqi@0 | 53 | ciInstanceKlass* _known_to_link_with_get; |
aoqi@0 | 54 | ciConstant _constant_value; |
aoqi@0 | 55 | |
aoqi@0 | 56 | ciType* compute_type(); |
aoqi@0 | 57 | ciType* compute_type_impl(); |
aoqi@0 | 58 | |
aoqi@0 | 59 | ciField(ciInstanceKlass* klass, int index); |
aoqi@0 | 60 | ciField(fieldDescriptor* fd); |
aoqi@0 | 61 | |
aoqi@0 | 62 | // shared constructor code |
aoqi@0 | 63 | void initialize_from(fieldDescriptor* fd); |
aoqi@0 | 64 | |
aoqi@0 | 65 | public: |
aoqi@0 | 66 | ciFlags flags() { return _flags; } |
aoqi@0 | 67 | |
aoqi@0 | 68 | // Of which klass is this field a member? |
aoqi@0 | 69 | // |
aoqi@0 | 70 | // Usage note: the declared holder of a field is the class |
aoqi@0 | 71 | // referenced by name in the bytecodes. The canonical holder |
aoqi@0 | 72 | // is the most general class which holds the field. This |
aoqi@0 | 73 | // method returns the canonical holder. The declared holder |
aoqi@0 | 74 | // can be accessed via a method in ciBytecodeStream. |
aoqi@0 | 75 | // |
aoqi@0 | 76 | // Ex. |
aoqi@0 | 77 | // class A { |
aoqi@0 | 78 | // public int f = 7; |
aoqi@0 | 79 | // } |
aoqi@0 | 80 | // class B extends A { |
aoqi@0 | 81 | // public void test() { |
aoqi@0 | 82 | // System.out.println(f); |
aoqi@0 | 83 | // } |
aoqi@0 | 84 | // } |
aoqi@0 | 85 | // |
aoqi@0 | 86 | // A java compiler is permitted to compile the access to |
aoqi@0 | 87 | // field f as: |
aoqi@0 | 88 | // |
aoqi@0 | 89 | // getfield B.f |
aoqi@0 | 90 | // |
aoqi@0 | 91 | // In that case the declared holder of f would be B and |
aoqi@0 | 92 | // the canonical holder of f would be A. |
aoqi@0 | 93 | ciInstanceKlass* holder() { return _holder; } |
aoqi@0 | 94 | |
aoqi@0 | 95 | // Name of this field? |
aoqi@0 | 96 | ciSymbol* name() { return _name; } |
aoqi@0 | 97 | |
aoqi@0 | 98 | // Signature of this field? |
aoqi@0 | 99 | ciSymbol* signature() { return _signature; } |
aoqi@0 | 100 | |
aoqi@0 | 101 | // Of what type is this field? |
aoqi@0 | 102 | ciType* type() { return (_type == NULL) ? compute_type() : _type; } |
aoqi@0 | 103 | |
aoqi@0 | 104 | // How is this field actually stored in memory? |
aoqi@0 | 105 | BasicType layout_type() { return type2field[(_type == NULL) ? T_OBJECT : _type->basic_type()]; } |
aoqi@0 | 106 | |
aoqi@0 | 107 | // How big is this field in memory? |
aoqi@0 | 108 | int size_in_bytes() { return type2aelembytes(layout_type()); } |
aoqi@0 | 109 | |
aoqi@0 | 110 | // What is the offset of this field? |
aoqi@0 | 111 | int offset() { |
aoqi@0 | 112 | assert(_offset >= 1, "illegal call to offset()"); |
aoqi@0 | 113 | return _offset; |
aoqi@0 | 114 | } |
aoqi@0 | 115 | |
aoqi@0 | 116 | // Same question, explicit units. (Fields are aligned to the byte level.) |
aoqi@0 | 117 | int offset_in_bytes() { |
aoqi@0 | 118 | return offset(); |
aoqi@0 | 119 | } |
aoqi@0 | 120 | |
aoqi@0 | 121 | // Is this field shared? |
aoqi@0 | 122 | bool is_shared() { |
aoqi@0 | 123 | // non-static fields of shared holders are cached |
aoqi@0 | 124 | return _holder->is_shared() && !is_static(); |
aoqi@0 | 125 | } |
aoqi@0 | 126 | |
zmajo@8664 | 127 | // Is this field a constant? See ciField::initialize_from() for details |
zmajo@8664 | 128 | // about how a field is determined to be constant. |
aoqi@0 | 129 | bool is_constant() { return _is_constant; } |
aoqi@0 | 130 | |
aoqi@0 | 131 | // Get the constant value of this field. |
aoqi@0 | 132 | ciConstant constant_value() { |
aoqi@0 | 133 | assert(is_static() && is_constant(), "illegal call to constant_value()"); |
aoqi@0 | 134 | return _constant_value; |
aoqi@0 | 135 | } |
aoqi@0 | 136 | |
aoqi@0 | 137 | // Get the constant value of non-static final field in the given |
aoqi@0 | 138 | // object. |
aoqi@0 | 139 | ciConstant constant_value_of(ciObject* object) { |
aoqi@0 | 140 | assert(!is_static() && is_constant(), "only if field is non-static constant"); |
aoqi@0 | 141 | assert(object->is_instance(), "must be instance"); |
aoqi@0 | 142 | return object->as_instance()->field_value(this); |
aoqi@0 | 143 | } |
aoqi@0 | 144 | |
aoqi@0 | 145 | // Check for link time errors. Accessing a field from a |
aoqi@0 | 146 | // certain class via a certain bytecode may or may not be legal. |
aoqi@0 | 147 | // This call checks to see if an exception may be raised by |
aoqi@0 | 148 | // an access of this field. |
aoqi@0 | 149 | // |
aoqi@0 | 150 | // Usage note: if the same field is accessed multiple times |
aoqi@0 | 151 | // in the same compilation, will_link will need to be checked |
aoqi@0 | 152 | // at each point of access. |
aoqi@0 | 153 | bool will_link(ciInstanceKlass* accessing_klass, |
aoqi@0 | 154 | Bytecodes::Code bc); |
aoqi@0 | 155 | |
aoqi@0 | 156 | // Java access flags |
aoqi@0 | 157 | bool is_public () { return flags().is_public(); } |
aoqi@0 | 158 | bool is_private () { return flags().is_private(); } |
aoqi@0 | 159 | bool is_protected () { return flags().is_protected(); } |
aoqi@0 | 160 | bool is_static () { return flags().is_static(); } |
aoqi@0 | 161 | bool is_final () { return flags().is_final(); } |
aoqi@0 | 162 | bool is_stable () { return flags().is_stable(); } |
aoqi@0 | 163 | bool is_volatile () { return flags().is_volatile(); } |
aoqi@0 | 164 | bool is_transient () { return flags().is_transient(); } |
zmajo@8664 | 165 | // The field is modified outside of instance initializer methods |
zmajo@8664 | 166 | // (or class/initializer methods if the field is static). |
zmajo@8664 | 167 | bool has_initialized_final_update() { return flags().has_initialized_final_update(); } |
aoqi@0 | 168 | |
aoqi@0 | 169 | bool is_call_site_target() { |
aoqi@0 | 170 | ciInstanceKlass* callsite_klass = CURRENT_ENV->CallSite_klass(); |
aoqi@0 | 171 | if (callsite_klass == NULL) |
aoqi@0 | 172 | return false; |
aoqi@0 | 173 | return (holder()->is_subclass_of(callsite_klass) && (name() == ciSymbol::target_name())); |
aoqi@0 | 174 | } |
aoqi@0 | 175 | |
aoqi@0 | 176 | // Debugging output |
aoqi@0 | 177 | void print(); |
aoqi@0 | 178 | void print_name_on(outputStream* st); |
aoqi@0 | 179 | }; |
aoqi@0 | 180 | |
aoqi@0 | 181 | #endif // SHARE_VM_CI_CIFIELD_HPP |