1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.logging.log4j.core.helpers;
18
19 import org.apache.logging.log4j.Logger;
20 import org.apache.logging.log4j.status.StatusLogger;
21
22 import java.io.InputStream;
23 import java.io.InterruptedIOException;
24 import java.lang.reflect.InvocationTargetException;
25 import java.net.URL;
26
27
28
29
30 public final class Loader {
31
32 private static final String TSTR = "Caught Exception while in Loader.getResource. This may be innocuous.";
33
34 private static boolean ignoreTCL = false;
35
36 private static final Logger LOGGER = StatusLogger.getLogger();
37
38 static {
39 String ignoreTCLProp = OptionConverter.getSystemProperty("log4j.ignoreTCL", null);
40 if (ignoreTCLProp != null) {
41 ignoreTCL = OptionConverter.toBoolean(ignoreTCLProp, true);
42 }
43 }
44
45 private Loader() {
46 }
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70 public static URL getResource(String resource, ClassLoader defaultLoader) {
71 try {
72 ClassLoader classLoader = getTCL();
73 if (classLoader != null) {
74 LOGGER.trace("Trying to find [" + resource + "] using context classloader "
75 + classLoader + '.');
76 URL url = classLoader.getResource(resource);
77 if (url != null) {
78 return url;
79 }
80 }
81
82
83 classLoader = Loader.class.getClassLoader();
84 if (classLoader != null) {
85 LOGGER.trace("Trying to find [" + resource + "] using " + classLoader + " class loader.");
86 URL url = classLoader.getResource(resource);
87 if (url != null) {
88 return url;
89 }
90 }
91
92 if (defaultLoader != null) {
93 LOGGER.trace("Trying to find [" + resource + "] using " + defaultLoader + " class loader.");
94 URL url = defaultLoader.getResource(resource);
95 if (url != null) {
96 return url;
97 }
98 }
99 } catch (IllegalAccessException t) {
100 LOGGER.warn(TSTR, t);
101 } catch (InvocationTargetException t) {
102 if (t.getTargetException() instanceof InterruptedException
103 || t.getTargetException() instanceof InterruptedIOException) {
104 Thread.currentThread().interrupt();
105 }
106 LOGGER.warn(TSTR, t);
107 } catch (Throwable t) {
108
109
110
111 LOGGER.warn(TSTR, t);
112 }
113
114
115
116
117
118 LOGGER.trace("Trying to find [" + resource + "] using ClassLoader.getSystemResource().");
119 return ClassLoader.getSystemResource(resource);
120 }
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144 public static InputStream getResourceAsStream(String resource, ClassLoader defaultLoader) {
145 ClassLoader classLoader;
146 InputStream is;
147
148 try {
149 classLoader = getTCL();
150 if (classLoader != null) {
151 LOGGER.trace("Trying to find [" + resource + "] using context classloader " + classLoader + '.');
152 is = classLoader.getResourceAsStream(resource);
153 if (is != null) {
154 return is;
155 }
156 }
157
158
159 classLoader = Loader.class.getClassLoader();
160 if (classLoader != null) {
161 LOGGER.trace("Trying to find [" + resource + "] using " + classLoader + " class loader.");
162 is = classLoader.getResourceAsStream(resource);
163 if (is != null) {
164 return is;
165 }
166 }
167
168
169 if (defaultLoader != null) {
170 LOGGER.trace("Trying to find [" + resource + "] using " + defaultLoader + " class loader.");
171 is = defaultLoader.getResourceAsStream(resource);
172 if (is != null) {
173 return is;
174 }
175 }
176 } catch (IllegalAccessException t) {
177 LOGGER.warn(TSTR, t);
178 } catch (InvocationTargetException t) {
179 if (t.getTargetException() instanceof InterruptedException
180 || t.getTargetException() instanceof InterruptedIOException) {
181 Thread.currentThread().interrupt();
182 }
183 LOGGER.warn(TSTR, t);
184 } catch (Throwable t) {
185
186
187
188 LOGGER.warn(TSTR, t);
189 }
190
191
192
193
194
195 LOGGER.trace("Trying to find [" + resource + "] using ClassLoader.getSystemResource().");
196 return ClassLoader.getSystemResourceAsStream(resource);
197 }
198
199
200
201
202
203
204
205 public static Class<?> loadClass(String className) throws ClassNotFoundException {
206
207 if (ignoreTCL) {
208 return Class.forName(className);
209 } else {
210 try {
211 return getTCL().loadClass(className);
212 } catch (Throwable e) {
213 return Class.forName(className);
214 }
215 }
216 }
217
218 public static ClassLoader getClassLoader(Class<?> class1, Class<?> class2) {
219
220 ClassLoader loader1 = null;
221 try {
222 loader1 = getTCL();
223 } catch (Exception ex) {
224 LOGGER.warn("Caught exception locating thread ClassLoader {}", ex.getMessage());
225 }
226 ClassLoader loader2 = class1 == null ? null : class1.getClassLoader();
227 ClassLoader loader3 = class2 == null ? null : class2.getClass().getClassLoader();
228
229 if (isChild(loader1, loader2)) {
230 return isChild(loader1, loader3) ? loader1 : loader3;
231 } else {
232 return isChild(loader2, loader3) ? loader2 : loader3;
233 }
234 }
235
236 private static boolean isChild(ClassLoader loader1, ClassLoader loader2) {
237 if (loader1 != null && loader2 != null) {
238 ClassLoader parent = loader1.getParent();
239 while (parent != null && parent != loader2) {
240 parent = parent.getParent();
241 }
242 return parent != null;
243 }
244 return loader1 != null;
245 }
246
247
248
249
250
251 public static ClassLoader getClassLoader() {
252
253 return getClassLoader(Loader.class, null);
254 }
255
256 private static ClassLoader getTCL() throws IllegalAccessException, InvocationTargetException {
257 ClassLoader cl;
258 if (System.getSecurityManager() == null) {
259 cl = Thread.currentThread().getContextClassLoader();
260 } else {
261 cl = java.security.AccessController.doPrivileged(
262 new java.security.PrivilegedAction<ClassLoader>() {
263 public ClassLoader run() {
264 return Thread.currentThread().getContextClassLoader();
265 }
266 }
267 );
268 }
269
270 return cl;
271 }
272 }