Index: src/java/org/apache/lucene/store/NIOFSDirectory.java
===================================================================
--- src/java/org/apache/lucene/store/NIOFSDirectory.java	(revision 904520)
+++ src/java/org/apache/lucene/store/NIOFSDirectory.java	(working copy)
@@ -20,23 +20,46 @@
 import java.io.File;
 import java.io.IOException;
 import java.nio.ByteBuffer;
+import java.nio.channels.ClosedByInterruptException;
+import java.nio.channels.ClosedChannelException;
 import java.nio.channels.FileChannel;
+import java.util.concurrent.Future;
+
+import org.apache.lucene.index.IndexReader;
 
 /**
- * An {@link FSDirectory} implementation that uses
- * java.nio's FileChannel's positional read, which allows
- * multiple threads to read from the same file without
- * synchronizing.
- *
- * <p>This class only uses FileChannel when reading; writing
- * is achieved with {@link SimpleFSDirectory.SimpleFSIndexOutput}.
+ * An {@link FSDirectory} implementation that uses java.nio's FileChannel's
+ * positional read, which allows multiple threads to read from the same file
+ * without synchronizing.
  * 
- * <p><b>NOTE</b>: NIOFSDirectory is not recommended on Windows because of a bug
- * in how FileChannel.read is implemented in Sun's JRE.
- * Inside of the implementation the position is apparently
- * synchronized.  See <a
+ * <p>
+ * This class only uses FileChannel when reading; writing is achieved with
+ * {@link SimpleFSDirectory.SimpleFSIndexOutput}.
+ * 
+ * <p>
+ * <b>NOTE</b>: NIOFSDirectory is not recommended on Windows because of a bug in
+ * how FileChannel.read is implemented in Sun's JRE. Inside of the
+ * implementation the position is apparently synchronized. See <a
  * href="http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6265734">here</a>
  * for details.
+ * </p>
+ * <p>
+ * <font color="red"><b>NOTE:</b> As this class uses {@link FileChannel}
+ * internally it is crucial to prevent calls to {@link Thread#interrupt()} or
+ * {@link Future#cancel(boolean)} on threads that could be accessing
+ * {@link IndexInput} instances obtained from {@link NIOFSDirectory}. A call to
+ * {@link Thread#interrupt()} will close the {@link FileChannel} immediately if
+ * the interrupt occurs while the thread executes the channels low level IO
+ * operations in an unrecoverable manner. <br>
+ * If a {@link FileChannel} is closed by an interrupt the {@link IndexReader}
+ * maintaining the affected {@link IndexInput} instance is doesn't necessarily
+ * notice the {@link ClosedByInterruptException} an will remain open. Due to the
+ * fact that {@link FileChannel} instances are shared between {@link IndexInput}
+ * instances, subsequent {@link FileChannel} access will raise
+ * {@link ClosedChannelException}. <br>
+ * If your application uses {@link Thread#interrupt()} you may prefer
+ * {@link SimpleFSDirectory} over {@link NIOFSDirectory}. </font>
+ * </p>
  */
 public class NIOFSDirectory extends FSDirectory {
 
Index: src/test/org/apache/lucene/store/TestInterruptNIOFSDirectory.java
===================================================================
--- src/test/org/apache/lucene/store/TestInterruptNIOFSDirectory.java	(revision 0)
+++ src/test/org/apache/lucene/store/TestInterruptNIOFSDirectory.java	(revision 0)
@@ -0,0 +1,137 @@
+package org.apache.lucene.store;
+
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import java.io.File;
+import java.io.IOException;
+import java.nio.channels.ClosedByInterruptException;
+import java.nio.channels.ClosedChannelException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Random;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
+
+import org.apache.lucene.analysis.standard.StandardAnalyzer;
+import org.apache.lucene.document.Document;
+import org.apache.lucene.document.Field;
+import org.apache.lucene.document.Field.Index;
+import org.apache.lucene.document.Field.Store;
+import org.apache.lucene.index.CorruptIndexException;
+import org.apache.lucene.index.IndexReader;
+import org.apache.lucene.index.IndexWriter;
+import org.apache.lucene.index.Term;
+import org.apache.lucene.index.TermPositions;
+import org.apache.lucene.index.IndexWriter.MaxFieldLength;
+import org.apache.lucene.store.LockObtainFailedException;
+import org.apache.lucene.store.NIOFSDirectory;
+import org.apache.lucene.util.LuceneTestCaseJ4;
+import org.apache.lucene.util.Version;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+/**
+ * Testcase triggering the {@link ClosedByInterruptException} on
+ * {@link NIOFSDirectory}
+ */
+public class TestInterruptNIOFSDirectory extends LuceneTestCaseJ4 {
+  private NIOFSDirectory dir;
+
+  /**
+   * Create a large enough index
+   */
+  @Before
+  public void beforeClass() throws CorruptIndexException,
+      LockObtainFailedException, IOException {
+    Random oNewRandom = newRandom();
+    File path = new File(System.getProperty("java.io.tmpdir"), "footest");
+    path.mkdirs();
+    dir = new NIOFSDirectory(path);
+    IndexWriter writer = new IndexWriter(dir, new StandardAnalyzer(
+        Version.LUCENE_CURRENT), true, MaxFieldLength.UNLIMITED);
+    int docs = 1000000 + oNewRandom.nextInt(100);
+    writer.setUseCompoundFile(false);
+    for (int oI = 0; oI < docs; oI++) {
+      Document doc = new Document();
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      doc.add(new Field("foo", "hello world hello m world", Store.NO,
+          Index.ANALYZED));
+      writer.addDocument(doc);
+    }
+
+    writer.commit();
+    writer.optimize();
+    writer.close();
+  }
+
+  @Test
+  public void testInterruptOnNIOFSDirectory() throws CorruptIndexException,
+      IOException, InterruptedException {
+    final IndexReader reader = IndexReader.open(dir);
+    ExecutorService service = Executors.newFixedThreadPool(20);
+    List<Future<Exception>> list = new ArrayList<Future<Exception>>();
+    for (int oI = 0; oI < 40; oI++) {
+      Callable<Exception> oRunnable = new Callable<Exception>() {
+
+        public Exception call() {
+          try {
+            TermPositions oTermDocs = reader.termPositions(new Term("foo",
+                "hello"));
+            while (oTermDocs.next()) {
+              int res = oTermDocs.freq() + oTermDocs.doc()
+                  + oTermDocs.nextPosition();
+            }
+
+          } catch (Exception oPEx) {
+            return oPEx;
+          }
+          return null;
+        }
+      };
+      list.add(service.submit(oRunnable));
+    }
+
+    for (Future<Exception> oFuture : list) {
+      oFuture.cancel(true);
+
+    }
+    try {
+      TermPositions oTermDocs = reader.termPositions(new Term("foo", "hello"));
+
+      while (oTermDocs.next()) {
+        int res = oTermDocs.freq() + oTermDocs.doc() + oTermDocs.nextPosition();
+      }
+      Assert.fail("close by interrupt");
+    } catch (ClosedChannelException e) {
+      // expected
+    }
+
+  }
+}
\ No newline at end of file
