1 /*
2  * Copyright (C) 2007 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 dalvik.system;
18 
19 import android.compat.annotation.UnsupportedAppUsage;
20 
21 import java.io.FileDescriptor;
22 import java.io.IOException;
23 import java.util.HashMap;
24 import java.util.Map;
25 
26 import dalvik.annotation.optimization.FastNative;
27 
28 /**
29  * Provides access to some VM-specific debug features. Though this class and
30  * many of its members are public, this class is meant to be wrapped in a more
31  * friendly way for use by application developers. On the Android platform, the
32  * recommended way to access this functionality is through the class
33  * <code>android.os.Debug</code>.
34  *
35  * @hide
36  */
37 @libcore.api.CorePlatformApi(status = libcore.api.CorePlatformApi.Status.STABLE)
38 public final class VMDebug {
39     /**
40      * flag for startMethodTracing(), which adds the results from
41      * startAllocCounting to the trace key file.
42      */
43     @libcore.api.CorePlatformApi(status = libcore.api.CorePlatformApi.Status.STABLE)
44     public static final int TRACE_COUNT_ALLOCS = 1;
45 
46     /* constants for getAllocCount */
47     private static final int KIND_ALLOCATED_OBJECTS     = 1<<0;
48     private static final int KIND_ALLOCATED_BYTES       = 1<<1;
49     private static final int KIND_FREED_OBJECTS         = 1<<2;
50     private static final int KIND_FREED_BYTES           = 1<<3;
51     private static final int KIND_GC_INVOCATIONS        = 1<<4;
52     private static final int KIND_CLASS_INIT_COUNT      = 1<<5;
53     private static final int KIND_CLASS_INIT_TIME       = 1<<6;
54     private static final int KIND_EXT_ALLOCATED_OBJECTS = 1<<12;
55     private static final int KIND_EXT_ALLOCATED_BYTES   = 1<<13;
56     private static final int KIND_EXT_FREED_OBJECTS     = 1<<14;
57     private static final int KIND_EXT_FREED_BYTES       = 1<<15;
58 
59     @libcore.api.CorePlatformApi
60     public static final int KIND_GLOBAL_ALLOCATED_OBJECTS =
61         KIND_ALLOCATED_OBJECTS;
62     @libcore.api.CorePlatformApi
63     public static final int KIND_GLOBAL_ALLOCATED_BYTES =
64         KIND_ALLOCATED_BYTES;
65     @libcore.api.CorePlatformApi
66     public static final int KIND_GLOBAL_FREED_OBJECTS =
67         KIND_FREED_OBJECTS;
68     @libcore.api.CorePlatformApi
69     public static final int KIND_GLOBAL_FREED_BYTES =
70         KIND_FREED_BYTES;
71     @libcore.api.CorePlatformApi
72     public static final int KIND_GLOBAL_GC_INVOCATIONS =
73         KIND_GC_INVOCATIONS;
74     @libcore.api.CorePlatformApi
75     public static final int KIND_GLOBAL_CLASS_INIT_COUNT =
76         KIND_CLASS_INIT_COUNT;
77     @libcore.api.CorePlatformApi
78     public static final int KIND_GLOBAL_CLASS_INIT_TIME =
79         KIND_CLASS_INIT_TIME;
80     public static final int KIND_GLOBAL_EXT_ALLOCATED_OBJECTS =
81         KIND_EXT_ALLOCATED_OBJECTS;
82     public static final int KIND_GLOBAL_EXT_ALLOCATED_BYTES =
83         KIND_EXT_ALLOCATED_BYTES;
84     public static final int KIND_GLOBAL_EXT_FREED_OBJECTS =
85         KIND_EXT_FREED_OBJECTS;
86     public static final int KIND_GLOBAL_EXT_FREED_BYTES =
87         KIND_EXT_FREED_BYTES;
88 
89     @libcore.api.CorePlatformApi
90     public static final int KIND_THREAD_ALLOCATED_OBJECTS =
91         KIND_ALLOCATED_OBJECTS << 16;
92     @libcore.api.CorePlatformApi
93     public static final int KIND_THREAD_ALLOCATED_BYTES =
94         KIND_ALLOCATED_BYTES << 16;
95     public static final int KIND_THREAD_FREED_OBJECTS =
96         KIND_FREED_OBJECTS << 16;
97     public static final int KIND_THREAD_FREED_BYTES =
98         KIND_FREED_BYTES << 16;
99     @libcore.api.CorePlatformApi
100     public static final int KIND_THREAD_GC_INVOCATIONS =
101         KIND_GC_INVOCATIONS << 16;
102     public static final int KIND_THREAD_CLASS_INIT_COUNT =
103         KIND_CLASS_INIT_COUNT << 16;
104     public static final int KIND_THREAD_CLASS_INIT_TIME =
105         KIND_CLASS_INIT_TIME << 16;
106     public static final int KIND_THREAD_EXT_ALLOCATED_OBJECTS =
107         KIND_EXT_ALLOCATED_OBJECTS << 16;
108     public static final int KIND_THREAD_EXT_ALLOCATED_BYTES =
109         KIND_EXT_ALLOCATED_BYTES << 16;
110     public static final int KIND_THREAD_EXT_FREED_OBJECTS =
111         KIND_EXT_FREED_OBJECTS << 16;
112     public static final int KIND_THREAD_EXT_FREED_BYTES =
113         KIND_EXT_FREED_BYTES << 16;
114 
115     @libcore.api.CorePlatformApi
116     public static final int KIND_ALL_COUNTS = 0xffffffff;
117 
118     /* all methods are static */
VMDebug()119     private VMDebug() {}
120 
121     /**
122      * Returns the time since the last known debugger activity.
123      *
124      * @return the time in milliseconds, or -1 if the debugger is not connected
125      */
126     @libcore.api.CorePlatformApi
127     @FastNative
lastDebuggerActivity()128     public static native long lastDebuggerActivity();
129 
130     /**
131      * Determines if debugging is enabled in this VM.  If debugging is not
132      * enabled, a debugger cannot be attached.
133      *
134      * @return true if debugging is enabled
135      */
136     @libcore.api.CorePlatformApi
137     @FastNative
isDebuggingEnabled()138     public static native boolean isDebuggingEnabled();
139 
140     /**
141      * Determines if a debugger is currently attached.
142      *
143      * @return true if (and only if) a debugger is connected
144      */
145     @UnsupportedAppUsage
146     @libcore.api.CorePlatformApi
147     @FastNative
isDebuggerConnected()148     public static native boolean isDebuggerConnected();
149 
150     /**
151      * Returns an array of strings that identify VM features.  This is
152      * used by DDMS to determine what sorts of operations the VM can
153      * perform.
154      */
155     @libcore.api.CorePlatformApi
getVmFeatureList()156     public static native String[] getVmFeatureList();
157 
158     /**
159      * Start method tracing with default name, size, and with <code>0</code>
160      * flags.
161      *
162      * @deprecated Not used, not needed.
163      */
164     @Deprecated
startMethodTracing()165     public static void startMethodTracing() {
166         throw new UnsupportedOperationException();
167     }
168 
169     /**
170      * Start method tracing, specifying a file name as well as a default
171      * buffer size. See <a
172      * href="{@docRoot}guide/developing/tools/traceview.html"> Running the
173      * Traceview Debugging Program</a> for information about reading
174      * trace files.
175      *
176      * <p>You can use either a fully qualified path and
177      * name, or just a name. If only a name is specified, the file will
178      * be created under the /sdcard/ directory. If a name is not given,
179      * the default is /sdcard/dmtrace.trace.</p>
180      *
181      * @param traceFileName name to give the trace file
182      * @param bufferSize the maximum size of both files combined. If passed
183      * as <code>0</code>, it defaults to 8MB.
184      * @param flags flags to control method tracing. The only one that
185      * is currently defined is {@link #TRACE_COUNT_ALLOCS}.
186      * @param samplingEnabled if true, sample profiling is enabled. Otherwise,
187      * method instrumentation is used.
188      * @param intervalUs the time between samples in microseconds when
189      * sampling is enabled.
190      */
191     @libcore.api.CorePlatformApi
startMethodTracing(String traceFileName, int bufferSize, int flags, boolean samplingEnabled, int intervalUs)192     public static void startMethodTracing(String traceFileName, int bufferSize, int flags, boolean samplingEnabled, int intervalUs) {
193         startMethodTracingFilename(traceFileName, checkBufferSize(bufferSize), flags, samplingEnabled, intervalUs);
194     }
195 
196     /**
197      * Like startMethodTracing(String, int, int), but taking an already-opened
198      * FileDescriptor in which the trace is written.  The file name is also
199      * supplied simply for logging.  Makes a dup of the file descriptor.
200      */
startMethodTracing(String traceFileName, FileDescriptor fd, int bufferSize, int flags, boolean samplingEnabled, int intervalUs)201     public static void startMethodTracing(String traceFileName, FileDescriptor fd, int bufferSize,
202                                           int flags, boolean samplingEnabled, int intervalUs) {
203         startMethodTracing(traceFileName, fd, bufferSize, flags, samplingEnabled, intervalUs,
204                            false);
205     }
206 
207     /**
208      * Like startMethodTracing(String, int, int), but taking an already-opened
209      * FileDescriptor in which the trace is written.  The file name is also
210      * supplied simply for logging.  Makes a dup of the file descriptor.
211      * Streams tracing data to the file if streamingOutput is true.
212      */
213     @libcore.api.CorePlatformApi
startMethodTracing(String traceFileName, FileDescriptor fd, int bufferSize, int flags, boolean samplingEnabled, int intervalUs, boolean streamingOutput)214     public static void startMethodTracing(String traceFileName, FileDescriptor fd, int bufferSize,
215                                           int flags, boolean samplingEnabled, int intervalUs,
216                                           boolean streamingOutput) {
217         if (fd == null) {
218             throw new NullPointerException("fd == null");
219         }
220         startMethodTracingFd(traceFileName, fd.getInt$(), checkBufferSize(bufferSize), flags,
221                              samplingEnabled, intervalUs, streamingOutput);
222     }
223 
224     /**
225      * Starts method tracing without a backing file.  When stopMethodTracing
226      * is called, the result is sent directly to DDMS.  (If DDMS is not
227      * attached when tracing ends, the profiling data will be discarded.)
228      */
229     @libcore.api.CorePlatformApi
startMethodTracingDdms(int bufferSize, int flags, boolean samplingEnabled, int intervalUs)230     public static void startMethodTracingDdms(int bufferSize, int flags, boolean samplingEnabled, int intervalUs) {
231         startMethodTracingDdmsImpl(checkBufferSize(bufferSize), flags, samplingEnabled, intervalUs);
232     }
233 
checkBufferSize(int bufferSize)234     private static int checkBufferSize(int bufferSize) {
235         if (bufferSize == 0) {
236             // Default to 8MB per the documentation.
237             bufferSize = 8 * 1024 * 1024;
238         }
239         if (bufferSize < 1024) {
240             throw new IllegalArgumentException("buffer size < 1024: " + bufferSize);
241         }
242         return bufferSize;
243     }
244 
startMethodTracingDdmsImpl(int bufferSize, int flags, boolean samplingEnabled, int intervalUs)245     private static native void startMethodTracingDdmsImpl(int bufferSize, int flags, boolean samplingEnabled, int intervalUs);
startMethodTracingFd(String traceFileName, int fd, int bufferSize, int flags, boolean samplingEnabled, int intervalUs, boolean streamingOutput)246     private static native void startMethodTracingFd(String traceFileName, int fd, int bufferSize,
247             int flags, boolean samplingEnabled, int intervalUs, boolean streamingOutput);
startMethodTracingFilename(String traceFileName, int bufferSize, int flags, boolean samplingEnabled, int intervalUs)248     private static native void startMethodTracingFilename(String traceFileName, int bufferSize, int flags, boolean samplingEnabled, int intervalUs);
249 
250     /**
251      * Determine whether method tracing is currently active and what type is
252      * active.
253      */
254     @libcore.api.CorePlatformApi
getMethodTracingMode()255     public static native int getMethodTracingMode();
256 
257     /**
258      * Stops method tracing.
259      */
260     @libcore.api.CorePlatformApi
stopMethodTracing()261     public static native void stopMethodTracing();
262 
263     /**
264      * Get an indication of thread CPU usage. The value returned indicates the
265      * amount of time that the current thread has spent executing code or
266      * waiting for certain types of I/O.
267      * <p>
268      * The time is expressed in nanoseconds, and is only meaningful when
269      * compared to the result from an earlier call. Note that nanosecond
270      * resolution does not imply nanosecond accuracy.
271      *
272      * @return the CPU usage. A value of -1 means the system does not support
273      *         this feature.
274      */
275     @libcore.api.CorePlatformApi
276     @FastNative
threadCpuTimeNanos()277     public static native long threadCpuTimeNanos();
278 
279     /**
280      * Count the number and aggregate size of memory allocations between
281      * two points.
282      */
283     @libcore.api.CorePlatformApi
startAllocCounting()284     public static native void startAllocCounting();
285     @libcore.api.CorePlatformApi
stopAllocCounting()286     public static native void stopAllocCounting();
287     @libcore.api.CorePlatformApi
getAllocCount(int kind)288     public static native int getAllocCount(int kind);
289     @libcore.api.CorePlatformApi
resetAllocCount(int kinds)290     public static native void resetAllocCount(int kinds);
291 
292     /**
293      * This method exists for binary compatibility.  It was part of
294      * the allocation limits API which was removed in Android 3.0 (Honeycomb).
295      */
296     @Deprecated
setAllocationLimit(int limit)297     public static int setAllocationLimit(int limit) {
298         return -1;
299     }
300 
301     /**
302      * This method exists for binary compatibility.  It was part of
303      * the allocation limits API which was removed in Android 3.0 (Honeycomb).
304      */
305     @Deprecated
setGlobalAllocationLimit(int limit)306     public static int setGlobalAllocationLimit(int limit) {
307         return -1;
308     }
309 
310     /**
311      * Count the number of instructions executed between two points.
312      */
startInstructionCounting()313     public static native void startInstructionCounting();
stopInstructionCounting()314     public static native void stopInstructionCounting();
getInstructionCount(int[] counts)315     public static native void getInstructionCount(int[] counts);
resetInstructionCount()316     public static native void resetInstructionCount();
317 
318     /**
319      * Dumps a list of loaded class to the log file.
320      */
321     @libcore.api.CorePlatformApi
322     @FastNative
printLoadedClasses(int flags)323     public static native void printLoadedClasses(int flags);
324 
325     /**
326      * Gets the number of loaded classes.
327      *
328      * @return the number of loaded classes
329      */
330     @libcore.api.CorePlatformApi
331     @FastNative
getLoadedClassCount()332     public static native int getLoadedClassCount();
333 
334     /**
335      * Dumps "hprof" data to the specified file.  This may cause a GC.
336      *
337      * The VM may create a temporary file in the same directory.
338      *
339      * @param filename Full pathname of output file (e.g. "/sdcard/dump.hprof").
340      * @throws UnsupportedOperationException if the VM was built without
341      *         HPROF support.
342      * @throws IOException if an error occurs while opening or writing files.
343      */
344     @libcore.api.CorePlatformApi
dumpHprofData(String filename)345     public static void dumpHprofData(String filename) throws IOException {
346         if (filename == null) {
347             throw new NullPointerException("filename == null");
348         }
349         dumpHprofData(filename, null);
350     }
351 
352     /**
353      * Collects "hprof" heap data and sends it to DDMS.  This may cause a GC.
354      *
355      * @throws UnsupportedOperationException if the VM was built without
356      *         HPROF support.
357      */
358     @libcore.api.CorePlatformApi
dumpHprofDataDdms()359     public static native void dumpHprofDataDdms();
360 
361     /**
362      * Dumps "hprof" heap data to a file, by name or descriptor.
363      *
364      * @param fileName Name of output file.  If fd is non-null, the
365      *        file name is only used in log messages (and may be null).
366      * @param fd Descriptor of open file that will receive the output.
367      *        If this is null, the fileName is used instead.
368      */
369     @libcore.api.CorePlatformApi
dumpHprofData(String fileName, FileDescriptor fd)370     public static void dumpHprofData(String fileName, FileDescriptor fd)
371             throws IOException {
372        dumpHprofData(fileName, fd != null ? fd.getInt$() : -1);
373     }
374 
dumpHprofData(String fileName, int fd)375     private static native void dumpHprofData(String fileName, int fd)
376             throws IOException;
377 
378     /**
379      * Dumps the contents of the VM reference tables (e.g. JNI locals and
380      * globals) to the log file.
381      */
382     @UnsupportedAppUsage
383     @libcore.api.CorePlatformApi
dumpReferenceTables()384     public static native void dumpReferenceTables();
385 
386     /**
387      * Crashes the VM.  Seriously.  Dumps the interpreter stack trace for
388      * the current thread and then aborts the VM so you can see the native
389      * stack trace.  Useful for figuring out how you got somewhere when
390      * lots of native code is involved.
391      */
crash()392     public static native void crash();
393 
394     /**
395      * Together with gdb, provide a handy way to stop the VM at user-tagged
396      * locations.
397      */
infopoint(int id)398     public static native void infopoint(int id);
399 
400     /*
401      * Fake method, inserted into dmtrace output when the garbage collector
402      * runs.  Not actually called.
403      */
startGC()404     private static void startGC() {}
405 
406     /*
407      * Fake method, inserted into dmtrace output during class preparation
408      * (loading and linking, but not verification or initialization).  Not
409      * actually called.
410      */
startClassPrep()411     private static void startClassPrep() {}
412 
413     /**
414      * Counts the instances of a class.
415      * It is the caller's responsibility to do GC if they don't want unreachable
416      * objects to get counted.
417      *
418      * @param klass the class to be counted.
419      * @param assignable if true, any instance whose class is assignable to
420      *                   <code>klass</code>, as defined by {@link Class#isAssignableFrom},
421      *                   is counted. If false, only instances whose class is
422      *                   equal to <code>klass</code> are counted.
423      * @return the number of matching instances.
424      */
425     @libcore.api.CorePlatformApi
countInstancesOfClass(Class klass, boolean assignable)426     public static native long countInstancesOfClass(Class klass, boolean assignable);
427 
428     /**
429      * Counts the instances of classes.
430      * It is the caller's responsibility to do GC if they don't want unreachable
431      * objects to get counted.
432      *
433      * @param classes the classes to be counted.
434      * @param assignable if true, any instance whose class is assignable to
435      *                   <code>classes[i]</code>, as defined by {@link Class#isAssignableFrom},
436      *                   is counted. If false, only instances whose class is
437      *                   equal to <code>classes[i]</code> are counted.
438      * @return an array containing the number of matching instances. The value
439      *         for index <code>i</code> is the number of instances of
440      *         the class <code>classes[i]</code>
441      */
442     @libcore.api.CorePlatformApi
countInstancesOfClasses(Class[] classes, boolean assignable)443     public static native long[] countInstancesOfClasses(Class[] classes, boolean assignable);
444 
445     /**
446      * Gets instances of classes on the Java heap.
447      * It is the caller's responsibility to do GC if they don't want unreachable
448      * objects to be included.
449      *
450      * @param classes the classes to get instances of.
451      * @param assignable if true, any instance whose class is assignable to
452      *                   <code>classes[i]</code>, as defined by {@link Class#isAssignableFrom},
453      *                   is included. If false, only instances whose class is
454      *                   equal to <code>classes[i]</code> are included.
455      * @return an array containing the list of matching instances. The value
456      *         for index <code>i</code> is an array containing the instances
457      *         of the class <code>classes[i]</code>
458      */
getInstancesOfClasses(Class[] classes, boolean assignable)459     public static native Object[][] getInstancesOfClasses(Class[] classes, boolean assignable);
460 
461     /**
462      * Export the heap per-space stats for dumpsys meminfo.
463      *
464      * The content of the array is:
465      *
466      * <pre>
467      *   data[0] : the application heap space size
468      *   data[1] : the application heap space allocated bytes
469      *   data[2] : the application heap space free bytes
470      *   data[3] : the zygote heap space size
471      *   data[4] : the zygote heap space allocated size
472      *   data[5] : the zygote heap space free size
473      *   data[6] : the large object space size
474      *   data[7] : the large object space allocated bytes
475      *   data[8] : the large object space free bytes
476      * </pre>
477      *
478      * @param data the array into which the stats are written.
479      */
getHeapSpaceStats(long[] data)480     public static native void getHeapSpaceStats(long[] data);
481 
482     /* Map from the names of the runtime stats supported by getRuntimeStat() to their IDs */
483     private static final HashMap<String, Integer> runtimeStatsMap = new HashMap<>();
484 
485     static {
486         runtimeStatsMap.put("art.gc.gc-count", 0);
487         runtimeStatsMap.put("art.gc.gc-time", 1);
488         runtimeStatsMap.put("art.gc.bytes-allocated", 2);
489         runtimeStatsMap.put("art.gc.bytes-freed", 3);
490         runtimeStatsMap.put("art.gc.blocking-gc-count", 4);
491         runtimeStatsMap.put("art.gc.blocking-gc-time", 5);
492         runtimeStatsMap.put("art.gc.gc-count-rate-histogram", 6);
493         runtimeStatsMap.put("art.gc.blocking-gc-count-rate-histogram", 7);
494     }
495 
496     /**
497      * Returns the value of a particular runtime statistic or {@code null} if no
498      * such runtime statistic exists.
499      *
500      * @param statName
501      *            the name of the runtime statistic to look up.
502      * @return the value of the runtime statistic.
503      */
504     @libcore.api.CorePlatformApi
getRuntimeStat(String statName)505     public static String getRuntimeStat(String statName) {
506         if (statName == null) {
507             throw new NullPointerException("statName == null");
508         }
509         Integer statId = runtimeStatsMap.get(statName);
510         if (statId != null) {
511             return getRuntimeStatInternal(statId);
512         }
513         return null;
514     }
515 
516     /**
517      * Returns a map of the names/values of the runtime statistics
518      * that {@link #getRuntimeStat()} supports.
519      *
520      * @return a map of the names/values of the supported runtime statistics.
521      */
522     @libcore.api.CorePlatformApi
getRuntimeStats()523     public static Map<String, String> getRuntimeStats() {
524         HashMap<String, String> map = new HashMap<>();
525         String[] values = getRuntimeStatsInternal();
526         for (String name : runtimeStatsMap.keySet()) {
527             int id = runtimeStatsMap.get(name);
528             String value = values[id];
529             map.put(name, value);
530         }
531         return map;
532     }
533 
getRuntimeStatInternal(int statId)534     private static native String getRuntimeStatInternal(int statId);
getRuntimeStatsInternal()535     private static native String[] getRuntimeStatsInternal();
536 
537     /**
538      * Attaches an agent to the VM.
539      *
540      * @param agent The path to the agent .so file plus optional agent arguments.
541      */
attachAgent(String agent)542     public static void attachAgent(String agent) throws IOException {
543         attachAgent(agent, null);
544     }
545 
546     /**
547      * Attaches an agent to the VM.
548      *
549      * @param agent The path to the agent .so file plus optional agent arguments.
550      * @param classLoader The classloader to use as a loading context.
551      */
552     @libcore.api.CorePlatformApi
attachAgent(String agent, ClassLoader classLoader)553     public static void attachAgent(String agent, ClassLoader classLoader) throws IOException {
554         nativeAttachAgent(agent, classLoader);
555     }
556 
nativeAttachAgent(String agent, ClassLoader classLoader)557     private static native void nativeAttachAgent(String agent, ClassLoader classLoader)
558             throws IOException;
559 
560     /**
561      * Exempts a class from any future non-SDK API access checks.
562      * Methods declared in the class will be allowed to perform
563      * reflection/JNI against the framework completely unrestricted.
564      * Note that this does not affect uses of non-SDK APIs that the class links against.
565      * Note that this does not affect methods declared outside this class, e.g.
566      * inherited from a superclass or an implemented interface.
567      *
568      * @param klass The class whose methods should be exempted.
569      */
570     @UnsupportedAppUsage
allowHiddenApiReflectionFrom(Class<?> klass)571     public static native void allowHiddenApiReflectionFrom(Class<?> klass);
572 
573     /**
574      * Sets the number of frames recorded for allocation tracking.
575      *
576      * @param stackDepth The number of frames captured for each stack trace.
577      */
578     @libcore.api.CorePlatformApi
setAllocTrackerStackDepth(int stackDepth)579     public static native void setAllocTrackerStackDepth(int stackDepth);
580 }
581