Source Code Cross Referenced for AbstractObjectPool.java in  » Collaboration » JacORB » org » jacorb » notification » util » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Collaboration » JacORB » org.jacorb.notification.util 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        package org.jacorb.notification.util;
002:
003:        /*
004:         *        JacORB - a free Java ORB
005:         *
006:         *   Copyright (C) 1999-2004 Gerald Brose
007:         *
008:         *   This library is free software; you can redistribute it and/or
009:         *   modify it under the terms of the GNU Library General Public
010:         *   License as published by the Free Software Foundation; either
011:         *   version 2 of the License, or (at your option) any later version.
012:         *
013:         *   This library is distributed in the hope that it will be useful,
014:         *   but WITHOUT ANY WARRANTY; without even the implied warranty of
015:         *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
016:         *   Library General Public License for more details.
017:         *
018:         *   You should have received a copy of the GNU Library General Public
019:         *   License along with this library; if not, write to the Free
020:         *   Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
021:         *
022:         */
023:
024:        import java.util.ArrayList;
025:        import java.util.Collection;
026:        import java.util.Collections;
027:        import java.util.Iterator;
028:        import java.util.LinkedList;
029:        import java.util.List;
030:        import java.util.Set;
031:
032:        import org.apache.avalon.framework.configuration.Configurable;
033:        import org.apache.avalon.framework.configuration.Configuration;
034:        import org.apache.avalon.framework.configuration.ConfigurationException;
035:        import org.apache.avalon.framework.logger.Logger;
036:        import org.jacorb.notification.interfaces.Disposable;
037:
038:        import edu.emory.mathcs.backport.java.util.concurrent.atomic.AtomicBoolean;
039:
040:        /**
041:         * Abstract Base Class for Simple Pooling Mechanism. Subclasses must at least implement the method
042:         * newInstance. To use a Object call lendObject. After use the Object must be returned with
043:         * returnObject(Object). An Object must not be used after it has been returned to its pool!
044:         *
045:         * This class needs a two phase initialization: configure MUST be invoked before an instance can be used.
046:         *
047:         * @author Alphonse Bendt
048:         * @version $Id: AbstractObjectPool.java,v 1.22 2006/06/14 11:57:54 alphonse.bendt Exp $
049:         */
050:
051:        public abstract class AbstractObjectPool implements  Runnable,
052:                Configurable {
053:            public static final boolean DEBUG = false;
054:
055:            /**
056:             * time the cleaner thread sleeps between two cleanups
057:             */
058:            public static final long SLEEP = 5000L;
059:
060:            public static final int LOWER_WATERMARK_DEFAULT = 5;
061:
062:            public static final int SIZE_INCREASE_DEFAULT = 3;
063:
064:            public static final int INITIAL_SIZE_DEFAULT = 10;
065:
066:            public static final int MAXIMUM_WATERMARK_DEFAULT = 20;
067:
068:            public static final int MAXIMUM_SIZE_DEFAULT = 0;
069:
070:            /**
071:             * non synchronized as all accessing methods are synchronized.
072:             */
073:            private static final List sPoolsToLookAfter = new ArrayList();
074:
075:            private static AbstractObjectPool[] asArray;
076:
077:            private static boolean modified = true;
078:
079:            private final static AbstractObjectPool[] ARRAY_TEMPLATE = new AbstractObjectPool[0];
080:
081:            private static Thread sCleanerThread;
082:
083:            private static final Logger sLogger_ = LogUtil
084:                    .getLogger(AbstractObjectPool.class.getName());
085:
086:            private static ListCleaner sListCleaner;
087:
088:            private static boolean sUseListCleaner = true;
089:
090:            private static AbstractObjectPool[] getAllPools() {
091:                synchronized (sPoolsToLookAfter) {
092:                    if (modified) {
093:                        asArray = (AbstractObjectPool[]) sPoolsToLookAfter
094:                                .toArray(ARRAY_TEMPLATE);
095:                        modified = false;
096:                    }
097:                }
098:                return asArray;
099:            }
100:
101:            private static void registerPool(AbstractObjectPool pool) {
102:                synchronized (sPoolsToLookAfter) {
103:                    sPoolsToLookAfter.add(pool);
104:                    modified = true;
105:                    startListCleaner();
106:                }
107:            }
108:
109:            private static void deregisterPool(AbstractObjectPool pool) {
110:                synchronized (sPoolsToLookAfter) {
111:                    sPoolsToLookAfter.remove(pool);
112:                    modified = true;
113:                    if (sPoolsToLookAfter.isEmpty()) {
114:                        // this cleans up the asArray_ array for the GC.
115:                        getAllPools();
116:
117:                        stopListCleaner();
118:                    }
119:                }
120:            }
121:
122:            private static class ListCleaner extends Thread {
123:                private AtomicBoolean active_ = new AtomicBoolean(true);
124:
125:                public void setInactive() {
126:                    active_.set(false);
127:
128:                    interrupt();
129:                }
130:
131:                private void ensureIsActive() throws InterruptedException {
132:                    if (!active_.get()) {
133:                        throw new InterruptedException();
134:                    }
135:                }
136:
137:                public void run() {
138:                    try {
139:                        while (active_.get()) {
140:                            try {
141:                                runLoop();
142:                            } catch (InterruptedException e) {
143:                                sLogger_.info("PoolCleaner was interrupted");
144:                            } catch (Exception e) {
145:                                sLogger_.error("Error cleaning Pool", e);
146:                            }
147:                        }
148:                    } finally {
149:                        synchronized (AbstractObjectPool.class) {
150:                            sCleanerThread = null;
151:                        }
152:                    }
153:                }
154:
155:                private void runLoop() throws InterruptedException {
156:                    while (true) {
157:                        try {
158:                            sleep(SLEEP);
159:                        } catch (InterruptedException ie) {
160:                            // ignore here.
161:                            // ensureIsActive is called below to see if this Thread should
162:                            // still be active.
163:                        }
164:
165:                        ensureIsActive();
166:
167:                        Runnable[] poolsToCheck = getAllPools();
168:
169:                        for (int x = 0; x < poolsToCheck.length; ++x) {
170:                            try {
171:                                poolsToCheck[x].run();
172:                            } catch (Exception t) {
173:                                // should not happen
174:                                sLogger_.error("Error cleaning up Pool", t);
175:                            }
176:                        }
177:                    }
178:                }
179:            }
180:
181:            private static ListCleaner getListCleaner() {
182:                synchronized (AbstractObjectPool.class) {
183:                    if (sListCleaner == null) {
184:                        sListCleaner = new ListCleaner();
185:                    }
186:                    return sListCleaner;
187:                }
188:            }
189:
190:            private static void stopListCleaner() {
191:                synchronized (AbstractObjectPool.class) {
192:                    if (sCleanerThread != null) {
193:                        sListCleaner.setInactive();
194:                    }
195:                }
196:            }
197:
198:            private static void startListCleaner() {
199:                synchronized (AbstractObjectPool.class) {
200:                    if (sCleanerThread == null && sUseListCleaner) {
201:                        sCleanerThread = new Thread(getListCleaner());
202:
203:                        sCleanerThread.setName("ObjectPoolCleaner");
204:                        sCleanerThread.setPriority(Thread.MIN_PRIORITY + 1);
205:                        sCleanerThread.setDaemon(true);
206:                        sCleanerThread.start();
207:                    }
208:                }
209:            }
210:
211:            private final String name_;
212:
213:            private final LinkedList pool_;
214:
215:            private boolean isInitialized_;
216:
217:            /**
218:             * Set that contains all objects that were created by this pool and are in use. Problems occured
219:             * as access to this member used to be non-synchronized see
220:             * news://news.gmane.org:119/200406041629.48096.Farrell_John_W@cat.com
221:             */
222:            private final Set active_ = Collections
223:                    .synchronizedSet(new WeakHashSet());
224:
225:            /**
226:             * lower watermark. if pool size is below that value, create sizeIncrease_ new elements.
227:             */
228:            private int lowerWatermark_;
229:
230:            /**
231:             * how many instances should the pool maximal keep. instances that are returned to a pool which
232:             * size is greater than maxWatermark_ are discarded and left for the Garbage Collector.
233:             */
234:            private int maxWatermark_;
235:
236:            /**
237:             * how many instances should be created if pool size falls below lowerWatermark_.
238:             */
239:            private int sizeIncrease_;
240:
241:            /**
242:             * how many instances should be created at startup of the pool.
243:             */
244:            private int initialSize_;
245:
246:            private int maximumSize_;
247:
248:            protected final Logger logger_ = LogUtil.getLogger(getClass()
249:                    .getName());
250:
251:            protected Configuration config_;
252:
253:            public void configure(Configuration conf) {
254:                config_ = conf;
255:
256:                init();
257:            }
258:
259:            protected AbstractObjectPool(String name) {
260:                this (name, LOWER_WATERMARK_DEFAULT, SIZE_INCREASE_DEFAULT,
261:                        INITIAL_SIZE_DEFAULT, MAXIMUM_WATERMARK_DEFAULT,
262:                        MAXIMUM_SIZE_DEFAULT);
263:            }
264:
265:            protected AbstractObjectPool(String name, int lowerWatermark,
266:                    int sizeincrease, int initialsize, int maxWatermark,
267:                    int maximumSize) {
268:                if (maximumSize > 0 && initialsize > maximumSize) {
269:                    throw new IllegalArgumentException("InitialSize: "
270:                            + initialsize
271:                            + " may not be larger than MaximumSize: "
272:                            + maximumSize);
273:                }
274:
275:                name_ = name;
276:                pool_ = new LinkedList();
277:                lowerWatermark_ = lowerWatermark;
278:                sizeIncrease_ = sizeincrease;
279:                initialSize_ = initialsize;
280:                maxWatermark_ = maxWatermark;
281:                maximumSize_ = maximumSize;
282:            }
283:
284:            public void run() {
285:                final int maxToBeCreated;
286:
287:                synchronized (pool_) {
288:                    if (pool_.size() > lowerWatermark_) {
289:                        return;
290:                    }
291:
292:                    maxToBeCreated = getNumberOfCreationsAllowed();
293:                }
294:
295:                final int sizeIncrease = Math
296:                        .min(sizeIncrease_, maxToBeCreated);
297:
298:                if (sizeIncrease > 0) {
299:                    List os = new ArrayList(sizeIncrease);
300:
301:                    for (int x = 0; x < sizeIncrease; ++x) {
302:                        Object _i = createInstance();
303:
304:                        os.add(_i);
305:                    }
306:
307:                    synchronized (pool_) {
308:                        pool_.addAll(os);
309:                    }
310:                }
311:            }
312:
313:            /**
314:             * check the number of instances that are allowed to be created.
315:             *
316:             * <b>preCondition:</b> lock pool_ must be held.
317:             */
318:            private int getNumberOfCreationsAllowed() {
319:                final int maxToBeCreated;
320:
321:                if (maximumSize_ > 0) {
322:                    maxToBeCreated = maximumSize_ - active_.size()
323:                            - pool_.size();
324:                } else {
325:                    maxToBeCreated = Integer.MAX_VALUE;
326:                }
327:
328:                return maxToBeCreated;
329:            }
330:
331:            private Object createInstance() {
332:                if (logger_.isDebugEnabled()) {
333:                    logger_.debug("created newInstance " + getInfo());
334:                }
335:                return newInstance();
336:            }
337:
338:            /**
339:             * Initialize this Pool. An initial Number of Objects is created. Cleanup Thread is started.
340:             */
341:            private void init() {
342:                registerPool(this );
343:
344:                synchronized (pool_) {
345:                    if (isInitialized_) {
346:                        throw new IllegalStateException("Already Initialized");
347:                    }
348:
349:                    for (int x = 0; x < initialSize_; ++x) {
350:                        Object _i = createInstance();
351:
352:                        pool_.add(_i);
353:                    }
354:
355:                    isInitialized_ = true;
356:                }
357:            }
358:
359:            /**
360:             * Release this Pool.
361:             */
362:            public void dispose() {
363:                deregisterPool(this );
364:                disposeCollection(pool_);
365:                pool_.clear();
366:                disposeCollection(active_);
367:                active_.clear();
368:            }
369:
370:            private void disposeCollection(Collection collection) {
371:                final Iterator i = collection.iterator();
372:
373:                while (i.hasNext()) {
374:                    final Object o = i.next();
375:
376:                    try {
377:                        Disposable disposable = (Disposable) o;
378:
379:                        try {
380:                            ((AbstractPoolable) o).setObjectPool(null);
381:                        } catch (ClassCastException e) {
382:                            // ignored
383:                        }
384:
385:                        disposable.dispose();
386:                    } catch (ClassCastException e) {
387:                        // ignored
388:                    }
389:                }
390:            }
391:
392:            /**
393:             * lend an object from the pool.
394:             */
395:            public Object lendObject() {
396:                checkIsInitialized();
397:
398:                Object _result = null;
399:
400:                synchronized (pool_) {
401:                    if (!pool_.isEmpty()) {
402:                        _result = pool_.removeFirst();
403:                    }
404:
405:                    if (_result == null) {
406:                        while (!isCreationAllowed()) {
407:                            poolIsEmpty();
408:                        }
409:                    }
410:                }
411:
412:                if (_result == null) {
413:                    _result = createInstance();
414:                }
415:
416:                try {
417:                    ((Configurable) _result).configure(this .config_);
418:                } catch (ClassCastException cce) {
419:                    // no worries, just don't configure
420:                } catch (ConfigurationException ce) {
421:                    throw new RuntimeException("Could not configure instance");
422:                }
423:
424:                doActivateObject(_result);
425:                active_.add(_result);
426:
427:                return _result;
428:            }
429:
430:            /**
431:             *
432:             */
433:            private void checkIsInitialized() {
434:                synchronized (pool_) {
435:                    if (!isInitialized_) {
436:                        throw new IllegalStateException("Not initialized");
437:                    }
438:                }
439:            }
440:
441:            /**
442:             * check if it is allowed to create more instances.
443:             *
444:             * <b>preCondition:</b> lock pool_ must be held.
445:             */
446:            protected boolean isCreationAllowed() {
447:                return getNumberOfCreationsAllowed() > 0;
448:            }
449:
450:            /**
451:             *
452:             */
453:            protected void poolIsEmpty() {
454:                throw new RuntimeException(getInfo()
455:                        + ": No more Elements allowed. ");
456:            }
457:
458:            /**
459:             * return an Object to the pool.
460:             */
461:            public void returnObject(Object o) {
462:                checkIsInitialized();
463:
464:                if (active_.remove(o)) {
465:                    doPassivateObject(o);
466:
467:                    if (pool_.size() < maxWatermark_) {
468:                        synchronized (pool_) {
469:                            pool_.add(o);
470:                            pool_.notifyAll();
471:                        }
472:                    } else {
473:                        doDestroyObject(o);
474:                    }
475:                } else {
476:                    throw new IllegalArgumentException("Object " + o
477:                            + " was not created by this pool");
478:                }
479:            }
480:
481:            public String toString() {
482:                return getInfo();
483:            }
484:
485:            private String getInfo() {
486:                return "["
487:                        + name_
488:                        + "] Active="
489:                        + active_.size()
490:                        + " Pooled="
491:                        + pool_.size()
492:                        + " MaximumSize="
493:                        + ((maximumSize_ > 0) ? Integer.toString(maximumSize_)
494:                                : "unlimited");
495:            }
496:
497:            /**
498:             * This method is called by the Pool to create a new Instance. Subclasses must override
499:             * appropiately .
500:             */
501:            public abstract Object newInstance();
502:
503:            /**
504:             * Is called after Object is returned to pool. No Op.
505:             */
506:            public void doPassivateObject(Object o) {
507:                // No Op
508:            }
509:
510:            /**
511:             * Is called before Object is returned to Client (lendObject). No Op
512:             */
513:            public void doActivateObject(Object o) {
514:                // No Op
515:            }
516:
517:            /**
518:             * Is called if Pool is full and returned Object is discarded. No Op.
519:             */
520:            public void doDestroyObject(Object o) {
521:                // No Op
522:            }
523:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.