    001    /*
    002     * Licensed to the Apache Software Foundation (ASF) under one or more
    003     *  contributor license agreements.  See the NOTICE file distributed with
    004     *  this work for additional information regarding copyright ownership.
    005     *  The ASF licenses this file to You under the Apache License, Version 2.0
    006     *  (the "License"); you may not use this file except in compliance with
    007     *  the License.  You may obtain a copy of the License at
    008     *
    009     *      http://www.apache.org/licenses/LICENSE-2.0
    010     *
    011     *  Unless required by applicable law or agreed to in writing, software
    012     *  distributed under the License is distributed on an "AS IS" BASIS,
    013     *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    014     *  See the License for the specific language governing permissions and
    015     *  limitations under the License.
    016     *
    017     */
    018
    019    package org.apache.commons.exec;
    020
    021    import java.util.Enumeration;
    022    import java.util.Vector;
    023
    024    /**
    025     * Generalization of <code>ExecuteWatchdog</code>
    026     *
    027     * @see org.apache.commons.exec.ExecuteWatchdog
    028     */
    029    public class Watchdog implements Runnable {
    030
    031        private Vector observers = new Vector(1);
    032
    033        private final long timeout;
    034
    035        private boolean stopped = false;
    036
    037        public Watchdog(final long timeout) {
    038            if (timeout < 1) {
    039                throw new IllegalArgumentException("timeout must not be less than 1.");
    040            }
    041            this.timeout = timeout;
    042        }
    043
    044        public void addTimeoutObserver(final TimeoutObserver to) {
    045            observers.addElement(to);
    046        }
    047
    048        public void removeTimeoutObserver(final TimeoutObserver to) {
    049            observers.removeElement(to);
    050        }
    051
    052        protected final void fireTimeoutOccured() {
    053            Enumeration e = observers.elements();
    054            while (e.hasMoreElements()) {
    055                ((TimeoutObserver) e.nextElement()).timeoutOccured(this);
    056            }
    057        }
    058
    059        public synchronized void start() {
    060            stopped = false;
    061            Thread t = new Thread(this, "WATCHDOG");
    062            t.setDaemon(true);
    063            t.start();
    064        }
    065
    066        public synchronized void stop() {
    067            stopped = true;
    068            notifyAll();
    069        }
    070
    071        public synchronized void run() {
    072            final long until = System.currentTimeMillis() + timeout;
    073            long now;
    074            while (!stopped && until > (now = System.currentTimeMillis())) {
    075                try {
    076                    wait(until - now);
    077                } catch (InterruptedException e) {
    078                }
    079            }
    080            if (!stopped) {
    081                fireTimeoutOccured();
    082            }
    083        }
    084    }