37 _recorder_list = _recorder_list->next(); |
37 _recorder_list = _recorder_list->next(); |
38 MemTracker::release_thread_recorder(tmp); |
38 MemTracker::release_thread_recorder(tmp); |
39 } |
39 } |
40 } |
40 } |
41 |
41 |
42 MemTrackWorker::MemTrackWorker() { |
42 MemTrackWorker::MemTrackWorker(MemSnapshot* snapshot): _snapshot(snapshot) { |
43 // create thread uses cgc thread type for now. We should revisit |
43 // create thread uses cgc thread type for now. We should revisit |
44 // the option, or create new thread type. |
44 // the option, or create new thread type. |
45 _has_error = !os::create_thread(this, os::cgc_thread); |
45 _has_error = !os::create_thread(this, os::cgc_thread); |
46 set_name("MemTrackWorker", 0); |
46 set_name("MemTrackWorker", 0); |
47 |
47 |
86 |
86 |
87 void MemTrackWorker::run() { |
87 void MemTrackWorker::run() { |
88 assert(MemTracker::is_on(), "native memory tracking is off"); |
88 assert(MemTracker::is_on(), "native memory tracking is off"); |
89 this->initialize_thread_local_storage(); |
89 this->initialize_thread_local_storage(); |
90 this->record_stack_base_and_size(); |
90 this->record_stack_base_and_size(); |
91 MemSnapshot* snapshot = MemTracker::get_snapshot(); |
91 assert(_snapshot != NULL, "Worker should not be started"); |
92 assert(snapshot != NULL, "Worker should not be started"); |
|
93 MemRecorder* rec; |
92 MemRecorder* rec; |
94 unsigned long processing_generation = 0; |
93 unsigned long processing_generation = 0; |
95 bool worker_idle = false; |
94 bool worker_idle = false; |
96 |
95 |
97 while (!MemTracker::shutdown_in_progress()) { |
96 while (!MemTracker::shutdown_in_progress()) { |
107 worker_idle = false; |
106 worker_idle = false; |
108 MemTracker::set_current_processing_generation(processing_generation); |
107 MemTracker::set_current_processing_generation(processing_generation); |
109 } |
108 } |
110 |
109 |
111 // merge the recorder into staging area |
110 // merge the recorder into staging area |
112 if (!snapshot->merge(rec)) { |
111 if (!_snapshot->merge(rec)) { |
113 MemTracker::shutdown(MemTracker::NMT_out_of_memory); |
112 MemTracker::shutdown(MemTracker::NMT_out_of_memory); |
114 } else { |
113 } else { |
115 NOT_PRODUCT(_merge_count ++;) |
114 NOT_PRODUCT(_merge_count ++;) |
116 } |
115 } |
117 MemTracker::release_thread_recorder(rec); |
116 MemTracker::release_thread_recorder(rec); |
130 |
129 |
131 // done with this generation, increment _head pointer |
130 // done with this generation, increment _head pointer |
132 _head = (_head + 1) % MAX_GENERATIONS; |
131 _head = (_head + 1) % MAX_GENERATIONS; |
133 } |
132 } |
134 // promote this generation data to snapshot |
133 // promote this generation data to snapshot |
135 if (!snapshot->promote(number_of_classes)) { |
134 if (!_snapshot->promote(number_of_classes)) { |
136 // failed to promote, means out of memory |
135 // failed to promote, means out of memory |
137 MemTracker::shutdown(MemTracker::NMT_out_of_memory); |
136 MemTracker::shutdown(MemTracker::NMT_out_of_memory); |
138 } |
137 } |
139 } else { |
138 } else { |
140 // worker thread is idle |
139 // worker thread is idle |
141 worker_idle = true; |
140 worker_idle = true; |
142 MemTracker::report_worker_idle(); |
141 MemTracker::report_worker_idle(); |
143 snapshot->wait(1000); |
142 _snapshot->wait(1000); |
144 ThreadCritical tc; |
143 ThreadCritical tc; |
145 // check if more data arrived |
144 // check if more data arrived |
146 if (!_gen[_head].has_more_recorder()) { |
145 if (!_gen[_head].has_more_recorder()) { |
147 _gen[_head].add_recorders(MemTracker::get_pending_recorders()); |
146 _gen[_head].add_recorders(MemTracker::get_pending_recorders()); |
148 } |
147 } |