1 /* 2 * Copyright (c) 2003, 2015, 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 4530538 27 * @summary Basic test of ThreadMXBean.getThreadCpuTime and 28 * getCurrentThreadCpuTime. 29 * @author Mandy Chung 30 * @modules java.management 31 */ 32 33 import java.lang.management.*; 34 35 public class ThreadCpuTime { 36 private static ThreadMXBean mbean = ManagementFactory.getThreadMXBean(); 37 private static boolean testFailed = false; 38 private static boolean done = 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 private static long[] times = new long[NUM_THREADS]; 43 44 // careful about this value 45 private static final int DELTA = 100; 46 47 public static void main(String[] argv) 48 throws Exception { 49 if (!mbean.isCurrentThreadCpuTimeSupported()) { 50 return; 51 } 52 53 // disable CPU time 54 if (mbean.isThreadCpuTimeEnabled()) { 55 mbean.setThreadCpuTimeEnabled(false); 56 } 57 58 Thread curThread = Thread.currentThread(); 59 long t = mbean.getCurrentThreadCpuTime(); 60 if (t != -1) { 61 throw new RuntimeException("Invalid CurrenThreadCpuTime returned = " + 62 t + " expected = -1"); 63 } 64 65 if (mbean.isThreadCpuTimeSupported()) { 66 long t1 = mbean.getThreadCpuTime(curThread.getId()); 67 if (t1 != -1) { 68 throw new RuntimeException("Invalid ThreadCpuTime returned = " + 69 t1 + " expected = -1"); 70 } 71 } 72 73 // Enable CPU Time measurement 74 if (!mbean.isThreadCpuTimeEnabled()) { 75 mbean.setThreadCpuTimeEnabled(true); 76 } 77 78 if (!mbean.isThreadCpuTimeEnabled()) { 79 throw new RuntimeException("ThreadCpuTime is expected to be enabled"); 80 } 81 82 long time = mbean.getCurrentThreadCpuTime(); 83 if (time < 0) { 84 throw new RuntimeException("Invalid CPU time returned = " + time); 85 } 86 87 if (!mbean.isThreadCpuTimeSupported()) { 88 return; 89 } 90 91 92 // Expected to be time1 >= time 93 long time1 = mbean.getThreadCpuTime(curThread.getId()); 94 if (time1 < time) { 95 throw new RuntimeException("CPU time " + time1 + 96 " expected >= " + time); 97 } 98 System.out.println(curThread.getName() + 99 " Current Thread Cpu Time = " + time + 100 " CPU time = " + time1); 101 102 for (int i = 0; i < NUM_THREADS; i++) { 103 threads[i] = new MyThread("MyThread-" + i); 104 threads[i].start(); 105 } 106 107 waitUntilThreadBlocked(); 108 109 for (int i = 0; i < NUM_THREADS; i++) { 110 times[i] = mbean.getThreadCpuTime(threads[i].getId()); 111 } 112 113 goSleep(200); 114 115 for (int i = 0; i < NUM_THREADS; i++) { 116 long newTime = mbean.getThreadCpuTime(threads[i].getId()); 117 if (times[i] > newTime) { 118 throw new RuntimeException("TEST FAILED: " + 119 threads[i].getName() + 120 " previous CPU time = " + times[i] + 121 " > current CPU time = " + newTime); 122 } 123 if ((times[i] + DELTA) < newTime) { 124 throw new RuntimeException("TEST FAILED: " + 125 threads[i].getName() + 126 " CPU time = " + newTime + 127 " previous CPU time " + times[i] + 128 " out of expected range"); 129 } 130 131 System.out.println(threads[i].getName() + 132 " Previous Cpu Time = " + times[i] + 133 " Current CPU time = " + newTime); 134 } 135 136 synchronized (obj) { 137 done = true; 138 obj.notifyAll(); 139 } 140 141 for (int i = 0; i < NUM_THREADS; i++) { 142 try { 143 threads[i].join(); 144 } catch (InterruptedException e) { 145 System.out.println("Unexpected exception is thrown."); 146 e.printStackTrace(System.out); 147 testFailed = true; 148 break; 149 } 150 } 151 if (testFailed) { 152 throw new RuntimeException("TEST FAILED"); 153 } 154 155 System.out.println("Test passed"); 156 } 157 158 159 private static void goSleep(long ms) throws Exception { 160 try { 161 Thread.sleep(ms); 162 } catch (InterruptedException e) { 163 System.out.println("Unexpected exception is thrown."); 164 throw e; 165 } 166 } 167 168 private static void waitUntilThreadBlocked() 169 throws Exception { 170 int count = 0; 171 while (count != NUM_THREADS) { 172 goSleep(100); 173 count = 0; 174 for (int i = 0; i < NUM_THREADS; i++) { 175 ThreadInfo info = mbean.getThreadInfo(threads[i].getId()); 176 if (info.getThreadState() == Thread.State.WAITING) { 177 count++; 178 } 179 } 180 } 181 } 182 183 static class MyThread extends Thread { 184 public MyThread(String name) { 185 super(name); 186 } 187 188 public void run() { 189 double sum = 0; 190 for (int i = 0; i < 5000; i++) { 191 double r = Math.random(); 192 double x = Math.pow(3, r); 193 sum += x - r; 194 } 195 synchronized (obj) { 196 while (!done) { 197 try { 198 obj.wait(); 199 } catch (InterruptedException e) { 200 System.out.println("Unexpected exception is thrown."); 201 e.printStackTrace(System.out); 202 testFailed = true; 203 break; 204 } 205 } 206 } 207 208 sum = 0; 209 for (int i = 0; i < 5000; i++) { 210 double r = Math.random(); 211 double x = Math.pow(3, r); 212 sum += x - r; 213 } 214 215 long utime1 = mbean.getCurrentThreadUserTime(); 216 long utime2 = mbean.getThreadUserTime(getId()); 217 long time1 = mbean.getCurrentThreadCpuTime(); 218 long time2 = mbean.getThreadCpuTime(getId()); 219 220 System.out.println(getName() + ": " + 221 "CurrentThreadUserTime = " + utime1 + 222 " ThreadUserTime = " + utime2); 223 System.out.println(getName() + ": " + 224 "CurrentThreadCpuTime = " + time1 + 225 " ThreadCpuTime = " + time2); 226 227 if (time1 > time2) { 228 throw new RuntimeException("TEST FAILED: " + getName() + 229 " CurrentThreadCpuTime = " + time1 + 230 " > ThreadCpuTime = " + time2); 231 } 232 /************* 233 * FIXME: Seems that on Solaris-sparc, 234 * It occasionally returns a different current thread user time > thread user time 235 if (utime1 > utime2) { 236 throw new RuntimeException("TEST FAILED: " + getName() + 237 " CurrentThreadUserTime = " + utime1 + 238 " > ThreadUserTime = " + utime2); 239 } 240 */ 241 } 242 } 243 244 }