1 /* 2 * Copyright (c) 2015, 2018, 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 import java.io.IOException; 25 import java.net.BindException; 26 import java.util.Properties; 27 import java.util.function.Predicate; 28 import static org.testng.Assert.*; 29 import org.testng.annotations.AfterMethod; 30 import org.testng.annotations.BeforeClass; 31 import org.testng.annotations.BeforeMethod; 32 import org.testng.annotations.BeforeTest; 33 import org.testng.annotations.Test; 34 35 import jdk.test.lib.process.ProcessTools; 36 37 38 /** 39 * @test 40 * @bug 8075926 41 * @key intermittent 42 * @summary Makes sure that the current management agent status is reflected 43 * in the related performance counters. 44 * 45 * @library /lib/testlibrary 46 * @library /test/lib 47 * 48 * @build jdk.testlibrary.* PortAllocator TestApp ManagementAgentJcmd 49 * @run testng/othervm -XX:+UsePerfData JMXStatusPerfCountersTest 50 */ 51 public class JMXStatusPerfCountersTest { 52 private final static String TEST_APP_NAME = "TestApp"; 53 54 private final static String REMOTE_STATUS_KEY = "sun.management.JMXConnectorServer.remote.enabled"; 55 56 private static ProcessBuilder testAppPb; 57 private Process testApp; 58 59 private ManagementAgentJcmd jcmd; 60 61 @BeforeClass 62 public static void setupClass() throws Exception { 63 testAppPb = ProcessTools.createJavaProcessBuilder( 64 "-XX:+UsePerfData", 65 "-cp", System.getProperty("test.class.path"), 66 TEST_APP_NAME 67 ); 68 } 69 70 @BeforeTest 71 public void setup() { 72 jcmd = new ManagementAgentJcmd(TEST_APP_NAME, false); 73 } 74 75 @BeforeMethod 76 public void startTestApp() throws Exception { 77 testApp = ProcessTools.startProcess( 78 TEST_APP_NAME, testAppPb, 79 (Predicate<String>)l->l.trim().equals("main enter") 80 ); 81 } 82 83 @AfterMethod 84 public void stopTestApp() throws Exception { 85 testApp.getOutputStream().write(1); 86 testApp.getOutputStream().flush(); 87 testApp.waitFor(); 88 testApp = null; 89 } 90 91 /** 92 * The 'sun.management.JMXConnectorServer.remote.enabled' counter must not be 93 * exported if the remote agent is not enabled. 94 * @throws Exception 95 */ 96 @Test 97 public void testNotInitializedRemote() throws Exception { 98 assertFalse( 99 getCounters().containsKey(REMOTE_STATUS_KEY), 100 "Unexpected occurrence of " + REMOTE_STATUS_KEY + " in perf counters" 101 ); 102 } 103 104 /** 105 * After enabling the remote agent the 'sun.management.JMXConnectorServer.remote.enabled' 106 * counter will be exported with value of '0' - corresponding to the actual 107 * version of the associated remote connector perf counters. 108 * @throws Exception 109 */ 110 @Test 111 public void testRemoteEnabled() throws Exception { 112 while (true) { 113 try { 114 int[] ports = PortAllocator.allocatePorts(1); 115 jcmd.start( 116 "jmxremote.port=" + ports[0], 117 "jmxremote.authenticate=false", 118 "jmxremote.ssl=false" 119 ); 120 String v = getCounters().getProperty(REMOTE_STATUS_KEY); 121 assertNotNull(v); 122 assertEquals("0", v); 123 return; 124 } catch (BindException e) { 125 System.out.println("Failed to allocate ports. Retrying ..."); 126 } 127 } 128 } 129 130 /** 131 * After disabling the remote agent the value of 'sun.management.JMXConnectorServer.remote.enabled' 132 * counter will become '-1'. 133 * @throws Exception 134 */ 135 @Test 136 public void testRemoteDisabled() throws Exception { 137 while (true) { 138 try { 139 int[] ports = PortAllocator.allocatePorts(1); 140 jcmd.start( 141 "jmxremote.port=" + ports[0], 142 "jmxremote.authenticate=false", 143 "jmxremote.ssl=false" 144 ); 145 jcmd.stop(); 146 String v = getCounters().getProperty(REMOTE_STATUS_KEY); 147 assertNotNull(v); 148 assertEquals("-1", v); 149 return; 150 } catch (BindException e) { 151 System.out.println("Failed to allocate ports. Retrying ..."); 152 } 153 } 154 } 155 156 /** 157 * Each subsequent re-enablement of the remote agent must keep the value of 158 * 'sun.management.JMXConnectorServer.remote.enabled' counter in sync with 159 * the actual version of the associated remote connector perf counters. 160 * @throws Exception 161 */ 162 @Test 163 public void testRemoteReEnabled() throws Exception { 164 while (true) { 165 try { 166 int[] ports = PortAllocator.allocatePorts(1); 167 jcmd.start( 168 "jmxremote.port=" + ports[0], 169 "jmxremote.authenticate=false", 170 "jmxremote.ssl=false" 171 ); 172 jcmd.stop(); 173 jcmd.start( 174 "jmxremote.port=" + ports[0], 175 "jmxremote.authenticate=false", 176 "jmxremote.ssl=false" 177 ); 178 179 String v = getCounters().getProperty(REMOTE_STATUS_KEY); 180 assertNotNull(v); 181 assertEquals("1", v); 182 return; 183 } catch (BindException e) { 184 System.out.println("Failed to allocate ports. Retrying ..."); 185 } 186 } 187 } 188 189 private Properties getCounters() throws IOException, InterruptedException { 190 return jcmd.perfCounters("sun\\.management\\.JMXConnectorServer\\..*"); 191 } 192 }