0
|
1 /*
|
|
2 * Copyright 2005-2006 Sun Microsystems, Inc. All Rights Reserved.
|
|
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
|
4 *
|
|
5 * This code is free software; you can redistribute it and/or modify it
|
|
6 * under the terms of the GNU General Public License version 2 only, as
|
|
7 * published by the Free Software Foundation.
|
|
8 *
|
|
9 * This code is distributed in the hope that it will be useful, but WITHOUT
|
|
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
12 * version 2 for more details (a copy is included in the LICENSE file that
|
|
13 * accompanied this code).
|
|
14 *
|
|
15 * You should have received a copy of the GNU General Public License version
|
|
16 * 2 along with this work; if not, write to the Free Software Foundation,
|
|
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
18 *
|
|
19 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
|
|
20 * CA 95054 USA or visit www.sun.com if you need additional information or
|
|
21 * have any questions.
|
|
22 *
|
|
23 */
|
|
24
|
|
25
|
|
26 class JvmtiConstantPoolReconstituter : public StackObj {
|
|
27 private:
|
|
28 int _cpool_size;
|
|
29 SymbolHashMap* _symmap;
|
|
30 SymbolHashMap* _classmap;
|
|
31 constantPoolHandle _cpool;
|
|
32 instanceKlassHandle _ikh;
|
|
33 jvmtiError _err;
|
|
34
|
|
35 protected:
|
|
36 instanceKlassHandle ikh() { return _ikh; };
|
|
37 constantPoolHandle cpool() { return _cpool; };
|
|
38
|
|
39 u2 symbol_to_cpool_index(symbolOop sym) {
|
|
40 return _symmap->symbol_to_value(sym);
|
|
41 }
|
|
42
|
|
43 u2 class_symbol_to_cpool_index(symbolOop sym) {
|
|
44 return _classmap->symbol_to_value(sym);
|
|
45 }
|
|
46
|
|
47 public:
|
|
48 // Calls to this constructor must be proceeded by a ResourceMark
|
|
49 // and a HandleMark
|
|
50 JvmtiConstantPoolReconstituter(instanceKlassHandle ikh){
|
|
51 set_error(JVMTI_ERROR_NONE);
|
|
52 _ikh = ikh;
|
|
53 _cpool = constantPoolHandle(Thread::current(), ikh->constants());
|
|
54 _symmap = new SymbolHashMap();
|
|
55 _classmap = new SymbolHashMap();
|
|
56 _cpool_size = _cpool->hash_entries_to(_symmap, _classmap);
|
|
57 if (_cpool_size == 0) {
|
|
58 set_error(JVMTI_ERROR_OUT_OF_MEMORY);
|
|
59 } else if (_cpool_size < 0) {
|
|
60 set_error(JVMTI_ERROR_INTERNAL);
|
|
61 }
|
|
62 }
|
|
63
|
|
64 ~JvmtiConstantPoolReconstituter() {
|
|
65 if (_symmap != NULL) {
|
|
66 os::free(_symmap);
|
|
67 _symmap = NULL;
|
|
68 }
|
|
69 if (_classmap != NULL) {
|
|
70 os::free(_classmap);
|
|
71 _classmap = NULL;
|
|
72 }
|
|
73 }
|
|
74
|
|
75
|
|
76 void set_error(jvmtiError err) { _err = err; }
|
|
77 jvmtiError get_error() { return _err; }
|
|
78
|
|
79 int cpool_size() { return _cpool_size; }
|
|
80
|
|
81 void copy_cpool_bytes(unsigned char *cpool_bytes) {
|
|
82 if (cpool_bytes == NULL) {
|
|
83 assert(cpool_bytes != NULL, "cpool_bytes pointer must not be NULL");
|
|
84 return;
|
|
85 }
|
|
86 cpool()->copy_cpool_bytes(cpool_size(), _symmap, cpool_bytes);
|
|
87 }
|
|
88 };
|
|
89
|
|
90
|
|
91 class JvmtiClassFileReconstituter : public JvmtiConstantPoolReconstituter {
|
|
92 private:
|
|
93 size_t _buffer_size;
|
|
94 u1* _buffer;
|
|
95 u1* _buffer_ptr;
|
|
96 Thread* _thread;
|
|
97
|
|
98 enum {
|
|
99 // initial size should be power of two
|
|
100 initial_buffer_size = 1024
|
|
101 };
|
|
102
|
|
103 inline Thread* thread() { return _thread; }
|
|
104
|
|
105 void write_class_file_format();
|
|
106 void write_field_infos();
|
|
107 void write_method_infos();
|
|
108 void write_method_info(methodHandle method);
|
|
109 void write_code_attribute(methodHandle method);
|
|
110 void write_exceptions_attribute(constMethodHandle const_method);
|
|
111 void write_synthetic_attribute();
|
|
112 void write_class_attributes();
|
|
113 void write_source_file_attribute();
|
|
114 void write_source_debug_extension_attribute();
|
|
115 u2 line_number_table_entries(methodHandle method);
|
|
116 void write_line_number_table_attribute(methodHandle method, u2 num_entries);
|
|
117 void write_stackmap_table_attribute(methodHandle method, int stackmap_table_len);
|
|
118 u2 inner_classes_attribute_length();
|
|
119 void write_inner_classes_attribute(int length);
|
|
120 void write_signature_attribute(u2 generic_signaure_index);
|
|
121 void write_attribute_name_index(const char* name);
|
|
122 void write_annotations_attribute(const char* attr_name, typeArrayHandle annos);
|
|
123
|
|
124 address writeable_address(size_t size);
|
|
125 void write_u1(u1 x);
|
|
126 void write_u2(u2 x);
|
|
127 void write_u4(u4 x);
|
|
128 void write_u8(u8 x);
|
|
129
|
|
130 public:
|
|
131 // Calls to this constructor must be proceeded by a ResourceMark
|
|
132 // and a HandleMark
|
|
133 JvmtiClassFileReconstituter(instanceKlassHandle ikh) :
|
|
134 JvmtiConstantPoolReconstituter(ikh) {
|
|
135 _buffer_size = initial_buffer_size;
|
|
136 _buffer = _buffer_ptr = NEW_RESOURCE_ARRAY(u1, _buffer_size);
|
|
137 _thread = Thread::current();
|
|
138 write_class_file_format();
|
|
139 };
|
|
140
|
|
141 size_t class_file_size() { return _buffer_ptr - _buffer; }
|
|
142
|
|
143 u1* class_file_bytes() { return _buffer; }
|
|
144
|
|
145 static void copy_bytecodes(methodHandle method, unsigned char* bytecodes);
|
|
146 };
|