1 /* 2 * Copyright (c) 2013, 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 package org.graalvm.compiler.debug.test; 24 25 import static org.junit.Assert.assertEquals; 26 import static org.junit.Assert.assertTrue; 27 28 import java.lang.management.ThreadMXBean; 29 30 import org.junit.Assert; 31 import org.junit.Assume; 32 import org.junit.Before; 33 import org.junit.Test; 34 35 import org.graalvm.compiler.debug.Debug; 36 import org.graalvm.compiler.debug.DebugCloseable; 37 import org.graalvm.compiler.debug.DebugConfig; 38 import org.graalvm.compiler.debug.DebugConfigScope; 39 import org.graalvm.compiler.debug.DebugTimer; 40 import org.graalvm.compiler.debug.Management; 41 42 @SuppressWarnings("try") 43 public class DebugTimerTest { 44 45 private static final ThreadMXBean threadMXBean = Management.getThreadMXBean(); 46 47 @Before 48 public void checkCapabilities() { 49 Assume.assumeTrue("skipping management interface test", threadMXBean.isCurrentThreadCpuTimeSupported()); 50 } 51 52 /** 53 * Actively spins the current thread for at least a given number of milliseconds in such a way 54 * that timers for the current thread keep ticking over. 55 * 56 * @return the number of milliseconds actually spent spinning which is guaranteed to be >= 57 * {@code ms} 58 */ 59 private static long spin(long ms) { 60 long start = threadMXBean.getCurrentThreadCpuTime(); 61 do { 62 long durationMS = (threadMXBean.getCurrentThreadCpuTime() - start) / 1000; 63 if (durationMS >= ms) { 64 return durationMS; 65 } 66 } while (true); 67 } 68 69 @Test 70 public void test1() { 71 DebugConfig debugConfig = Debug.fixedConfig(0, 0, false, false, true, false, false, null, null, System.out); 72 try (DebugConfigScope dcs = new DebugConfigScope(debugConfig); Debug.Scope s = Debug.scope("DebugTimerTest")) { 73 74 DebugTimer timerA = Debug.timer("TimerA"); 75 DebugTimer timerB = Debug.timer("TimerB"); 76 77 long spinA; 78 long spinB; 79 80 try (DebugCloseable a1 = timerA.start()) { 81 spinA = spin(50); 82 try (DebugCloseable b1 = timerB.start()) { 83 spinB = spin(50); 84 } 85 } 86 87 Assert.assertTrue(timerB.getCurrentValue() < timerA.getCurrentValue()); 88 if (timerA.getFlat() != null && timerB.getFlat() != null) { 89 assertTrue(spinB >= spinA || timerB.getFlat().getCurrentValue() < timerA.getFlat().getCurrentValue()); 90 assertEquals(timerA.getFlat().getCurrentValue(), timerA.getCurrentValue() - timerB.getFlat().getCurrentValue(), 10D); 91 } 92 } 93 } 94 95 @Test 96 public void test2() { 97 DebugConfig debugConfig = Debug.fixedConfig(0, 0, false, false, true, false, false, null, null, System.out); 98 try (DebugConfigScope dcs = new DebugConfigScope(debugConfig); Debug.Scope s = Debug.scope("DebugTimerTest")) { 99 DebugTimer timerC = Debug.timer("TimerC"); 100 try (DebugCloseable c1 = timerC.start()) { 101 spin(50); 102 try (DebugCloseable c2 = timerC.start()) { 103 spin(50); 104 try (DebugCloseable c3 = timerC.start()) { 105 spin(50); 106 try (DebugCloseable c4 = timerC.start()) { 107 spin(50); 108 try (DebugCloseable c5 = timerC.start()) { 109 spin(50); 110 } 111 } 112 } 113 } 114 } 115 if (timerC.getFlat() != null) { 116 assertEquals(timerC.getFlat().getCurrentValue(), timerC.getCurrentValue()); 117 } 118 } 119 } 120 121 @Test 122 public void test3() { 123 DebugConfig debugConfig = Debug.fixedConfig(0, 0, false, false, true, false, false, null, null, System.out); 124 try (DebugConfigScope dcs = new DebugConfigScope(debugConfig); Debug.Scope s = Debug.scope("DebugTimerTest")) { 125 126 DebugTimer timerD = Debug.timer("TimerD"); 127 DebugTimer timerE = Debug.timer("TimerE"); 128 129 long spinD1; 130 long spinE; 131 132 try (DebugCloseable d1 = timerD.start()) { 133 spinD1 = spin(50); 134 try (DebugCloseable e1 = timerE.start()) { 135 spinE = spin(50); 136 try (DebugCloseable d2 = timerD.start()) { 137 spin(50); 138 try (DebugCloseable d3 = timerD.start()) { 139 spin(50); 140 } 141 } 142 } 143 } 144 145 Assert.assertTrue(timerE.getCurrentValue() < timerD.getCurrentValue()); 146 if (timerD.getFlat() != null && timerE.getFlat() != null) { 147 assertTrue(spinE >= spinD1 || timerE.getFlat().getCurrentValue() < timerD.getFlat().getCurrentValue()); 148 assertEquals(timerD.getFlat().getCurrentValue(), timerD.getCurrentValue() - timerE.getFlat().getCurrentValue(), 10D); 149 } 150 } 151 } 152 }