KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jboss > mx > loading > DomainClassLoaderUCLImpl


1 package org.jboss.mx.loading;
2
3 import java.net.URL JavaDoc;
4 import java.security.CodeSource JavaDoc;
5 import java.security.Permission JavaDoc;
6 import java.security.PermissionCollection JavaDoc;
7 import java.security.Policy JavaDoc;
8 import java.security.ProtectionDomain JavaDoc;
9 import java.util.Enumeration JavaDoc;
10
11 import javax.management.MBeanServer JavaDoc;
12 import javax.management.MalformedObjectNameException JavaDoc;
13 import javax.management.ObjectName JavaDoc;
14
15 import org.jboss.logging.Logger;
16
17 /**
18 * A port of the UnifiedClassLoader3 to a DomainClassLoader
19 *
20 * @author <a HREF="marc.fleury@jboss.org">Marc Fleury</a>
21 * @author <a HREF="christoph.jung@jboss.org">Christoph G. Jung</a>
22 * @author <a HREF="scott.stark@jboss.org">Scott Stark</a>
23 * @author <a HREF="juha@jboss.org">Juha Lindfors</a>
24 * @author <a HREF="bill@jboss.org">Bill Burke</a>
25 * @version $Revision: 44243 $
26 */

27 public class DomainClassLoaderUCLImpl extends LegacyDomainClassLoader
28    implements UnifiedClassLoaderMBean
29 {
30    // Static --------------------------------------------------------
31

32    private static final Logger log = Logger.getLogger(DomainClassLoaderUCLImpl.class);
33
34    // Attributes ----------------------------------------------------
35

36    // Constructors --------------------------------------------------
37
/**
38     * Construct a DomainClassLoaderUCLImpl with the given classpath and register
39     * it to the given repository.
40     * @param cp - the loader classpath
41     * @param repository - the repository this classloader delegates to
42     */

43    public DomainClassLoaderUCLImpl(URL JavaDoc[] cp, LoaderRepositoryDomain repository)
44    {
45       super(cp, null);
46
47       // register this loader to the given repository
48
repository.addClassLoader(this);
49    }
50
51    // Public --------------------------------------------------------
52

53    /** Obtain the ObjectName under which the UCL can be registered with the
54     JMX server. This creates a name of the form "jmx.loading:UCL=hashCode"
55     since we don't currently care that UCL be easily queriable.
56     */

57    public ObjectName JavaDoc getObjectName() throws MalformedObjectNameException JavaDoc
58    {
59       String JavaDoc name = "jmx.loading:UCL="+Integer.toHexString(super.hashCode());
60       return new ObjectName JavaDoc(name);
61    }
62
63    /**
64     * Get the class loader package names from the class loader URLs
65     */

66    public String JavaDoc[] getPackageNames()
67    {
68       UnifiedLoaderRepositoryDCL ulr = (UnifiedLoaderRepositoryDCL) domain;
69       return ulr.getPackageNames(this);
70    }
71
72    public void unregister()
73    {
74       super.unregister();
75    }
76
77    public synchronized Class JavaDoc loadClassImpl(String JavaDoc name, boolean resolve, int stopAt)
78       throws ClassNotFoundException JavaDoc
79    {
80       loadClassDepth ++;
81       boolean trace = log.isTraceEnabled();
82
83       if( trace )
84          log.trace("loadClassImpl, name="+name+", resolve="+resolve);
85       if( domain == null )
86       {
87          // If we have been undeployed we can still try locally
88
try
89          {
90             return super.loadClass(name, resolve);
91          }
92          catch (ClassNotFoundException JavaDoc ignored)
93          {
94          }
95          String JavaDoc msg = "Invalid use of destroyed classloader, UCL destroyed at:";
96          throw new ClassNotFoundException JavaDoc(msg, this.unregisterTrace);
97       }
98
99       /* Since loadClass can be called from loadClassInternal with the monitor
100          already held, we need to determine if there is a ClassLoadingTask
101          which requires this UCL. If there is, we release the UCL monitor
102          so that the ClassLoadingTask can use the UCL.
103        */

104       boolean acquired = attempt(1);
105       while( acquired == false )
106       {
107          /* Another thread needs this UCL to load a class so release the
108           monitor acquired by the synchronized method. We loop until
109           we can acquire the class loading lock.
110          */

111         try
112          {
113             if( trace )
114                log.trace("Waiting for loadClass lock");
115             this.wait();
116          }
117          catch(InterruptedException JavaDoc ignore)
118          {
119          }
120          acquired = attempt(1);
121       }
122
123       ClassLoadingTaskDCL task = null;
124       try
125       {
126          Thread JavaDoc t = Thread.currentThread();
127          // Register this thread as owning this UCL
128
if( loadLock.holds() == 1 )
129             LoadMgrDCL.registerLoaderThread(this, t);
130
131          // Create a class loading task and submit it to the repository
132
task = new ClassLoadingTaskDCL(name, this, t, stopAt);
133          /* Process class loading tasks needing this UCL until our task has
134             been completed by the thread owning the required UCL(s).
135           */

136          UnifiedLoaderRepositoryDCL repository = (UnifiedLoaderRepositoryDCL) domain;
137          if( LoadMgrDCL.beginLoadTask(task, repository) == false )
138          {
139             while( task.threadTaskCount != 0 )
140             {
141                try
142                {
143                   LoadMgrDCL.nextTask(t, task, repository);
144                }
145                catch(InterruptedException JavaDoc e)
146                {
147                   // Abort the load or retry?
148
break;
149                }
150             }
151          }
152       }
153       finally
154       {
155          // Unregister as the UCL owner to reschedule any remaining load tasks
156
if( loadLock.holds() == 1 )
157             LoadMgrDCL.endLoadTask(task);
158          // Notify any threads waiting to use this UCL
159
this.release();
160          this.notifyAll();
161          loadClassDepth --;
162       }
163
164       if( task.loadedClass == null )
165       {
166          if( task.loadException instanceof ClassNotFoundException JavaDoc )
167             throw (ClassNotFoundException JavaDoc) task.loadException;
168          else if( task.loadException instanceof NoClassDefFoundError JavaDoc )
169             throw (NoClassDefFoundError JavaDoc) task.loadException;
170          else if( task.loadException != null )
171          {
172             if( log.isTraceEnabled() )
173                log.trace("Unexpected error during load of:"+name, task.loadException);
174             String JavaDoc msg = "Unexpected error during load of: "+name
175                + ", msg="+task.loadException.getMessage();
176             ClassNotFoundException JavaDoc cnfe = new ClassNotFoundException JavaDoc(msg, task.loadException);
177             throw cnfe;
178          }
179          // Assert that loadedClass is not null
180
else
181             throw new IllegalStateException JavaDoc("ClassLoadingTask.loadedTask is null, name: "+name);
182       }
183
184       return task.loadedClass;
185    }
186
187    // URLClassLoader overrides --------------------------------------
188

189    /** Override the permissions accessor to use the CodeSource
190     based on the original URL if one exists. This allows the
191     security policy to be defined in terms of the static URL
192     namespace rather than the local copy or nested URL.
193     This builds a PermissionCollection from:
194     1. The origURL CodeSource
195     2. The argument CodeSource
196     3. The Policy.getPermission(origURL CodeSource)
197
198     This is necessary because we cannot define the CodeSource the
199     SecureClassLoader uses to register the class under.
200
201     @param cs the location and signatures of the codebase.
202     */

203    protected PermissionCollection JavaDoc getPermissions(CodeSource JavaDoc cs)
204    {
205       CodeSource JavaDoc permCS = cs;
206       Policy JavaDoc policy = Policy.getPolicy();
207       PermissionCollection JavaDoc perms = super.getPermissions(permCS);
208       PermissionCollection JavaDoc perms2 = super.getPermissions(cs);
209       PermissionCollection JavaDoc perms3 = policy.getPermissions(permCS);
210       Enumeration JavaDoc iter = perms2.elements();
211       while( iter.hasMoreElements() )
212          perms.add((Permission JavaDoc) iter.nextElement());
213       iter = perms3.elements();
214       while( iter.hasMoreElements() )
215          perms.add((Permission JavaDoc) iter.nextElement());
216       if( log.isTraceEnabled() )
217          log.trace("getPermissions, cp: "+getURLs()+" -> "+perms);
218       return perms;
219    }
220
221 }
222
Popular Tags