Merge "Handling race condition when dumping heaps." into qt-dev
am: 98876f0727
Change-Id: I37ba96de00db0350a37232eab232ba9b896cfb30
This commit is contained in:
@@ -879,6 +879,7 @@ public final class ActivityThread extends ClientTransactionHandler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static final class DumpHeapData {
|
static final class DumpHeapData {
|
||||||
|
// Whether to dump the native or managed heap.
|
||||||
public boolean managed;
|
public boolean managed;
|
||||||
public boolean mallocInfo;
|
public boolean mallocInfo;
|
||||||
public boolean runGc;
|
public boolean runGc;
|
||||||
@@ -1137,7 +1138,14 @@ public final class ActivityThread extends ClientTransactionHandler {
|
|||||||
dhd.mallocInfo = mallocInfo;
|
dhd.mallocInfo = mallocInfo;
|
||||||
dhd.runGc = runGc;
|
dhd.runGc = runGc;
|
||||||
dhd.path = path;
|
dhd.path = path;
|
||||||
dhd.fd = fd;
|
try {
|
||||||
|
// Since we're going to dump the heap asynchronously, dup the file descriptor before
|
||||||
|
// it's closed on returning from the IPC call.
|
||||||
|
dhd.fd = fd.dup();
|
||||||
|
} catch (IOException e) {
|
||||||
|
Slog.e(TAG, "Failed to duplicate heap dump file descriptor", e);
|
||||||
|
return;
|
||||||
|
}
|
||||||
dhd.finishCallback = finishCallback;
|
dhd.finishCallback = finishCallback;
|
||||||
sendMessage(H.DUMP_HEAP, dhd, 0, 0, true /*async*/);
|
sendMessage(H.DUMP_HEAP, dhd, 0, 0, true /*async*/);
|
||||||
}
|
}
|
||||||
@@ -3106,9 +3114,10 @@ public final class ActivityThread extends ClientTransactionHandler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
|
private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
|
||||||
if (DEBUG_MESSAGES) Slog.v(
|
if (DEBUG_MESSAGES) {
|
||||||
TAG, "SCHEDULE " + what + " " + mH.codeToString(what)
|
Slog.v(TAG,
|
||||||
+ ": " + arg1 + " / " + obj);
|
"SCHEDULE " + what + " " + mH.codeToString(what) + ": " + arg1 + " / " + obj);
|
||||||
|
}
|
||||||
Message msg = Message.obtain();
|
Message msg = Message.obtain();
|
||||||
msg.what = what;
|
msg.what = what;
|
||||||
msg.obj = obj;
|
msg.obj = obj;
|
||||||
@@ -5827,23 +5836,24 @@ public final class ActivityThread extends ClientTransactionHandler {
|
|||||||
System.runFinalization();
|
System.runFinalization();
|
||||||
System.gc();
|
System.gc();
|
||||||
}
|
}
|
||||||
|
try (ParcelFileDescriptor fd = dhd.fd) {
|
||||||
if (dhd.managed) {
|
if (dhd.managed) {
|
||||||
try {
|
Debug.dumpHprofData(dhd.path, fd.getFileDescriptor());
|
||||||
Debug.dumpHprofData(dhd.path, dhd.fd.getFileDescriptor());
|
|
||||||
} catch (IOException e) {
|
|
||||||
Slog.w(TAG, "Managed heap dump failed on path " + dhd.path
|
|
||||||
+ " -- can the process access this path?");
|
|
||||||
} finally {
|
|
||||||
try {
|
|
||||||
dhd.fd.close();
|
|
||||||
} catch (IOException e) {
|
|
||||||
Slog.w(TAG, "Failure closing profile fd", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (dhd.mallocInfo) {
|
} else if (dhd.mallocInfo) {
|
||||||
Debug.dumpNativeMallocInfo(dhd.fd.getFileDescriptor());
|
Debug.dumpNativeMallocInfo(fd.getFileDescriptor());
|
||||||
} else {
|
} else {
|
||||||
Debug.dumpNativeHeap(dhd.fd.getFileDescriptor());
|
Debug.dumpNativeHeap(fd.getFileDescriptor());
|
||||||
|
}
|
||||||
|
} catch (IOException e) {
|
||||||
|
if (dhd.managed) {
|
||||||
|
Slog.w(TAG, "Managed heap dump failed on path " + dhd.path
|
||||||
|
+ " -- can the process access this path?", e);
|
||||||
|
} else {
|
||||||
|
Slog.w(TAG, "Failed to dump heap", e);
|
||||||
|
}
|
||||||
|
} catch (RuntimeException e) {
|
||||||
|
// This should no longer happening now that we're copying the file descriptor.
|
||||||
|
Slog.wtf(TAG, "Heap dumper threw a runtime exception", e);
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
ActivityManager.getService().dumpHeapFinished(dhd.path);
|
ActivityManager.getService().dumpHeapFinished(dhd.path);
|
||||||
|
|||||||
Reference in New Issue
Block a user