1 /*
   2  * Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
   3  * 
   4  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   5  *
   6  * The contents of this file are subject to the terms of either the Universal Permissive License
   7  * v 1.0 as shown at http://oss.oracle.com/licenses/upl
   8  *
   9  * or the following license:
  10  *
  11  * Redistribution and use in source and binary forms, with or without modification, are permitted
  12  * provided that the following conditions are met:
  13  * 
  14  * 1. Redistributions of source code must retain the above copyright notice, this list of conditions
  15  * and the following disclaimer.
  16  * 
  17  * 2. Redistributions in binary form must reproduce the above copyright notice, this list of
  18  * conditions and the following disclaimer in the documentation and/or other materials provided with
  19  * the distribution.
  20  * 
  21  * 3. Neither the name of the copyright holder nor the names of its contributors may be used to
  22  * endorse or promote products derived from this software without specific prior written permission.
  23  * 
  24  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR
  25  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
  26  * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
  27  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  28  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  29  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
  30  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY
  31  * WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  32  */
  33 package org.openjdk.jmc.console.uitest.mbeanhelpers;
  34 
  35 import java.io.Serializable;
  36 import java.lang.management.ManagementFactory;
  37 import java.math.BigInteger;
  38 import java.util.ArrayList;
  39 import java.util.Arrays;
  40 import java.util.Collection;
  41 import java.util.Hashtable;
  42 import java.util.Map;
  43 
  44 import javax.management.AttributeChangeNotification;
  45 import javax.management.MBeanNotificationInfo;
  46 import javax.management.NotificationBroadcasterSupport;
  47 import javax.management.ObjectName;
  48 
  49 public class Testable extends NotificationBroadcasterSupport implements TestableMBean, Runnable, Serializable {
  50 
  51         private static final long serialVersionUID = 0;
  52 
  53         private boolean primitiveBoolean;
  54         private Boolean _boolean;
  55         private Boolean nullBoolean;
  56 
  57         private char primitiveCharacter;
  58         private Character character;
  59         private Character nullCharacter;
  60 
  61         private byte primitiveByte;
  62         private Byte _byte;
  63         private Byte nullByte;
  64 
  65         private short primitiveShort;
  66         private Short _short;
  67         private Short nullShort;
  68 
  69         private int primitiveInteger;
  70         private Integer integer;
  71         private Integer nullInteger;
  72 
  73         private long primitiveLong;
  74         private Long _long;
  75         private Long nullLong;
  76 
  77         private BigInteger bigInteger;
  78         private BigInteger nullBigInteger;
  79 
  80         private float primitiveFloat;
  81         private Float _float;
  82         private Float nullFloat;
  83 
  84         private double primitiveDouble;
  85         private Double _double;
  86         private Double nullDouble;
  87 
  88         private String string;
  89         private String nullString;
  90 
  91         private int[] primitiveArray;
  92         private int[] nullPrimitiveArray;
  93 
  94         private boolean[] primitivBooleanArray;
  95 
  96         private String[] stringArray;
  97         private String[] nullStringArray;
  98 
  99         private String[][] multiArray;
 100         private String[][] nullMultiArray;
 101 
 102         private Collection<String> collection;
 103         private Map<String, Integer> map;
 104         private Map<String, Integer> largeMap;
 105 
 106         private Object[] editableObjectArray;
 107         private Collection<Object> editableCollection;
 108         private Map<Integer, Object> editableMap;
 109 
 110         private long startTime;
 111         private long lastTime;
 112         private long updateTime;
 113         private long sequenceNumber = 0;
 114 
 115         private boolean stop = false;
 116 
 117         // @jmx.mbean.description("Abstract Webservice deployer")
 118         // @javax.management.ManagedAttribute
 119         public Testable() {
 120                 this("Hello there");
 121         }
 122 
 123         public Testable(String s) {
 124                 this(s, 5000);
 125         }
 126 
 127         /**
 128          * Creates a new Hello bean with given message and update time.
 129          *
 130          * @param s
 131          *            a message string
 132          * @param updateTime
 133          *            time between updates of alive time in ms
 134          */
 135         public Testable(String s, long updateTime) {
 136                 reinitSimpleData();
 137                 string = s;
 138                 lastTime = startTime = System.currentTimeMillis();
 139                 this.updateTime = updateTime;
 140                 Thread myTimer = new Thread(this);
 141                 myTimer.setDaemon(true);
 142                 myTimer.start();
 143         }
 144 
 145         @Override
 146         public void reinitSimpleData() {
 147                 primitiveBoolean = false;
 148                 _boolean = Boolean.TRUE;
 149                 nullBoolean = null;
 150 
 151                 primitiveCharacter = 'a';
 152                 character = Character.valueOf('0');
 153                 nullCharacter = null;
 154 
 155                 primitiveByte = Byte.MIN_VALUE;
 156                 _byte = Byte.valueOf(Byte.MAX_VALUE);
 157                 nullByte = null;
 158 
 159                 primitiveShort = Short.MIN_VALUE;
 160                 _short = Short.valueOf(Short.MAX_VALUE);
 161                 nullShort = null;
 162 
 163                 primitiveInteger = Integer.MIN_VALUE;
 164                 integer = Integer.valueOf(Integer.MAX_VALUE);
 165                 nullInteger = null;
 166 
 167                 primitiveLong = Long.MIN_VALUE;
 168                 _long = Long.valueOf(Long.MAX_VALUE);
 169                 nullLong = null;
 170 
 171                 bigInteger = new BigInteger("123456789012345678901234567890");
 172                 nullBigInteger = null;
 173 
 174                 primitiveFloat = Float.MIN_VALUE;
 175                 _float = Float.valueOf(Float.MAX_VALUE);
 176                 nullFloat = null;
 177 
 178                 primitiveDouble = Math.E;
 179                 _double = Double.valueOf(Math.PI);
 180                 nullDouble = null;
 181 
 182                 string = "Hello there";
 183                 nullString = null;
 184 
 185                 primitiveArray = new int[] {1, 2, 3};
 186                 nullPrimitiveArray = null;
 187                 primitivBooleanArray = new boolean[] {true, false};
 188 
 189                 stringArray = new String[256];
 190                 for (int i = 0; i < stringArray.length; i += 1) {
 191                         stringArray[i] = Integer.toHexString(i);
 192                 }
 193                 nullStringArray = null;
 194 
 195                 multiArray = new String[][] {{"1-1", "1-2", "1-3"}, {"2-2", "2-3"}, {null}, null};
 196                 nullMultiArray = null;
 197 
 198                 collection = Arrays.asList("one", "two", "three");
 199                 map = new Hashtable<>();
 200                 map.put("one", Integer.valueOf(1));
 201                 map.put("two", Integer.valueOf(2));
 202                 map.put("three", Integer.valueOf(3));
 203                 largeMap = new Hashtable<>();
 204                 for (int i = 0; i < 256; i += 1) {
 205                         largeMap.put("nr_" + i, Integer.valueOf(i));
 206                 }
 207 
 208                 editableObjectArray = new Object[] {1, Float.valueOf(1.5f), "two", null};
 209                 editableCollection = new ArrayList<>();
 210                 editableCollection.add(1);
 211                 editableCollection.add(Float.valueOf(1.5f));
 212                 editableCollection.add("two");
 213                 editableMap = new Hashtable<>();
 214                 editableMap.put(0, 1);
 215                 editableMap.put(1, Float.valueOf(1.5f));
 216                 editableMap.put(2, "two");
 217         }
 218 
 219         // Boolean
 220         @Override
 221         public boolean getPrimitiveBoolean() {
 222                 return primitiveBoolean;
 223         }
 224 
 225         @Override
 226         public void setPrimitiveBoolean(boolean b) {
 227                 primitiveBoolean = b;
 228         }
 229 
 230         @Override
 231         public boolean getReadOnlyPrimitiveBoolean() {
 232                 return primitiveBoolean;
 233         }
 234 
 235         @Override
 236         public Boolean getBoolean() {
 237                 return _boolean;
 238         }
 239 
 240         @Override
 241         public void setBoolean(Boolean b) {
 242                 _boolean = b;
 243         }
 244 
 245         @Override
 246         public Boolean getReadOnlyBoolean() {
 247                 return _boolean;
 248         }
 249 
 250         @Override
 251         public Boolean getNullBoolean() {
 252                 return nullBoolean;
 253         }
 254 
 255         @Override
 256         public void setNullBoolean(Boolean b) {
 257                 nullBoolean = b;
 258         }
 259 
 260         // Character
 261         @Override
 262         public char getPrimitiveCharacter() {
 263                 return primitiveCharacter;
 264         }
 265 
 266         @Override
 267         public void setPrimitiveCharacter(char c) {
 268                 primitiveCharacter = c;
 269         }
 270 
 271         @Override
 272         public char getReadOnlyPrimitiveCharacter() {
 273                 return primitiveCharacter;
 274         }
 275 
 276         @Override
 277         public Character getCharacter() {
 278                 return character;
 279         }
 280 
 281         @Override
 282         public void setCharacter(Character c) {
 283                 character = c;
 284         }
 285 
 286         @Override
 287         public Character getReadOnlyCharacter() {
 288                 return character;
 289         }
 290 
 291         @Override
 292         public Character getNullCharacter() {
 293                 return nullCharacter;
 294         }
 295 
 296         @Override
 297         public void setNullCharacter(Character c) {
 298                 nullCharacter = c;
 299         }
 300 
 301         // Byte
 302         @Override
 303         public byte getPrimitiveByte() {
 304                 return primitiveByte;
 305         }
 306 
 307         @Override
 308         public void setPrimitiveByte(byte b) {
 309                 primitiveByte = b;
 310         }
 311 
 312         @Override
 313         public byte getReadOnlyPrimitiveByte() {
 314                 return primitiveByte;
 315         }
 316 
 317         @Override
 318         public Byte getByte() {
 319                 return _byte;
 320         }
 321 
 322         @Override
 323         public void setByte(Byte b) {
 324                 _byte = b;
 325         }
 326 
 327         @Override
 328         public Byte getReadOnlyByte() {
 329                 return _byte;
 330         }
 331 
 332         @Override
 333         public Byte getNullByte() {
 334                 return nullByte;
 335         }
 336 
 337         @Override
 338         public void setNullByte(Byte b) {
 339                 nullByte = b;
 340         }
 341 
 342         // Short
 343         @Override
 344         public short getPrimitiveShort() {
 345                 return primitiveShort;
 346         }
 347 
 348         @Override
 349         public void setPrimitiveShort(short s) {
 350                 primitiveShort = s;
 351         }
 352 
 353         @Override
 354         public short getReadOnlyPrimitiveShort() {
 355                 return primitiveShort;
 356         }
 357 
 358         @Override
 359         public Short getShort() {
 360                 return _short;
 361         }
 362 
 363         @Override
 364         public void setShort(Short s) {
 365                 _short = s;
 366         }
 367 
 368         @Override
 369         public Short getReadOnlyShort() {
 370                 return _short;
 371         }
 372 
 373         @Override
 374         public Short getNullShort() {
 375                 return nullShort;
 376         }
 377 
 378         @Override
 379         public void setNullShort(Short s) {
 380                 nullShort = s;
 381         }
 382 
 383         // Integer
 384         @Override
 385         public int getPrimitiveInteger() {
 386                 return primitiveInteger;
 387         }
 388 
 389         @Override
 390         public void setPrimitiveInteger(int i) {
 391                 primitiveInteger = i;
 392         }
 393 
 394         @Override
 395         public int getReadOnlyPrimitiveInteger() {
 396                 return primitiveInteger;
 397         }
 398 
 399         @Override
 400         public Integer getInteger() {
 401                 return integer;
 402         }
 403 
 404         @Override
 405         public void setInteger(Integer i) {
 406                 integer = i;
 407         }
 408 
 409         @Override
 410         public Integer getReadOnlyInteger() {
 411                 return integer;
 412         }
 413 
 414         @Override
 415         public Integer getNullInteger() {
 416                 return nullInteger;
 417         }
 418 
 419         @Override
 420         public void setNullInteger(Integer i) {
 421                 nullInteger = i;
 422         }
 423 
 424         // Long
 425         @Override
 426         public long getPrimitiveLong() {
 427                 return primitiveLong;
 428         }
 429 
 430         @Override
 431         public void setPrimitiveLong(long l) {
 432                 primitiveLong = l;
 433         }
 434 
 435         @Override
 436         public long getReadOnlyPrimitiveLong() {
 437                 return primitiveLong;
 438         }
 439 
 440         @Override
 441         public Long getLong() {
 442                 return _long;
 443         }
 444 
 445         @Override
 446         public void setLong(Long l) {
 447                 _long = l;
 448         }
 449 
 450         @Override
 451         public Long getReadOnlyLong() {
 452                 return _long;
 453         }
 454 
 455         @Override
 456         public Long getNullLong() {
 457                 return nullLong;
 458         }
 459 
 460         @Override
 461         public void setNullLong(Long l) {
 462                 nullLong = l;
 463         }
 464 
 465         // BigInteger
 466         @Override
 467         public BigInteger getBigInteger() {
 468                 return bigInteger;
 469         }
 470 
 471         @Override
 472         public void setBigInteger(BigInteger bigInteger) {
 473                 this.bigInteger = bigInteger;
 474         }
 475 
 476         @Override
 477         public BigInteger getReadOnlyBigInteger() {
 478                 return bigInteger;
 479         }
 480 
 481         @Override
 482         public BigInteger getNullBigInteger() {
 483                 return nullBigInteger;
 484         }
 485 
 486         @Override
 487         public void setNullBigInteger(BigInteger bigInteger) {
 488                 nullBigInteger = bigInteger;
 489         }
 490 
 491         // Float
 492         @Override
 493         public float getPrimitiveFloat() {
 494                 return primitiveFloat;
 495         }
 496 
 497         @Override
 498         public void setPrimitiveFloat(float f) {
 499                 primitiveFloat = f;
 500         }
 501 
 502         @Override
 503         public float getReadOnlyPrimitiveFloat() {
 504                 return primitiveFloat;
 505         }
 506 
 507         @Override
 508         public Float getFloat() {
 509                 return _float;
 510         }
 511 
 512         @Override
 513         public void setFloat(Float f) {
 514                 _float = f;
 515         }
 516 
 517         @Override
 518         public Float getReadOnlyFloat() {
 519                 return _float;
 520         }
 521 
 522         @Override
 523         public Float getNullFloat() {
 524                 return nullFloat;
 525         }
 526 
 527         @Override
 528         public void setNullFloat(Float f) {
 529                 nullFloat = f;
 530         }
 531 
 532         // Double
 533         @Override
 534         public double getPrimitiveDouble() {
 535                 return primitiveDouble;
 536         }
 537 
 538         @Override
 539         public void setPrimitiveDouble(double d) {
 540                 primitiveDouble = d;
 541         }
 542 
 543         @Override
 544         public double getReadOnlyPrimitiveDouble() {
 545                 return primitiveDouble;
 546         }
 547 
 548         @Override
 549         public Double getDouble() {
 550                 return _double;
 551         }
 552 
 553         @Override
 554         public void setDouble(Double d) {
 555                 _double = d;
 556         }
 557 
 558         @Override
 559         public Double getReadOnlyDouble() {
 560                 return _double;
 561         }
 562 
 563         @Override
 564         public Double getNullDouble() {
 565                 return nullDouble;
 566         }
 567 
 568         @Override
 569         public void setNullDouble(Double d) {
 570                 nullDouble = d;
 571         }
 572 
 573         // Object
 574         @Override
 575         public Object getNullObject() {
 576                 return null;
 577         }
 578 
 579         // String
 580         @Override
 581         public String getString() {
 582                 return string;
 583         }
 584 
 585         @Override
 586         public void setString(String s) {
 587                 string = s;
 588         }
 589 
 590         @Override
 591         public String getReadOnlyString() {
 592                 return string;
 593         }
 594 
 595         @Override
 596         public void printString() {
 597                 System.out.println(string);
 598         }
 599 
 600         @Override
 601         public String getNullString() {
 602                 return nullString;
 603         }
 604 
 605         @Override
 606         public void setNullString(String s) {
 607                 nullString = s;
 608         }
 609 
 610         // primitive array
 611         @Override
 612         public int[] getPrimitiveArray() {
 613                 return primitiveArray;
 614         }
 615 
 616         @Override
 617         public void setPrimitiveArray(int[] array) {
 618                 primitiveArray = array;
 619         }
 620 
 621         @Override
 622         public int[] getReadOnlyPrimitiveArray() {
 623                 return primitiveArray;
 624         }
 625 
 626         @Override
 627         public int[] getNullPrimitiveArray() {
 628                 return nullPrimitiveArray;
 629         }
 630 
 631         @Override
 632         public void setNullPrimitiveArray(int[] array) {
 633                 nullPrimitiveArray = array;
 634         }
 635 
 636         @Override
 637         public boolean[] getPrimitiveBooleanArray() {
 638                 return primitivBooleanArray;
 639         }
 640 
 641         @Override
 642         public void setPrimitiveBooleanArray(boolean[] array) {
 643                 primitivBooleanArray = array;
 644         }
 645 
 646         // String array
 647         @Override
 648         public String[] getStringArray() {
 649                 return stringArray;
 650         }
 651 
 652         @Override
 653         public void setStringArray(String[] array) {
 654                 stringArray = array;
 655         }
 656 
 657         @Override
 658         public String[] getReadOnlyStringArray() {
 659                 return stringArray;
 660         }
 661 
 662         @Override
 663         public String[] getNullStringArray() {
 664                 return nullStringArray;
 665         }
 666 
 667         @Override
 668         public void setNullStringArray(String[] array) {
 669                 nullStringArray = array;
 670         }
 671 
 672         // Multi array
 673         @Override
 674         public String[][] getMultiArray() {
 675                 return multiArray;
 676         }
 677 
 678         @Override
 679         public String getMultiArrayAsString() {
 680                 String[] strings = new String[multiArray.length];
 681                 for (int i = 0; i < strings.length; i += 1) {
 682                         strings[i] = Arrays.toString(multiArray[i]);
 683                 }
 684                 return Arrays.toString(strings);
 685         }
 686 
 687         @Override
 688         public void setMultiArray(String[][] multiArray) {
 689                 this.multiArray = multiArray;
 690         }
 691 
 692         @Override
 693         public String[][] getReadOnlyMultiArray() {
 694                 return multiArray;
 695         }
 696 
 697         @Override
 698         public String[][] getNullMultiArray() {
 699                 return nullMultiArray;
 700         }
 701 
 702         @Override
 703         public void setNullMultiArray(String[][] multiArray) {
 704                 nullMultiArray = multiArray;
 705         }
 706 
 707         // Collection
 708         @Override
 709         public Collection<String> getCollection() {
 710                 return collection;
 711         }
 712 
 713         @Override
 714         public void setCollection(Collection<String> collection) {
 715                 this.collection = collection;
 716         }
 717 
 718         @Override
 719         public Collection<String> getReadOnlyCollection() {
 720                 return collection;
 721         }
 722 
 723         @Override
 724         public Collection<Object> getReadOnlyObjectCollection() {
 725                 Collection<Object> c = new ArrayList<>();
 726                 c.add("one");
 727                 c.add("two");
 728                 c.add("three");
 729                 return c;
 730         }
 731 
 732         @Override
 733         public Collection<Object> getReadOnlyNullCollection() {
 734                 return null;
 735         }
 736 
 737         public Collection<String> theReadOnlyCollection() {
 738                 return getReadOnlyCollection();
 739         }
 740 
 741         // Map
 742         @Override
 743         public Map<String, Integer> getMap() {
 744                 return map;
 745         }
 746 
 747         @Override
 748         public void setMap(Map<String, Integer> map) {
 749                 this.map = map;
 750         }
 751 
 752         @Override
 753         public Map<String, Integer> getReadOnlyMap() {
 754                 return map;
 755         }
 756 
 757         @Override
 758         public Map<String, Integer> getReadOnlyLargeMap() {
 759                 return largeMap;
 760         }
 761 
 762         @Override
 763         public Map<Object, Object> getReadOnlyNullMap() {
 764                 return null;
 765         }
 766 
 767         /****/
 768 
 769         /*
 770          * public Class<? extends TestMBean> getUneditableClass() { return getClass(); }
 771          */
 772 
 773         @Override
 774         public TestContainer getUneditableTestContainer() {
 775                 return new TestContainer(new String[] {"this", "is", "an", "opaque", "object"});
 776         }
 777 
 778         @Override
 779         public TestableMBean[] getUneditableArray() {
 780                 return new TestableMBean[] {this};
 781         }
 782 
 783         @Override
 784         public Object[] getUneditableObjectArray() {
 785                 return getUneditableArray();
 786         }
 787 
 788         @Override
 789         public Object[] getAnotherUneditableObjectArray() {
 790                 return new Object[] {this};
 791         }
 792 
 793         @Override
 794         public Object[] getEditableObjectArray() {
 795                 return editableObjectArray;
 796         }
 797 
 798         @Override
 799         public void setEditableObjectArray(Object[] editableObjectArray) {
 800                 this.editableObjectArray = editableObjectArray;
 801         }
 802 
 803         @Override
 804         public Collection<Object> getEditableCollection() {
 805                 return editableCollection;
 806         }
 807 
 808         @Override
 809         public void setEditableCollection(Collection<Object> editableCollection) {
 810                 this.editableCollection = editableCollection;
 811         }
 812 
 813         @Override
 814         public Map<Integer, Object> getEditableMap() {
 815                 return editableMap;
 816         }
 817 
 818         @Override
 819         public void setEditableMap(Map<Integer, Object> editableMap) {
 820                 this.editableMap = editableMap;
 821         }
 822 
 823         @Override
 824         public void run() {
 825                 while (!stop) {
 826                         synchronized (this) {
 827                                 long oldLastTime = lastTime;
 828                                 lastTime = System.currentTimeMillis();
 829 //                              System.out.println("Current time: " + getAliveTime());
 830                                 sendNotification(new AttributeChangeNotification(this, sequenceNumber++, lastTime, "Update",
 831                                                 "AliveTime", "long", Long.valueOf(oldLastTime - startTime),
 832                                                 Long.valueOf(lastTime - startTime)));
 833                                 try {
 834                                         wait(Math.max(1, updateTime));
 835                                 } catch (InterruptedException e) {
 836                                 }
 837                         }
 838                 }
 839         }
 840 
 841         @Override
 842         public long getAliveTime() {
 843                 return lastTime - startTime;
 844         }
 845 
 846         @Override
 847         public void resetAliveTime() {
 848                 synchronized (this) {
 849                         lastTime = startTime = System.currentTimeMillis();
 850                         notify();
 851                 }
 852         }
 853 
 854         @Override
 855         public long getUpdateTime() {
 856                 return updateTime;
 857         }
 858 
 859         @Override
 860         public void setUpdateTime(long updateTime) {
 861                 synchronized (this) {
 862                         this.updateTime = updateTime;
 863                         notify();
 864                 }
 865         }
 866 
 867         @Override
 868         public boolean killExistingHelloMBean(String name) {
 869                 try {
 870                         ObjectName mbeanName = new ObjectName("SimpleAgent:name=" + name);
 871                         ManagementFactory.getPlatformMBeanServer().unregisterMBean(mbeanName);
 872                         return true;
 873                 } catch (Exception e) {
 874                         e.printStackTrace();
 875                         return false;
 876                 }
 877         }
 878 
 879         @Override
 880         public boolean startNewHelloMBeanWithType(String name, String type) {
 881                 Testable test = new Testable();
 882                 ObjectName mbeanName = null;
 883 
 884                 try {
 885                         mbeanName = new ObjectName("SimpleAgent:name=" + name + ',' + type);
 886                         ManagementFactory.getPlatformMBeanServer().registerMBean(test, mbeanName);
 887                         return true;
 888                 } catch (Exception e) {
 889                         e.printStackTrace();
 890                         test.stop = true;
 891                         return false;
 892                 }
 893         }
 894 
 895         @Override
 896         public boolean startNewHelloMBean(String name) {
 897                 return startNewHelloMBeanWithType(name, "type=added");
 898         }
 899 
 900         @Override
 901         public boolean startManyNewHelloMBean(String name, int number) {
 902                 for (int i = 0; i < number; i += 1) {
 903                         if (!startNewHelloMBean(name + '_' + i)) {
 904                                 return false;
 905                         }
 906                 }
 907                 return true;
 908         }
 909 
 910         @Override
 911         public void gc() {
 912                 System.gc();
 913         }
 914 
 915         @Override
 916         public MBeanNotificationInfo[] getNotificationInfo() {
 917                 String[] types = new String[] {AttributeChangeNotification.ATTRIBUTE_CHANGE};
 918                 String name = AttributeChangeNotification.class.getName();
 919                 String description = "An attribute of this MBean has changed";
 920                 MBeanNotificationInfo info = new MBeanNotificationInfo(types, name, description);
 921                 return new MBeanNotificationInfo[] {info};
 922         }
 923 }