Path: blob/master/test/jdk/javax/management/MBeanServer/ExceptionTest.java
41149 views
/*1* Copyright (c) 2008, 2015, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223/*24* @test25* @bug 805886526* @summary Checks that exceptions are correctly wired (compared to reference).27* @author Olivier Lagneau28* @modules java.management.rmi29* @run main/othervm/timeout=300 -DDEBUG_STANDARD ExceptionTest30*/3132import java.util.Map;33import java.util.HashMap;34import java.util.Properties;35import java.lang.reflect.Method;3637import java.lang.management.ManagementFactory;38import javax.management.ObjectName;39import javax.management.MBeanServer;40import javax.management.MBeanServerConnection;41import javax.management.remote.JMXConnector;42import javax.management.remote.JMXConnectorFactory;43import javax.management.remote.JMXConnectorServer;44import javax.management.remote.JMXConnectorServerFactory;45import javax.management.remote.JMXServiceURL;464748public class ExceptionTest {4950/*51* First Debug properties and arguments are collect in expected52* map (argName, value) format, then calls original test's run method.53*/54public static void main(String args[]) throws Exception {5556System.out.println("=================================================");5758// Parses parameters59Utils.parseDebugProperties();60Map<String, Object> map = Utils.parseParameters(args) ;6162// Run test63ExceptionTest test = new ExceptionTest();64test.run(map);6566}6768public void run(Map<String, Object> args) {6970System.out.println("ExceptionTest::run: Start");71int errorCount = 0;7273JMXConnectorServer cs = null;74JMXConnector cc = null;7576try {77// JMX MbeanServer used inside single VM as if remote.78MBeanServer mbs = ManagementFactory.getPlatformMBeanServer();7980JMXServiceURL url = new JMXServiceURL("rmi", null, 0);81cs = JMXConnectorServerFactory.newJMXConnectorServer(url, null, mbs);82cs.start();8384JMXServiceURL addr = cs.getAddress();85cc = JMXConnectorFactory.connect(addr);86MBeanServerConnection mbsc = cc.getMBeanServerConnection();8788// ----89ObjectName objName =90new ObjectName(ExceptionThrower.EXCEPTION_THROWER_NAME);91System.out.println("ExceptionTest::run: Create and register MBean " + objName);92mbsc.createMBean("ExceptionThrower", objName);93System.out.println("---- OK\n");9495// ----96System.out.println("ExceptionTest::run: Ask for exception(s)");97Object[] throwExceptionParam = new Object[1];98String[] throwExceptionSig = new String[]{"int"};99100for (int i = 0; i < ExceptionFactory.exceptions.size(); i++) {101throwExceptionParam[0] = new Integer(i);102103Exception ex =104(Exception)mbsc.invoke(objName,105"throwException", throwExceptionParam, throwExceptionSig);106107if ( ! matches(ex, ExceptionFactory.exceptions.get(i)) ) {108errorCount++;109System.out.println("ExceptionTest::run: (ERROR) Received \n["110+ ex + "]\nin place of\n["111+ ExceptionFactory.exceptions.get(i) + "]");112} else {113System.out.println("OK [" + ex + "]");114}115}116117System.out.println("---- DONE\n");118119} catch (Exception e) {120Utils.printThrowable(e, true);121throw new RuntimeException();122} finally {123try {124// Close JMX Connector Client125cc.close();126// Stop connertor server127cs.stop();128129} catch (Exception e) {130Utils.printThrowable(e, true);131throw new RuntimeException(132"Unable to either close connector client or stop connector server");133}134}135136if (errorCount == 0) {137System.out.println("ExceptionTest::run: Done without any error");138} else {139System.out.println("ExceptionTest::run: Done with " + errorCount140+ " error(s)");141throw new RuntimeException("errorCount = " + errorCount);142}143144System.out.println("ExceptionTest::run: Done");145}146147// Check both Exception are identical.148// That means:149// - none is null.150// - they are of the same Class.151// - if their respective messages aren't null they're equal.152// - if the message of one is null the message of the other is null too.153private boolean matches(Exception ex, Exception refex) {154if ( ex == null || refex == null ) {155System.out.println("(ERROR) Called with one or more null parameter; check "156+ ex + " against " + refex);157return false;158}159160String exClass = ex.getClass().getName();161String refexClass = refex.getClass().getName();162163if ( ! exClass.equals(refexClass) ) {164System.out.println("(ERROR) Class names don't match; check ["165+ exClass + "] against [" + refexClass + "]");166return false;167}168169String exMes = ex.getMessage();170String refexMes = refex.getMessage();171172if ( exMes != null && refexMes != null ) {173if ( ! exMes.equals(refexMes) ) {174System.out.println("(ERROR) Non null messages don't match; check ["175+ exMes + "] against [" + refexMes + "]");176return false;177}178} else if ( (exMes == null && refexMes != null)179|| (exMes != null && refexMes == null) ) {180System.out.println("(ERROR) Messages don't match; check [" + exMes181+ "] against [" + refexMes + "]");182}183184return true;185}186187// Utility inner class coming from JMX Tonga test suite.188// Also used by ExceptionFactory.189static class Utils {190191// DEBUG is printed depending on the DEBUG and DEBUG_LEVEL JAVA property192static final String DEBUG_HEADER = "[debug] ";193194// DEBUG levels195static int selectedDebugLevel = 0;196static final int DEBUG_STANDARD = 1;197static final int DEBUG_VERBOSE = 2; // Mainly used for stress tests198static final int DEBUG_ALL = DEBUG_STANDARD | DEBUG_VERBOSE;199200static void parseDebugProperties() {201int level = 0;202Properties p = System.getProperties();203204// get selected levels205if (p.getProperty("DEBUG_STANDARD") != null) {206level |= DEBUG_STANDARD;207}208209if (p.getProperty("DEBUG_VERBOSE") != null) {210level |= DEBUG_VERBOSE;211}212213if (p.getProperty("DEBUG_ALL") != null) {214level |= DEBUG_ALL;215}216217selectedDebugLevel = level;218}219220/**221* Reproduces the original parsing and collection of test parameters222* from the DTonga JMX test suite.223*224* Collects passed args and returns them in a map(argname, value) structure,225* which will be then propagated as necessary to various called methods.226*/227static Map<String, Object> parseParameters(String args[])228throws Exception {229debug(DEBUG_STANDARD, "TestRoot::parseParameters: Start");230HashMap<String, Object> map = new HashMap<>();231232for ( int i = 0; i < args.length; i++ ) {233if ( args[i].trim().startsWith("-") ) {234if ((i+1) < args.length && !args[i+1].startsWith("-") ) {235debug(DEBUG_STANDARD,236"TestRoot::parseParameters: added in map = " +237args[i] +238" with value " +239args[i+1]) ;240map.put(args[i].trim(), args[i+1].trim()) ;241} else if ((i+1) < args.length && args[i+1].startsWith("-") ||242(i+1) == args.length ) {243debug(DEBUG_STANDARD,244"TestRoot::parseParameters: added in map = " +245args[i] +246" with null value") ;247map.put(args[i].trim(), null) ;248} else {249System.out.println(250"TestRoot::parseParameters: (WARNING) not added in map = " +251args[i]) ;252}253}254}255256debug(DEBUG_STANDARD, "TestRoot::parseParameters: Done") ;257return map ;258}259260/**261* This method is to be used in all tests to print anything262* that is temporary.263* Printing is done only when debug is activated by the property DEBUG.264* Printing depends also on the DEBUG_LEVEL property.265* Here it encapsulates a System.out.println.266*/267static void debug(int level, String line) {268if ((selectedDebugLevel & level) != 0) {269System.out.println(DEBUG_HEADER + line);270}271}272273/**274* Do print stack trace when withStack is true.275* Does try to call getTargetException() and getTargetError() then276* print embedded stacks in the case of an Exception wrapping277* another Exception or an Error. Recurse until no more wrapping278* is found.279*/280static void printThrowable(Throwable theThro, boolean withStack) {281try {282if (withStack) {283theThro.printStackTrace(System.out);284}285if (theThro instanceof Exception) {286Exception t = (Exception) theThro;287Method target = null;288String blank = " ";289try {290target = t.getClass().getMethod("getTargetException",291(java.lang.Class<?>[]) null);292} catch (Exception ee) {293// OK: getTargetException method could be there or not294}295System.out.println(blank + t.getClass() + "==>" + t.getMessage());296while (target != null) {297try {298t = (Exception) target.invoke(t,299(java.lang.Object[]) null);300} catch (Exception ee) {301t = null;302}303try {304if (t != null) {305blank = blank + " ";306System.out.println(blank + t.getClass() + "==>" +307t.getMessage());308try {309target =310t.getClass().getMethod("getTargetException",311(java.lang.Class<?>[]) null);312} catch (Exception ee) {313// OK: getTargetException method could be there or not }314}315} else {316target = null;317}318} catch (Exception ee) {319target = null;320}321}322323// We may have exceptions wrapping an Error then it is324// getTargetError that is likely to be called325try {326target = ((Exception) theThro).getClass().getMethod("getTargetError",327(java.lang.Class<?>[]) null);328} catch (Exception ee) {329// OK: getTargetError method could be there or not330}331Throwable err = theThro;332while (target != null) {333try {334err = (Error) target.invoke(err,335(java.lang.Object[]) null);336} catch (Exception ee) {337err = null;338}339try {340if (err != null) {341blank = blank + " ";342System.out.println(blank + err.getClass() + "==>" +343err.getMessage());344if (withStack) {345err.printStackTrace(System.out);346}347try {348target = err.getClass().getMethod("getTargetError",349(java.lang.Class<?>[]) null);350} catch (Exception ee) {351// OK: getTargetError method could be there or not352}353} else {354target = null;355}356} catch (Exception ee) {357target = null;358}359}360} else {361System.out.println("Throwable is : " + theThro);362}363} catch (Throwable x) {364System.out.println("Exception : raised in printException : " + x);365}366}367}368369}370371372