LOG4NET-554 Use AsyncLocal for LogicalThreadContext Patch by Thomas Clegg.
closes #52 Project: http://git-wip-us.apache.org/repos/asf/logging-log4net/repo Commit: http://git-wip-us.apache.org/repos/asf/logging-log4net/commit/201ad1ae Tree: http://git-wip-us.apache.org/repos/asf/logging-log4net/tree/201ad1ae Diff: http://git-wip-us.apache.org/repos/asf/logging-log4net/diff/201ad1ae Branch: refs/heads/master Commit: 201ad1ae3ced298e77469f99e548244a7f772b06 Parents: c0b95f9 Author: Stefan Bodewig <bode...@apache.org> Authored: Fri Mar 3 21:45:41 2017 +0000 Committer: Stefan Bodewig <bode...@apache.org> Committed: Fri Mar 3 21:45:41 2017 +0000 ---------------------------------------------------------------------- netstandard/log4net.tests/log4net.tests.xproj | 1 + netstandard/log4net.tests/project.json | 1 + netstandard/log4net/log4net.xproj | 6 ++-- netstandard/log4net/project.json | 3 -- src/Core/LoggingEvent.cs | 6 ++-- src/Util/LogicalThreadContextProperties.cs | 31 ++++++++++++++------ .../PropertyPatternConverter.cs | 2 +- src/site/xdoc/release/framework-support.xml | 10 +++++-- tests/src/Context/LogicalThreadContextTest.cs | 2 +- tests/src/Utils.cs | 2 +- 10 files changed, 40 insertions(+), 24 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/netstandard/log4net.tests/log4net.tests.xproj ---------------------------------------------------------------------- diff --git a/netstandard/log4net.tests/log4net.tests.xproj b/netstandard/log4net.tests/log4net.tests.xproj index 00fecb3..92eecae 100644 --- a/netstandard/log4net.tests/log4net.tests.xproj +++ b/netstandard/log4net.tests/log4net.tests.xproj @@ -36,6 +36,7 @@ limitations under the License. <Compile Include="../../tests/src/Appender/SmtpPickupDirAppenderTest.cs" /> <Compile Include="../../tests/src/Appender/StringAppender.cs" /> <Compile Include="../../tests/src/Appender/TraceAppenderTest.cs" /> + <Compile Include="../../tests/src/Context/LogicalThreadContextTest.cs" /> <Compile Include="../../tests/src/Context/ThreadContextTest.cs" /> <Compile Include="../../tests/src/Core/**/*.cs" /> <Compile Include="../../tests/src/DateFormatter/**/*.cs" /> http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/netstandard/log4net.tests/project.json ---------------------------------------------------------------------- diff --git a/netstandard/log4net.tests/project.json b/netstandard/log4net.tests/project.json index 1e2396d..49af8d7 100644 --- a/netstandard/log4net.tests/project.json +++ b/netstandard/log4net.tests/project.json @@ -11,6 +11,7 @@ "../../tests/src/Appender/SmtpPickupDirAppenderTest.cs", "../../tests/src/Appender/StringAppender.cs", "../../tests/src/Appender/TraceAppenderTest.cs", + "../../tests/src/Context/LogicalThreadContextTest.cs", "../../tests/src/Context/ThreadContextTest.cs", "../../tests/src/Core/**/*.cs", "../../tests/src/DateFormatter/**/*.cs", http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/netstandard/log4net/log4net.xproj ---------------------------------------------------------------------- diff --git a/netstandard/log4net/log4net.xproj b/netstandard/log4net/log4net.xproj index ff371a0..083a7a4 100644 --- a/netstandard/log4net/log4net.xproj +++ b/netstandard/log4net/log4net.xproj @@ -161,7 +161,7 @@ limitations under the License. <Compile Include="../../src/Layout/XmlLayout.cs" /> <Compile Include="../../src/Layout/XmlLayoutBase.cs" /> <Compile Include="../../src/Layout/XmlLayoutSchemaLog4j.cs" /> - <!--<Compile Include="../../src/LogicalThreadContext.cs" />--> + <Compile Include="../../src/LogicalThreadContext.cs" /> <Compile Include="../../src/LogManager.cs" /> <Compile Include="../../src/MDC.cs" /> <Compile Include="../../src/NDC.cs" /> @@ -201,9 +201,9 @@ limitations under the License. <Compile Include="../../src/Util/ILogExtensions.cs" /> <Compile Include="../../src/Util/LevelMapping.cs" /> <Compile Include="../../src/Util/LevelMappingEntry.cs" /> - <!--<Compile Include="../../src/Util/LogicalThreadContextProperties.cs" />--> + <Compile Include="../../src/Util/LogicalThreadContextProperties.cs" /> <Compile Include="../../src/Util/LogicalThreadContextStack.cs" /> - <!--<Compile Include="../../src/Util/LogicalThreadContextStacks.cs" />--> + <Compile Include="../../src/Util/LogicalThreadContextStacks.cs" /> <Compile Include="../../src/Util/LogLog.cs" /> <!--<Compile Include="../../src/Util/NativeError.cs" />--> <Compile Include="../../src/Util/NullDictionaryEnumerator.cs" /> http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/netstandard/log4net/project.json ---------------------------------------------------------------------- diff --git a/netstandard/log4net/project.json b/netstandard/log4net/project.json index 75978e5..53164d9 100644 --- a/netstandard/log4net/project.json +++ b/netstandard/log4net/project.json @@ -16,7 +16,6 @@ "../../src/Appender/NetSendAppender.cs", "../../src/Appender/RemotingAppender.cs", "../../src/Appender/SmtpAppender.cs", - "../../src/LogicalThreadContext.cs", "../../src/Config/DOMConfigurator.cs", "../../src/Config/DOMConfiguratorAttribute.cs", "../../src/Config/Log4NetConfigurationSectionHandler.cs", @@ -30,8 +29,6 @@ "../../src/Plugin/RemoteLoggingServerPlugin.cs", "../../src/Util/PatternStringConverters/AppSettingPatternConverter.cs", "../../src/Util/PatternStringConverters/EnvironmentFolderPathPatternConverter.cs", - "../../src/Util/LogicalThreadContextProperties.cs", - "../../src/Util/LogicalThreadContextStacks.cs", "../../src/Util/NativeError.cs", "../../src/Util/WindowsSecurityContext.cs" ] http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/src/Core/LoggingEvent.cs ---------------------------------------------------------------------- diff --git a/src/Core/LoggingEvent.cs b/src/Core/LoggingEvent.cs index fb9a506..eb54a60 100644 --- a/src/Core/LoggingEvent.cs +++ b/src/Core/LoggingEvent.cs @@ -461,7 +461,7 @@ namespace log4net.Core #region Protected Instance Constructors -#if !(NETCF || NETSTANDARD1_3) +#if !NETCF /// <summary> /// Serialization constructor @@ -814,7 +814,7 @@ namespace log4net.Core { if (m_data.ThreadName == null && this.m_cacheUpdatable) { -#if NETCF || NETSTANDARD1_3 +#if NETCF // Get thread ID only m_data.ThreadName = SystemInfo.CurrentThreadId.ToString(System.Globalization.NumberFormatInfo.InvariantInfo); #else @@ -1394,7 +1394,7 @@ namespace log4net.Core { compositeProperties.Add(m_eventProperties); } -#if !(NETCF || NETSTANDARD1_3) +#if !NETCF PropertiesDictionary logicalThreadProperties = LogicalThreadContext.Properties.GetProperties(false); if (logicalThreadProperties != null) { http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/src/Util/LogicalThreadContextProperties.cs ---------------------------------------------------------------------- diff --git a/src/Util/LogicalThreadContextProperties.cs b/src/Util/LogicalThreadContextProperties.cs index fb9684f..904229d 100644 --- a/src/Util/LogicalThreadContextProperties.cs +++ b/src/Util/LogicalThreadContextProperties.cs @@ -21,8 +21,13 @@ #if !NETCF using System; +#if !NETSTANDARD1_3 using System.Runtime.Remoting.Messaging; +#endif using System.Security; +#if NETSTANDARD1_3 +using System.Threading; +#endif namespace log4net.Util { @@ -49,7 +54,11 @@ namespace log4net.Util /// <author>Nicko Cadell</author> public sealed class LogicalThreadContextProperties : ContextPropertiesBase { + #if NETSTANDARD1_3 + private static readonly AsyncLocal<PropertiesDictionary> AsyncLocalDictionary = new AsyncLocal<PropertiesDictionary>(); + #else private const string c_SlotName = "log4net.Util.LogicalThreadContextProperties"; + #endif /// <summary> /// Flag used to disable this context if we don't have permission to access the CallContext. @@ -105,7 +114,7 @@ namespace log4net.Util // need to be immutable to correctly flow through async/await PropertiesDictionary immutableProps = new PropertiesDictionary(props); immutableProps[key] = value; - SetCallContextData(immutableProps); + SetLogicalProperties(immutableProps); } } @@ -129,7 +138,7 @@ namespace log4net.Util { PropertiesDictionary immutableProps = new PropertiesDictionary(dictionary); immutableProps.Remove(key); - SetCallContextData(immutableProps); + SetLogicalProperties(immutableProps); } } @@ -147,7 +156,7 @@ namespace log4net.Util if (dictionary != null) { PropertiesDictionary immutableProps = new PropertiesDictionary(); - SetCallContextData(immutableProps); + SetLogicalProperties(immutableProps); } } @@ -173,11 +182,11 @@ namespace log4net.Util { try { - PropertiesDictionary properties = GetCallContextData(); + PropertiesDictionary properties = GetLogicalProperties(); if (properties == null && create) { properties = new PropertiesDictionary(); - SetCallContextData(properties); + SetLogicalProperties(properties); } return properties; } @@ -214,9 +223,11 @@ namespace log4net.Util #if NET_4_0 || MONO_4_0 [System.Security.SecuritySafeCritical] #endif - private static PropertiesDictionary GetCallContextData() + private static PropertiesDictionary GetLogicalProperties() { -#if NET_2_0 || MONO_2_0 || MONO_3_5 || MONO_4_0 +#if NETSTANDARD1_3 + return AsyncLocalDictionary.Value; +#elif NET_2_0 || MONO_2_0 || MONO_3_5 || MONO_4_0 return CallContext.LogicalGetData(c_SlotName) as PropertiesDictionary; #else return CallContext.GetData(c_SlotName) as PropertiesDictionary; @@ -235,9 +246,11 @@ namespace log4net.Util #if NET_4_0 || MONO_4_0 [System.Security.SecuritySafeCritical] #endif - private static void SetCallContextData(PropertiesDictionary properties) + private static void SetLogicalProperties(PropertiesDictionary properties) { -#if NET_2_0 || MONO_2_0 || MONO_3_5 || MONO_4_0 +#if NETSTANDARD1_3 + AsyncLocalDictionary.Value = properties; +#elif NET_2_0 || MONO_2_0 || MONO_3_5 || MONO_4_0 CallContext.LogicalSetData(c_SlotName, properties); #else CallContext.SetData(c_SlotName, properties); http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/src/Util/PatternStringConverters/PropertyPatternConverter.cs ---------------------------------------------------------------------- diff --git a/src/Util/PatternStringConverters/PropertyPatternConverter.cs b/src/Util/PatternStringConverters/PropertyPatternConverter.cs index 9c2051e..3124b31 100644 --- a/src/Util/PatternStringConverters/PropertyPatternConverter.cs +++ b/src/Util/PatternStringConverters/PropertyPatternConverter.cs @@ -68,7 +68,7 @@ namespace log4net.Util.PatternStringConverters { CompositeProperties compositeProperties = new CompositeProperties(); -#if !(NETCF || NETSTANDARD1_3) +#if !NETCF PropertiesDictionary logicalThreadProperties = LogicalThreadContext.Properties.GetProperties(false); if (logicalThreadProperties != null) { http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/src/site/xdoc/release/framework-support.xml ---------------------------------------------------------------------- diff --git a/src/site/xdoc/release/framework-support.xml b/src/site/xdoc/release/framework-support.xml index 7cf2b34..f8e25b8 100644 --- a/src/site/xdoc/release/framework-support.xml +++ b/src/site/xdoc/release/framework-support.xml @@ -614,9 +614,6 @@ limitations under the License. <li>anything related to ASP.NET (trace appender and several pattern converters)</li> <li>.NET Remoting</li> - <li><code>log4net.LogicalThreadContext</code> - and the associated properties and stack - classes</li> <li>the colored console appender</li> <li>the event log appender</li> <li>The <code>NetSendAppender</code></li> @@ -630,6 +627,13 @@ limitations under the License. <code>EnvironmentFolderPathPatternConverter</code></li> <li>Impersonation of Windows accounts</li> </ul> + + <p><code>log4net.LogicalThreadContext</code> and + the associated properties and stack classes use + <code>AsyncLocal</code> rather than + <code>CallContext</code>. Prior to log4net 2.0.8 + they haven't been supported for .NET Standard at + all.</p> </section> <section id="net1.0" name="Microsoft .NET Framework 1.0"> http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/tests/src/Context/LogicalThreadContextTest.cs ---------------------------------------------------------------------- diff --git a/tests/src/Context/LogicalThreadContextTest.cs b/tests/src/Context/LogicalThreadContextTest.cs index f3f0a19..849d963 100644 --- a/tests/src/Context/LogicalThreadContextTest.cs +++ b/tests/src/Context/LogicalThreadContextTest.cs @@ -17,7 +17,7 @@ // #endregion -#if NET_4_5 +#if NET_4_5 || NETSTANDARD1_3 using System; using System.Threading.Tasks; using System.Linq; http://git-wip-us.apache.org/repos/asf/logging-log4net/blob/201ad1ae/tests/src/Utils.cs ---------------------------------------------------------------------- diff --git a/tests/src/Utils.cs b/tests/src/Utils.cs index 5cbfb9c..14e55d3 100644 --- a/tests/src/Utils.cs +++ b/tests/src/Utils.cs @@ -114,7 +114,7 @@ namespace log4net.Tests internal static void RemovePropertyFromAllContexts() { GlobalContext.Properties.Remove(PROPERTY_KEY); ThreadContext.Properties.Remove(PROPERTY_KEY); -#if !(NETCF || NETSTANDARD1_3) +#if !NETCF LogicalThreadContext.Properties.Remove(PROPERTY_KEY); #endif }