KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > core > runtime > internal > adaptor > EclipseClassLoadingHook


1 /*******************************************************************************
2  * Copyright (c) 2005, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  *******************************************************************************/

11
12 package org.eclipse.core.runtime.internal.adaptor;
13
14 import java.io.File JavaDoc;
15 import java.security.ProtectionDomain JavaDoc;
16 import java.util.ArrayList JavaDoc;
17 import java.util.jar.Attributes JavaDoc;
18 import java.util.jar.Manifest JavaDoc;
19 import org.eclipse.osgi.baseadaptor.*;
20 import org.eclipse.osgi.baseadaptor.bundlefile.BundleEntry;
21 import org.eclipse.osgi.baseadaptor.bundlefile.BundleFile;
22 import org.eclipse.osgi.baseadaptor.hooks.ClassLoadingHook;
23 import org.eclipse.osgi.baseadaptor.loader.*;
24 import org.eclipse.osgi.framework.adaptor.BundleProtectionDomain;
25 import org.eclipse.osgi.framework.adaptor.ClassLoaderDelegate;
26 import org.eclipse.osgi.internal.baseadaptor.BaseClassLoadingHook;
27 import org.eclipse.osgi.internal.baseadaptor.BaseStorageHook;
28
29 public class EclipseClassLoadingHook implements ClassLoadingHook, HookConfigurator {
30     private static String JavaDoc[] NL_JAR_VARIANTS = buildNLJarVariants(EclipseEnvironmentInfo.getDefault().getNL());
31     private static boolean DEFINE_PACKAGES;
32     private static String JavaDoc[] LIB_VARIANTS = buildLibraryVariants();
33
34     static {
35         try {
36             Class.forName("java.lang.Package"); //$NON-NLS-1$
37
DEFINE_PACKAGES = true;
38         } catch (ClassNotFoundException JavaDoc e) {
39             DEFINE_PACKAGES = false;
40         }
41     }
42
43     private static String JavaDoc[] buildLibraryVariants() {
44         ArrayList JavaDoc result = new ArrayList JavaDoc();
45         EclipseEnvironmentInfo info = EclipseEnvironmentInfo.getDefault();
46         result.add("ws/" + info.getWS() + "/"); //$NON-NLS-1$ //$NON-NLS-2$
47
result.add("os/" + info.getOS() + "/" + info.getOSArch() + "/"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
48
result.add("os/" + info.getOS() + "/"); //$NON-NLS-1$ //$NON-NLS-2$
49
String JavaDoc nl = info.getNL();
50         nl = nl.replace('_', '/');
51         while (nl.length() > 0) {
52             result.add("nl/" + nl + "/"); //$NON-NLS-1$ //$NON-NLS-2$
53
int i = nl.lastIndexOf('/');
54             nl = (i < 0) ? "" : nl.substring(0, i); //$NON-NLS-1$
55
}
56         result.add(""); //$NON-NLS-1$
57
return (String JavaDoc[]) result.toArray(new String JavaDoc[result.size()]);
58     }
59
60     public byte[] processClass(String JavaDoc name, byte[] classbytes, ClasspathEntry classpathEntry, BundleEntry entry, ClasspathManager manager) {
61         if (!DEFINE_PACKAGES)
62             return null;
63         // Define the package if it is not the default package.
64
int lastIndex = name.lastIndexOf('.');
65         if (lastIndex < 0)
66             return null;
67         String JavaDoc packageName = name.substring(0, lastIndex);
68         Object JavaDoc pkg = manager.getBaseClassLoader().publicGetPackage(packageName);
69         if (pkg != null)
70             return null;
71
72         // get info about the package from the classpath entry's manifest.
73
String JavaDoc specTitle = null, specVersion = null, specVendor = null, implTitle = null, implVersion = null, implVendor = null;
74         ClasspathManifest cpm = (ClasspathManifest) classpathEntry.getUserObject(ClasspathManifest.KEY);
75         if (cpm == null) {
76             cpm = new ClasspathManifest();
77             classpathEntry.addUserObject(cpm);
78         }
79         Manifest JavaDoc mf = cpm.getManifest(classpathEntry, manager);
80         if (mf != null) {
81             Attributes JavaDoc mainAttributes = mf.getMainAttributes();
82             String JavaDoc dirName = packageName.replace('.', '/') + '/';
83             Attributes JavaDoc packageAttributes = mf.getAttributes(dirName);
84             boolean noEntry = false;
85             if (packageAttributes == null) {
86                 noEntry = true;
87                 packageAttributes = mainAttributes;
88             }
89             specTitle = packageAttributes.getValue(Attributes.Name.SPECIFICATION_TITLE);
90             if (specTitle == null && !noEntry)
91                 specTitle = mainAttributes.getValue(Attributes.Name.SPECIFICATION_TITLE);
92             specVersion = packageAttributes.getValue(Attributes.Name.SPECIFICATION_VERSION);
93             if (specVersion == null && !noEntry)
94                 specVersion = mainAttributes.getValue(Attributes.Name.SPECIFICATION_VERSION);
95             specVendor = packageAttributes.getValue(Attributes.Name.SPECIFICATION_VENDOR);
96             if (specVendor == null && !noEntry)
97                 specVendor = mainAttributes.getValue(Attributes.Name.SPECIFICATION_VENDOR);
98             implTitle = packageAttributes.getValue(Attributes.Name.IMPLEMENTATION_TITLE);
99             if (implTitle == null && !noEntry)
100                 implTitle = mainAttributes.getValue(Attributes.Name.IMPLEMENTATION_TITLE);
101             implVersion = packageAttributes.getValue(Attributes.Name.IMPLEMENTATION_VERSION);
102             if (implVersion == null && !noEntry)
103                 implVersion = mainAttributes.getValue(Attributes.Name.IMPLEMENTATION_VERSION);
104             implVendor = packageAttributes.getValue(Attributes.Name.IMPLEMENTATION_VENDOR);
105             if (implVendor == null && !noEntry)
106                 implVendor = mainAttributes.getValue(Attributes.Name.IMPLEMENTATION_VENDOR);
107         }
108         // The package is not defined yet define it before we define the class.
109
// TODO still need to seal packages.
110
manager.getBaseClassLoader().publicDefinePackage(packageName, specTitle, specVersion, specVendor, implTitle, implVersion, implVendor, null);
111         // not doing any byte processing
112
return null;
113     }
114
115     public boolean addClassPathEntry(ArrayList JavaDoc cpEntries, String JavaDoc cp, ClasspathManager hostmanager, BaseData sourcedata, ProtectionDomain JavaDoc sourcedomain) {
116         String JavaDoc var = hasPrefix(cp);
117         if (var != null)
118             // find internal library using eclipse predefined vars
119
return addInternalClassPath(var, cpEntries, cp, hostmanager, sourcedata, sourcedomain);
120         if (cp.startsWith(BaseStorageHook.EXTERNAL_LIB_PREFIX)) {
121             cp = cp.substring(BaseStorageHook.EXTERNAL_LIB_PREFIX.length());
122             // find external library using system property substitution
123
ClasspathEntry cpEntry = hostmanager.getExternalClassPath(BaseStorageHook.substituteVars(cp), sourcedata, sourcedomain);
124             if (cpEntry != null) {
125                 cpEntries.add(cpEntry);
126                 return true;
127             }
128         }
129         return false;
130     }
131
132     private boolean addInternalClassPath(String JavaDoc var, ArrayList JavaDoc cpEntries, String JavaDoc cp, ClasspathManager hostloader, BaseData sourcedata, ProtectionDomain JavaDoc sourcedomain) {
133         if (var.equals("ws")) //$NON-NLS-1$
134
return ClasspathManager.addClassPathEntry(cpEntries, "ws/" + EclipseEnvironmentInfo.getDefault().getWS() + cp.substring(4), hostloader, sourcedata, sourcedomain); //$NON-NLS-1$
135
if (var.equals("os")) //$NON-NLS-1$
136
return ClasspathManager.addClassPathEntry(cpEntries, "os/" + EclipseEnvironmentInfo.getDefault().getOS() + cp.substring(4), hostloader, sourcedata, sourcedomain); //$NON-NLS-1$
137
if (var.equals("nl")) { //$NON-NLS-1$
138
cp = cp.substring(4);
139             for (int i = 0; i < NL_JAR_VARIANTS.length; i++)
140                 if (ClasspathManager.addClassPathEntry(cpEntries, "nl/" + NL_JAR_VARIANTS[i] + cp, hostloader, sourcedata, sourcedomain)) //$NON-NLS-1$
141
return true;
142         }
143         return false;
144     }
145
146     //return a String representing the string found between the $s
147
private static String JavaDoc hasPrefix(String JavaDoc libPath) {
148         if (libPath.startsWith("$ws$")) //$NON-NLS-1$
149
return "ws"; //$NON-NLS-1$
150
if (libPath.startsWith("$os$")) //$NON-NLS-1$
151
return "os"; //$NON-NLS-1$
152
if (libPath.startsWith("$nl$")) //$NON-NLS-1$
153
return "nl"; //$NON-NLS-1$
154
return null;
155     }
156
157     private static String JavaDoc[] buildNLJarVariants(String JavaDoc nl) {
158         ArrayList JavaDoc result = new ArrayList JavaDoc();
159         nl = nl.replace('_', '/');
160         while (nl.length() > 0) {
161             result.add("nl/" + nl + "/"); //$NON-NLS-1$ //$NON-NLS-2$
162
int i = nl.lastIndexOf('/');
163             nl = (i < 0) ? "" : nl.substring(0, i); //$NON-NLS-1$
164
}
165         result.add(""); //$NON-NLS-1$
166
return (String JavaDoc[]) result.toArray(new String JavaDoc[result.size()]);
167     }
168
169     public void recordClassDefine(String JavaDoc name, Class JavaDoc clazz, byte[] classbytes, ClasspathEntry classpathEntry, BundleEntry entry, ClasspathManager manager) {
170         // do nothing
171
}
172
173     public String JavaDoc findLibrary(BaseData data, String JavaDoc libName) {
174         if (libName.length() == 0)
175             return null;
176         if (libName.charAt(0) == '/' || libName.charAt(0) == '\\')
177             libName = libName.substring(1);
178         String JavaDoc mappedLibName = System.mapLibraryName(libName);
179         String JavaDoc result = searchVariants(data, mappedLibName);
180         if (result != null)
181             return result;
182         String JavaDoc[] mappedLibNames = BaseClassLoadingHook.mapLibraryNames(mappedLibName);
183         for (int i = 0; i < mappedLibNames.length && result == null; i++)
184             result = searchVariants(data, mappedLibNames[i]);
185         return result;
186     }
187
188     private String JavaDoc searchVariants(BaseData bundledata, String JavaDoc path) {
189         for (int i = 0; i < LIB_VARIANTS.length; i++) {
190             BundleFile baseBundleFile = bundledata.getBundleFile();
191             BundleEntry libEntry = baseBundleFile.getEntry(LIB_VARIANTS[i] + path);
192             if (libEntry != null) {
193                 File JavaDoc libFile = baseBundleFile.getFile(LIB_VARIANTS[i] + path, true);
194                 if (libFile == null)
195                     return null;
196                 // see bug 88697 - HP requires libraries to have executable permissions
197
if (org.eclipse.osgi.service.environment.Constants.OS_HPUX.equals(EclipseEnvironmentInfo.getDefault().getOS())) {
198                     try {
199                         // use the string array method in case there is a space in the path
200
Runtime.getRuntime().exec(new String JavaDoc[] {"chmod", "755", libFile.getAbsolutePath()}).waitFor(); //$NON-NLS-1$ //$NON-NLS-2$
201
} catch (Exception JavaDoc e) {
202                         e.printStackTrace();
203                     }
204                 }
205                 return libFile.getAbsolutePath();
206             }
207         }
208         return null;
209     }
210
211     public ClassLoader JavaDoc getBundleClassLoaderParent() {
212         return null; // do nothing
213
}
214
215     public void addHooks(HookRegistry hookRegistry) {
216         hookRegistry.addClassLoadingHook(this);
217     }
218
219     public BaseClassLoader createClassLoader(ClassLoader JavaDoc parent, ClassLoaderDelegate delegate, BundleProtectionDomain domain, BaseData data, String JavaDoc[] bundleclasspath) {
220         // TODO Auto-generated method stub
221
return null;
222     }
223
224     public void initializedClassLoader(BaseClassLoader baseClassLoader, BaseData data) {
225         // TODO Auto-generated method stub
226

227     }
228 }
229
Popular Tags