1f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project/* 2f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Copyright (C) 2008 Google Inc. 3f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * 4f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 5f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * you may not use this file except in compliance with the License. 6f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * You may obtain a copy of the License at 7f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * 8f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 9f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * 10f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 11f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 12f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * See the License for the specific language governing permissions and 14f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * limitations under the License. 15f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */ 16f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 17f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectpackage com.android.hit; 18f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 19f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectimport java.util.ArrayList; 20f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectimport java.util.HashMap; 21f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 22f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectpublic class Heap { 23f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project String mName; 24de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 25f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // List of individual stack frames 26f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<Long, StackFrame> mFrames = new HashMap<Long, StackFrame>(); 27de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 28f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // List stack traces, which are lists of stack frames 29f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<Integer, StackTrace> mTraces = new HashMap<Integer, StackTrace>(); 30de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 31f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // Root objects such as interned strings, jni locals, etc 32f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project ArrayList<RootObj> mRoots = new ArrayList<RootObj>(); 33de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 34f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // List of threads 35f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<Integer, ThreadObj> mThreads = new HashMap<Integer, ThreadObj>(); 36f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 37f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // Class definitions 38f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<Long, ClassObj> mClassesById = new HashMap<Long, ClassObj>(); 39f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<String, ClassObj> mClassesByName = new HashMap<String, ClassObj>(); 40f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 41f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // List of instances of above class definitions 42f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project HashMap<Long, Instance> mInstances = new HashMap<Long, Instance>(); 43f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 44f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project // The super-state that this heap is part of 45f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project State mState; 46f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 47f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public Heap(String name) { 48f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mName = name; 49f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 50de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 51f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addStackFrame(StackFrame theFrame) { 52f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mFrames.put(theFrame.mId, theFrame); 53f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 54f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 55f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final StackFrame getStackFrame(long id) { 56f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mFrames.get(id); 57f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 58f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 59f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addStackTrace(StackTrace theTrace) { 60f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mTraces.put(theTrace.mSerialNumber, theTrace); 61f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 62f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 63f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final StackTrace getStackTrace(int traceSerialNumber) { 64f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mTraces.get(traceSerialNumber); 65f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 66f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 67de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro public final StackTrace getStackTraceAtDepth(int traceSerialNumber, 68f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project int depth) { 69f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project StackTrace trace = mTraces.get(traceSerialNumber); 70de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 71f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (trace != null) { 72f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project trace = trace.fromDepth(depth); 73f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 74de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 75f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return trace; 76f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 77f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 78f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addRoot(RootObj root) { 79f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project root.mIndex = mRoots.size(); 80f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mRoots.add(root); 81f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 82f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 83f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addThread(ThreadObj thread, int serialNumber) { 84f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mThreads.put(serialNumber, thread); 85f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 86de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 87f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final ThreadObj getThread(int serialNumber) { 88f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mThreads.get(serialNumber); 89f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 90f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 91f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addInstance(long id, Instance instance) { 92f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mInstances.put(id, instance); 93f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 94de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 95f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final Instance getInstance(long id) { 96f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mInstances.get(id); 97f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 98f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 99f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void addClass(long id, ClassObj theClass) { 100f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mClassesById.put(id, theClass); 101f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project mClassesByName.put(theClass.mClassName, theClass); 102f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 103de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 104f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final ClassObj getClass(long id) { 105f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mClassesById.get(id); 106f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 107f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 108f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final ClassObj getClass(String name) { 109f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project return mClassesByName.get(name); 110f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 111f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 112f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void dumpInstanceCounts() { 113f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (ClassObj theClass: mClassesById.values()) { 114f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project int count = theClass.mInstances.size(); 115de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 116f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (count > 0) { 117f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project System.out.println(theClass + ": " + count); 118f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 119f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 120f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 121f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 122f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void dumpSubclasses() { 123f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (ClassObj theClass: mClassesById.values()) { 124f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project int count = theClass.mSubclasses.size(); 125de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 126f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (count > 0) { 127f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project System.out.println(theClass); 128f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project theClass.dumpSubclasses(); 129f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 130f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 131f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 132de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 133f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void dumpSizes() { 134f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (ClassObj theClass: mClassesById.values()) { 135f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project int size = 0; 136de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 137f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (Instance instance: theClass.mInstances) { 138f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project size += instance.getCompositeSize(); 139f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 140f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 141f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (size > 0) { 142f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project System.out.println(theClass + ": base " + theClass.getSize() 143f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project + ", composite " + size); 144f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 145f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 146f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 147de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 148f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project /* 149f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Spin through all of the class instances and link them to their 150f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * parent class definition objects. Then have each instance resolve 151f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * its own internal object references. 152f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */ 153f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void resolveInstanceRefs(State state) { 154f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (Instance instance : mInstances.values()) { 155f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project ClassObj theClass = mClassesById.get(instance.mClassId); 156f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 157f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (theClass == null) { 158f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project continue; 159f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 160f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 161f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project String name = theClass.mClassName; 162f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project String superclassName = "none"; 163f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project ClassObj superClass = mClassesById.get(theClass.mSuperclassId); 164de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 165f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project if (superClass != null) { 166f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project superclassName = superClass.mClassName; 167f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 168de75089fb7216d19e9c22cce4dc62a49513477d3Carl Shapiro 169f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project theClass.addInstance(instance); 170f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project instance.resolveReferences(state); 171f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 172f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 173f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 174f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void resolveClassStatics(State state) { 175f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (ClassObj theClass: mClassesById.values()) { 176f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project theClass.resolveReferences(state); 177f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 178f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 179f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project 180f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project public final void resolveRoots(State state) { 181f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project for (RootObj root: mRoots) { 182f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project root.resolveReferences(state); 183f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 184f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project } 185f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project} 186