25 #ifndef SHARE_CDS_DUMPTIMECLASSINFO_HPP
26 #define SHARE_CDS_DUMPTIMECLASSINFO_HPP
27
28 #include "cds/archiveBuilder.hpp"
29 #include "cds/archiveUtils.hpp"
30 #include "cds/cdsConfig.hpp"
31 #include "cds/metaspaceShared.hpp"
32 #include "classfile/compactHashtable.hpp"
33 #include "memory/metaspaceClosure.hpp"
34 #include "oops/instanceKlass.hpp"
35 #include "prims/jvmtiExport.hpp"
36 #include "utilities/growableArray.hpp"
37
38 class Method;
39 class Symbol;
40
41 class DumpTimeClassInfo: public CHeapObj<mtClass> {
42 bool _excluded;
43 bool _is_early_klass;
44 bool _has_checked_exclusion;
45 bool _is_required_hidden_class;
46 bool _has_scanned_constant_pool;
47 class DTLoaderConstraint {
48 Symbol* _name;
49 char _loader_type1;
50 char _loader_type2;
51 public:
52 DTLoaderConstraint() : _name(nullptr), _loader_type1('0'), _loader_type2('0') {}
53 DTLoaderConstraint(Symbol* name, char l1, char l2) : _name(name), _loader_type1(l1), _loader_type2(l2) {
54 Symbol::maybe_increment_refcount(_name);
55 }
56 DTLoaderConstraint(const DTLoaderConstraint& src) {
57 _name = src._name;
58 _loader_type1 = src._loader_type1;
59 _loader_type2 = src._loader_type2;
60 Symbol::maybe_increment_refcount(_name);
61 }
62 DTLoaderConstraint& operator=(DTLoaderConstraint src) {
63 swap(_name, src._name); // c++ copy-and-swap idiom
64 _loader_type1 = src._loader_type1;
121
122 public:
123 InstanceKlass* _klass;
124 InstanceKlass* _nest_host;
125 bool _failed_verification;
126 bool _is_archived_lambda_proxy;
127 int _id;
128 int _clsfile_size;
129 int _clsfile_crc32;
130 GrowableArray<DTVerifierConstraint>* _verifier_constraints;
131 GrowableArray<char>* _verifier_constraint_flags;
132 GrowableArray<DTLoaderConstraint>* _loader_constraints;
133 GrowableArray<int>* _enum_klass_static_fields;
134
135 DumpTimeClassInfo() {
136 _klass = nullptr;
137 _nest_host = nullptr;
138 _failed_verification = false;
139 _is_archived_lambda_proxy = false;
140 _has_checked_exclusion = false;
141 _is_required_hidden_class = false;
142 _has_scanned_constant_pool = false;
143 _id = -1;
144 _clsfile_size = -1;
145 _clsfile_crc32 = -1;
146 _excluded = false;
147 _is_early_klass = JvmtiExport::is_early_phase();
148 _verifier_constraints = nullptr;
149 _verifier_constraint_flags = nullptr;
150 _loader_constraints = nullptr;
151 _enum_klass_static_fields = nullptr;
152 }
153 DumpTimeClassInfo& operator=(const DumpTimeClassInfo&) = delete;
154 ~DumpTimeClassInfo();
155
156 void add_verification_constraint(InstanceKlass* k, Symbol* name,
157 Symbol* from_name, bool from_field_is_protected, bool from_is_array, bool from_is_object);
158 void record_linking_constraint(Symbol* name, Handle loader1, Handle loader2);
159 void add_enum_klass_static_field(int archived_heap_root_index);
160 int enum_klass_static_field(int which_field);
182
183 int num_enum_klass_static_fields() const {
184 return array_length_or_zero(_enum_klass_static_fields);
185 }
186
187 void metaspace_pointers_do(MetaspaceClosure* it) {
188 it->push(&_klass);
189 it->push(&_nest_host);
190 if (_verifier_constraints != nullptr) {
191 for (int i = 0; i < _verifier_constraints->length(); i++) {
192 _verifier_constraints->adr_at(i)->metaspace_pointers_do(it);
193 }
194 }
195 if (_loader_constraints != nullptr) {
196 for (int i = 0; i < _loader_constraints->length(); i++) {
197 _loader_constraints->adr_at(i)->metaspace_pointers_do(it);
198 }
199 }
200 }
201
202 bool is_excluded() {
203 return _excluded || _failed_verification;
204 }
205
206 // Was this class loaded while JvmtiExport::is_early_phase()==true
207 bool is_early_klass() {
208 return _is_early_klass;
209 }
210
211 // simple accessors
212 void set_excluded() { _excluded = true; }
213 bool has_checked_exclusion() const { return _has_checked_exclusion; }
214 void set_has_checked_exclusion() { _has_checked_exclusion = true; }
215 bool failed_verification() const { return _failed_verification; }
216 void set_failed_verification() { _failed_verification = true; }
217 InstanceKlass* nest_host() const { return _nest_host; }
218 void set_nest_host(InstanceKlass* nest_host) { _nest_host = nest_host; }
219
220 bool is_required_hidden_class() const { return _is_required_hidden_class; }
221 void set_is_required_hidden_class() { _is_required_hidden_class = true; }
222 bool has_scanned_constant_pool() const { return _has_scanned_constant_pool; }
223 void set_has_scanned_constant_pool() { _has_scanned_constant_pool = true; }
224
225 size_t runtime_info_bytesize() const;
226 };
227
228 template <typename T>
229 inline unsigned DumpTimeSharedClassTable_hash(T* const& k) {
230 if (CDSConfig::is_dumping_static_archive()) {
231 // Deterministic archive contents
232 uintx delta = k->name() - MetaspaceShared::symbol_rs_base();
233 return primitive_hash<uintx>(delta);
234 } else {
235 // Deterministic archive is not possible because classes can be loaded
236 // in multiple threads.
237 return primitive_hash<T*>(k);
238 }
239 }
240
241 using DumpTimeSharedClassTableBaseType = ResourceHashtable<
242 InstanceKlass*,
243 DumpTimeClassInfo,
244 15889, // prime number
253 public:
254 DumpTimeSharedClassTable() {
255 _builtin_count = 0;
256 _unregistered_count = 0;
257 }
258 DumpTimeClassInfo* allocate_info(InstanceKlass* k);
259 DumpTimeClassInfo* get_info(InstanceKlass* k);
260 void inc_builtin_count() { _builtin_count++; }
261 void inc_unregistered_count() { _unregistered_count++; }
262 void update_counts();
263 int count_of(bool is_builtin) const {
264 if (is_builtin) {
265 return _builtin_count;
266 } else {
267 return _unregistered_count;
268 }
269 }
270
271 template<class ITER> void iterate_all_live_classes(ITER* iter) const;
272 template<typename Function> void iterate_all_live_classes(Function function) const;
273
274 private:
275 // It's unsafe to iterate on classes whose loader is dead.
276 // Declare these private and don't implement them. This forces users of
277 // DumpTimeSharedClassTable to use the iterate_all_live_classes() methods
278 // instead.
279 template<class ITER> void iterate(ITER* iter) const;
280 template<typename Function> void iterate(Function function) const;
281 template<typename Function> void iterate_all(Function function) const;
282 };
283
284 #endif // SHARE_CDS_DUMPTIMECLASSINFO_HPP
|
25 #ifndef SHARE_CDS_DUMPTIMECLASSINFO_HPP
26 #define SHARE_CDS_DUMPTIMECLASSINFO_HPP
27
28 #include "cds/archiveBuilder.hpp"
29 #include "cds/archiveUtils.hpp"
30 #include "cds/cdsConfig.hpp"
31 #include "cds/metaspaceShared.hpp"
32 #include "classfile/compactHashtable.hpp"
33 #include "memory/metaspaceClosure.hpp"
34 #include "oops/instanceKlass.hpp"
35 #include "prims/jvmtiExport.hpp"
36 #include "utilities/growableArray.hpp"
37
38 class Method;
39 class Symbol;
40
41 class DumpTimeClassInfo: public CHeapObj<mtClass> {
42 bool _excluded;
43 bool _is_early_klass;
44 bool _has_checked_exclusion;
45 bool _can_be_preinited;
46 bool _has_done_preinit_check;
47 bool _is_required_hidden_class;
48 bool _has_scanned_constant_pool;
49 class DTLoaderConstraint {
50 Symbol* _name;
51 char _loader_type1;
52 char _loader_type2;
53 public:
54 DTLoaderConstraint() : _name(nullptr), _loader_type1('0'), _loader_type2('0') {}
55 DTLoaderConstraint(Symbol* name, char l1, char l2) : _name(name), _loader_type1(l1), _loader_type2(l2) {
56 Symbol::maybe_increment_refcount(_name);
57 }
58 DTLoaderConstraint(const DTLoaderConstraint& src) {
59 _name = src._name;
60 _loader_type1 = src._loader_type1;
61 _loader_type2 = src._loader_type2;
62 Symbol::maybe_increment_refcount(_name);
63 }
64 DTLoaderConstraint& operator=(DTLoaderConstraint src) {
65 swap(_name, src._name); // c++ copy-and-swap idiom
66 _loader_type1 = src._loader_type1;
123
124 public:
125 InstanceKlass* _klass;
126 InstanceKlass* _nest_host;
127 bool _failed_verification;
128 bool _is_archived_lambda_proxy;
129 int _id;
130 int _clsfile_size;
131 int _clsfile_crc32;
132 GrowableArray<DTVerifierConstraint>* _verifier_constraints;
133 GrowableArray<char>* _verifier_constraint_flags;
134 GrowableArray<DTLoaderConstraint>* _loader_constraints;
135 GrowableArray<int>* _enum_klass_static_fields;
136
137 DumpTimeClassInfo() {
138 _klass = nullptr;
139 _nest_host = nullptr;
140 _failed_verification = false;
141 _is_archived_lambda_proxy = false;
142 _has_checked_exclusion = false;
143 _can_be_preinited = false;
144 _has_done_preinit_check = false;
145 _is_required_hidden_class = false;
146 _has_scanned_constant_pool = false;
147 _id = -1;
148 _clsfile_size = -1;
149 _clsfile_crc32 = -1;
150 _excluded = false;
151 _is_early_klass = JvmtiExport::is_early_phase();
152 _verifier_constraints = nullptr;
153 _verifier_constraint_flags = nullptr;
154 _loader_constraints = nullptr;
155 _enum_klass_static_fields = nullptr;
156 }
157 DumpTimeClassInfo& operator=(const DumpTimeClassInfo&) = delete;
158 ~DumpTimeClassInfo();
159
160 void add_verification_constraint(InstanceKlass* k, Symbol* name,
161 Symbol* from_name, bool from_field_is_protected, bool from_is_array, bool from_is_object);
162 void record_linking_constraint(Symbol* name, Handle loader1, Handle loader2);
163 void add_enum_klass_static_field(int archived_heap_root_index);
164 int enum_klass_static_field(int which_field);
186
187 int num_enum_klass_static_fields() const {
188 return array_length_or_zero(_enum_klass_static_fields);
189 }
190
191 void metaspace_pointers_do(MetaspaceClosure* it) {
192 it->push(&_klass);
193 it->push(&_nest_host);
194 if (_verifier_constraints != nullptr) {
195 for (int i = 0; i < _verifier_constraints->length(); i++) {
196 _verifier_constraints->adr_at(i)->metaspace_pointers_do(it);
197 }
198 }
199 if (_loader_constraints != nullptr) {
200 for (int i = 0; i < _loader_constraints->length(); i++) {
201 _loader_constraints->adr_at(i)->metaspace_pointers_do(it);
202 }
203 }
204 }
205
206 bool is_excluded();
207
208 // Was this class loaded while JvmtiExport::is_early_phase()==true
209 bool is_early_klass() {
210 return _is_early_klass;
211 }
212
213 // simple accessors
214 void set_excluded() { _excluded = true; }
215 bool has_checked_exclusion() const { return _has_checked_exclusion; }
216 void set_has_checked_exclusion() { _has_checked_exclusion = true; }
217 bool failed_verification() const { return _failed_verification; }
218 void set_failed_verification() { _failed_verification = true; }
219 InstanceKlass* nest_host() const { return _nest_host; }
220 void set_nest_host(InstanceKlass* nest_host) { _nest_host = nest_host; }
221
222 bool can_be_preinited() const { return _can_be_preinited; }
223 bool has_done_preinit_check() const { return _has_done_preinit_check; }
224 bool is_required_hidden_class() const { return _is_required_hidden_class; }
225 void set_is_required_hidden_class() { _is_required_hidden_class = true; }
226 bool has_scanned_constant_pool() const { return _has_scanned_constant_pool; }
227 void set_has_scanned_constant_pool() { _has_scanned_constant_pool = true; }
228
229 void set_can_be_preinited(bool v) {
230 _can_be_preinited = v;
231 _has_done_preinit_check = true;
232 }
233 void reset_preinit_check() {
234 _can_be_preinited = false;
235 _has_done_preinit_check = false;
236 }
237
238 size_t runtime_info_bytesize() const;
239 };
240
241 template <typename T>
242 inline unsigned DumpTimeSharedClassTable_hash(T* const& k) {
243 if (CDSConfig::is_dumping_static_archive()) {
244 // Deterministic archive contents
245 uintx delta = k->name() - MetaspaceShared::symbol_rs_base();
246 return primitive_hash<uintx>(delta);
247 } else {
248 // Deterministic archive is not possible because classes can be loaded
249 // in multiple threads.
250 return primitive_hash<T*>(k);
251 }
252 }
253
254 using DumpTimeSharedClassTableBaseType = ResourceHashtable<
255 InstanceKlass*,
256 DumpTimeClassInfo,
257 15889, // prime number
266 public:
267 DumpTimeSharedClassTable() {
268 _builtin_count = 0;
269 _unregistered_count = 0;
270 }
271 DumpTimeClassInfo* allocate_info(InstanceKlass* k);
272 DumpTimeClassInfo* get_info(InstanceKlass* k);
273 void inc_builtin_count() { _builtin_count++; }
274 void inc_unregistered_count() { _unregistered_count++; }
275 void update_counts();
276 int count_of(bool is_builtin) const {
277 if (is_builtin) {
278 return _builtin_count;
279 } else {
280 return _unregistered_count;
281 }
282 }
283
284 template<class ITER> void iterate_all_live_classes(ITER* iter) const;
285 template<typename Function> void iterate_all_live_classes(Function function) const;
286 template<typename Function> void iterate_all_classes_in_builtin_loaders(Function function) const;
287
288 private:
289 // It's unsafe to iterate on classes whose loader is dead.
290 // Declare these private and don't implement them. This forces users of
291 // DumpTimeSharedClassTable to use the iterate_all_live_classes() methods
292 // instead.
293 template<class ITER> void iterate(ITER* iter) const;
294 template<typename Function> void iterate(Function function) const;
295 template<typename Function> void iterate_all(Function function) const;
296 };
297
298 #endif // SHARE_CDS_DUMPTIMECLASSINFO_HPP
|