1 /* 2 * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24 /* 25 * @test 26 * @bug 6173675 27 * @summary Basic test of ThreadMXBean.getThreadAllocatedBytes(long[]) 28 * @author Paul Hohensee 29 */ 30 31 import java.lang.management.*; 32 33 public class ThreadAllocatedMemoryArray { 34 private static com.sun.management.ThreadMXBean mbean = 35 (com.sun.management.ThreadMXBean)ManagementFactory.getThreadMXBean(); 36 private static boolean testFailed = false; 37 private static boolean done = false; 38 private static boolean done1 = false; 39 private static Object obj = new Object(); 40 private static final int NUM_THREADS = 10; 41 private static Thread[] threads = new Thread[NUM_THREADS]; 42 43 public static void main(String[] argv) 44 throws Exception { 45 46 if (!mbean.isThreadAllocatedMemorySupported()) { 47 return; 48 } 49 50 51 // start threads, wait for them to block 52 long[] ids = new long[NUM_THREADS]; 53 54 for (int i = 0; i < NUM_THREADS; i++) { 55 threads[i] = new MyThread("MyThread-" + i); 56 threads[i].start(); 57 ids[i] = threads[i].getId(); 58 } 59 60 waitUntilThreadBlocked(); 61 62 63 // disable allocated memory measurement 64 if (mbean.isThreadAllocatedMemoryEnabled()) { 65 mbean.setThreadAllocatedMemoryEnabled(false); 66 } 67 68 if (mbean.isThreadAllocatedMemoryEnabled()) { 69 throw new RuntimeException( 70 "ThreadAllocatedMemory is expected to be disabled"); 71 } 72 73 long sizes[] = mbean.getThreadAllocatedBytes(ids); 74 75 if (sizes == null) { 76 throw new RuntimeException("Null ThreadAllocatedBytes array returned"); 77 } 78 79 for (int i = 0; i < NUM_THREADS; i++) { 80 long s = sizes[i]; 81 if (s != -1) { 82 throw new RuntimeException( 83 "Invalid ThreadAllocatedBytes returned for thread " + 84 threads[i].getName() + " = " + s + " expected = -1"); 85 } 86 } 87 88 // Enable allocated memory measurement 89 if (!mbean.isThreadAllocatedMemoryEnabled()) { 90 mbean.setThreadAllocatedMemoryEnabled(true); 91 } 92 93 if (!mbean.isThreadAllocatedMemoryEnabled()) { 94 throw new RuntimeException( 95 "ThreadAllocatedMemory is expected to be enabled"); 96 } 97 98 sizes = mbean.getThreadAllocatedBytes(ids); 99 100 for (int i = 0; i < NUM_THREADS; i++) { 101 long s = sizes[i]; 102 if (s < 0) { 103 throw new RuntimeException( 104 "Invalid allocated bytes returned for thread " + 105 threads[i].getName() + " = " + s); 106 } 107 } 108 109 // let threads go and do some more allocation 110 synchronized (obj) { 111 done = true; 112 obj.notifyAll(); 113 } 114 115 // wait for threads to get going again. we don't care if we 116 // catch them in mid-execution or if some of them haven't 117 // restarted after we're done sleeping. 118 goSleep(400); 119 120 long[] sizes1 = mbean.getThreadAllocatedBytes(ids); 121 122 for (int i = 0; i < NUM_THREADS; i++) { 123 long newSize = sizes1[i]; 124 if (sizes[i] > newSize) { 125 throw new RuntimeException("TEST FAILED: " + 126 threads[i].getName() + 127 " previous allocated bytes = " + sizes[i] + 128 " > current allocated bytes = " + newSize); 129 } 130 System.out.println(threads[i].getName() + 131 " Previous allocated bytes = " + sizes[i] + 132 " Current allocated bytes = " + newSize); 133 } 134 135 try { 136 sizes = mbean.getThreadAllocatedBytes(null); 137 } catch (NullPointerException e) { 138 System.out.println( 139 "Caught expected NullPointerException: " + e.getMessage()); 140 } 141 142 try { 143 ids[0] = 0; 144 sizes = mbean.getThreadAllocatedBytes(ids); 145 } catch (IllegalArgumentException e) { 146 System.out.println( 147 "Caught expected IllegalArgumentException: " + e.getMessage()); 148 } 149 150 151 // let threads exit 152 synchronized (obj) { 153 done1 = true; 154 obj.notifyAll(); 155 } 156 157 for (int i = 0; i < NUM_THREADS; i++) { 158 try { 159 threads[i].join(); 160 } catch (InterruptedException e) { 161 System.out.println("Unexpected exception is thrown."); 162 e.printStackTrace(System.out); 163 testFailed = true; 164 break; 165 } 166 } 167 168 if (testFailed) { 169 throw new RuntimeException("TEST FAILED"); 170 } 171 172 System.out.println("Test passed"); 173 } 174 175 176 private static void goSleep(long ms) throws Exception { 177 try { 178 Thread.sleep(ms); 179 } catch (InterruptedException e) { 180 System.out.println("Unexpected exception is thrown."); 181 throw e; 182 } 183 } 184 185 private static void waitUntilThreadBlocked() 186 throws Exception { 187 int count = 0; 188 while (count != NUM_THREADS) { 189 goSleep(100); 190 count = 0; 191 for (int i = 0; i < NUM_THREADS; i++) { 192 ThreadInfo info = mbean.getThreadInfo(threads[i].getId()); 193 if (info.getThreadState() == Thread.State.WAITING) { 194 count++; 195 } 196 } 197 } 198 } 199 200 public static void doit() { 201 String tmp = ""; 202 long hashCode = 0; 203 for (int counter = 0; counter < 1000; counter++) { 204 tmp += counter; 205 hashCode = tmp.hashCode(); 206 } 207 System.out.println(Thread.currentThread().getName() + 208 " hashcode: " + hashCode); 209 } 210 211 static class MyThread extends Thread { 212 public MyThread(String name) { 213 super(name); 214 } 215 216 public void run() { 217 ThreadAllocatedMemoryArray.doit(); 218 219 synchronized (obj) { 220 while (!done) { 221 try { 222 obj.wait(); 223 } catch (InterruptedException e) { 224 System.out.println("Unexpected exception is thrown."); 225 e.printStackTrace(System.out); 226 testFailed = true; 227 break; 228 } 229 } 230 } 231 232 ThreadAllocatedMemoryArray.doit(); 233 234 synchronized (obj) { 235 while (!done1) { 236 try { 237 obj.wait(); 238 } catch (InterruptedException e) { 239 System.out.println("Unexpected exception is thrown."); 240 e.printStackTrace(System.out); 241 testFailed = true; 242 break; 243 } 244 } 245 } 246 247 } 248 } 249 }