/*
 * JBoss, Home of Professional Open Source.
 * Copyright 2006, Red Hat Middleware LLC, and individual contributors
 * as indicated by the @author tags. See the copyright.txt file in the
 * distribution for a full listing of individual contributors.
 *
 * This is free software; you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as
 * published by the Free Software Foundation; either version 2.1 of
 * the License, or (at your option) any later version.
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this software; if not, write to the Free
 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
 */
package org.jboss.jca.core.connectionmanager.pool.mcp;

import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

import org.jboss.logging.Logger;

/**
 * PoolFiller
 * 
 * @author <a href="mailto:d_jencks@users.sourceforge.net">David Jencks</a>
 * @author Scott.Stark@jboss.org
 * @author <a href="mailto:adrian@jboss.com">Adrian Brock</a>
 * @author <a href="mailto:gurkanerdogdu@yahoo.com">Gurkan Erdogdu</a>
 * @version $Rev: $
 */
class PoolFiller implements Runnable
{
   /** Log instance */
   private static Logger log = Logger.getLogger(PoolFiller.class);

   /** Singleton instance */
   private static final PoolFiller FILLER = new PoolFiller();

   /** Pools list */
   private final LinkedBlockingQueue<ManagedConnectionPool> pools = 
      new LinkedBlockingQueue<ManagedConnectionPool>();

   /** Filler thread */
   private final Thread fillerThread;

   /** Thread name */
   private static final String THREAD_FILLER_NAME = "JCA PoolFiller";

   /** Lock instance */
   private ReentrantLock lock = new ReentrantLock();

   /** Lock condition */
   private Condition condition = this.lock.newCondition();
   
   /**Thread is configured or not*/
   private AtomicBoolean threadStarted = new AtomicBoolean(false);

   /**
    * Fill given pool.
    * 
    * @param mcp internal managed connection pool
    */
   static void fillPool(ManagedConnectionPool mcp)
   {
      FILLER.internalFillPool(mcp);
   }

   /**
    * Creates a new pool filler instance.
    */
   PoolFiller()
   {
      fillerThread = new Thread(this, THREAD_FILLER_NAME);
      fillerThread.setDaemon(true);
   }

   /**
    * {@inheritDoc}
    */
   public void run()
   {
      final ClassLoader myClassLoader = getClass().getClassLoader();
      SecurityActions.setThreadContextClassLoader(myClassLoader);

      // keep going unless interrupted
      while (true)
      {
         ManagedConnectionPool mcp = null;
         try
         {
            // keep iterating through pools till empty, exception escapes.
            while (true)
            {
               mcp = pools.remove();

               if (mcp == null)
               {
                  break;
               }

               mcp.fillToMin();
            }
         }
         catch (Exception e)
         {
            log.warn("Exception is occured while filling pool : " + mcp);
         }

         try
         {
            this.lock.lock();

            while (pools.isEmpty())
            {
               condition.await();
            }
         }
         catch (InterruptedException ie)
         {
            return;

         }
         finally
         {
            this.lock.unlock();
         }
      }
   }

   /**
    *  fill pool.
    * @param mcp connection pool
    */
   private void internalFillPool(ManagedConnectionPool mcp)
   {
      if (this.threadStarted.compareAndSet(false, true))         
      {
         this.fillerThread.start();
      }
      
      this.pools.add(mcp);
      this.condition.signal();
   }
}

@@ -1102,38 +1102,18 @@
 til.
-concurrent.LinkedBlockingQueue
+LinkedList
 ;%0Aim
@@ -1163,102 +1163,8 @@
 ean;
-%0Aimport java.util.concurrent.locks.Condition;%0Aimport java.util.concurrent.locks.ReentrantLock;
 %0A%0Aim
@@ -1745,37 +1745,28 @@
 final Linked
-BlockingQueue
+List
 %3CManagedConn
@@ -1785,23 +1785,16 @@
 pools = 
-%0A      
 new Link
@@ -1799,21 +1799,12 @@
 nked
-BlockingQueue
+List
 %3CMan
@@ -1987,174 +1987,8 @@
 %22;%0A%0A
-   /** Lock instance */%0A   private ReentrantLock lock = new ReentrantLock();%0A%0A   /** Lock condition */%0A   private Condition condition = this.lock.newCondition();%0A   %0A
    /
@@ -2663,68 +2663,57 @@
     
-// keep going unless interrupted%0A      while (true)%0A
+while (true)%0A      %7B%0A         try %0A  
       
+ 
 %7B%0A
+   
     
@@ -2751,16 +2751,17 @@
 = null;%0A
+%0A
         
@@ -2753,36 +2753,51 @@
 null;%0A%0A         
-try%0A
+   while (true)%0A   
          %7B%0A     
@@ -2807,103 +2807,56 @@
     
-// keep iterating through pools till empty, exception escapes.%0A            while (true)
+   synchronized (pools)%0A               %7B
 %0A       
     
@@ -2843,39 +2843,32 @@
        %7B%0A       
-     %7B%0A
                m
@@ -2862,20 +2862,16 @@
         
-    
 mcp = po
@@ -2880,19 +2880,41 @@
 s.remove
-();
+First();%0A               %7D
 %0A%0A      
@@ -2938,33 +2938,17 @@
 == null)
-%0A               %7B
+ 
 %0A       
@@ -2972,34 +2972,41 @@
 %0A               
-%7D%0A
+         
 %0A               
@@ -3103,81 +3103,53 @@
     
-log.warn(%22Exception is occured while filling pool : %22 + mcp);%0A         %7D%0A
+// Ignore%0A         %7D%0A                        
 %0A   
@@ -3157,16 +3157,17 @@
      try
+ 
 %0A       
@@ -3186,27 +3186,46 @@
     
-this.lock.lock();%0A%0A
+synchronized (pools)%0A            %7B%0A   
     
@@ -3260,32 +3260,35 @@
 ())%0A            
+   
 %7B%0A              
@@ -3292,26 +3292,84 @@
     
-condition.await();
+   pools.wait();                        %0A                  %0A               %7D
 %0A   
@@ -3458,86 +3458,62 @@
     
-return;%0A%0A         %7D%0A         finally%0A         %7B%0A            this.lock.unlock()
+Thread.currentThread().interrupt();%0A            return
 ;%0A  
@@ -3796,21 +3796,54 @@
  %0A      
-this.
+synchronized (pools)%0A      %7B%0A         
 pools.ad
@@ -3843,16 +3843,20 @@
 ools.add
+Last
 (mcp);%0A 
@@ -3864,32 +3864,34 @@
     
-this.condition.signal();
+   pools.notify();%0A      %7D
 %0A   

Use synchronized list for now