KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > objectweb > perseus > persistence > concurrency > PPessimisticConcurrencyManager


1 /**
2  * Copyright (C) 2003 France Telecom R&D
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  */

18 package org.objectweb.perseus.persistence.concurrency;
19
20 import java.util.ArrayList JavaDoc;
21 import java.util.Iterator JavaDoc;
22
23 import org.objectweb.fractal.api.NoSuchInterfaceException;
24 import org.objectweb.fractal.api.control.IllegalBindingException;
25 import org.objectweb.perseus.cache.api.CacheEntry;
26 import org.objectweb.perseus.concurrency.api.ConcurrencyException;
27 import org.objectweb.perseus.concurrency.pessimistic.Lock;
28 import org.objectweb.perseus.concurrency.pessimistic.PessimisticConcurrencyManager;
29 import org.objectweb.perseus.persistence.api.NoDSIPersistenceException;
30 import org.objectweb.perseus.persistence.api.PersistenceException;
31 import org.objectweb.perseus.persistence.api.State;
32 import org.objectweb.perseus.persistence.api.StateManager;
33 import org.objectweb.perseus.persistence.api.StorageManager;
34 import org.objectweb.perseus.persistence.api.VirtualState;
35 import org.objectweb.perseus.persistence.api.WorkingSet;
36 import org.objectweb.util.monolog.api.BasicLevel;
37
38 /**
39  *
40  * @author S.Chassande-Barrioz
41  */

