src/share/vm/services/memoryManager.cpp
Print this page
*** 188,233 ****
}
GCMemoryManager::GCMemoryManager() : MemoryManager() {
_num_collections = 0;
_last_gc_stat = NULL;
_num_gc_threads = 1;
}
GCMemoryManager::~GCMemoryManager() {
delete _last_gc_stat;
}
void GCMemoryManager::initialize_gc_stat_info() {
assert(MemoryService::num_memory_pools() > 0, "should have one or more memory pools");
_last_gc_stat = new GCStatInfo(MemoryService::num_memory_pools());
}
! void GCMemoryManager::gc_begin() {
! assert(_last_gc_stat != NULL, "Just checking");
_accumulated_timer.start();
! _num_collections++;
! _last_gc_stat->set_index(_num_collections);
! _last_gc_stat->set_start_time(Management::timestamp());
// Keep memory usage of all memory pools
for (int i = 0; i < MemoryService::num_memory_pools(); i++) {
MemoryPool* pool = MemoryService::get_memory_pool(i);
MemoryUsage usage = pool->get_memory_usage();
! _last_gc_stat->set_before_gc_usage(i, usage);
HS_DTRACE_PROBE8(hotspot, mem__pool__gc__begin,
name(), strlen(name()),
pool->name(), strlen(pool->name()),
usage.init_size(), usage.used(),
usage.committed(), usage.max_size());
}
}
! void GCMemoryManager::gc_end() {
_accumulated_timer.stop();
! _last_gc_stat->set_end_time(Management::timestamp());
int i;
// keep the last gc statistics for all memory pools
for (i = 0; i < MemoryService::num_memory_pools(); i++) {
MemoryPool* pool = MemoryService::get_memory_pool(i);
MemoryUsage usage = pool->get_memory_usage();
--- 188,255 ----
}
GCMemoryManager::GCMemoryManager() : MemoryManager() {
_num_collections = 0;
_last_gc_stat = NULL;
+ _current_gc_stat = NULL;
_num_gc_threads = 1;
}
GCMemoryManager::~GCMemoryManager() {
delete _last_gc_stat;
+ delete _current_gc_stat;
}
void GCMemoryManager::initialize_gc_stat_info() {
assert(MemoryService::num_memory_pools() > 0, "should have one or more memory pools");
_last_gc_stat = new GCStatInfo(MemoryService::num_memory_pools());
+ _current_gc_stat = new GCStatInfo(MemoryService::num_memory_pools());
+ // tracking concurrent collections requires two objects: one to update, and one to
+ // be the publicly available "last (completed) gc".
}
! void GCMemoryManager::gc_begin(bool recordGCBeginTime, bool recordPreGCUsage,
! bool recordAccumulatedGCTime) {
! assert(_last_gc_stat != NULL && _current_gc_stat != NULL, "Just checking");
! if (recordAccumulatedGCTime) {
_accumulated_timer.start();
! }
! // _num_collections now increases in gc_end, to count completed collections
! if (recordGCBeginTime) {
! _current_gc_stat->set_index(_num_collections+1);
! _current_gc_stat->set_start_time(Management::timestamp());
! }
+ if (recordPreGCUsage) {
// Keep memory usage of all memory pools
for (int i = 0; i < MemoryService::num_memory_pools(); i++) {
MemoryPool* pool = MemoryService::get_memory_pool(i);
MemoryUsage usage = pool->get_memory_usage();
! _current_gc_stat->set_before_gc_usage(i, usage);
HS_DTRACE_PROBE8(hotspot, mem__pool__gc__begin,
name(), strlen(name()),
pool->name(), strlen(pool->name()),
usage.init_size(), usage.used(),
usage.committed(), usage.max_size());
}
+ }
}
! // A collector MUST, even if it does not complete for some reason,
! // make a TraceMemoryManagerStats object where countCollection is true,
! // to ensure the current gc stat is placed in _last_gc_stat.
! void GCMemoryManager::gc_end(bool recordPostGCUsage,
! bool recordAccumulatedGCTime,
! bool recordGCEndTime, bool countCollection) {
! if (recordAccumulatedGCTime) {
_accumulated_timer.stop();
! }
! if (recordGCEndTime) {
! _current_gc_stat->set_end_time(Management::timestamp());
! }
+ if (recordPostGCUsage) {
int i;
// keep the last gc statistics for all memory pools
for (i = 0; i < MemoryService::num_memory_pools(); i++) {
MemoryPool* pool = MemoryService::get_memory_pool(i);
MemoryUsage usage = pool->get_memory_usage();
*** 236,246 ****
name(), strlen(name()),
pool->name(), strlen(pool->name()),
usage.init_size(), usage.used(),
usage.committed(), usage.max_size());
! _last_gc_stat->set_after_gc_usage(i, usage);
}
// Set last collection usage of the memory pools managed by this collector
for (i = 0; i < num_memory_pools(); i++) {
MemoryPool* pool = get_memory_pool(i);
--- 258,268 ----
name(), strlen(name()),
pool->name(), strlen(pool->name()),
usage.init_size(), usage.used(),
usage.committed(), usage.max_size());
! _current_gc_stat->set_after_gc_usage(i, usage);
}
// Set last collection usage of the memory pools managed by this collector
for (i = 0; i < num_memory_pools(); i++) {
MemoryPool* pool = get_memory_pool(i);
*** 248,253 ****
--- 270,294 ----
// Compare with GC usage threshold
pool->set_last_collection_usage(usage);
LowMemoryDetector::detect_after_gc_memory(pool);
}
+ }
+ if (countCollection) {
+ _num_collections++;
+ // alternately update two objects making one public when complete
+ GCStatInfo *tmp = _last_gc_stat;
+ _last_gc_stat = _current_gc_stat;
+ _current_gc_stat = tmp;
+ #ifdef ASSERT
+ // reset the current stat for diagnosability purposes
+ _current_gc_stat->set_index(0);
+ _current_gc_stat->set_start_time(0);
+ _current_gc_stat->set_end_time(0);
+ for (int i = 0; i < MemoryService::num_memory_pools(); i++) {
+ MemoryUsage empty_usage = MemoryUsage();
+ _current_gc_stat->set_before_gc_usage(i, empty_usage);
+ _current_gc_stat->set_after_gc_usage(i, empty_usage);
+ }
+ #endif
+ }
}