66 } 67 }; 68 69 class KlassSizeStats; 70 71 class ConstantPool : public Metadata { 72 friend class VMStructs; 73 friend class BytecodeInterpreter; // Directly extracts a klass in the pool for fast instanceof/checkcast 74 friend class Universe; // For null constructor 75 private: 76 Array<u1>* _tags; // the tag array describing the constant pool's contents 77 ConstantPoolCache* _cache; // the cache holding interpreter runtime information 78 InstanceKlass* _pool_holder; // the corresponding class 79 Array<u2>* _operands; // for variable-sized (InvokeDynamic) nodes, usually empty 80 81 // Array of resolved objects from the constant pool and map from resolved 82 // object index to original constant pool index 83 jobject _resolved_references; 84 Array<u2>* _reference_map; 85 86 enum { 87 _has_preresolution = 1, // Flags 88 _on_stack = 2 89 }; 90 91 int _flags; // old fashioned bit twiddling 92 int _length; // number of elements in the array 93 94 union { 95 // set for CDS to restore resolved references 96 int _resolved_reference_length; 97 // keeps version number for redefined classes (used in backtrace) 98 int _version; 99 } _saved; 100 101 void set_tags(Array<u1>* tags) { _tags = tags; } 102 void tag_at_put(int which, jbyte t) { tags()->at_put(which, t); } 103 void release_tag_at_put(int which, jbyte t) { tags()->release_at_put(which, t); } 104 105 u1* tag_addr_at(int which) const { return tags()->adr_at(which); } 143 jfloat* float_at_addr(int which) const { 144 assert(is_within_bounds(which), "index out of bounds"); 145 return (jfloat*) &base()[which]; 146 } 147 148 jdouble* double_at_addr(int which) const { 149 assert(is_within_bounds(which), "index out of bounds"); 150 return (jdouble*) &base()[which]; 151 } 152 153 ConstantPool(Array<u1>* tags); 154 ConstantPool() { assert(DumpSharedSpaces || UseSharedSpaces, "only for CDS"); } 155 public: 156 static ConstantPool* allocate(ClassLoaderData* loader_data, int length, TRAPS); 157 158 bool is_constantPool() const volatile { return true; } 159 160 Array<u1>* tags() const { return _tags; } 161 Array<u2>* operands() const { return _operands; } 162 163 bool has_preresolution() const { return (_flags & _has_preresolution) != 0; } 164 void set_has_preresolution() { _flags |= _has_preresolution; } 165 166 // Redefine classes support. If a method refering to this constant pool 167 // is on the executing stack, or as a handle in vm code, this constant pool 168 // can't be removed from the set of previous versions saved in the instance 169 // class. 170 bool on_stack() const { return (_flags &_on_stack) != 0; } 171 void set_on_stack(const bool value); 172 173 // Klass holding pool 174 InstanceKlass* pool_holder() const { return _pool_holder; } 175 void set_pool_holder(InstanceKlass* k) { _pool_holder = k; } 176 InstanceKlass** pool_holder_addr() { return &_pool_holder; } 177 178 // Interpreter runtime support 179 ConstantPoolCache* cache() const { return _cache; } 180 void set_cache(ConstantPoolCache* cache){ _cache = cache; } 181 182 // Create object cache in the constant pool | 66 } 67 }; 68 69 class KlassSizeStats; 70 71 class ConstantPool : public Metadata { 72 friend class VMStructs; 73 friend class BytecodeInterpreter; // Directly extracts a klass in the pool for fast instanceof/checkcast 74 friend class Universe; // For null constructor 75 private: 76 Array<u1>* _tags; // the tag array describing the constant pool's contents 77 ConstantPoolCache* _cache; // the cache holding interpreter runtime information 78 InstanceKlass* _pool_holder; // the corresponding class 79 Array<u2>* _operands; // for variable-sized (InvokeDynamic) nodes, usually empty 80 81 // Array of resolved objects from the constant pool and map from resolved 82 // object index to original constant pool index 83 jobject _resolved_references; 84 Array<u2>* _reference_map; 85 86 // Needed for JvmtiConstantPoolReconstituter. 87 // Map from a pseudo-string index to the original Utf8 entry index. 88 // Each u4 entry consist of two packed u2 integers: 89 // JVM_CONSTANT_String index and JVM_CONSTANT_Utf8 index 90 GrowableArray<u4>* _pseudo_string_map; 91 92 enum { 93 _has_preresolution = 1, // Flags 94 _on_stack = 2 95 }; 96 97 int _flags; // old fashioned bit twiddling 98 int _length; // number of elements in the array 99 100 union { 101 // set for CDS to restore resolved references 102 int _resolved_reference_length; 103 // keeps version number for redefined classes (used in backtrace) 104 int _version; 105 } _saved; 106 107 void set_tags(Array<u1>* tags) { _tags = tags; } 108 void tag_at_put(int which, jbyte t) { tags()->at_put(which, t); } 109 void release_tag_at_put(int which, jbyte t) { tags()->release_at_put(which, t); } 110 111 u1* tag_addr_at(int which) const { return tags()->adr_at(which); } 149 jfloat* float_at_addr(int which) const { 150 assert(is_within_bounds(which), "index out of bounds"); 151 return (jfloat*) &base()[which]; 152 } 153 154 jdouble* double_at_addr(int which) const { 155 assert(is_within_bounds(which), "index out of bounds"); 156 return (jdouble*) &base()[which]; 157 } 158 159 ConstantPool(Array<u1>* tags); 160 ConstantPool() { assert(DumpSharedSpaces || UseSharedSpaces, "only for CDS"); } 161 public: 162 static ConstantPool* allocate(ClassLoaderData* loader_data, int length, TRAPS); 163 164 bool is_constantPool() const volatile { return true; } 165 166 Array<u1>* tags() const { return _tags; } 167 Array<u2>* operands() const { return _operands; } 168 169 GrowableArray<u4>* pseudo_string_map() { 170 if (_pseudo_string_map == NULL) { 171 _pseudo_string_map = new(ResourceObj::C_HEAP, mtClass) GrowableArray<u4>(1, true); 172 } 173 return _pseudo_string_map; 174 } 175 176 void map_pseudo_string_indices(u2 index, u2 utf8_idx) { 177 u4 packed = index << 16 | utf8_idx; 178 pseudo_string_map()->append(packed); 179 } 180 181 u2 get_pseudo_string_utf8_index(u2 index) { 182 GrowableArray<u4>* map = pseudo_string_map(); 183 int len = map->length(); 184 // The entries are ordered by value so that a binary search can be 185 // used if a performance bottleneck is observed in this area. 186 for (int i = 0; i < len; i++) { 187 u4 packed = map->at(i); 188 u2 idx = (packed >> 16) & 0xFF; 189 if (idx == index) { 190 u2 utf8_idx = packed & 0xFF; 191 assert(utf8_idx > 0, "Utf8 cp index in pseudo-string map must be positive"); 192 return utf8_idx; 193 } 194 } 195 assert(true, "not found a matching entry in pseudo-string map"); 196 return 0; 197 } 198 199 bool has_preresolution() const { return (_flags & _has_preresolution) != 0; } 200 void set_has_preresolution() { _flags |= _has_preresolution; } 201 202 // Redefine classes support. If a method refering to this constant pool 203 // is on the executing stack, or as a handle in vm code, this constant pool 204 // can't be removed from the set of previous versions saved in the instance 205 // class. 206 bool on_stack() const { return (_flags &_on_stack) != 0; } 207 void set_on_stack(const bool value); 208 209 // Klass holding pool 210 InstanceKlass* pool_holder() const { return _pool_holder; } 211 void set_pool_holder(InstanceKlass* k) { _pool_holder = k; } 212 InstanceKlass** pool_holder_addr() { return &_pool_holder; } 213 214 // Interpreter runtime support 215 ConstantPoolCache* cache() const { return _cache; } 216 void set_cache(ConstantPoolCache* cache){ _cache = cache; } 217 218 // Create object cache in the constant pool |