TARGET_J2EE compilation & integration fixes.
[mono.git] / mcs / class / System.Web / System.Web.Caching / CacheEntry.cs
1 // 
2 // System.Web.Caching
3 //
4 // Author:
5 //   Patrik Torstensson
6 //   Daniel Cazzulino (dcazzulino@users.sf.net)
7 //
8
9 //
10 // Permission is hereby granted, free of charge, to any person obtaining
11 // a copy of this software and associated documentation files (the
12 // "Software"), to deal in the Software without restriction, including
13 // without limitation the rights to use, copy, modify, merge, publish,
14 // distribute, sublicense, and/or sell copies of the Software, and to
15 // permit persons to whom the Software is furnished to do so, subject to
16 // the following conditions:
17 // 
18 // The above copyright notice and this permission notice shall be
19 // included in all copies or substantial portions of the Software.
20 // 
21 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
24 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
25 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
26 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
27 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
28 //
29
30 using System;
31 using System.Threading;
32
33 namespace System.Web.Caching {
34         internal class CacheEntry {
35                 enum Flags {
36                         Removed = 1,
37                         Public  = 2
38                 }
39
40                 internal static readonly byte NoBucketHash = byte.MaxValue;
41                 internal static readonly int NoIndexInBucket = int.MaxValue;
42
43                 CacheItemPriority _enumPriority;
44                 long _longHits;
45                 byte _byteExpiresBucket;
46                 int _intExpiresIndex;
47                 long _ticksExpires;     
48                 long _ticksSlidingExpiration;
49                 string _strKey;
50                 object _objItem;
51                 long _longMinHits;
52                 Flags _enumFlags;
53                 CacheDependency _objDependency;
54                 Cache _objCache;
55                 ReaderWriterLock _lock = new ReaderWriterLock();
56
57                 internal event CacheItemRemovedCallback _onRemoved;
58
59                 internal CacheEntry (Cache objManager, string strKey, object objItem,CacheDependency objDependency,
60                                 CacheItemRemovedCallback eventRemove, DateTime dtExpires, TimeSpan tsSpan,
61                                 long longMinHits, bool boolPublic, CacheItemPriority enumPriority )
62                 {
63                         if (boolPublic)
64                                 _enumFlags |= Flags.Public;
65
66                         _strKey = strKey;
67                         _objItem = objItem;
68                         _objCache = objManager;
69                         _onRemoved += eventRemove;
70                         _enumPriority = enumPriority;
71                         _ticksExpires = dtExpires.ToUniversalTime ().Ticks;
72                         _ticksSlidingExpiration = tsSpan.Ticks;
73
74                         // If we have a sliding expiration it overrides the absolute expiration (MS behavior)
75                         // This is because sliding expiration causes the absolute expiration to be 
76                         // moved after each period, and the absolute expiration is the value used 
77                         // for all expiration calculations.
78                         if (tsSpan.Ticks != Cache.NoSlidingExpiration.Ticks)
79                                 _ticksExpires = DateTime.UtcNow.AddTicks (_ticksSlidingExpiration).Ticks;
80                         
81                         _objDependency = objDependency;
82                         if (_objDependency != null)
83                                 // Add the entry to the cache dependency handler (we support multiple entries per handler)
84                                 _objDependency.Changed += new CacheDependencyChangedHandler (OnChanged); 
85
86                         _longMinHits = longMinHits;
87                 }
88
89
90                 internal void OnChanged (object sender, CacheDependencyChangedArgs objDependency)
91                 {
92                         _objCache.Remove (_strKey, CacheItemRemovedReason.DependencyChanged);
93                 }
94
95                 internal void Close (CacheItemRemovedReason enumReason)
96                 {
97                         Delegate [] removedEvents = null;
98
99                         _lock.AcquireWriterLock(-1);
100                         try {
101                                 // Check if the item already is removed
102                                 if ((_enumFlags & Flags.Removed) != 0)
103                                         return;
104
105                                 _enumFlags |= Flags.Removed;
106
107                                 if (_onRemoved != null)
108                                         removedEvents = _onRemoved.GetInvocationList ();
109                         } finally {
110                                 _lock.ReleaseWriterLock();
111                         }
112
113                         if (removedEvents != null) {
114                                 // Call the delegate to tell that we are now removing the entry
115                                 foreach (Delegate del in removedEvents) {
116                                         CacheItemRemovedCallback removed = (CacheItemRemovedCallback) del;
117                                         try {
118                                                 removed (_strKey, _objItem, enumReason);                
119                                         } catch (Exception obj) {
120                                                 if (IsPublic)
121                                                         HttpApplicationFactory.SignalError (obj);
122                                         }
123                                 }
124                         }
125
126                         _lock.AcquireWriterLock(-1);
127                         try {
128                                 // If we have a dependency, remove the entry
129                                 if (_objDependency != null)
130                                         _objDependency.Changed -= new CacheDependencyChangedHandler (OnChanged);
131                         } finally {
132                                 _lock.ReleaseWriterLock();
133                         }
134                 }
135         
136                 internal bool HasUsage {
137                         get { 
138                                 if (_longMinHits == System.Int64.MaxValue)
139                                         return false;
140
141                                 return true;
142                         }
143                 }
144
145                 internal bool HasAbsoluteExpiration {
146                         get { 
147                                 if (_ticksExpires == Cache.NoAbsoluteExpiration.Ticks) 
148                                         return false;
149
150                                 return true;
151                         }
152                 }
153
154                 internal bool HasSlidingExpiration {
155                         get { 
156                                 if (_ticksSlidingExpiration == Cache.NoSlidingExpiration.Ticks) 
157                                         return false;
158
159                                 return true;
160                         }
161                 }
162                 
163                 internal byte ExpiresBucket {
164                         get { return _byteExpiresBucket; }
165                         set { _byteExpiresBucket = value; }
166                 }
167
168                 internal int ExpiresIndex {
169                         get { return _intExpiresIndex; }
170                         set { _intExpiresIndex = value; }
171                 }
172         
173                 internal long Expires {
174                         get { return _ticksExpires; }
175                         set { _ticksExpires = value; }
176                 }
177
178                 internal long SlidingExpiration {
179                         get { return _ticksSlidingExpiration; }
180                 }
181
182                 internal object Item {
183                         get { return _objItem; }
184                 }
185
186                 internal string Key {
187                         get { return _strKey; }
188                 }
189
190                 internal long Hits {
191                         get { return _longHits; }
192                 }
193
194                 internal long MinimumHits {
195                         get { return _longMinHits; }
196                 }
197
198                 internal CacheItemPriority Priority {
199                         get { return _enumPriority; }
200                 }
201
202                 internal bool IsPublic {
203                         get { return (_enumFlags & Flags.Public) != 0; }
204                 }
205
206                 internal void Hit ()
207                 {
208                         Interlocked.Increment (ref _longHits);
209                 }
210         }
211 }
212