ChannelFactoryRefCache.cs 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. //------------------------------------------------------------
  2. // Copyright (c) Microsoft Corporation. All rights reserved.
  3. //------------------------------------------------------------
  4. namespace System.ServiceModel
  5. {
  6. using System.Collections.Generic;
  7. using System.Runtime;
  8. using System.ServiceModel.Channels;
  9. using System.ServiceModel.Diagnostics.Application;
  10. sealed class ChannelFactoryRef<TChannel>
  11. where TChannel : class
  12. {
  13. ChannelFactory<TChannel> channelFactory;
  14. int refCount = 1;
  15. public ChannelFactoryRef(ChannelFactory<TChannel> channelFactory)
  16. {
  17. this.channelFactory = channelFactory;
  18. }
  19. public void AddRef()
  20. {
  21. this.refCount++;
  22. }
  23. // The caller should call Close/Abort when the return value is true.
  24. public bool Release()
  25. {
  26. --this.refCount;
  27. Fx.Assert(this.refCount >= 0, "RefCount should not be less than zero.");
  28. if (this.refCount == 0)
  29. {
  30. return true;
  31. }
  32. return false;
  33. }
  34. public void Close(TimeSpan timeout)
  35. {
  36. this.channelFactory.Close(timeout);
  37. }
  38. public void Abort()
  39. {
  40. this.channelFactory.Abort();
  41. }
  42. public ChannelFactory<TChannel> ChannelFactory
  43. {
  44. get
  45. {
  46. return this.channelFactory;
  47. }
  48. }
  49. }
  50. class ChannelFactoryRefCache<TChannel> : MruCache<EndpointTrait<TChannel>, ChannelFactoryRef<TChannel>>
  51. where TChannel : class
  52. {
  53. static EndpointTraitComparer DefaultEndpointTraitComparer = new EndpointTraitComparer();
  54. readonly int watermark;
  55. class EndpointTraitComparer : IEqualityComparer<EndpointTrait<TChannel>>
  56. {
  57. public bool Equals(EndpointTrait<TChannel> x, EndpointTrait<TChannel> y)
  58. {
  59. if (x != null)
  60. {
  61. if (y != null)
  62. return x.Equals(y);
  63. return false;
  64. }
  65. if (y != null)
  66. return false;
  67. return true;
  68. }
  69. public int GetHashCode(EndpointTrait<TChannel> obj)
  70. {
  71. if (obj == null)
  72. return 0;
  73. return obj.GetHashCode();
  74. }
  75. }
  76. public ChannelFactoryRefCache(int watermark)
  77. : base(watermark * 4 / 5, watermark, DefaultEndpointTraitComparer)
  78. {
  79. this.watermark = watermark;
  80. }
  81. protected override void OnSingleItemRemoved(ChannelFactoryRef<TChannel> item)
  82. {
  83. // Remove from cache.
  84. if (item.Release())
  85. {
  86. item.Abort();
  87. }
  88. if (TD.ClientBaseCachedChannelFactoryCountIsEnabled())
  89. {
  90. TD.ClientBaseCachedChannelFactoryCount(this.Count, this.watermark, this);
  91. }
  92. }
  93. protected override void OnItemAgedOutOfCache(ChannelFactoryRef<TChannel> item)
  94. {
  95. if (TD.ClientBaseChannelFactoryAgedOutofCacheIsEnabled())
  96. {
  97. TD.ClientBaseChannelFactoryAgedOutofCache(this.watermark, this);
  98. }
  99. }
  100. }
  101. }