1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.logging.log4j.spi;
18
19 import org.apache.logging.log4j.LogManager;
20 import org.apache.logging.log4j.Logger;
21 import org.apache.logging.log4j.ThreadContext;
22 import org.apache.logging.log4j.status.StatusLogger;
23 import org.apache.logging.log4j.util.Constants;
24 import org.apache.logging.log4j.util.PropertiesUtil;
25 import org.apache.logging.log4j.util.ProviderUtil;
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48 public final class ThreadContextMapFactory {
49 private static final Logger LOGGER = StatusLogger.getLogger();
50 private static final String THREAD_CONTEXT_KEY = "log4j2.threadContextMap";
51 private static final String GC_FREE_THREAD_CONTEXT_KEY = "log4j2.garbagefree.threadContextMap";
52
53 private ThreadContextMapFactory() {
54 }
55
56 public static ThreadContextMap createThreadContextMap() {
57 final PropertiesUtil managerProps = PropertiesUtil.getProperties();
58 final String threadContextMapName = managerProps.getStringProperty(THREAD_CONTEXT_KEY);
59 final ClassLoader cl = ProviderUtil.findClassLoader();
60 ThreadContextMap result = null;
61 if (threadContextMapName != null) {
62 try {
63 final Class<?> clazz = cl.loadClass(threadContextMapName);
64 if (ThreadContextMap.class.isAssignableFrom(clazz)) {
65 result = (ThreadContextMap) clazz.newInstance();
66 }
67 } catch (final ClassNotFoundException cnfe) {
68 LOGGER.error("Unable to locate configured ThreadContextMap {}", threadContextMapName);
69 } catch (final Exception ex) {
70 LOGGER.error("Unable to create configured ThreadContextMap {}", threadContextMapName, ex);
71 }
72 }
73 if (result == null && ProviderUtil.hasProviders() && LogManager.getFactory() != null) {
74 final String factoryClassName = LogManager.getFactory().getClass().getName();
75 for (final Provider provider : ProviderUtil.getProviders()) {
76 if (factoryClassName.equals(provider.getClassName())) {
77 final Class<? extends ThreadContextMap> clazz = provider.loadThreadContextMap();
78 if (clazz != null) {
79 try {
80 result = clazz.newInstance();
81 break;
82 } catch (final Exception e) {
83 LOGGER.error("Unable to locate or load configured ThreadContextMap {}",
84 provider.getThreadContextMap(), e);
85 result = createDefaultThreadContextMap();
86 }
87 }
88 }
89 }
90 }
91 if (result == null) {
92 result = createDefaultThreadContextMap();
93 }
94 return result;
95 }
96
97 private static ThreadContextMap createDefaultThreadContextMap() {
98 if (Constants.ENABLE_THREADLOCALS) {
99 if (PropertiesUtil.getProperties().getBooleanProperty(GC_FREE_THREAD_CONTEXT_KEY)) {
100 return new GarbageFreeSortedArrayThreadContextMap();
101 }
102 return new CopyOnWriteSortedArrayThreadContextMap();
103 }
104 return new DefaultThreadContextMap(true);
105 }
106 }