Clover coverage report - Ant Coverage
Coverage timestamp: Tue Apr 8 2003 20:43:55 EST
file stats: LOC: 213   Methods: 9
NCLOC: 68   Classes: 1
 
 Source file Conditionals Statements Methods TOTAL
ExecuteWatchdog.java 37.5% 79.3% 77.8% 71.7%
 1   
 /*
 2   
  * The Apache Software License, Version 1.1
 3   
  *
 4   
  * Copyright (c) 2000-2002 The Apache Software Foundation.  All rights
 5   
  * reserved.
 6   
  *
 7   
  * Redistribution and use in source and binary forms, with or without
 8   
  * modification, are permitted provided that the following conditions
 9   
  * are met:
 10   
  *
 11   
  * 1. Redistributions of source code must retain the above copyright
 12   
  *    notice, this list of conditions and the following disclaimer.
 13   
  *
 14   
  * 2. Redistributions in binary form must reproduce the above copyright
 15   
  *    notice, this list of conditions and the following disclaimer in
 16   
  *    the documentation and/or other materials provided with the
 17   
  *    distribution.
 18   
  *
 19   
  * 3. The end-user documentation included with the redistribution, if
 20   
  *    any, must include the following acknowlegement:
 21   
  *       "This product includes software developed by the
 22   
  *        Apache Software Foundation (http://www.apache.org/)."
 23   
  *    Alternately, this acknowlegement may appear in the software itself,
 24   
  *    if and wherever such third-party acknowlegements normally appear.
 25   
  *
 26   
  * 4. The names "Ant" and "Apache Software
 27   
  *    Foundation" must not be used to endorse or promote products derived
 28   
  *    from this software without prior written permission. For written
 29   
  *    permission, please contact apache@apache.org.
 30   
  *
 31   
  * 5. Products derived from this software may not be called "Apache"
 32   
  *    nor may "Apache" appear in their names without prior written
 33   
  *    permission of the Apache Group.
 34   
  *
 35   
  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 36   
  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 37   
  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 38   
  * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
 39   
  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 40   
  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 41   
  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
 42   
  * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 43   
  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 44   
  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
 45   
  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 46   
  * SUCH DAMAGE.
 47   
  * ====================================================================
 48   
  *
 49   
  * This software consists of voluntary contributions made by many
 50   
  * individuals on behalf of the Apache Software Foundation.  For more
 51   
  * information on the Apache Software Foundation, please see
 52   
  * <http://www.apache.org/>.
 53   
  */
 54   
 
 55   
 package org.apache.tools.ant.taskdefs;
 56   
 
 57   
 import org.apache.tools.ant.BuildException;
 58   
 import org.apache.tools.ant.util.TimeoutObserver;
 59   
 import org.apache.tools.ant.util.Watchdog;
 60   
 
 61   
 /**
 62   
  * Destroys a process running for too long.
 63   
  * For example:
 64   
  * <pre>
 65   
  * ExecuteWatchdog watchdog = new ExecuteWatchdog(30000);
 66   
  * Execute exec = new Execute(myloghandler, watchdog);
 67   
  * exec.setCommandLine(mycmdline);
 68   
  * int exitvalue = exec.execute();
 69   
  * if (exitvalue != SUCCESS && watchdog.killedProcess()){
 70   
  *              // it was killed on purpose by the watchdog
 71   
  * }
 72   
  * </pre>
 73   
  
 74   
  * @author thomas.haas@softwired-inc.com
 75   
  * @author <a href="mailto:sbailliez_at_apache.org">Stephane Bailliez</a>
 76   
  * @see Execute
 77   
  * @see org.apache.tools.ant.util.Watchdog
 78   
  * @since Ant 1.2
 79   
  */
 80   
 public class ExecuteWatchdog implements TimeoutObserver {
 81   
         
 82   
     /** the process to execute and watch for duration */
 83   
     private Process process;
 84   
 
 85   
     /** say whether or not the watchog is currently monitoring a process */
 86   
     private boolean watch = false;
 87   
         
 88   
     /** exception that might be thrown during the process execution */
 89   
     private Exception caught = null;
 90   
 
 91   
     /** say whether or not the process was killed due to running overtime */
 92   
     private boolean     killedProcess = false;
 93   
 
 94   
     /** will tell us whether timeout has occured */
 95   
     private Watchdog watchdog;
 96   
 
 97   
     /**
 98   
      * Creates a new watchdog with a given timeout.
 99   
      *
 100   
      * @param timeout the timeout for the process in milliseconds. 
 101   
      * It must be greather than 0.
 102   
      */
 103  4
     public ExecuteWatchdog(long timeout) {
 104  4
         watchdog = new Watchdog(timeout);
 105  4
         watchdog.addTimeoutObserver(this);
 106   
     }
 107   
 
 108   
     /**
 109   
      * @see #ExecuteWatchdog(long)
 110   
      * @deprecated Use constructor with a long type instead.
 111   
      * (1.4.x compatibility)
 112   
      */
 113  4
     public ExecuteWatchdog(int timeout) {
 114  4
         this((long)timeout);
 115   
     }
 116   
 
 117   
     /**
 118   
      * Watches the given process and terminates it, if it runs for too long.
 119   
      * All information from the previous run are reset.
 120   
      * @param process the process to monitor. It cannot be <tt>null</tt>
 121   
      * @throws IllegalStateException if a process is still being monitored.
 122   
      */
 123  4
     public synchronized void start(Process process) {
 124  4
         if (process == null) {
 125  0
             throw new NullPointerException("process is null.");
 126   
         }
 127  4
         if (this.process != null) {
 128  0
             throw new IllegalStateException("Already running.");
 129   
         }
 130  4
         this.caught = null;
 131  4
         this.killedProcess = false;
 132  4
         this.watch = true;
 133  4
         this.process = process;
 134  4
         watchdog.start();
 135   
     }
 136   
 
 137   
     /**
 138   
      * Stops the watcher. It will notify all threads possibly waiting 
 139   
      * on this object.
 140   
      */
 141  1
     public synchronized void stop() {
 142  1
         watchdog.stop();
 143  1
         watch = false;
 144  1
         process = null;
 145   
     }
 146   
 
 147   
     /**
 148   
      * Called after watchdog has finished.
 149   
      */
 150  3
     public void timeoutOccured(Watchdog w) {
 151  3
         try {
 152  3
             try {
 153   
                 // We must check if the process was not stopped
 154   
                 // before being here
 155  3
                 process.exitValue();
 156   
             } catch (IllegalThreadStateException itse){
 157   
                 // the process is not terminated, if this is really
 158   
                 // a timeout and not a manual stop then kill it.
 159  1
                 if (watch){
 160  1
                     killedProcess = true;
 161  1
                     process.destroy();
 162   
                 }
 163   
             }
 164   
         } catch (Exception e) {
 165  0
             caught = e;
 166   
         } finally {
 167  3
             cleanUp();
 168   
         }
 169   
     }
 170   
 
 171   
     /**
 172   
      * reset the monitor flag and the process.
 173   
      */
 174  3
     protected void cleanUp() {
 175  3
         watch = false;
 176  3
         process = null;
 177   
     }
 178   
 
 179   
     /**
 180   
      * This method will rethrow the exception that was possibly caught during 
 181   
      * the run of the process. It will only remains valid once the process has 
 182   
      * been terminated either by 'error', timeout or manual intervention. 
 183   
      * Information will be discarded once a new process is ran.
 184   
      * @throws  BuildException  a wrapped exception over the one that was 
 185   
      * silently swallowed and stored during the process run.
 186   
      */
 187  0
     public void checkException() throws BuildException {
 188  0
         if (caught != null) {
 189  0
             throw new BuildException("Exception in ExecuteWatchdog.run: "
 190   
                                      + caught.getMessage(), caught);
 191   
         }
 192   
     }
 193   
 
 194   
     /**
 195   
      * Indicates whether or not the watchdog is still monitoring the process.
 196   
      * @return  <tt>true</tt> if the process is still running, otherwise 
 197   
      *          <tt>false</tt>.
 198   
      */
 199  0
     public boolean isWatching(){
 200  0
         return watch;
 201   
     }
 202   
 
 203   
     /**
 204   
      * Indicates whether the last process run was killed on timeout or not.
 205   
      * @return  <tt>true</tt> if the process was killed otherwise 
 206   
      *          <tt>false</tt>.
 207   
      */
 208  4
     public boolean killedProcess(){
 209  4
         return killedProcess;
 210   
     }
 211   
 }
 212   
 
 213