1e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera/* 2e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved. 3e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * 5e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * This code is free software; you can redistribute it and/or modify it 6e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * under the terms of the GNU General Public License version 2 only, as 7e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * published by the Free Software Foundation. Oracle designates this 8e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * particular file as subject to the "Classpath" exception as provided 9e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * by Oracle in the LICENSE file that accompanied this code. 10e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * 11e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * This code is distributed in the hope that it will be useful, but WITHOUT 12e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * version 2 for more details (a copy is included in the LICENSE file that 15e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * accompanied this code). 16e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * 17e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * You should have received a copy of the GNU General Public License version 18e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * 2 along with this work; if not, write to the Free Software Foundation, 19e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * 21e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * or visit www.oracle.com if you need additional information or have any 23e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * questions. 24e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 25e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 26e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmerapackage sun.nio.fs; 27e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 28e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmeraimport java.nio.file.*; 29e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmeraimport java.util.concurrent.*; 30e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmeraimport java.io.IOException; 31e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 32e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera/** 33e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Base implementation class for watch services. 34e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 35e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 36e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmeraabstract class AbstractWatchService implements WatchService { 37e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 38e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // signaled keys waiting to be dequeued 39e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private final LinkedBlockingDeque<WatchKey> pendingKeys = 40e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera new LinkedBlockingDeque<WatchKey>(); 41e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 42e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // special key to indicate that watch service is closed 43e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private final WatchKey CLOSE_KEY = 44e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera new AbstractWatchKey(null, null) { 45e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 46e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public boolean isValid() { 47e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return true; 48e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 49e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 50e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 51e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public void cancel() { 52e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 53e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera }; 54e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 55e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // used when closing watch service 56e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private volatile boolean closed; 57e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private final Object closeLock = new Object(); 58e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 59e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera protected AbstractWatchService() { 60e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 61e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 62e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 63e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Register the given object with this watch service 64e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 65e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera abstract WatchKey register(Path path, 66e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera WatchEvent.Kind<?>[] events, 67e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera WatchEvent.Modifier... modifers) 68e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera throws IOException; 69e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 70e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // used by AbstractWatchKey to enqueue key 71e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera final void enqueueKey(WatchKey key) { 72e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera pendingKeys.offer(key); 73e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 74e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 75e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 76e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Throws ClosedWatchServiceException if watch service is closed 77e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 78e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private void checkOpen() { 79e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera if (closed) 80e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera throw new ClosedWatchServiceException(); 81e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 82e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 83e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 84e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Checks the key isn't the special CLOSE_KEY used to unblock threads when 85e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * the watch service is closed. 86e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 87e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera private void checkKey(WatchKey key) { 88e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera if (key == CLOSE_KEY) { 89e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // re-queue in case there are other threads blocked in take/poll 90e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera enqueueKey(key); 91e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 92e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkOpen(); 93e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 94e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 95e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 96e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public final WatchKey poll() { 97e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkOpen(); 98e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera WatchKey key = pendingKeys.poll(); 99e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkKey(key); 100e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return key; 101e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 102e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 103e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 104e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public final WatchKey poll(long timeout, TimeUnit unit) 105e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera throws InterruptedException 106e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera { 107e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkOpen(); 108e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera WatchKey key = pendingKeys.poll(timeout, unit); 109e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkKey(key); 110e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return key; 111e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 112e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 113e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 114e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public final WatchKey take() 115e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera throws InterruptedException 116e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera { 117e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkOpen(); 118e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera WatchKey key = pendingKeys.take(); 119e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera checkKey(key); 120e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return key; 121e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 122e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 123e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 124e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Tells whether or not this watch service is open. 125e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 126e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera final boolean isOpen() { 127e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return !closed; 128e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 129e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 130e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 131e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Retrieves the object upon which the close method synchronizes. 132e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 133e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera final Object closeLock() { 134e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return closeLock; 135e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 136e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 137e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera /** 138e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * Closes this watch service. This method is invoked by the close 139e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera * method to perform the actual work of closing the watch service. 140e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera */ 141e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera abstract void implClose() throws IOException; 142e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 143e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera @Override 144e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera public final void close() 145e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera throws IOException 146e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera { 147e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera synchronized (closeLock) { 148e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // nothing to do if already closed 149e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera if (closed) 150e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera return; 151e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera closed = true; 152e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 153e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera implClose(); 154e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera 155e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // clear pending keys and queue special key to ensure that any 156e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera // threads blocked in take/poll wakeup 157e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera pendingKeys.clear(); 158e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera pendingKeys.offer(CLOSE_KEY); 159e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 160e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera } 161e6bac4bf9c85c2454ce22c91da6c654552c268e0Shubham Ajmera} 162