Home | History | Annotate | Download | only in os
      1 /*
      2  * Copyright (C) 2009 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 android.os;
     18 
     19 
     20 import java.util.ArrayList;
     21 
     22 /**
     23  * Collects performance data between two function calls in Bundle objects and
     24  * outputs the results using writer of type {@link PerformanceResultsWriter}.
     25  * <p>
     26  * {@link #beginSnapshot(String)} and {@link #endSnapshot()} functions collect
     27  * memory usage information and measure runtime between calls to begin and end.
     28  * These functions logically wrap around an entire test, and should be called
     29  * with name of test as the label, e.g. EmailPerformanceTest.
     30  * <p>
     31  * {@link #startTiming(String)} and {@link #stopTiming(String)} functions
     32  * measure runtime between calls to start and stop. These functions logically
     33  * wrap around a single test case or a small block of code, and should be called
     34  * with the name of test case as the label, e.g. testSimpleSendMailSequence.
     35  * <p>
     36  * {@link #addIteration(String)} inserts intermediate measurement point which
     37  * can be labeled with a String, e.g. Launch email app, compose, send, etc.
     38  * <p>
     39  * Snapshot and timing functions do not interfere with each other, and thus can
     40  * be called in any order. The intended structure is to wrap begin/endSnapshot
     41  * around calls to start/stopTiming, for example:
     42  * <p>
     43  * <code>beginSnapshot("EmailPerformanceTest");
     44  * startTiming("testSimpleSendSequence");
     45  * addIteration("Launch email app");
     46  * addIteration("Compose");
     47  * stopTiming("Send");
     48  * startTiming("testComplexSendSequence");
     49  * stopTiming("");
     50  * startTiming("testAddLabel");
     51  * stopTiming("");
     52  * endSnapshot();</code>
     53  * <p>
     54  * Structure of results output is up to implementor of
     55  * {@link PerformanceResultsWriter }.
     56  *
     57  * {@hide} Pending approval for public API.
     58  */
     59 public class PerformanceCollector {
     60 
     61     /**
     62      * Interface for reporting performance data.
     63      */
     64     public interface PerformanceResultsWriter {
     65 
     66         /**
     67          * Callback invoked as first action in
     68          * PerformanceCollector#beginSnapshot(String) for reporting the start of
     69          * a performance snapshot.
     70          *
     71          * @param label description of code block between beginSnapshot and
     72          *              PerformanceCollector#endSnapshot()
     73          * @see PerformanceCollector#beginSnapshot(String)
     74          */
     75         public void writeBeginSnapshot(String label);
     76 
     77         /**
     78          * Callback invoked as last action in PerformanceCollector#endSnapshot()
     79          * for reporting performance data collected in the snapshot.
     80          *
     81          * @param results memory and runtime metrics stored as key/value pairs,
     82          *        in the same structure as returned by
     83          *        PerformanceCollector#endSnapshot()
     84          * @see PerformanceCollector#endSnapshot()
     85          */
     86         public void writeEndSnapshot(Bundle results);
     87 
     88         /**
     89          * Callback invoked as first action in
     90          * PerformanceCollector#startTiming(String) for reporting the start of
     91          * a timing measurement.
     92          *
     93          * @param label description of code block between startTiming and
     94          *              PerformanceCollector#stopTiming(String)
     95          * @see PerformanceCollector#startTiming(String)
     96          */
     97         public void writeStartTiming(String label);
     98 
     99         /**
    100          * Callback invoked as last action in
    101          * {@link PerformanceCollector#stopTiming(String)} for reporting the
    102          * sequence of timings measured.
    103          *
    104          * @param results runtime metrics of code block between calls to
    105          *                startTiming and stopTiming, in the same structure as
    106          *                returned by PerformanceCollector#stopTiming(String)
    107          * @see PerformanceCollector#stopTiming(String)
    108          */
    109         public void writeStopTiming(Bundle results);
    110 
    111         /**
    112          * Callback invoked as last action in
    113          * {@link PerformanceCollector#addMeasurement(String, long)} for
    114          * reporting an integer type measurement.
    115          *
    116          * @param label short description of the metric that was measured
    117          * @param value long value of the measurement
    118          */
    119         public void writeMeasurement(String label, long value);
    120 
    121         /**
    122          * Callback invoked as last action in
    123          * {@link PerformanceCollector#addMeasurement(String, float)} for
    124          * reporting a float type measurement.
    125          *
    126          * @param label short description of the metric that was measured
    127          * @param value float value of the measurement
    128          */
    129         public void writeMeasurement(String label, float value);
    130 
    131         /**
    132          * Callback invoked as last action in
    133          * {@link PerformanceCollector#addMeasurement(String, String)} for
    134          * reporting a string field.
    135          *
    136          * @param label short description of the metric that was measured
    137          * @param value string summary of the measurement
    138          */
    139         public void writeMeasurement(String label, String value);
    140     }
    141 
    142     /**
    143      * In a results Bundle, this key references a List of iteration Bundles.
    144      */
    145     public static final String METRIC_KEY_ITERATIONS = "iterations";
    146     /**
    147      * In an iteration Bundle, this key describes the iteration.
    148      */
    149     public static final String METRIC_KEY_LABEL = "label";
    150     /**
    151      * In a results Bundle, this key reports the cpu time of the code block
    152      * under measurement.
    153      */
    154     public static final String METRIC_KEY_CPU_TIME = "cpu_time";
    155     /**
    156      * In a results Bundle, this key reports the execution time of the code
    157      * block under measurement.
    158      */
    159     public static final String METRIC_KEY_EXECUTION_TIME = "execution_time";
    160     /**
    161      * In a snapshot Bundle, this key reports the number of received
    162      * transactions from the binder driver before collection started.
    163      */
    164     public static final String METRIC_KEY_PRE_RECEIVED_TRANSACTIONS = "pre_received_transactions";
    165     /**
    166      * In a snapshot Bundle, this key reports the number of transactions sent by
    167      * the running program before collection started.
    168      */
    169     public static final String METRIC_KEY_PRE_SENT_TRANSACTIONS = "pre_sent_transactions";
    170     /**
    171      * In a snapshot Bundle, this key reports the number of received
    172      * transactions from the binder driver.
    173      */
    174     public static final String METRIC_KEY_RECEIVED_TRANSACTIONS = "received_transactions";
    175     /**
    176      * In a snapshot Bundle, this key reports the number of transactions sent by
    177      * the running program.
    178      */
    179     public static final String METRIC_KEY_SENT_TRANSACTIONS = "sent_transactions";
    180     /**
    181      * In a snapshot Bundle, this key reports the number of garbage collection
    182      * invocations.
    183      */
    184     public static final String METRIC_KEY_GC_INVOCATION_COUNT = "gc_invocation_count";
    185     /**
    186      * In a snapshot Bundle, this key reports the amount of allocated memory
    187      * used by the running program.
    188      */
    189     public static final String METRIC_KEY_JAVA_ALLOCATED = "java_allocated";
    190     /**
    191      * In a snapshot Bundle, this key reports the amount of free memory
    192      * available to the running program.
    193      */
    194     public static final String METRIC_KEY_JAVA_FREE = "java_free";
    195     /**
    196      * In a snapshot Bundle, this key reports the number of private dirty pages
    197      * used by dalvik.
    198      */
    199     public static final String METRIC_KEY_JAVA_PRIVATE_DIRTY = "java_private_dirty";
    200     /**
    201      * In a snapshot Bundle, this key reports the proportional set size for
    202      * dalvik.
    203      */
    204     public static final String METRIC_KEY_JAVA_PSS = "java_pss";
    205     /**
    206      * In a snapshot Bundle, this key reports the number of shared dirty pages
    207      * used by dalvik.
    208      */
    209     public static final String METRIC_KEY_JAVA_SHARED_DIRTY = "java_shared_dirty";
    210     /**
    211      * In a snapshot Bundle, this key reports the total amount of memory
    212      * available to the running program.
    213      */
    214     public static final String METRIC_KEY_JAVA_SIZE = "java_size";
    215     /**
    216      * In a snapshot Bundle, this key reports the amount of allocated memory in
    217      * the native heap.
    218      */
    219     public static final String METRIC_KEY_NATIVE_ALLOCATED = "native_allocated";
    220     /**
    221      * In a snapshot Bundle, this key reports the amount of free memory in the
    222      * native heap.
    223      */
    224     public static final String METRIC_KEY_NATIVE_FREE = "native_free";
    225     /**
    226      * In a snapshot Bundle, this key reports the number of private dirty pages
    227      * used by the native heap.
    228      */
    229     public static final String METRIC_KEY_NATIVE_PRIVATE_DIRTY = "native_private_dirty";
    230     /**
    231      * In a snapshot Bundle, this key reports the proportional set size for the
    232      * native heap.
    233      */
    234     public static final String METRIC_KEY_NATIVE_PSS = "native_pss";
    235     /**
    236      * In a snapshot Bundle, this key reports the number of shared dirty pages
    237      * used by the native heap.
    238      */
    239     public static final String METRIC_KEY_NATIVE_SHARED_DIRTY = "native_shared_dirty";
    240     /**
    241      * In a snapshot Bundle, this key reports the size of the native heap.
    242      */
    243     public static final String METRIC_KEY_NATIVE_SIZE = "native_size";
    244     /**
    245      * In a snapshot Bundle, this key reports the number of objects allocated
    246      * globally.
    247      */
    248     public static final String METRIC_KEY_GLOBAL_ALLOC_COUNT = "global_alloc_count";
    249     /**
    250      * In a snapshot Bundle, this key reports the size of all objects allocated
    251      * globally.
    252      */
    253     public static final String METRIC_KEY_GLOBAL_ALLOC_SIZE = "global_alloc_size";
    254     /**
    255      * In a snapshot Bundle, this key reports the number of objects freed
    256      * globally.
    257      */
    258     public static final String METRIC_KEY_GLOBAL_FREED_COUNT = "global_freed_count";
    259     /**
    260      * In a snapshot Bundle, this key reports the size of all objects freed
    261      * globally.
    262      */
    263     public static final String METRIC_KEY_GLOBAL_FREED_SIZE = "global_freed_size";
    264     /**
    265      * In a snapshot Bundle, this key reports the number of private dirty pages
    266      * used by everything else.
    267      */
    268     public static final String METRIC_KEY_OTHER_PRIVATE_DIRTY = "other_private_dirty";
    269     /**
    270      * In a snapshot Bundle, this key reports the proportional set size for
    271      * everything else.
    272      */
    273     public static final String METRIC_KEY_OTHER_PSS = "other_pss";
    274     /**
    275      * In a snapshot Bundle, this key reports the number of shared dirty pages
    276      * used by everything else.
    277      */
    278     public static final String METRIC_KEY_OTHER_SHARED_DIRTY = "other_shared_dirty";
    279 
    280     private PerformanceResultsWriter mPerfWriter;
    281     private Bundle mPerfSnapshot;
    282     private Bundle mPerfMeasurement;
    283     private long mSnapshotCpuTime;
    284     private long mSnapshotExecTime;
    285     private long mCpuTime;
    286     private long mExecTime;
    287 
    288     public PerformanceCollector() {
    289     }
    290 
    291     public PerformanceCollector(PerformanceResultsWriter writer) {
    292         setPerformanceResultsWriter(writer);
    293     }
    294 
    295     public void setPerformanceResultsWriter(PerformanceResultsWriter writer) {
    296         mPerfWriter = writer;
    297     }
    298 
    299     /**
    300      * Begin collection of memory usage information.
    301      *
    302      * @param label description of code block between beginSnapshot and
    303      *              endSnapshot, used to label output
    304      */
    305     public void beginSnapshot(String label) {
    306         if (mPerfWriter != null)
    307             mPerfWriter.writeBeginSnapshot(label);
    308         startPerformanceSnapshot();
    309     }
    310 
    311     /**
    312      * End collection of memory usage information. Returns collected data in a
    313      * Bundle object.
    314      *
    315      * @return Memory and runtime metrics stored as key/value pairs. Values are
    316      *         of type long, and keys include:
    317      *         <ul>
    318      *         <li>{@link #METRIC_KEY_CPU_TIME cpu_time}
    319      *         <li>{@link #METRIC_KEY_EXECUTION_TIME execution_time}
    320      *         <li>{@link #METRIC_KEY_PRE_RECEIVED_TRANSACTIONS
    321      *         pre_received_transactions}
    322      *         <li>{@link #METRIC_KEY_PRE_SENT_TRANSACTIONS
    323      *         pre_sent_transactions}
    324      *         <li>{@link #METRIC_KEY_RECEIVED_TRANSACTIONS
    325      *         received_transactions}
    326      *         <li>{@link #METRIC_KEY_SENT_TRANSACTIONS sent_transactions}
    327      *         <li>{@link #METRIC_KEY_GC_INVOCATION_COUNT gc_invocation_count}
    328      *         <li>{@link #METRIC_KEY_JAVA_ALLOCATED java_allocated}
    329      *         <li>{@link #METRIC_KEY_JAVA_FREE java_free}
    330      *         <li>{@link #METRIC_KEY_JAVA_PRIVATE_DIRTY java_private_dirty}
    331      *         <li>{@link #METRIC_KEY_JAVA_PSS java_pss}
    332      *         <li>{@link #METRIC_KEY_JAVA_SHARED_DIRTY java_shared_dirty}
    333      *         <li>{@link #METRIC_KEY_JAVA_SIZE java_size}
    334      *         <li>{@link #METRIC_KEY_NATIVE_ALLOCATED native_allocated}
    335      *         <li>{@link #METRIC_KEY_NATIVE_FREE native_free}
    336      *         <li>{@link #METRIC_KEY_NATIVE_PRIVATE_DIRTY native_private_dirty}
    337      *         <li>{@link #METRIC_KEY_NATIVE_PSS native_pss}
    338      *         <li>{@link #METRIC_KEY_NATIVE_SHARED_DIRTY native_shared_dirty}
    339      *         <li>{@link #METRIC_KEY_NATIVE_SIZE native_size}
    340      *         <li>{@link #METRIC_KEY_GLOBAL_ALLOC_COUNT global_alloc_count}
    341      *         <li>{@link #METRIC_KEY_GLOBAL_ALLOC_SIZE global_alloc_size}
    342      *         <li>{@link #METRIC_KEY_GLOBAL_FREED_COUNT global_freed_count}
    343      *         <li>{@link #METRIC_KEY_GLOBAL_FREED_SIZE global_freed_size}
    344      *         <li>{@link #METRIC_KEY_OTHER_PRIVATE_DIRTY other_private_dirty}
    345      *         <li>{@link #METRIC_KEY_OTHER_PSS other_pss}
    346      *         <li>{@link #METRIC_KEY_OTHER_SHARED_DIRTY other_shared_dirty}
    347      *         </ul>
    348      */
    349     public Bundle endSnapshot() {
    350         endPerformanceSnapshot();
    351         if (mPerfWriter != null)
    352             mPerfWriter.writeEndSnapshot(mPerfSnapshot);
    353         return mPerfSnapshot;
    354     }
    355 
    356     /**
    357      * Start measurement of user and cpu time.
    358      *
    359      * @param label description of code block between startTiming and
    360      *        stopTiming, used to label output
    361      */
    362     public void startTiming(String label) {
    363         if (mPerfWriter != null)
    364             mPerfWriter.writeStartTiming(label);
    365         mPerfMeasurement = new Bundle();
    366         mPerfMeasurement.putParcelableArrayList(
    367                 METRIC_KEY_ITERATIONS, new ArrayList<Parcelable>());
    368         mExecTime = SystemClock.uptimeMillis();
    369         mCpuTime = Process.getElapsedCpuTime();
    370     }
    371 
    372     /**
    373      * Add a measured segment, and start measuring the next segment. Returns
    374      * collected data in a Bundle object.
    375      *
    376      * @param label description of code block between startTiming and
    377      *              addIteration, and between two calls to addIteration, used
    378      *              to label output
    379      * @return Runtime metrics stored as key/value pairs. Values are of type
    380      *         long, and keys include:
    381      *         <ul>
    382      *         <li>{@link #METRIC_KEY_LABEL label}
    383      *         <li>{@link #METRIC_KEY_CPU_TIME cpu_time}
    384      *         <li>{@link #METRIC_KEY_EXECUTION_TIME execution_time}
    385      *         </ul>
    386      */
    387     public Bundle addIteration(String label) {
    388         mCpuTime = Process.getElapsedCpuTime() - mCpuTime;
    389         mExecTime = SystemClock.uptimeMillis() - mExecTime;
    390 
    391         Bundle iteration = new Bundle();
    392         iteration.putString(METRIC_KEY_LABEL, label);
    393         iteration.putLong(METRIC_KEY_EXECUTION_TIME, mExecTime);
    394         iteration.putLong(METRIC_KEY_CPU_TIME, mCpuTime);
    395         mPerfMeasurement.getParcelableArrayList(METRIC_KEY_ITERATIONS).add(iteration);
    396 
    397         mExecTime = SystemClock.uptimeMillis();
    398         mCpuTime = Process.getElapsedCpuTime();
    399         return iteration;
    400     }
    401 
    402     /**
    403      * Stop measurement of user and cpu time.
    404      *
    405      * @param label description of code block between addIteration or
    406      *              startTiming and stopTiming, used to label output
    407      * @return Runtime metrics stored in a bundle, including all iterations
    408      *         between calls to startTiming and stopTiming. List of iterations
    409      *         is keyed by {@link #METRIC_KEY_ITERATIONS iterations}.
    410      */
    411     public Bundle stopTiming(String label) {
    412         addIteration(label);
    413         if (mPerfWriter != null)
    414             mPerfWriter.writeStopTiming(mPerfMeasurement);
    415         return mPerfMeasurement;
    416     }
    417 
    418     /**
    419      * Add an integer type measurement to the collector.
    420      *
    421      * @param label short description of the metric that was measured
    422      * @param value long value of the measurement
    423      */
    424     public void addMeasurement(String label, long value) {
    425         if (mPerfWriter != null)
    426             mPerfWriter.writeMeasurement(label, value);
    427     }
    428 
    429     /**
    430      * Add a float type measurement to the collector.
    431      *
    432      * @param label short description of the metric that was measured
    433      * @param value float value of the measurement
    434      */
    435     public void addMeasurement(String label, float value) {
    436         if (mPerfWriter != null)
    437             mPerfWriter.writeMeasurement(label, value);
    438     }
    439 
    440     /**
    441      * Add a string field to the collector.
    442      *
    443      * @param label short description of the metric that was measured
    444      * @param value string summary of the measurement
    445      */
    446     public void addMeasurement(String label, String value) {
    447         if (mPerfWriter != null)
    448             mPerfWriter.writeMeasurement(label, value);
    449     }
    450 
    451     /*
    452      * Starts tracking memory usage, binder transactions, and real & cpu timing.
    453      */
    454     private void startPerformanceSnapshot() {
    455         // Create new snapshot
    456         mPerfSnapshot = new Bundle();
    457 
    458         // Add initial binder counts
    459         Bundle binderCounts = getBinderCounts();
    460         for (String key : binderCounts.keySet()) {
    461             mPerfSnapshot.putLong("pre_" + key, binderCounts.getLong(key));
    462         }
    463 
    464         // Force a GC and zero out the performance counters. Do this
    465         // before reading initial CPU/wall-clock times so we don't include
    466         // the cost of this setup in our final metrics.
    467         startAllocCounting();
    468 
    469         // Record CPU time up to this point, and start timing. Note: this
    470         // must happen at the end of this method, otherwise the timing will
    471         // include noise.
    472         mSnapshotExecTime = SystemClock.uptimeMillis();
    473         mSnapshotCpuTime = Process.getElapsedCpuTime();
    474     }
    475 
    476     /*
    477      * Stops tracking memory usage, binder transactions, and real & cpu timing.
    478      * Stores collected data as type long into Bundle object for reporting.
    479      */
    480     private void endPerformanceSnapshot() {
    481         // Stop the timing. This must be done first before any other counting is
    482         // stopped.
    483         mSnapshotCpuTime = Process.getElapsedCpuTime() - mSnapshotCpuTime;
    484         mSnapshotExecTime = SystemClock.uptimeMillis() - mSnapshotExecTime;
    485 
    486         stopAllocCounting();
    487 
    488         long nativeMax = Debug.getNativeHeapSize() / 1024;
    489         long nativeAllocated = Debug.getNativeHeapAllocatedSize() / 1024;
    490         long nativeFree = Debug.getNativeHeapFreeSize() / 1024;
    491 
    492         Debug.MemoryInfo memInfo = new Debug.MemoryInfo();
    493         Debug.getMemoryInfo(memInfo);
    494 
    495         Runtime runtime = Runtime.getRuntime();
    496 
    497         long dalvikMax = runtime.totalMemory() / 1024;
    498         long dalvikFree = runtime.freeMemory() / 1024;
    499         long dalvikAllocated = dalvikMax - dalvikFree;
    500 
    501         // Add final binder counts
    502         Bundle binderCounts = getBinderCounts();
    503         for (String key : binderCounts.keySet()) {
    504             mPerfSnapshot.putLong(key, binderCounts.getLong(key));
    505         }
    506 
    507         // Add alloc counts
    508         Bundle allocCounts = getAllocCounts();
    509         for (String key : allocCounts.keySet()) {
    510             mPerfSnapshot.putLong(key, allocCounts.getLong(key));
    511         }
    512 
    513         mPerfSnapshot.putLong(METRIC_KEY_EXECUTION_TIME, mSnapshotExecTime);
    514         mPerfSnapshot.putLong(METRIC_KEY_CPU_TIME, mSnapshotCpuTime);
    515 
    516         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_SIZE, nativeMax);
    517         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_ALLOCATED, nativeAllocated);
    518         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_FREE, nativeFree);
    519         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_PSS, memInfo.nativePss);
    520         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_PRIVATE_DIRTY, memInfo.nativePrivateDirty);
    521         mPerfSnapshot.putLong(METRIC_KEY_NATIVE_SHARED_DIRTY, memInfo.nativeSharedDirty);
    522 
    523         mPerfSnapshot.putLong(METRIC_KEY_JAVA_SIZE, dalvikMax);
    524         mPerfSnapshot.putLong(METRIC_KEY_JAVA_ALLOCATED, dalvikAllocated);
    525         mPerfSnapshot.putLong(METRIC_KEY_JAVA_FREE, dalvikFree);
    526         mPerfSnapshot.putLong(METRIC_KEY_JAVA_PSS, memInfo.dalvikPss);
    527         mPerfSnapshot.putLong(METRIC_KEY_JAVA_PRIVATE_DIRTY, memInfo.dalvikPrivateDirty);
    528         mPerfSnapshot.putLong(METRIC_KEY_JAVA_SHARED_DIRTY, memInfo.dalvikSharedDirty);
    529 
    530         mPerfSnapshot.putLong(METRIC_KEY_OTHER_PSS, memInfo.otherPss);
    531         mPerfSnapshot.putLong(METRIC_KEY_OTHER_PRIVATE_DIRTY, memInfo.otherPrivateDirty);
    532         mPerfSnapshot.putLong(METRIC_KEY_OTHER_SHARED_DIRTY, memInfo.otherSharedDirty);
    533     }
    534 
    535     /*
    536      * Starts allocation counting. This triggers a gc and resets the counts.
    537      */
    538     private static void startAllocCounting() {
    539         // Before we start trigger a GC and reset the debug counts. Run the
    540         // finalizers and another GC before starting and stopping the alloc
    541         // counts. This will free up any objects that were just sitting around
    542         // waiting for their finalizers to be run.
    543         Runtime.getRuntime().gc();
    544         Runtime.getRuntime().runFinalization();
    545         Runtime.getRuntime().gc();
    546 
    547         Debug.resetAllCounts();
    548 
    549         // start the counts
    550         Debug.startAllocCounting();
    551     }
    552 
    553     /*
    554      * Stops allocation counting.
    555      */
    556     private static void stopAllocCounting() {
    557         Runtime.getRuntime().gc();
    558         Runtime.getRuntime().runFinalization();
    559         Runtime.getRuntime().gc();
    560         Debug.stopAllocCounting();
    561     }
    562 
    563     /*
    564      * Returns a bundle with the current results from the allocation counting.
    565      */
    566     private static Bundle getAllocCounts() {
    567         Bundle results = new Bundle();
    568         results.putLong(METRIC_KEY_GLOBAL_ALLOC_COUNT, Debug.getGlobalAllocCount());
    569         results.putLong(METRIC_KEY_GLOBAL_ALLOC_SIZE, Debug.getGlobalAllocSize());
    570         results.putLong(METRIC_KEY_GLOBAL_FREED_COUNT, Debug.getGlobalFreedCount());
    571         results.putLong(METRIC_KEY_GLOBAL_FREED_SIZE, Debug.getGlobalFreedSize());
    572         results.putLong(METRIC_KEY_GC_INVOCATION_COUNT, Debug.getGlobalGcInvocationCount());
    573         return results;
    574     }
    575 
    576     /*
    577      * Returns a bundle with the counts for various binder counts for this
    578      * process. Currently the only two that are reported are the number of send
    579      * and the number of received transactions.
    580      */
    581     private static Bundle getBinderCounts() {
    582         Bundle results = new Bundle();
    583         results.putLong(METRIC_KEY_SENT_TRANSACTIONS, Debug.getBinderSentTransactions());
    584         results.putLong(METRIC_KEY_RECEIVED_TRANSACTIONS, Debug.getBinderReceivedTransactions());
    585         return results;
    586     }
    587 }
    588