97 ss.print("(%s) ", Deoptimization::format_trap_state(buf, sizeof(buf), trap));
98 }
99 break;
100 case DataLayout::bit_data_tag:
101 break;
102 case DataLayout::no_tag:
103 case DataLayout::arg_info_data_tag:
104 return ss.as_string();
105 break;
106 default:
107 fatal(err_msg("unexpected tag %d", dp->tag()));
108 }
109 }
110 return NULL;
111 }
112
113 void ProfileData::print_data_on(outputStream* st, const MethodData* md) const {
114 print_data_on(st, print_data_on_helper(md));
115 }
116
117 #ifndef PRODUCT
118 void ProfileData::print_shared(outputStream* st, const char* name, const char* extra) const {
119 st->print("bci: %d", bci());
120 st->fill_to(tab_width_one);
121 st->print("%s", name);
122 tab(st);
123 int trap = trap_state();
124 if (trap != 0) {
125 char buf[100];
126 st->print("trap(%s) ", Deoptimization::format_trap_state(buf, sizeof(buf), trap));
127 }
128 if (extra != NULL) {
129 st->print(extra);
130 }
131 int flags = data()->flags();
132 if (flags != 0) {
133 st->print("flags(%d) ", flags);
134 }
135 }
136
137 void ProfileData::tab(outputStream* st, bool first) const {
138 st->fill_to(first ? tab_width_one : tab_width_two);
139 }
140 #endif // !PRODUCT
141
142 // ==================================================================
143 // BitData
144 //
145 // A BitData corresponds to a one-bit flag. This is used to indicate
146 // whether a checkcast bytecode has seen a null value.
147
148
149 #ifndef PRODUCT
150 void BitData::print_data_on(outputStream* st, const char* extra) const {
151 print_shared(st, "BitData", extra);
152 }
153 #endif // !PRODUCT
154
155 // ==================================================================
156 // CounterData
157 //
158 // A CounterData corresponds to a simple counter.
159
160 #ifndef PRODUCT
161 void CounterData::print_data_on(outputStream* st, const char* extra) const {
162 print_shared(st, "CounterData", extra);
163 st->print_cr("count(%u)", count());
164 }
165 #endif // !PRODUCT
166
167 // ==================================================================
168 // JumpData
169 //
170 // A JumpData is used to access profiling information for a direct
171 // branch. It is a counter, used for counting the number of branches,
172 // plus a data displacement, used for realigning the data pointer to
173 // the corresponding target bci.
174
175 void JumpData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
176 assert(stream->bci() == bci(), "wrong pos");
177 int target;
178 Bytecodes::Code c = stream->code();
179 if (c == Bytecodes::_goto_w || c == Bytecodes::_jsr_w) {
180 target = stream->dest_w();
181 } else {
182 target = stream->dest();
183 }
184 int my_di = mdo->dp_to_di(dp());
185 int target_di = mdo->bci_to_di(target);
186 int offset = target_di - my_di;
187 set_displacement(offset);
188 }
189
190 #ifndef PRODUCT
191 void JumpData::print_data_on(outputStream* st, const char* extra) const {
192 print_shared(st, "JumpData", extra);
193 st->print_cr("taken(%u) displacement(%d)", taken(), displacement());
194 }
195 #endif // !PRODUCT
196
197 int TypeStackSlotEntries::compute_cell_count(Symbol* signature, bool include_receiver, int max) {
198 // Parameter profiling include the receiver
199 int args_count = include_receiver ? 1 : 0;
200 ResourceMark rm;
201 SignatureStream ss(signature);
202 args_count += ss.reference_parameter_count();
203 args_count = MIN2(args_count, max);
204 return args_count * per_arg_cell_count;
205 }
206
207 int TypeEntriesAtCall::compute_cell_count(BytecodeStream* stream) {
208 assert(Bytecodes::is_invoke(stream->code()), "should be invoke");
209 assert(TypeStackSlotEntries::per_arg_count() > ReturnTypeEntry::static_cell_count(), "code to test for arguments/results broken");
210 Bytecode_invoke inv(stream->method(), stream->bci());
211 int args_cell = 0;
212 if (arguments_profiling_enabled()) {
213 args_cell = TypeStackSlotEntries::compute_cell_count(inv.signature(), false, TypeProfileArgsLimit);
214 }
215 int ret_cell = 0;
324 set_type(i, with_status((Klass*)NULL, p));
325 }
326 }
327 }
328
329 void ReturnTypeEntry::clean_weak_klass_links(BoolObjectClosure* is_alive_cl) {
330 intptr_t p = type();
331 if (!is_loader_alive(is_alive_cl, p)) {
332 set_type(with_status((Klass*)NULL, p));
333 }
334 }
335
336 bool TypeEntriesAtCall::return_profiling_enabled() {
337 return MethodData::profile_return();
338 }
339
340 bool TypeEntriesAtCall::arguments_profiling_enabled() {
341 return MethodData::profile_arguments();
342 }
343
344 #ifndef PRODUCT
345 void TypeEntries::print_klass(outputStream* st, intptr_t k) {
346 if (is_type_none(k)) {
347 st->print("none");
348 } else if (is_type_unknown(k)) {
349 st->print("unknown");
350 } else {
351 valid_klass(k)->print_value_on(st);
352 }
353 if (was_null_seen(k)) {
354 st->print(" (null seen)");
355 }
356 }
357
358 void TypeStackSlotEntries::print_data_on(outputStream* st) const {
359 for (int i = 0; i < _number_of_entries; i++) {
360 _pd->tab(st);
361 st->print("%d: stack(%u) ", i, stack_slot(i));
362 print_klass(st, type(i));
363 st->cr();
364 }
380 if (has_return()) {
381 tab(st, true);
382 st->print("return type");
383 _ret.print_data_on(st);
384 }
385 }
386
387 void VirtualCallTypeData::print_data_on(outputStream* st, const char* extra) const {
388 VirtualCallData::print_data_on(st, extra);
389 if (has_arguments()) {
390 tab(st, true);
391 st->print("argument types");
392 _args.print_data_on(st);
393 }
394 if (has_return()) {
395 tab(st, true);
396 st->print("return type");
397 _ret.print_data_on(st);
398 }
399 }
400 #endif
401
402 // ==================================================================
403 // ReceiverTypeData
404 //
405 // A ReceiverTypeData is used to access profiling information about a
406 // dynamic type check. It consists of a counter which counts the total times
407 // that the check is reached, and a series of (Klass*, count) pairs
408 // which are used to store a type profile for the receiver of the check.
409
410 void ReceiverTypeData::clean_weak_klass_links(BoolObjectClosure* is_alive_cl) {
411 for (uint row = 0; row < row_limit(); row++) {
412 Klass* p = receiver(row);
413 if (p != NULL && !p->is_loader_alive(is_alive_cl)) {
414 clear_row(row);
415 }
416 }
417 }
418
419 #ifndef PRODUCT
420 void ReceiverTypeData::print_receiver_data_on(outputStream* st) const {
421 uint row;
422 int entries = 0;
423 for (row = 0; row < row_limit(); row++) {
424 if (receiver(row) != NULL) entries++;
425 }
426 st->print_cr("count(%u) entries(%u)", count(), entries);
427 int total = count();
428 for (row = 0; row < row_limit(); row++) {
429 if (receiver(row) != NULL) {
430 total += receiver_count(row);
431 }
432 }
433 for (row = 0; row < row_limit(); row++) {
434 if (receiver(row) != NULL) {
435 tab(st);
436 receiver(row)->print_value_on(st);
437 st->print_cr("(%u %4.2f)", receiver_count(row), (float) receiver_count(row) / (float) total);
438 }
439 }
440 }
441 void ReceiverTypeData::print_data_on(outputStream* st, const char* extra) const {
442 print_shared(st, "ReceiverTypeData", extra);
443 print_receiver_data_on(st);
444 }
445 void VirtualCallData::print_data_on(outputStream* st, const char* extra) const {
446 print_shared(st, "VirtualCallData", extra);
447 print_receiver_data_on(st);
448 }
449 #endif // !PRODUCT
450
451 // ==================================================================
452 // RetData
453 //
454 // A RetData is used to access profiling information for a ret bytecode.
455 // It is composed of a count of the number of times that the ret has
456 // been executed, followed by a series of triples of the form
457 // (bci, count, di) which count the number of times that some bci was the
458 // target of the ret and cache a corresponding displacement.
459
460 void RetData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
461 for (uint row = 0; row < row_limit(); row++) {
462 set_bci_displacement(row, -1);
463 set_bci(row, no_bci);
464 }
465 // release so other threads see a consistent state. bci is used as
466 // a valid flag for bci_displacement.
467 OrderAccess::release();
468 }
469
481 // Now check to see if any of the cache slots are open.
482 for (uint row = 0; row < row_limit(); row++) {
483 if (bci(row) == no_bci) {
484 set_bci_displacement(row, mdp - dp());
485 set_bci_count(row, DataLayout::counter_increment);
486 // Barrier to ensure displacement is written before the bci; allows
487 // the interpreter to read displacement without fear of race condition.
488 release_set_bci(row, return_bci);
489 break;
490 }
491 }
492 return mdp;
493 }
494
495 #ifdef CC_INTERP
496 DataLayout* RetData::advance(MethodData *md, int bci) {
497 return (DataLayout*) md->bci_to_dp(bci);
498 }
499 #endif // CC_INTERP
500
501 #ifndef PRODUCT
502 void RetData::print_data_on(outputStream* st, const char* extra) const {
503 print_shared(st, "RetData", extra);
504 uint row;
505 int entries = 0;
506 for (row = 0; row < row_limit(); row++) {
507 if (bci(row) != no_bci) entries++;
508 }
509 st->print_cr("count(%u) entries(%u)", count(), entries);
510 for (row = 0; row < row_limit(); row++) {
511 if (bci(row) != no_bci) {
512 tab(st);
513 st->print_cr("bci(%d: count(%u) displacement(%d))",
514 bci(row), bci_count(row), bci_displacement(row));
515 }
516 }
517 }
518 #endif // !PRODUCT
519
520 // ==================================================================
521 // BranchData
522 //
523 // A BranchData is used to access profiling data for a two-way branch.
524 // It consists of taken and not_taken counts as well as a data displacement
525 // for the taken case.
526
527 void BranchData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
528 assert(stream->bci() == bci(), "wrong pos");
529 int target = stream->dest();
530 int my_di = mdo->dp_to_di(dp());
531 int target_di = mdo->bci_to_di(target);
532 int offset = target_di - my_di;
533 set_displacement(offset);
534 }
535
536 #ifndef PRODUCT
537 void BranchData::print_data_on(outputStream* st, const char* extra) const {
538 print_shared(st, "BranchData", extra);
539 st->print_cr("taken(%u) displacement(%d)",
540 taken(), displacement());
541 tab(st);
542 st->print_cr("not taken(%u)", not_taken());
543 }
544 #endif
545
546 // ==================================================================
547 // MultiBranchData
548 //
549 // A MultiBranchData is used to access profiling information for
550 // a multi-way branch (*switch bytecodes). It consists of a series
551 // of (count, displacement) pairs, which count the number of times each
552 // case was taken and specify the data displacment for each branch target.
553
554 int MultiBranchData::compute_cell_count(BytecodeStream* stream) {
555 int cell_count = 0;
556 if (stream->code() == Bytecodes::_tableswitch) {
557 Bytecode_tableswitch sw(stream->method()(), stream->bcp());
558 cell_count = 1 + per_case_cell_count * (1 + sw.length()); // 1 for default
559 } else {
560 Bytecode_lookupswitch sw(stream->method()(), stream->bcp());
561 cell_count = 1 + per_case_cell_count * (sw.number_of_pairs() + 1); // 1 for default
562 }
563 return cell_count;
564 }
590 } else {
591 Bytecode_lookupswitch sw(stream->method()(), stream->bcp());
592 int npairs = sw.number_of_pairs();
593 assert(array_len() == per_case_cell_count * (npairs + 1), "wrong len");
594 for (int count = 0; count < npairs; count++) {
595 LookupswitchPair pair = sw.pair_at(count);
596 target = pair.offset() + bci();
597 my_di = mdo->dp_to_di(dp());
598 target_di = mdo->bci_to_di(target);
599 offset = target_di - my_di;
600 set_displacement_at(count, offset);
601 }
602 target = sw.default_offset() + bci();
603 my_di = mdo->dp_to_di(dp());
604 target_di = mdo->bci_to_di(target);
605 offset = target_di - my_di;
606 set_default_displacement(offset);
607 }
608 }
609
610 #ifndef PRODUCT
611 void MultiBranchData::print_data_on(outputStream* st, const char* extra) const {
612 print_shared(st, "MultiBranchData", extra);
613 st->print_cr("default_count(%u) displacement(%d)",
614 default_count(), default_displacement());
615 int cases = number_of_cases();
616 for (int i = 0; i < cases; i++) {
617 tab(st);
618 st->print_cr("count(%u) displacement(%d)",
619 count_at(i), displacement_at(i));
620 }
621 }
622 #endif
623
624 #ifndef PRODUCT
625 void ArgInfoData::print_data_on(outputStream* st, const char* extra) const {
626 print_shared(st, "ArgInfoData", extra);
627 int nargs = number_of_args();
628 for (int i = 0; i < nargs; i++) {
629 st->print(" 0x%x", arg_modified(i));
630 }
631 st->cr();
632 }
633
634 #endif
635
636 int ParametersTypeData::compute_cell_count(Method* m) {
637 if (!MethodData::profile_parameters_for_method(m)) {
638 return 0;
639 }
640 int max = TypeProfileParmsLimit == -1 ? INT_MAX : TypeProfileParmsLimit;
641 int obj_args = TypeStackSlotEntries::compute_cell_count(m->signature(), !m->is_static(), max);
642 if (obj_args > 0) {
643 return obj_args + 1; // 1 cell for array len
644 }
645 return 0;
646 }
647
648 void ParametersTypeData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
649 _parameters.post_initialize(mdo->method()->signature(), !mdo->method()->is_static(), true);
650 }
651
652 bool ParametersTypeData::profiling_enabled() {
653 return MethodData::profile_parameters();
654 }
655
656 #ifndef PRODUCT
657 void ParametersTypeData::print_data_on(outputStream* st, const char* extra) const {
658 st->print("parameter types", extra);
659 _parameters.print_data_on(st);
660 }
661
662 void SpeculativeTrapData::print_data_on(outputStream* st, const char* extra) const {
663 print_shared(st, "SpeculativeTrapData", extra);
664 tab(st);
665 method()->print_short_name(st);
666 st->cr();
667 }
668 #endif
669
670 // ==================================================================
671 // MethodData*
672 //
673 // A MethodData* holds information which has been collected about
674 // a method.
675
676 MethodData* MethodData::allocate(ClassLoaderData* loader_data, methodHandle method, TRAPS) {
677 int size = MethodData::compute_allocation_size_in_words(method);
678
679 return new (loader_data, size, false, MetaspaceObj::MethodDataType, THREAD)
680 MethodData(method(), size, CHECK_NULL);
681 }
682
683 int MethodData::bytecode_cell_count(Bytecodes::Code code) {
684 #if defined(COMPILER1) && !defined(COMPILER2)
685 return no_profile_data;
686 #else
687 switch (code) {
688 case Bytecodes::_checkcast:
1324 SpeculativeTrapData* data = new SpeculativeTrapData(dp);
1325 data->set_method(m);
1326 return data;
1327 }
1328 }
1329 return NULL;
1330 }
1331
1332 ArgInfoData *MethodData::arg_info() {
1333 DataLayout* dp = extra_data_base();
1334 DataLayout* end = extra_data_limit();
1335 for (; dp < end; dp = next_extra(dp)) {
1336 if (dp->tag() == DataLayout::arg_info_data_tag)
1337 return new ArgInfoData(dp);
1338 }
1339 return NULL;
1340 }
1341
1342 // Printing
1343
1344 #ifndef PRODUCT
1345
1346 void MethodData::print_on(outputStream* st) const {
1347 assert(is_methodData(), "should be method data");
1348 st->print("method data for ");
1349 method()->print_value_on(st);
1350 st->cr();
1351 print_data_on(st);
1352 }
1353
1354 #endif //PRODUCT
1355
1356 void MethodData::print_value_on(outputStream* st) const {
1357 assert(is_methodData(), "should be method data");
1358 st->print("method data for ");
1359 method()->print_value_on(st);
1360 }
1361
1362 #ifndef PRODUCT
1363 void MethodData::print_data_on(outputStream* st) const {
1364 ResourceMark rm;
1365 ProfileData* data = first_data();
1366 if (_parameters_type_data_di != -1) {
1367 parameters_type_data()->print_data_on(st);
1368 }
1369 for ( ; is_valid(data); data = next_data(data)) {
1370 st->print("%d", dp_to_di(data->dp()));
1371 st->fill_to(6);
1372 data->print_data_on(st, this);
1373 }
1374 st->print_cr("--- Extra data:");
1375 DataLayout* dp = extra_data_base();
1376 DataLayout* end = extra_data_limit();
1377 for (;; dp = next_extra(dp)) {
1378 assert(dp < end, "moved past end of extra data");
1379 // No need for "OrderAccess::load_acquire" ops,
1380 // since the data structure is monotonic.
1381 switch(dp->tag()) {
1382 case DataLayout::no_tag:
1383 continue;
1384 case DataLayout::bit_data_tag:
1385 data = new BitData(dp);
1386 break;
1387 case DataLayout::speculative_trap_data_tag:
1388 data = new SpeculativeTrapData(dp);
1389 break;
1390 case DataLayout::arg_info_data_tag:
1391 data = new ArgInfoData(dp);
1392 dp = end; // ArgInfoData is at the end of extra data section.
1393 break;
1394 default:
1395 fatal(err_msg("unexpected tag %d", dp->tag()));
1396 }
1397 st->print("%d", dp_to_di(data->dp()));
1398 st->fill_to(6);
1399 data->print_data_on(st);
1400 if (dp >= end) return;
1401 }
1402 }
1403 #endif
1404
1405 #if INCLUDE_SERVICES
1406 // Size Statistics
1407 void MethodData::collect_statistics(KlassSizeStats *sz) const {
1408 int n = sz->count(this);
1409 sz->_method_data_bytes += n;
1410 sz->_method_all_bytes += n;
1411 sz->_rw_bytes += n;
1412 }
1413 #endif // INCLUDE_SERVICES
1414
1415 // Verification
1416
1417 void MethodData::verify_on(outputStream* st) {
1418 guarantee(is_methodData(), "object must be method data");
1419 // guarantee(m->is_perm(), "should be in permspace");
1420 this->verify_data_on(st);
1421 }
1422
1423 void MethodData::verify_data_on(outputStream* st) {
|
97 ss.print("(%s) ", Deoptimization::format_trap_state(buf, sizeof(buf), trap));
98 }
99 break;
100 case DataLayout::bit_data_tag:
101 break;
102 case DataLayout::no_tag:
103 case DataLayout::arg_info_data_tag:
104 return ss.as_string();
105 break;
106 default:
107 fatal(err_msg("unexpected tag %d", dp->tag()));
108 }
109 }
110 return NULL;
111 }
112
113 void ProfileData::print_data_on(outputStream* st, const MethodData* md) const {
114 print_data_on(st, print_data_on_helper(md));
115 }
116
117 void ProfileData::print_shared(outputStream* st, const char* name, const char* extra) const {
118 st->print("bci: %d", bci());
119 st->fill_to(tab_width_one);
120 st->print("%s", name);
121 tab(st);
122 int trap = trap_state();
123 if (trap != 0) {
124 char buf[100];
125 st->print("trap(%s) ", Deoptimization::format_trap_state(buf, sizeof(buf), trap));
126 }
127 if (extra != NULL) {
128 st->print(extra);
129 }
130 int flags = data()->flags();
131 if (flags != 0) {
132 st->print("flags(%d) ", flags);
133 }
134 }
135
136 void ProfileData::tab(outputStream* st, bool first) const {
137 st->fill_to(first ? tab_width_one : tab_width_two);
138 }
139
140 // ==================================================================
141 // BitData
142 //
143 // A BitData corresponds to a one-bit flag. This is used to indicate
144 // whether a checkcast bytecode has seen a null value.
145
146
147 void BitData::print_data_on(outputStream* st, const char* extra) const {
148 print_shared(st, "BitData", extra);
149 }
150
151 // ==================================================================
152 // CounterData
153 //
154 // A CounterData corresponds to a simple counter.
155
156 void CounterData::print_data_on(outputStream* st, const char* extra) const {
157 print_shared(st, "CounterData", extra);
158 st->print_cr("count(%u)", count());
159 }
160
161 // ==================================================================
162 // JumpData
163 //
164 // A JumpData is used to access profiling information for a direct
165 // branch. It is a counter, used for counting the number of branches,
166 // plus a data displacement, used for realigning the data pointer to
167 // the corresponding target bci.
168
169 void JumpData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
170 assert(stream->bci() == bci(), "wrong pos");
171 int target;
172 Bytecodes::Code c = stream->code();
173 if (c == Bytecodes::_goto_w || c == Bytecodes::_jsr_w) {
174 target = stream->dest_w();
175 } else {
176 target = stream->dest();
177 }
178 int my_di = mdo->dp_to_di(dp());
179 int target_di = mdo->bci_to_di(target);
180 int offset = target_di - my_di;
181 set_displacement(offset);
182 }
183
184 void JumpData::print_data_on(outputStream* st, const char* extra) const {
185 print_shared(st, "JumpData", extra);
186 st->print_cr("taken(%u) displacement(%d)", taken(), displacement());
187 }
188
189 int TypeStackSlotEntries::compute_cell_count(Symbol* signature, bool include_receiver, int max) {
190 // Parameter profiling include the receiver
191 int args_count = include_receiver ? 1 : 0;
192 ResourceMark rm;
193 SignatureStream ss(signature);
194 args_count += ss.reference_parameter_count();
195 args_count = MIN2(args_count, max);
196 return args_count * per_arg_cell_count;
197 }
198
199 int TypeEntriesAtCall::compute_cell_count(BytecodeStream* stream) {
200 assert(Bytecodes::is_invoke(stream->code()), "should be invoke");
201 assert(TypeStackSlotEntries::per_arg_count() > ReturnTypeEntry::static_cell_count(), "code to test for arguments/results broken");
202 Bytecode_invoke inv(stream->method(), stream->bci());
203 int args_cell = 0;
204 if (arguments_profiling_enabled()) {
205 args_cell = TypeStackSlotEntries::compute_cell_count(inv.signature(), false, TypeProfileArgsLimit);
206 }
207 int ret_cell = 0;
316 set_type(i, with_status((Klass*)NULL, p));
317 }
318 }
319 }
320
321 void ReturnTypeEntry::clean_weak_klass_links(BoolObjectClosure* is_alive_cl) {
322 intptr_t p = type();
323 if (!is_loader_alive(is_alive_cl, p)) {
324 set_type(with_status((Klass*)NULL, p));
325 }
326 }
327
328 bool TypeEntriesAtCall::return_profiling_enabled() {
329 return MethodData::profile_return();
330 }
331
332 bool TypeEntriesAtCall::arguments_profiling_enabled() {
333 return MethodData::profile_arguments();
334 }
335
336 void TypeEntries::print_klass(outputStream* st, intptr_t k) {
337 if (is_type_none(k)) {
338 st->print("none");
339 } else if (is_type_unknown(k)) {
340 st->print("unknown");
341 } else {
342 valid_klass(k)->print_value_on(st);
343 }
344 if (was_null_seen(k)) {
345 st->print(" (null seen)");
346 }
347 }
348
349 void TypeStackSlotEntries::print_data_on(outputStream* st) const {
350 for (int i = 0; i < _number_of_entries; i++) {
351 _pd->tab(st);
352 st->print("%d: stack(%u) ", i, stack_slot(i));
353 print_klass(st, type(i));
354 st->cr();
355 }
371 if (has_return()) {
372 tab(st, true);
373 st->print("return type");
374 _ret.print_data_on(st);
375 }
376 }
377
378 void VirtualCallTypeData::print_data_on(outputStream* st, const char* extra) const {
379 VirtualCallData::print_data_on(st, extra);
380 if (has_arguments()) {
381 tab(st, true);
382 st->print("argument types");
383 _args.print_data_on(st);
384 }
385 if (has_return()) {
386 tab(st, true);
387 st->print("return type");
388 _ret.print_data_on(st);
389 }
390 }
391
392 // ==================================================================
393 // ReceiverTypeData
394 //
395 // A ReceiverTypeData is used to access profiling information about a
396 // dynamic type check. It consists of a counter which counts the total times
397 // that the check is reached, and a series of (Klass*, count) pairs
398 // which are used to store a type profile for the receiver of the check.
399
400 void ReceiverTypeData::clean_weak_klass_links(BoolObjectClosure* is_alive_cl) {
401 for (uint row = 0; row < row_limit(); row++) {
402 Klass* p = receiver(row);
403 if (p != NULL && !p->is_loader_alive(is_alive_cl)) {
404 clear_row(row);
405 }
406 }
407 }
408
409 void ReceiverTypeData::print_receiver_data_on(outputStream* st) const {
410 uint row;
411 int entries = 0;
412 for (row = 0; row < row_limit(); row++) {
413 if (receiver(row) != NULL) entries++;
414 }
415 st->print_cr("count(%u) entries(%u)", count(), entries);
416 int total = count();
417 for (row = 0; row < row_limit(); row++) {
418 if (receiver(row) != NULL) {
419 total += receiver_count(row);
420 }
421 }
422 for (row = 0; row < row_limit(); row++) {
423 if (receiver(row) != NULL) {
424 tab(st);
425 receiver(row)->print_value_on(st);
426 st->print_cr("(%u %4.2f)", receiver_count(row), (float) receiver_count(row) / (float) total);
427 }
428 }
429 }
430 void ReceiverTypeData::print_data_on(outputStream* st, const char* extra) const {
431 print_shared(st, "ReceiverTypeData", extra);
432 print_receiver_data_on(st);
433 }
434 void VirtualCallData::print_data_on(outputStream* st, const char* extra) const {
435 print_shared(st, "VirtualCallData", extra);
436 print_receiver_data_on(st);
437 }
438
439 // ==================================================================
440 // RetData
441 //
442 // A RetData is used to access profiling information for a ret bytecode.
443 // It is composed of a count of the number of times that the ret has
444 // been executed, followed by a series of triples of the form
445 // (bci, count, di) which count the number of times that some bci was the
446 // target of the ret and cache a corresponding displacement.
447
448 void RetData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
449 for (uint row = 0; row < row_limit(); row++) {
450 set_bci_displacement(row, -1);
451 set_bci(row, no_bci);
452 }
453 // release so other threads see a consistent state. bci is used as
454 // a valid flag for bci_displacement.
455 OrderAccess::release();
456 }
457
469 // Now check to see if any of the cache slots are open.
470 for (uint row = 0; row < row_limit(); row++) {
471 if (bci(row) == no_bci) {
472 set_bci_displacement(row, mdp - dp());
473 set_bci_count(row, DataLayout::counter_increment);
474 // Barrier to ensure displacement is written before the bci; allows
475 // the interpreter to read displacement without fear of race condition.
476 release_set_bci(row, return_bci);
477 break;
478 }
479 }
480 return mdp;
481 }
482
483 #ifdef CC_INTERP
484 DataLayout* RetData::advance(MethodData *md, int bci) {
485 return (DataLayout*) md->bci_to_dp(bci);
486 }
487 #endif // CC_INTERP
488
489 void RetData::print_data_on(outputStream* st, const char* extra) const {
490 print_shared(st, "RetData", extra);
491 uint row;
492 int entries = 0;
493 for (row = 0; row < row_limit(); row++) {
494 if (bci(row) != no_bci) entries++;
495 }
496 st->print_cr("count(%u) entries(%u)", count(), entries);
497 for (row = 0; row < row_limit(); row++) {
498 if (bci(row) != no_bci) {
499 tab(st);
500 st->print_cr("bci(%d: count(%u) displacement(%d))",
501 bci(row), bci_count(row), bci_displacement(row));
502 }
503 }
504 }
505
506 // ==================================================================
507 // BranchData
508 //
509 // A BranchData is used to access profiling data for a two-way branch.
510 // It consists of taken and not_taken counts as well as a data displacement
511 // for the taken case.
512
513 void BranchData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
514 assert(stream->bci() == bci(), "wrong pos");
515 int target = stream->dest();
516 int my_di = mdo->dp_to_di(dp());
517 int target_di = mdo->bci_to_di(target);
518 int offset = target_di - my_di;
519 set_displacement(offset);
520 }
521
522 void BranchData::print_data_on(outputStream* st, const char* extra) const {
523 print_shared(st, "BranchData", extra);
524 st->print_cr("taken(%u) displacement(%d)",
525 taken(), displacement());
526 tab(st);
527 st->print_cr("not taken(%u)", not_taken());
528 }
529
530 // ==================================================================
531 // MultiBranchData
532 //
533 // A MultiBranchData is used to access profiling information for
534 // a multi-way branch (*switch bytecodes). It consists of a series
535 // of (count, displacement) pairs, which count the number of times each
536 // case was taken and specify the data displacment for each branch target.
537
538 int MultiBranchData::compute_cell_count(BytecodeStream* stream) {
539 int cell_count = 0;
540 if (stream->code() == Bytecodes::_tableswitch) {
541 Bytecode_tableswitch sw(stream->method()(), stream->bcp());
542 cell_count = 1 + per_case_cell_count * (1 + sw.length()); // 1 for default
543 } else {
544 Bytecode_lookupswitch sw(stream->method()(), stream->bcp());
545 cell_count = 1 + per_case_cell_count * (sw.number_of_pairs() + 1); // 1 for default
546 }
547 return cell_count;
548 }
574 } else {
575 Bytecode_lookupswitch sw(stream->method()(), stream->bcp());
576 int npairs = sw.number_of_pairs();
577 assert(array_len() == per_case_cell_count * (npairs + 1), "wrong len");
578 for (int count = 0; count < npairs; count++) {
579 LookupswitchPair pair = sw.pair_at(count);
580 target = pair.offset() + bci();
581 my_di = mdo->dp_to_di(dp());
582 target_di = mdo->bci_to_di(target);
583 offset = target_di - my_di;
584 set_displacement_at(count, offset);
585 }
586 target = sw.default_offset() + bci();
587 my_di = mdo->dp_to_di(dp());
588 target_di = mdo->bci_to_di(target);
589 offset = target_di - my_di;
590 set_default_displacement(offset);
591 }
592 }
593
594 void MultiBranchData::print_data_on(outputStream* st, const char* extra) const {
595 print_shared(st, "MultiBranchData", extra);
596 st->print_cr("default_count(%u) displacement(%d)",
597 default_count(), default_displacement());
598 int cases = number_of_cases();
599 for (int i = 0; i < cases; i++) {
600 tab(st);
601 st->print_cr("count(%u) displacement(%d)",
602 count_at(i), displacement_at(i));
603 }
604 }
605
606 void ArgInfoData::print_data_on(outputStream* st, const char* extra) const {
607 print_shared(st, "ArgInfoData", extra);
608 int nargs = number_of_args();
609 for (int i = 0; i < nargs; i++) {
610 st->print(" 0x%x", arg_modified(i));
611 }
612 st->cr();
613 }
614
615 int ParametersTypeData::compute_cell_count(Method* m) {
616 if (!MethodData::profile_parameters_for_method(m)) {
617 return 0;
618 }
619 int max = TypeProfileParmsLimit == -1 ? INT_MAX : TypeProfileParmsLimit;
620 int obj_args = TypeStackSlotEntries::compute_cell_count(m->signature(), !m->is_static(), max);
621 if (obj_args > 0) {
622 return obj_args + 1; // 1 cell for array len
623 }
624 return 0;
625 }
626
627 void ParametersTypeData::post_initialize(BytecodeStream* stream, MethodData* mdo) {
628 _parameters.post_initialize(mdo->method()->signature(), !mdo->method()->is_static(), true);
629 }
630
631 bool ParametersTypeData::profiling_enabled() {
632 return MethodData::profile_parameters();
633 }
634
635 void ParametersTypeData::print_data_on(outputStream* st, const char* extra) const {
636 st->print("parameter types", extra);
637 _parameters.print_data_on(st);
638 }
639
640 void SpeculativeTrapData::print_data_on(outputStream* st, const char* extra) const {
641 print_shared(st, "SpeculativeTrapData", extra);
642 tab(st);
643 method()->print_short_name(st);
644 st->cr();
645 }
646
647 // ==================================================================
648 // MethodData*
649 //
650 // A MethodData* holds information which has been collected about
651 // a method.
652
653 MethodData* MethodData::allocate(ClassLoaderData* loader_data, methodHandle method, TRAPS) {
654 int size = MethodData::compute_allocation_size_in_words(method);
655
656 return new (loader_data, size, false, MetaspaceObj::MethodDataType, THREAD)
657 MethodData(method(), size, CHECK_NULL);
658 }
659
660 int MethodData::bytecode_cell_count(Bytecodes::Code code) {
661 #if defined(COMPILER1) && !defined(COMPILER2)
662 return no_profile_data;
663 #else
664 switch (code) {
665 case Bytecodes::_checkcast:
1301 SpeculativeTrapData* data = new SpeculativeTrapData(dp);
1302 data->set_method(m);
1303 return data;
1304 }
1305 }
1306 return NULL;
1307 }
1308
1309 ArgInfoData *MethodData::arg_info() {
1310 DataLayout* dp = extra_data_base();
1311 DataLayout* end = extra_data_limit();
1312 for (; dp < end; dp = next_extra(dp)) {
1313 if (dp->tag() == DataLayout::arg_info_data_tag)
1314 return new ArgInfoData(dp);
1315 }
1316 return NULL;
1317 }
1318
1319 // Printing
1320
1321 void MethodData::print_on(outputStream* st) const {
1322 assert(is_methodData(), "should be method data");
1323 st->print("method data for ");
1324 method()->print_value_on(st);
1325 st->cr();
1326 print_data_on(st);
1327 }
1328
1329 void MethodData::print_value_on(outputStream* st) const {
1330 assert(is_methodData(), "should be method data");
1331 st->print("method data for ");
1332 method()->print_value_on(st);
1333 }
1334
1335 void MethodData::print_data_on(outputStream* st) const {
1336 ResourceMark rm;
1337 ProfileData* data = first_data();
1338 if (_parameters_type_data_di != -1) {
1339 parameters_type_data()->print_data_on(st);
1340 }
1341 for ( ; is_valid(data); data = next_data(data)) {
1342 st->print("%d", dp_to_di(data->dp()));
1343 st->fill_to(6);
1344 data->print_data_on(st, this);
1345 }
1346 st->print_cr("--- Extra data:");
1347 DataLayout* dp = extra_data_base();
1348 DataLayout* end = extra_data_limit();
1349 for (;; dp = next_extra(dp)) {
1350 assert(dp < end, "moved past end of extra data");
1351 // No need for "OrderAccess::load_acquire" ops,
1352 // since the data structure is monotonic.
1353 switch(dp->tag()) {
1354 case DataLayout::no_tag:
1355 continue;
1356 case DataLayout::bit_data_tag:
1357 data = new BitData(dp);
1358 break;
1359 case DataLayout::speculative_trap_data_tag:
1360 data = new SpeculativeTrapData(dp);
1361 break;
1362 case DataLayout::arg_info_data_tag:
1363 data = new ArgInfoData(dp);
1364 dp = end; // ArgInfoData is at the end of extra data section.
1365 break;
1366 default:
1367 fatal(err_msg("unexpected tag %d", dp->tag()));
1368 }
1369 st->print("%d", dp_to_di(data->dp()));
1370 st->fill_to(6);
1371 data->print_data_on(st);
1372 if (dp >= end) return;
1373 }
1374 }
1375
1376 #if INCLUDE_SERVICES
1377 // Size Statistics
1378 void MethodData::collect_statistics(KlassSizeStats *sz) const {
1379 int n = sz->count(this);
1380 sz->_method_data_bytes += n;
1381 sz->_method_all_bytes += n;
1382 sz->_rw_bytes += n;
1383 }
1384 #endif // INCLUDE_SERVICES
1385
1386 // Verification
1387
1388 void MethodData::verify_on(outputStream* st) {
1389 guarantee(is_methodData(), "object must be method data");
1390 // guarantee(m->is_perm(), "should be in permspace");
1391 this->verify_data_on(st);
1392 }
1393
1394 void MethodData::verify_data_on(outputStream* st) {
|