1 /* 2 * Copyright 2004 Sun Microsystems, Inc. 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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, 20 * CA 95054 USA or visit www.sun.com if you need additional information or 21 * have any questions. 22 */ 23 24 /* 25 * @test 26 * @bug 5024531 27 * @summary Test type mapping of the platform MXBean proxy 28 * returned from Management.newPlatformMXBeanProxy(). 29 * @author Mandy Chung 30 * 31 * @compile -source 1.5 ProxyTypeMapping.java 32 * @run main/othervm -verbose:gc ProxyTypeMapping 33 */ 34 import java.lang.management.*; 35 import javax.management.*; 36 import static java.lang.management.ManagementFactory.*; 37 import java.util.List; 38 import java.util.Map; 39 import java.util.Properties; 40 import com.sun.management.GcInfo; 41 42 public class ProxyTypeMapping { 43 private static MBeanServer server = 44 ManagementFactory.getPlatformMBeanServer(); 45 private static RuntimeMXBean runtime; 46 private static ThreadMXBean thread; 47 private static MemoryMXBean memory; 48 private static MemoryPoolMXBean heapPool = null; 49 private static MemoryPoolMXBean nonHeapPool = null; 50 public static void main(String[] argv) throws Exception { 51 runtime = newPlatformMXBeanProxy(server, 52 RUNTIME_MXBEAN_NAME, 53 RuntimeMXBean.class); 54 thread = newPlatformMXBeanProxy(server, 55 THREAD_MXBEAN_NAME, 56 ThreadMXBean.class); 57 memory = newPlatformMXBeanProxy(server, 58 MEMORY_MXBEAN_NAME, 59 MemoryMXBean.class); 60 61 // check notification emitter 62 MyListener listener = new MyListener(); 63 NotificationEmitter emitter = (NotificationEmitter) memory; 64 emitter.addNotificationListener(listener, null, null); 65 emitter.removeNotificationListener(listener); 66 67 List<MemoryPoolMXBean> pools = getMemoryPoolMXBeans(); 68 for (MemoryPoolMXBean p : pools) { 69 if (heapPool == null && 70 p.getType() == MemoryType.HEAP && 71 p.isUsageThresholdSupported() && 72 p.isCollectionUsageThresholdSupported()) { 73 heapPool = p; 74 } 75 if (nonHeapPool == null && 76 p.getType() == MemoryType.NON_HEAP && 77 p.isUsageThresholdSupported()) { 78 nonHeapPool = p; 79 } 80 } 81 82 checkEnum(); 83 checkList(); 84 checkMap(); 85 checkMemoryUsage(); 86 checkThreadInfo(); 87 88 checkOS(); 89 checkSunGC(); 90 91 System.out.println("Test passed."); 92 } 93 94 private static void checkEnum() throws Exception { 95 MemoryType type = heapPool.getType(); 96 if (type != MemoryType.HEAP) { 97 throw new RuntimeException("TEST FAILED: " + 98 " incorrect memory type for " + heapPool.getName()); 99 } 100 101 type = nonHeapPool.getType(); 102 if (type != MemoryType.NON_HEAP) { 103 throw new RuntimeException("TEST FAILED: " + 104 " incorrect memory type for " + nonHeapPool.getName()); 105 } 106 } 107 108 private static final String OPTION = "-verbose:gc"; 109 private static void checkList() throws Exception { 110 List<String> args = runtime.getInputArguments(); 111 if (args.size() < 1) { 112 throw new RuntimeException("TEST FAILED: " + 113 " empty input arguments"); 114 } 115 // check if -verbose:gc exists 116 boolean found = false; 117 for (String option : args) { 118 if (option.equals(OPTION)) { 119 found = true; 120 break; 121 } 122 } 123 if (!found) { 124 throw new RuntimeException("TEST FAILED: " + 125 "VM option " + OPTION + " not found"); 126 } 127 } 128 129 private static final String KEY1 = "test.property.key1"; 130 private static final String VALUE1 = "test.property.value1"; 131 private static final String KEY2 = "test.property.key2"; 132 private static final String VALUE2 = "test.property.value2"; 133 private static final String KEY3 = "test.property.key3"; 134 private static void checkMap() throws Exception { 135 // Add new system properties 136 System.setProperty(KEY1, VALUE1); 137 System.setProperty(KEY2, VALUE2); 138 139 Map<String,String> props1 = runtime.getSystemProperties(); 140 String value1 = props1.get(KEY1); 141 if (value1 == null || !value1.equals(VALUE1)) { 142 throw new RuntimeException("TEST FAILED: " + 143 KEY1 + " property found" + 144 " with value = " + value1 + 145 " but expected to be " + VALUE1); 146 } 147 148 String value2 = props1.get(KEY2); 149 if (value2 == null || !value2.equals(VALUE2)) { 150 throw new RuntimeException("TEST FAILED: " + 151 KEY2 + " property found" + 152 " with value = " + value2 + 153 " but expected to be " + VALUE2); 154 } 155 156 String value3 = props1.get(KEY3); 157 if (value3 != null) { 158 throw new RuntimeException("TEST FAILED: " + 159 KEY3 + " property found" + 160 " but should not exist" ); 161 } 162 } 163 164 private static void checkMemoryUsage() throws Exception { 165 // sanity check to have non-zero usage 166 MemoryUsage u1 = memory.getHeapMemoryUsage(); 167 MemoryUsage u2 = memory.getNonHeapMemoryUsage(); 168 MemoryUsage u3 = heapPool.getUsage(); 169 MemoryUsage u4 = nonHeapPool.getUsage(); 170 if (u1.getCommitted() <= 0 || 171 u2.getCommitted() <= 0 || 172 u3.getCommitted() <= 0 || 173 u4.getCommitted() <= 0) { 174 throw new RuntimeException("TEST FAILED: " + 175 " expected non-zero committed usage"); 176 } 177 memory.gc(); 178 MemoryUsage u5 = heapPool.getCollectionUsage(); 179 if (u5.getCommitted() <= 0) { 180 throw new RuntimeException("TEST FAILED: " + 181 " expected non-zero committed collected usage"); 182 } 183 } 184 185 private static void checkThreadInfo() throws Exception { 186 // assume all threads stay alive 187 long[] ids = thread.getAllThreadIds(); 188 ThreadInfo[] infos = thread.getThreadInfo(ids); 189 for (ThreadInfo ti : infos) { 190 printThreadInfo(ti); 191 } 192 infos = thread.getThreadInfo(ids, 2); 193 for (ThreadInfo ti : infos) { 194 printThreadInfo(ti); 195 } 196 long id = Thread.currentThread().getId(); 197 ThreadInfo info = thread.getThreadInfo(id); 198 printThreadInfo(info); 199 info = thread.getThreadInfo(id, 2); 200 printThreadInfo(info); 201 } 202 203 private static void printThreadInfo(ThreadInfo info) { 204 if (info == null) { 205 throw new RuntimeException("TEST FAILED: " + 206 " Null ThreadInfo"); 207 } 208 209 System.out.print(info.getThreadName()); 210 System.out.print(" id=" + info.getThreadId()); 211 System.out.println(" " + info.getThreadState()); 212 213 for (StackTraceElement s : info.getStackTrace()) { 214 System.out.println(s); 215 } 216 } 217 218 private static void checkOS() throws Exception { 219 com.sun.management.OperatingSystemMXBean os = 220 newPlatformMXBeanProxy(server, 221 OPERATING_SYSTEM_MXBEAN_NAME, 222 com.sun.management.OperatingSystemMXBean.class); 223 System.out.println("# CPUs = " + os.getAvailableProcessors()); 224 System.out.println("Committed virtual memory = " + 225 os.getCommittedVirtualMemorySize()); 226 } 227 228 private static void checkSunGC() throws Exception { 229 // Test com.sun.management proxy 230 List<GarbageCollectorMXBean> gcs = getGarbageCollectorMXBeans(); 231 for (GarbageCollectorMXBean gc : gcs) { 232 com.sun.management.GarbageCollectorMXBean sunGc = 233 newPlatformMXBeanProxy(server, 234 GARBAGE_COLLECTOR_MXBEAN_DOMAIN_TYPE + ",name=" + gc.getName(), 235 com.sun.management.GarbageCollectorMXBean.class); 236 GcInfo info = sunGc.getLastGcInfo(); 237 if (info != null) { 238 System.out.println("GC statistic for : " + gc.getName()); 239 printGcInfo(info); 240 } 241 } 242 } 243 private static void printGcInfo(GcInfo info) throws Exception { 244 System.out.print("GC #" + info.getId()); 245 System.out.print(" start:" + info.getStartTime()); 246 System.out.print(" end:" + info.getEndTime()); 247 System.out.println(" (" + info.getDuration() + "ms)"); 248 Map<String,MemoryUsage> usage = info.getMemoryUsageBeforeGc(); 249 250 for (Map.Entry<String,MemoryUsage> entry : usage.entrySet()) { 251 String poolname = entry.getKey(); 252 MemoryUsage busage = entry.getValue(); 253 MemoryUsage ausage = info.getMemoryUsageAfterGc().get(poolname); 254 if (ausage == null) { 255 throw new RuntimeException("After Gc Memory does not exist" + 256 " for " + poolname); 257 } 258 System.out.println("Usage for pool " + poolname); 259 System.out.println(" Before GC: " + busage); 260 System.out.println(" After GC: " + ausage); 261 } 262 } 263 264 static class MyListener implements NotificationListener { 265 public void handleNotification(Notification notif, Object handback) { 266 return; 267 } 268 } 269 }