Mega Code Archive

 
Categories / Android / Network
 

TimeoutService (beta) Here you can register a timeout

//package com.trilead.ssh2.util; import java.io.PrintWriter; import java.io.StringWriter; import java.util.Collections; import java.util.LinkedList; /**  * TimeoutService (beta). Here you can register a timeout.  * <p>  * Implemented having large scale programs in mind: if you open many concurrent SSH connections  * that rely on timeouts, then there will be only one timeout thread. Once all timeouts  * have expired/are cancelled, the thread will (sooner or later) exit.  * Only after new timeouts arrive a new thread (singleton) will be instantiated.  *   * @author Christian Plattner, plattner@trilead.com  * @version $Id: TimeoutService.java,v 1.1 2007/10/15 12:49:57 cplattne Exp $  */ public class TimeoutService {   public static class TimeoutToken implements Comparable   {     private long runTime;     private Runnable handler;     private TimeoutToken(long runTime, Runnable handler)     {       this.runTime = runTime;       this.handler = handler;     }     public int compareTo(Object o)     {       TimeoutToken t = (TimeoutToken) o;       if (runTime > t.runTime)         return 1;       if (runTime == t.runTime)         return 0;       return -1;     }   }   private static class TimeoutThread extends Thread   {     public void run()     {       synchronized (todolist)       {         while (true)         {           if (todolist.size() == 0)           {             timeoutThread = null;             return;           }           long now = System.currentTimeMillis();           TimeoutToken tt = (TimeoutToken) todolist.getFirst();           if (tt.runTime > now)           {             /* Not ready yet, sleep a little bit */             try             {               todolist.wait(tt.runTime - now);             }             catch (InterruptedException e)             {             }             /* We cannot simply go on, since it could be that the token              * was removed (cancelled) or another one has been inserted in              * the meantime.              */             continue;           }           todolist.removeFirst();           try           {             tt.handler.run();           }           catch (Exception e)           {             StringWriter sw = new StringWriter();             e.printStackTrace(new PrintWriter(sw));                        }         }       }     }   }   /* The list object is also used for locking purposes */   private static final LinkedList todolist = new LinkedList();   private static Thread timeoutThread = null;   /**    * It is assumed that the passed handler will not execute for a long time.    *     * @param runTime    * @param handler    * @return a TimeoutToken that can be used to cancel the timeout.    */   public static final TimeoutToken addTimeoutHandler(long runTime, Runnable handler)   {     TimeoutToken token = new TimeoutToken(runTime, handler);     synchronized (todolist)     {       todolist.add(token);       Collections.sort(todolist);       if (timeoutThread != null)         timeoutThread.interrupt();       else       {         timeoutThread = new TimeoutThread();         timeoutThread.setDaemon(true);         timeoutThread.start();       }     }     return token;   }   public static final void cancelTimeoutHandler(TimeoutToken token)   {     synchronized (todolist)     {       todolist.remove(token);       if (timeoutThread != null)         timeoutThread.interrupt();     }   } }