42 public class PPessimisticConcurrencyManager
43         extends PessimisticConcurrencyManager {
44
45     public PPessimisticConcurrencyManager() throws ConcurrencyException {
46     }
47
48     public PPessimisticConcurrencyManager(short policy) throws ConcurrencyException {
49         super(policy);
50     }
51
52     public final static String JavaDoc STORAGE_MANAGER_BINDING = "storage-manager";
53     public final static String JavaDoc STATE_MANAGER_BINDING = "state-manager";
54
55     protected StateManager stateManager;
56
57     protected StorageManager storageManager;
58
59     //IMPLEMENTATION OF THE UserBindingControler INTERFACE //
60
//------------------------------------------------------//
61

62     public String JavaDoc[] listFc() {
63         String JavaDoc[] super_res = super.listFc();
64         String JavaDoc res[] = new String JavaDoc[super_res.length + 2];
65         for (int cpt = 0; cpt < super_res.length; cpt++) {
66             res[cpt] = super_res[cpt];
67         }
68         res[super_res.length + 0] = STORAGE_MANAGER_BINDING;
69         res[super_res.length + 1] = STATE_MANAGER_BINDING;
70         return res;
71     }
72
73     public Object JavaDoc lookupFc(String JavaDoc s) throws NoSuchInterfaceException {
74         if (STORAGE_MANAGER_BINDING.equals(s)) {
75             return storageManager;
76         } else if (STATE_MANAGER_BINDING.equals(s)) {
77             return stateManager;
78         } else {
79             return super.lookupFc(s);
80         }
81     }
82
83     public void bindFc(String JavaDoc s, Object JavaDoc o) throws NoSuchInterfaceException, IllegalBindingException {
84         if (STORAGE_MANAGER_BINDING.equals(s)) {
85             storageManager = (StorageManager) o;
86         } else if (STATE_MANAGER_BINDING.equals(s)) {
87             stateManager = (StateManager) o;
88         } else super.bindFc(s, o);
89     }
90
91     public void unbindFc(String JavaDoc s) throws NoSuchInterfaceException {
92         if (STORAGE_MANAGER_BINDING.equals(s)) {
93             storageManager = null;
94         } else if (STATE_MANAGER_BINDING.equals(s)) {
95             stateManager = null;
96         } else {
97             super.unbindFc(s);
98         }
99     }
100
101     /**
102      * Manage the state used in the working set
103      * @see org.objectweb.perseus.concurrency.api.ConcurrencyManager#finalize(java.lang.Object)
104      */

105     public void finalize(Object JavaDoc arg0) {
106         WorkingSet ws = (WorkingSet) arg0;
107         boolean retainValues = ws.getWSRetainValues();
108         for (Iterator JavaDoc it = ws.entries().iterator(); it.hasNext();) {
109             State state = (State) it.next();
110             if (state == VirtualState.instance) {
111                 continue;
112             }
113             CacheEntry ce = state.getCacheEntry();
114             if (!stateManager.isUnexported(state)) {
115                 //The object has not been unexported (deleted)
116
if (retainValues) {
117                     if (stateManager.isDirty(state)) {
118                         if (stateManager.isToMerge(state)) {
119                             //A thin lock has been allocated, then several
120
//working set potentialy commit the state delta.
121
//==>synchronize the state change
122
synchronized(ce) {
123                                 State s = stateManager.getReferenceState(ce);
124                                 if (s != null) {
125                                     s = stateManager.merge(s, state);
126                                     stateManager.setReferenceState(ce, s);
127                                 }
128                             }
129                         } else {
130                             // a single writer is autorized
131
// ==> no synchronization required
132
stateManager.makeClean(state);
133                             stateManager.setReferenceState(ce, state);
134                         }
135                     }//else state is clean ==> nothing to do
136
} else if (stateManager.getReferenceState(ce) == state) {
137                     //forget the state used as reference state
138
stateManager.setReferenceState(ce, null);
139                 }
140             }
141         }
142         //free locks
143
super.finalize(arg0);
144     }
145
146     public void abort(Object JavaDoc ctx) {
147         WorkingSet ws = (WorkingSet) ctx;
148         for (Iterator JavaDoc it = ws.entries().iterator(); it.hasNext();) {
149             State state = (State) it.next();
150             if (state == VirtualState.instance) {
151                 continue;
152             }
153             CacheEntry ce = state.getCacheEntry();
154             if (stateManager.isExported(state)) {
155                 stateManager.makeClean(state);
156             } else if (stateManager.isDirty(state)) {
157                 if (stateManager.isUnexported(state)) {
158                     stateManager.makeClean(state);
159                     stateManager.makeBound(ce, ce.getCeIdentifier());
160                 }
161                 if (state == stateManager.getReferenceState(ce)) {
162                     //The reference state
163
if (ws.getWSRestoreValues()) {
164                         //Restore value from the support
165
try {
166                             load(ws, ce, null);
167                         } catch (Exception JavaDoc e) {
168                             logger.log(BasicLevel.WARN, "Error during reloading of " + ce.getCeIdentifier()
169                                     + ":" , e);
170                         }
171                     } else {
172                         //At the next use it will be loaded
173
stateManager.setReferenceState(ce, null);
174                         stateManager.destroyState(state);
175                     }
176                 } else {
177                     stateManager.destroyState(state);
178                 }
179             } else if (state != stateManager.getReferenceState(ce)) {
180                 stateManager.destroyState(state);
181             } //else reference state is already clean
182
}
183         super.abort(ctx);
184         
185     }
186     
187     public void closeLock(Lock lock, Object JavaDoc ctx) {
188         WorkingSet ws = (WorkingSet) ctx;
189         State s = ws.lookup(lock.oid);
190         if (s != null && s != VirtualState.instance) {
191             stateManager.stateNoMoreUsed(s);
192         }
193     }
194     
195     protected Object JavaDoc getState(Object JavaDoc ctx,
196                               Object JavaDoc resource,
197                               Lock lock) throws ConcurrencyException {
198         CacheEntry ce = (CacheEntry) resource;
199         WorkingSet ws = (WorkingSet) ctx;
200         State state = stateManager.getReferenceState(ce);
201         State wsstate = ws.lookup(ce.getCeIdentifier());
202         if (thinLockAllowed && lock.hints != null) {
203             //manage a thin lock
204
if (wsstate == null
205                     || wsstate == VirtualState.instance
206                     || wsstate == state) {
207                 //no state dedicated to this working set
208
synchronized (ce) {//avoid multiple loading of the same thing
209
state = stateManager.getReferenceState(ce);
210                     if (state == null) {
211                         //no reference state (no cache)
212
//==>load data into a created reference state
213
state = load(ws, ce, lock);
214                         stateManager.setReferenceState(state.getCacheEntry(), state);
215                     }
216                 }
217                 //clone the reference state for this working set
218
state = stateManager.createState(state);
219                 stateManager.makeClean(state);
220             } else {
221                 state = wsstate;
222             }
223             stateManager.makeToMerge(state, lock.hints);
224         } else if (state == null) {
225             //no reference state (no cache)
226
if (wsstate == null || wsstate == VirtualState.instance) {
227                 //no state bound to the working set
228
synchronized (ce) {//avoid multiple loading of the same thing
229
state = stateManager.getReferenceState(ce);
230                     if (state == null) {
231                         //no reference state (no cache)
232
//==>load data into a created reference state
233
state = load(ws, ce, lock);
234                         stateManager.setReferenceState(state.getCacheEntry(), state);
235                     }
236                 }
237             } else {
238                 state = wsstate;
239             }
240         }
241         return state;
242     }
243     
244     private State load(WorkingSet ws, CacheEntry ce, Lock lock)
245         throws ConcurrencyException {
246         State state = stateManager.createState(ce);
247         try {
248             storageManager.read(ws, ce.getCeIdentifier(), state);
249             stateManager.makeClean(state);
250             return state;
251         } catch (PersistenceException e) {
252             stateManager.destroyState(state);
253             //The instance does not exist in the data support, remove the lock
254
synchronized (locks) {
255                 if (lock != null && lock.close(ws)) {
256                     locks.remove(lock);
257                 }
258             }
259             if (e instanceof NoDSIPersistenceException) {
260                 throw new NoDSIConcurrencyException(e);
261             } else {
262                 throw new ConcurrencyException(e);
263             }
264         }
265     }
266     protected Object JavaDoc getResourceId(Object JavaDoc object) {
267         return ((CacheEntry) object).getCeIdentifier();
268     }
269
270
271 }
272
Popular Tags