8230674: Heap dumps should exclude dormant CDS archived objects of unloaded classes
Reviewed-by: dholmes, jiangli
--- a/src/hotspot/share/services/heapDumper.cpp Wed Sep 11 12:32:01 2019 -0700
+++ b/src/hotspot/share/services/heapDumper.cpp Wed Sep 11 13:28:09 2019 -0700
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2005, 2018, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 2019, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -686,6 +686,16 @@
// fixes up the current dump record and writes HPROF_HEAP_DUMP_END record
static void end_of_dump(DumpWriter* writer);
+
+ static oop mask_dormant_archived_object(oop o) {
+ if (o != NULL && o->klass()->java_mirror() == NULL) {
+ // Ignore this object since the corresponding java mirror is not loaded.
+ // Might be a dormant archive object.
+ return NULL;
+ } else {
+ return o;
+ }
+ }
};
// write a header of the given type
@@ -761,6 +771,13 @@
case JVM_SIGNATURE_CLASS :
case JVM_SIGNATURE_ARRAY : {
oop o = obj->obj_field_access<ON_UNKNOWN_OOP_REF | AS_NO_KEEPALIVE>(offset);
+ if (o != NULL && log_is_enabled(Debug, cds, heap) && mask_dormant_archived_object(o) == NULL) {
+ ResourceMark rm;
+ log_debug(cds, heap)("skipped dormant archived object " INTPTR_FORMAT " (%s) referenced by " INTPTR_FORMAT " (%s)",
+ p2i(o), o->klass()->external_name(),
+ p2i(obj), obj->klass()->external_name());
+ }
+ o = mask_dormant_archived_object(o);
assert(oopDesc::is_oop_or_null(o), "Expected an oop or NULL at " PTR_FORMAT, p2i(o));
writer->write_objectID(o);
break;
@@ -958,11 +975,6 @@
// creates HPROF_GC_INSTANCE_DUMP record for the given object
void DumperSupport::dump_instance(DumpWriter* writer, oop o) {
Klass* k = o->klass();
- if (k->java_mirror() == NULL) {
- // Ignoring this object since the corresponding java mirror is not loaded.
- // Might be a dormant archive object.
- return;
- }
writer->write_u1(HPROF_GC_INSTANCE_DUMP);
writer->write_objectID(o);
@@ -1148,6 +1160,13 @@
// [id]* elements
for (int index = 0; index < length; index++) {
oop o = array->obj_at(index);
+ if (o != NULL && log_is_enabled(Debug, cds, heap) && mask_dormant_archived_object(o) == NULL) {
+ ResourceMark rm;
+ log_debug(cds, heap)("skipped dormant archived object " INTPTR_FORMAT " (%s) referenced by " INTPTR_FORMAT " (%s)",
+ p2i(o), o->klass()->external_name(),
+ p2i(array), array->klass()->external_name());
+ }
+ o = mask_dormant_archived_object(o);
writer->write_objectID(o);
}
}
@@ -1427,6 +1446,11 @@
}
}
+ if (DumperSupport::mask_dormant_archived_object(o) == NULL) {
+ log_debug(cds, heap)("skipped dormant archived object " INTPTR_FORMAT " (%s)", p2i(o), o->klass()->external_name());
+ return;
+ }
+
if (o->is_instance()) {
// create a HPROF_GC_INSTANCE record for each object
DumperSupport::dump_instance(writer(), o);