Stream interrupt status cleared - Java error may occur

This applies to the Path # register method. If a thread is working with a block containing this method, and another thread interrupts it in advance. Then it turns out that the method clears the interrupt status.

No, where the document mentions that it clears the thread interrupt status.

To replicate

import java.io.*; import java.nio.file.*; import static java.nio.file.LinkOption.*; import static java.nio.file.StandardWatchEventKinds.*; import java.nio.file.attribute.*; public class WatchDir { private final WatchService watcher; private void register(Path dir) throws IOException { //interrupt itself Thread.currentThread().interrupt(); boolean before = Thread.currentThread().isInterrupted(); WatchKey key = dir.register(watcher, ENTRY_CREATE, ENTRY_DELETE, ENTRY_MODIFY); boolean after = Thread.currentThread().isInterrupted(); if(before){ if(!after){ System.out.println("--------------------BUG-------------------"); System.out.format("Interrupt Status: true before making call to Path#register for folder folder: %s\n", dir); System.out.format("Interrupt Status: false after making call to Path#register for folder folder: %s\n", dir); System.out.println("The interrupt status was cleared by `register` (Unexpected Behavior)."); System.exit(0); }else{ System.out.println("Not a bug on your machine. The interrupt was not cleared after call to Path#register. Works as expected"); System.out.println("Works well on your machine. Didn't work for me on Windows and Ubuntu with Java 7"); } } } /** * Creates a WatchService and registers the given directory */ WatchDir(Path dir) throws IOException { this.watcher = FileSystems.getDefault().newWatchService(); register(dir); } public static void main(String[] args) throws Exception { // register directory and process its events Path dir = Paths.get("."); new WatchDir(dir); }} 

You may notice above that the interrupt status is cleared after calling the register function. Output Example:

 --------------------BUG------------------- Interrupt Status: true before making call to Path#register for folder folder: . Interrupt Status: false after making call to Path#register for folder folder: . The interrupt status was cleared by `register` (Unexpected Behavior). 

This problem arose because the service was found to be active even after a shutdown request. Any ideas?

edit: It turns out this only happens on Windows and Linux. The Mac behaves as expected. My OS: Win 7 64-bit. JDK 1.7.0_11. Also found by: Ubuntu 14.04 Java 1.7.0_45-b18

+8
java multithreading concurrency interrupt
source share
3 answers

The problem may be in the catch :

 } catch (InterruptedException ex) { Logger.getLogger(WatchDir.class.getName()).log(Level.SEVERE, null, ex); } 

Try to add

 // Restore the interrupted status Thread.currentThread().interrupt(); 

in the catch .

More information about this topic can be found in the message "Java Theory and Practice: Working with InterruptedException"

-one
source share

The interrupted flag for Thread not a good field to rely on only. You must control the interrupted flag and watch for interrupts.

See Sabotage Bell Act for a perfect discussion.

A particularly relevant quote from here (my emphasis):

interruption ... If this thread is blocked when the wait (), wait (long) or wait (long, int) methods of the Object class or join (), join (long), join (long, int), sleep (long) or sleep (long, int), methods of this class, then the interrupt status will be cleared and it will receive an interrupted exception.

-one
source share

It's simple. Once you have referenced interuption internaly status in the same thread. I will be cleaned.

If the interuption status refers to another thread, it will not be cleared

-2
source share

All Articles