--- old/test/hotspot/jtreg/serviceability/jvmti/HeapMonitor/MyPackage/HeapMonitor.java 2018-03-19 14:01:18.717596574 -0700 +++ new/test/hotspot/jtreg/serviceability/jvmti/HeapMonitor/MyPackage/HeapMonitor.java 2018-03-19 14:01:18.445597460 -0700 @@ -51,6 +51,8 @@ /** Set a specific sampling rate, 0 turns off sampling. */ public native static void setSamplingRate(int rate); + /** Set a specific garbage history buffer. */ + public native static void setGarbageHistory(int amount); public native static void enableSamplingEvents(); public native static void disableSamplingEvents(); @@ -64,11 +66,11 @@ List frames = new ArrayList(); if (depth > 1) { createStackDepth(depth - 1, frames); - frames.add(new Frame("allocate", "(I)Ljava/util/List;", "HeapMonitor.java", 61)); + frames.add(new Frame("allocate", "(I)Ljava/util/List;", "HeapMonitor.java", 68)); } else { actuallyAllocate(); - frames.add(new Frame("actuallyAllocate", "()I", "HeapMonitor.java", 126)); - frames.add(new Frame("allocate", "(I)Ljava/util/List;", "HeapMonitor.java", 64)); + frames.add(new Frame("actuallyAllocate", "()I", "HeapMonitor.java", 131)); + frames.add(new Frame("allocate", "(I)Ljava/util/List;", "HeapMonitor.java", 71)); } return frames; } @@ -82,17 +84,17 @@ int sum = 0; List frames = new ArrayList(); allocate(frames); - frames.add(new Frame("allocate", "()Ljava/util/List;", "HeapMonitor.java", 79)); + frames.add(new Frame("allocate", "()Ljava/util/List;", "HeapMonitor.java", 86)); return frames; } private static void createStackDepth(int depth, List frames) { if (depth > 1) { createStackDepth(depth - 1, frames); - frames.add(new Frame("createStackDepth", "(ILjava/util/List;)V", "HeapMonitor.java", 86)); + frames.add(new Frame("createStackDepth", "(ILjava/util/List;)V", "HeapMonitor.java", 93)); } else { allocate(frames); - frames.add(new Frame("createStackDepth", "(ILjava/util/List;)V", "HeapMonitor.java", 89)); + frames.add(new Frame("createStackDepth", "(ILjava/util/List;)V", "HeapMonitor.java", 96)); } } @@ -101,8 +103,8 @@ for (int j = 0; j < 1000; j++) { sum += actuallyAllocate(); } - frames.add(new Frame("actuallyAllocate", "()I", "HeapMonitor.java", 124)); - frames.add(new Frame("allocate", "(Ljava/util/List;)V", "HeapMonitor.java", 97)); + frames.add(new Frame("actuallyAllocate", "()I", "HeapMonitor.java", 131)); + frames.add(new Frame("allocate", "(Ljava/util/List;)V", "HeapMonitor.java", 104)); } public static List repeatAllocate(int max) { @@ -110,7 +112,7 @@ for (int i = 0; i < max; i++) { frames = allocate(); } - frames.add(new Frame("repeatAllocate", "(I)Ljava/util/List;", "HeapMonitor.java", 106)); + frames.add(new Frame("repeatAllocate", "(I)Ljava/util/List;", "HeapMonitor.java", 113)); return frames; } @@ -134,12 +136,43 @@ return sum; } + public static int allocateSize(int totalSize) { + int sum = 0; + + // Let us assume that a 1-element array is 24 bytes. + int iterations = totalSize / 24; + + if (arrays == null) { + arrays = new int[iterations][]; + } + + System.out.println("Allocating for " + iterations); + for (int i = 0; i < iterations; i++) { + int tmp[] = new int[1]; + + // Force it to be kept and, at the same time, wipe out any previous data. + arrays[i] = tmp; + sum += arrays[0][0]; + } + + return sum; + } + /** Remove the reference to the global array to free data at the next GC. */ public static void freeStorage() { arrays = null; } public native static boolean obtainedEvents(Frame[] frames); + public native static boolean garbageContains(Frame[] frames); public native static boolean eventStorageIsEmpty(); public native static void resetEventStorage(); + public native static int getEventStorageElementCount(); + public native static void forceGarbageCollection(); + + public static boolean statsHaveExpectedNumberSamples(int expected, int acceptedErrorPercentage) { + double actual = getEventStorageElementCount(); + double diffPercentage = Math.abs(actual - expected) / expected; + return diffPercentage < acceptedErrorPercentage; + } }