ThreadContextProperties.cs 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200
  1. #region Apache License
  2. //
  3. // Licensed to the Apache Software Foundation (ASF) under one or more
  4. // contributor license agreements. See the NOTICE file distributed with
  5. // this work for additional information regarding copyright ownership.
  6. // The ASF licenses this file to you under the Apache License, Version 2.0
  7. // (the "License"); you may not use this file except in compliance with
  8. // the License. You may obtain a copy of the License at
  9. //
  10. // http://www.apache.org/licenses/LICENSE-2.0
  11. //
  12. // Unless required by applicable law or agreed to in writing, software
  13. // distributed under the License is distributed on an "AS IS" BASIS,
  14. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15. // See the License for the specific language governing permissions and
  16. // limitations under the License.
  17. //
  18. #endregion
  19. using System;
  20. #if NETCF
  21. using System.Collections;
  22. #endif
  23. namespace log4net.Util
  24. {
  25. /// <summary>
  26. /// Implementation of Properties collection for the <see cref="log4net.ThreadContext"/>
  27. /// </summary>
  28. /// <remarks>
  29. /// <para>
  30. /// Class implements a collection of properties that is specific to each thread.
  31. /// The class is not synchronized as each thread has its own <see cref="PropertiesDictionary"/>.
  32. /// </para>
  33. /// </remarks>
  34. /// <author>Nicko Cadell</author>
  35. public sealed class ThreadContextProperties : ContextPropertiesBase
  36. {
  37. #region Private Instance Fields
  38. #if NETCF
  39. /// <summary>
  40. /// The thread local data slot to use to store a PropertiesDictionary.
  41. /// </summary>
  42. private readonly static LocalDataStoreSlot s_threadLocalSlot = System.Threading.Thread.AllocateDataSlot();
  43. #else
  44. /// <summary>
  45. /// Each thread will automatically have its instance.
  46. /// </summary>
  47. [ThreadStatic]
  48. private static PropertiesDictionary _dictionary;
  49. #endif
  50. #endregion Private Instance Fields
  51. #region Public Instance Constructors
  52. /// <summary>
  53. /// Internal constructor
  54. /// </summary>
  55. /// <remarks>
  56. /// <para>
  57. /// Initializes a new instance of the <see cref="ThreadContextProperties" /> class.
  58. /// </para>
  59. /// </remarks>
  60. internal ThreadContextProperties()
  61. {
  62. }
  63. #endregion Public Instance Constructors
  64. #region Public Instance Properties
  65. /// <summary>
  66. /// Gets or sets the value of a property
  67. /// </summary>
  68. /// <value>
  69. /// The value for the property with the specified key
  70. /// </value>
  71. /// <remarks>
  72. /// <para>
  73. /// Gets or sets the value of a property
  74. /// </para>
  75. /// </remarks>
  76. override public object this[string key]
  77. {
  78. get
  79. {
  80. #if NETCF
  81. PropertiesDictionary _dictionary = GetProperties(false);
  82. #endif
  83. if (_dictionary != null)
  84. {
  85. return _dictionary[key];
  86. }
  87. return null;
  88. }
  89. set
  90. {
  91. GetProperties(true)[key] = value;
  92. }
  93. }
  94. #endregion Public Instance Properties
  95. #region Public Instance Methods
  96. /// <summary>
  97. /// Remove a property
  98. /// </summary>
  99. /// <param name="key">the key for the entry to remove</param>
  100. /// <remarks>
  101. /// <para>
  102. /// Remove a property
  103. /// </para>
  104. /// </remarks>
  105. public void Remove(string key)
  106. {
  107. #if NETCF
  108. PropertiesDictionary _dictionary = GetProperties(false);
  109. #endif
  110. if (_dictionary != null)
  111. {
  112. _dictionary.Remove(key);
  113. }
  114. }
  115. /// <summary>
  116. /// Get the keys stored in the properties.
  117. /// </summary>
  118. /// <para>
  119. /// Gets the keys stored in the properties.
  120. /// </para>
  121. /// <returns>a set of the defined keys</returns>
  122. public string[] GetKeys()
  123. {
  124. #if NETCF
  125. PropertiesDictionary _dictionary = GetProperties(false);
  126. #endif
  127. if (_dictionary != null)
  128. {
  129. return _dictionary.GetKeys();
  130. }
  131. return null;
  132. }
  133. /// <summary>
  134. /// Clear all properties
  135. /// </summary>
  136. /// <remarks>
  137. /// <para>
  138. /// Clear all properties
  139. /// </para>
  140. /// </remarks>
  141. public void Clear()
  142. {
  143. #if NETCF
  144. PropertiesDictionary _dictionary = GetProperties(false);
  145. #endif
  146. if (_dictionary != null)
  147. {
  148. _dictionary.Clear();
  149. }
  150. }
  151. #endregion Public Instance Methods
  152. #region Internal Instance Methods
  153. /// <summary>
  154. /// Get the <c>PropertiesDictionary</c> for this thread.
  155. /// </summary>
  156. /// <param name="create">create the dictionary if it does not exist, otherwise return null if does not exist</param>
  157. /// <returns>the properties for this thread</returns>
  158. /// <remarks>
  159. /// <para>
  160. /// The collection returned is only to be used on the calling thread. If the
  161. /// caller needs to share the collection between different threads then the
  162. /// caller must clone the collection before doing so.
  163. /// </para>
  164. /// </remarks>
  165. internal PropertiesDictionary GetProperties(bool create)
  166. {
  167. #if NETCF
  168. PropertiesDictionary _dictionary = (PropertiesDictionary)System.Threading.Thread.GetData(s_threadLocalSlot);
  169. #endif
  170. if (_dictionary == null && create)
  171. {
  172. _dictionary = new PropertiesDictionary();
  173. #if NETCF
  174. System.Threading.Thread.SetData(s_threadLocalSlot, _dictionary);
  175. #endif
  176. }
  177. return _dictionary;
  178. }
  179. #endregion Internal Instance Methods
  180. }
  181. }