001: /*
002: * JBoss, Home of Professional Open Source.
003: * Copyright 2006, Red Hat Middleware LLC, and individual contributors
004: * as indicated by the @author tags. See the copyright.txt file in the
005: * distribution for a full listing of individual contributors.
006: *
007: * This is free software; you can redistribute it and/or modify it
008: * under the terms of the GNU Lesser General Public License as
009: * published by the Free Software Foundation; either version 2.1 of
010: * the License, or (at your option) any later version.
011: *
012: * This software is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * Lesser General Public License for more details.
016: *
017: * You should have received a copy of the GNU Lesser General Public
018: * License along with this software; if not, write to the Free
019: * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
021: */
022: package org.jboss.test.classloader.concurrentload;
023:
024: import java.util.HashSet;
025: import java.util.Timer;
026: import java.util.TimerTask;
027: import java.util.Vector;
028:
029: import org.jboss.logging.Logger;
030: import org.jboss.system.Service;
031: import org.jboss.system.ServiceMBeanSupport;
032:
033: /** A multi-threaded class loading test service.
034: *
035: * @author <a href="mailto:sacha.labourey@cogito-info.ch">Sacha Labourey</a>.
036: * @author Scott.Stark@jboss.org
037: * @version $Revision: 1.2
038: */
039: public class ConcurrentLoader extends ServiceMBeanSupport implements
040: ConcurrentLoaderMBean {
041:
042: // Constants -----------------------------------------------------
043:
044: // Attributes ----------------------------------------------------
045:
046: public Object lock = new Object();
047:
048: public final static int MAX_CLASSES = 10;
049: public final static int NUMBER_OF_LOADING = 10;
050: public final static int NUMBER_OF_THREADS = 20;
051: private HashSet classes = new HashSet();
052: private Vector ungarbaged = new Vector();
053: private Timer newInstanceTimer;
054: private int doneCount;
055:
056: // Static --------------------------------------------------------
057:
058: // Constructors --------------------------------------------------
059:
060: public ConcurrentLoader() {
061: }
062:
063: // Public --------------------------------------------------------
064:
065: // Z implementation ----------------------------------------------
066:
067: // ServiceMBeanSupport overrides ---------------------------------------------------
068:
069: protected void createService() throws Exception {
070: log.debug("Creating " + NUMBER_OF_THREADS + " threads...");
071: newInstanceTimer = new Timer(true);
072: newInstanceTimer.scheduleAtFixedRate(new NewInstanceTask(), 0,
073: 100);
074: doneCount = 0;
075: for (int t = 0; t < NUMBER_OF_THREADS; t++) {
076: ConcurrentLoader.Loader loader = new ConcurrentLoader.Loader(
077: t);
078: loader.start();
079: ungarbaged.add(loader);
080: }
081: log.info("All threads created");
082: Thread.sleep(2000);
083:
084: synchronized (lock) {
085: lock.notifyAll();
086: }
087: log.info("Unlocked all Loader threads");
088: synchronized (lock) {
089: while (doneCount < NUMBER_OF_THREADS) {
090: lock.wait();
091: }
092: log.info("Loader doneCount=" + doneCount);
093: }
094: log.info("All Loaders are done");
095: newInstanceTimer.cancel();
096: }
097:
098: protected void stopService() throws Exception {
099: newInstanceTimer.cancel();
100: classes.clear();
101: ungarbaged.clear();
102: }
103:
104: // Package protected ---------------------------------------------
105:
106: // Protected -----------------------------------------------------
107:
108: // Private -------------------------------------------------------
109:
110: // Inner classes -------------------------------------------------
111:
112: class NewInstanceTask extends TimerTask {
113: Logger theLog;
114:
115: NewInstanceTask() {
116: this .theLog = ConcurrentLoader.this .getLog();
117: }
118:
119: /** Create an instance of a class and exit
120: */
121: public void run() {
122: int size = classes.size();
123: Class[] theClasses = new Class[size];
124: classes.toArray(theClasses);
125: theLog.info("NewInstanceTask, creating " + size
126: + " instances");
127: for (int c = 0; c < theClasses.length; c++) {
128: try {
129: Class clazz = theClasses[c];
130: Object obj = clazz.newInstance();
131: theLog.debug("Created instance=" + obj);
132: } catch (Throwable t) {
133: t.printStackTrace();
134: }
135: }
136: }
137: }
138:
139: class Loader extends Thread {
140: int classid = 0;
141: Logger theLog;
142:
143: public Loader(int classid) {
144: super ("ConcurrentLoader - Thread #" + classid);
145: this .classid = classid;
146: this .theLog = ConcurrentLoader.this .getLog();
147: }
148:
149: public void run() {
150: int modId = classid % MAX_CLASSES;
151: String className = this .getClass().getPackage().getName()
152: + ".Anyclass" + modId;
153: ClassLoader cl = this .getContextClassLoader();
154:
155: synchronized (lock) {
156: try {
157: theLog.debug("Thread ready: " + classid);
158: lock.wait();
159: } catch (Exception e) {
160: theLog.error("Error during wait", e);
161: }
162: }
163: theLog.debug("loading class... " + className);
164: for (int i = 0; i < NUMBER_OF_LOADING; i++) {
165: theLog.debug("loading class with id " + classid
166: + " for the " + i + "th time");
167: try {
168: theLog.debug("before load...");
169: long sleep = (long) (1000 * Math.random());
170: Thread.sleep(sleep);
171: Class clazz = cl.loadClass(className);
172: classes.add(clazz);
173: Object obj = null; //clazz.newInstance();
174: theLog.debug("Class " + className + " loaded, obj="
175: + obj);
176: } catch (Throwable e) {
177: theLog.debug(
178: "Failed to load class and create instance",
179: e);
180: }
181: }
182: theLog.debug("...Done loading classes. " + classid);
183: synchronized (lock) {
184: doneCount++;
185: lock.notify();
186: }
187: }
188: }
189:
190: }
|