Home | History | Annotate | Download | only in heap
      1 /*
      2  * Copyright (C) 2011 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.ddmuilib.heap;
     18 
     19 import com.android.ddmlib.NativeAllocationInfo;
     20 
     21 import java.text.NumberFormat;
     22 import java.util.ArrayList;
     23 import java.util.Collection;
     24 import java.util.List;
     25 
     26 /**
     27  * A Native Heap Snapshot models a single heap dump.
     28  *
     29  * It primarily consists of a list of {@link NativeAllocationInfo} objects. From this list,
     30  * other objects of interest to the UI are computed and cached for future use.
     31  */
     32 public class NativeHeapSnapshot {
     33     private static final NumberFormat NUMBER_FORMATTER = NumberFormat.getInstance();
     34 
     35     private List<NativeAllocationInfo> mHeapAllocations;
     36     private List<NativeLibraryAllocationInfo> mHeapAllocationsByLibrary;
     37 
     38     private List<NativeAllocationInfo> mNonZygoteHeapAllocations;
     39     private List<NativeLibraryAllocationInfo> mNonZygoteHeapAllocationsByLibrary;
     40 
     41     private long mTotalSize;
     42 
     43     public NativeHeapSnapshot(List<NativeAllocationInfo> heapAllocations) {
     44         mHeapAllocations = heapAllocations;
     45 
     46         // precompute the total size as this is always needed.
     47         mTotalSize = getTotalMemory(heapAllocations);
     48     }
     49 
     50     protected long getTotalMemory(Collection<NativeAllocationInfo> heapSnapshot) {
     51         long total = 0;
     52 
     53         for (NativeAllocationInfo info : heapSnapshot) {
     54             total += info.getAllocationCount() * info.getSize();
     55         }
     56 
     57         return total;
     58     }
     59 
     60     public List<NativeAllocationInfo> getAllocations() {
     61         return mHeapAllocations;
     62     }
     63 
     64     public List<NativeLibraryAllocationInfo> getAllocationsByLibrary() {
     65         if (mHeapAllocationsByLibrary != null) {
     66             return mHeapAllocationsByLibrary;
     67         }
     68 
     69         List<NativeLibraryAllocationInfo> heapAllocations =
     70                 NativeLibraryAllocationInfo.constructFrom(mHeapAllocations);
     71 
     72         // cache for future uses only if it is fully resolved.
     73         if (isFullyResolved(heapAllocations)) {
     74             mHeapAllocationsByLibrary = heapAllocations;
     75         }
     76 
     77         return heapAllocations;
     78     }
     79 
     80     private boolean isFullyResolved(List<NativeLibraryAllocationInfo> heapAllocations) {
     81         for (NativeLibraryAllocationInfo info : heapAllocations) {
     82             if (info.getLibraryName().equals(NativeLibraryAllocationInfo.UNRESOLVED_LIBRARY_NAME)) {
     83                 return false;
     84             }
     85         }
     86 
     87         return true;
     88     }
     89 
     90     public long getTotalSize() {
     91         return mTotalSize;
     92     }
     93 
     94     public String getFormattedMemorySize() {
     95         return String.format("%s bytes", formatMemorySize(getTotalSize()));
     96     }
     97 
     98     protected String formatMemorySize(long memSize) {
     99         return NUMBER_FORMATTER.format(memSize);
    100     }
    101 
    102     public List<NativeAllocationInfo> getNonZygoteAllocations() {
    103         if (mNonZygoteHeapAllocations != null) {
    104             return mNonZygoteHeapAllocations;
    105         }
    106 
    107         // filter out all zygote allocations
    108         mNonZygoteHeapAllocations = new ArrayList<NativeAllocationInfo>();
    109         for (NativeAllocationInfo info : mHeapAllocations) {
    110             if (info.isZygoteChild()) {
    111                 mNonZygoteHeapAllocations.add(info);
    112             }
    113         }
    114 
    115         return mNonZygoteHeapAllocations;
    116     }
    117 
    118     public List<NativeLibraryAllocationInfo> getNonZygoteAllocationsByLibrary() {
    119         if (mNonZygoteHeapAllocationsByLibrary != null) {
    120             return mNonZygoteHeapAllocationsByLibrary;
    121         }
    122 
    123         List<NativeLibraryAllocationInfo> heapAllocations =
    124                 NativeLibraryAllocationInfo.constructFrom(getNonZygoteAllocations());
    125 
    126         // cache for future uses only if it is fully resolved.
    127         if (isFullyResolved(heapAllocations)) {
    128             mNonZygoteHeapAllocationsByLibrary = heapAllocations;
    129         }
    130 
    131         return heapAllocations;
    132     }
    133 }
    134