19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 #include "precompiled.hpp"
26 #include "gc/shared/collectedHeap.hpp"
27 #include "gc/shared/collectedHeap.inline.hpp"
28 #include "gc/shared/genCollectedHeap.hpp"
29 #include "memory/resourceArea.hpp"
30 #include "runtime/atomic.inline.hpp"
31 #include "runtime/init.hpp"
32 #include "runtime/interfaceSupport.hpp"
33 #include "runtime/orderAccess.inline.hpp"
34 #include "runtime/os.inline.hpp"
35 #include "runtime/threadLocalStorage.hpp"
36 #include "runtime/vframe.hpp"
37 #include "utilities/preserveException.hpp"
38
39 PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
40
41 // Implementation of InterfaceSupport
42
43 #ifdef ASSERT
44
45 long InterfaceSupport::_number_of_calls = 0;
46 long InterfaceSupport::_scavenge_alot_counter = 1;
47 long InterfaceSupport::_fullgc_alot_counter = 1;
48 long InterfaceSupport::_fullgc_alot_invocation = 0;
49
50 Histogram* RuntimeHistogram;
51
52 RuntimeHistogramElement::RuntimeHistogramElement(const char* elementName) {
53 static volatile jint RuntimeHistogram_lock = 0;
54 _name = elementName;
55 uintx count = 0;
56
57 while (Atomic::cmpxchg(1, &RuntimeHistogram_lock, 0) != 0) {
58 while (OrderAccess::load_acquire(&RuntimeHistogram_lock) != 0) {
59 count +=1;
60 if ( (WarnOnStalledSpinLock > 0)
61 && (count % WarnOnStalledSpinLock == 0)) {
62 warning("RuntimeHistogram_lock seems to be stalled");
63 }
64 }
65 }
66
67 if (RuntimeHistogram == NULL) {
68 RuntimeHistogram = new Histogram("VM Runtime Call Counts",200);
69 }
70
71 RuntimeHistogram->add_element(this);
72 Atomic::dec(&RuntimeHistogram_lock);
73 }
74
75 void InterfaceSupport::trace(const char* result_type, const char* header) {
76 tty->print_cr("%6d %s", _number_of_calls, header);
77 }
78
79 void InterfaceSupport::gc_alot() {
80 Thread *thread = Thread::current();
81 if (!thread->is_Java_thread()) return; // Avoid concurrent calls
82 // Check for new, not quite initialized thread. A thread in new mode cannot initiate a GC.
83 JavaThread *current_thread = (JavaThread *)thread;
84 if (current_thread->active_handles() == NULL) return;
85
86 // Short-circuit any possible re-entrant gc-a-lot attempt
87 if (thread->skip_gcalot()) return;
88
89 if (Threads::is_vm_complete()) {
90
91 if (++_fullgc_alot_invocation < FullGCALotStart) {
92 return;
93 }
94
95 // Use this line if you want to block at a specific point,
96 // e.g. one number_of_calls/scavenge/gc before you got into problems
97 if (FullGCALot) _fullgc_alot_counter--;
98
99 // Check if we should force a full gc
100 if (_fullgc_alot_counter == 0) {
101 // Release dummy so objects are forced to move
102 if (!Universe::release_fullgc_alot_dummy()) {
103 warning("FullGCALot: Unable to release more dummies at bottom of heap");
104 }
105 HandleMark hm(thread);
106 Universe::heap()->collect(GCCause::_full_gc_alot);
107 unsigned int invocations = Universe::heap()->total_full_collections();
108 // Compute new interval
109 if (FullGCALotInterval > 1) {
110 _fullgc_alot_counter = 1+(long)((double)FullGCALotInterval*os::random()/(max_jint+1.0));
111 if (PrintGCDetails && Verbose) {
112 tty->print_cr("Full gc no: %u\tInterval: %d", invocations,
113 _fullgc_alot_counter);
114 }
115 } else {
116 _fullgc_alot_counter = 1;
117 }
118 // Print progress message
119 if (invocations % 100 == 0) {
120 if (PrintGCDetails && Verbose) tty->print_cr("Full gc no: %u", invocations);
121 }
122 } else {
123 if (ScavengeALot) _scavenge_alot_counter--;
124 // Check if we should force a scavenge
125 if (_scavenge_alot_counter == 0) {
126 HandleMark hm(thread);
127 Universe::heap()->collect(GCCause::_scavenge_alot);
128 unsigned int invocations = Universe::heap()->total_collections() - Universe::heap()->total_full_collections();
129 // Compute new interval
130 if (ScavengeALotInterval > 1) {
131 _scavenge_alot_counter = 1+(long)((double)ScavengeALotInterval*os::random()/(max_jint+1.0));
132 if (PrintGCDetails && Verbose) {
133 tty->print_cr("Scavenge no: %u\tInterval: %d", invocations,
134 _scavenge_alot_counter);
135 }
136 } else {
137 _scavenge_alot_counter = 1;
138 }
139 // Print progress message
140 if (invocations % 1000 == 0) {
141 if (PrintGCDetails && Verbose) tty->print_cr("Scavenge no: %u", invocations);
142 }
143 }
144 }
145 }
146 }
147
148
149 vframe* vframe_array[50];
150 int walk_stack_counter = 0;
151
152 void InterfaceSupport::walk_stack_from(vframe* start_vf) {
153 // walk
154 int i = 0;
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 #include "precompiled.hpp"
26 #include "gc/shared/collectedHeap.hpp"
27 #include "gc/shared/collectedHeap.inline.hpp"
28 #include "gc/shared/genCollectedHeap.hpp"
29 #include "memory/resourceArea.hpp"
30 #include "runtime/atomic.inline.hpp"
31 #include "runtime/init.hpp"
32 #include "runtime/interfaceSupport.hpp"
33 #include "runtime/orderAccess.inline.hpp"
34 #include "runtime/os.inline.hpp"
35 #include "runtime/threadLocalStorage.hpp"
36 #include "runtime/vframe.hpp"
37 #include "utilities/preserveException.hpp"
38
39 // Implementation of InterfaceSupport
40
41 #ifdef ASSERT
42
43 long InterfaceSupport::_number_of_calls = 0;
44 long InterfaceSupport::_scavenge_alot_counter = 1;
45 long InterfaceSupport::_fullgc_alot_counter = 1;
46 long InterfaceSupport::_fullgc_alot_invocation = 0;
47
48 Histogram* RuntimeHistogram;
49
50 RuntimeHistogramElement::RuntimeHistogramElement(const char* elementName) {
51 static volatile jint RuntimeHistogram_lock = 0;
52 _name = elementName;
53 uintx count = 0;
54
55 while (Atomic::cmpxchg(1, &RuntimeHistogram_lock, 0) != 0) {
56 while (OrderAccess::load_acquire(&RuntimeHistogram_lock) != 0) {
57 count +=1;
58 if ( (WarnOnStalledSpinLock > 0)
59 && (count % WarnOnStalledSpinLock == 0)) {
60 warning("RuntimeHistogram_lock seems to be stalled");
61 }
62 }
63 }
64
65 if (RuntimeHistogram == NULL) {
66 RuntimeHistogram = new Histogram("VM Runtime Call Counts",200);
67 }
68
69 RuntimeHistogram->add_element(this);
70 Atomic::dec(&RuntimeHistogram_lock);
71 }
72
73 void InterfaceSupport::trace(const char* result_type, const char* header) {
74 tty->print_cr("%6ld %s", _number_of_calls, header);
75 }
76
77 void InterfaceSupport::gc_alot() {
78 Thread *thread = Thread::current();
79 if (!thread->is_Java_thread()) return; // Avoid concurrent calls
80 // Check for new, not quite initialized thread. A thread in new mode cannot initiate a GC.
81 JavaThread *current_thread = (JavaThread *)thread;
82 if (current_thread->active_handles() == NULL) return;
83
84 // Short-circuit any possible re-entrant gc-a-lot attempt
85 if (thread->skip_gcalot()) return;
86
87 if (Threads::is_vm_complete()) {
88
89 if (++_fullgc_alot_invocation < FullGCALotStart) {
90 return;
91 }
92
93 // Use this line if you want to block at a specific point,
94 // e.g. one number_of_calls/scavenge/gc before you got into problems
95 if (FullGCALot) _fullgc_alot_counter--;
96
97 // Check if we should force a full gc
98 if (_fullgc_alot_counter == 0) {
99 // Release dummy so objects are forced to move
100 if (!Universe::release_fullgc_alot_dummy()) {
101 warning("FullGCALot: Unable to release more dummies at bottom of heap");
102 }
103 HandleMark hm(thread);
104 Universe::heap()->collect(GCCause::_full_gc_alot);
105 unsigned int invocations = Universe::heap()->total_full_collections();
106 // Compute new interval
107 if (FullGCALotInterval > 1) {
108 _fullgc_alot_counter = 1+(long)((double)FullGCALotInterval*os::random()/(max_jint+1.0));
109 if (PrintGCDetails && Verbose) {
110 tty->print_cr("Full gc no: %u\tInterval: %ld", invocations, _fullgc_alot_counter);
111 }
112 } else {
113 _fullgc_alot_counter = 1;
114 }
115 // Print progress message
116 if (invocations % 100 == 0) {
117 if (PrintGCDetails && Verbose) tty->print_cr("Full gc no: %u", invocations);
118 }
119 } else {
120 if (ScavengeALot) _scavenge_alot_counter--;
121 // Check if we should force a scavenge
122 if (_scavenge_alot_counter == 0) {
123 HandleMark hm(thread);
124 Universe::heap()->collect(GCCause::_scavenge_alot);
125 unsigned int invocations = Universe::heap()->total_collections() - Universe::heap()->total_full_collections();
126 // Compute new interval
127 if (ScavengeALotInterval > 1) {
128 _scavenge_alot_counter = 1+(long)((double)ScavengeALotInterval*os::random()/(max_jint+1.0));
129 if (PrintGCDetails && Verbose) {
130 tty->print_cr("Scavenge no: %u\tInterval: %ld", invocations, _scavenge_alot_counter);
131 }
132 } else {
133 _scavenge_alot_counter = 1;
134 }
135 // Print progress message
136 if (invocations % 1000 == 0) {
137 if (PrintGCDetails && Verbose) tty->print_cr("Scavenge no: %u", invocations);
138 }
139 }
140 }
141 }
142 }
143
144
145 vframe* vframe_array[50];
146 int walk_stack_counter = 0;
147
148 void InterfaceSupport::walk_stack_from(vframe* start_vf) {
149 // walk
150 int i = 0;
|