How does I/O-methods like read() put a Thread in blocked state in java?
Asked Answered
F

2

6

So, if i have understood this correctly, a thread goes into waiting state when we call wait on an object and it goes into blocked state when it is waiting for a lock on an object(like when trying to get into a synchronized block or method).

How does I/O-methods like read() put a Thread in a blocked state though? I understand WHY it has to be in a blocked state, waiting for data that it can read but i'm also interested in HOW. How does the JVM notify the thread that it can continue when data in the resource its trying to read, is available again?

Flog answered 14/12, 2016 at 11:48 Comment(0)
H
7

It doesn't change the state of the thread to BLOCKED

public static void main(String[] args) throws IOException {
    Thread main = Thread.currentThread();
    new Thread(() -> {
        for (int i = 0; i < 10; i++) {
            System.out.println(main + " is in "+main.getState()+" state");
            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                throw new AssertionError(e);
            }
        }
    }).start();
    System.in.read();
}

prints

Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state
Thread[main,5,main] is in RUNNABLE state

instead the OS doesn't return from the read until there is some data and the OS decides whether and when to context switch the thread/process.

How does the JVM notify the thread that it can continue when data in the resource its trying to read, is available again?

The OS wakes the thread when there is more data or the stream has been closed. The JVM doesn't get involved.

Halfbound answered 14/12, 2016 at 12:36 Comment(0)
T
2

This depends on the native platform.

In POSIX, a call to read usually blocks until data is available, but there are many other reasons to return, such as an end-of-file was reached, the file descriptor was closed, the operation timed out or a signal interrupted the operation.

In Windows, the most closely related function is ReadFile.


The gory details, refering to Java 8 update 112 b15:

FileInputStream.read calls the native FileInputStream.read0, implemented natively through JNI in Java_java_io_FileInputStream_read0, which calls readSingle, which calls IO_Read.

In POSIX, IO_Read is defined as handleRead, which calls read. The RESTARTABLE macro loops while there's an error and the errno is EINTR.

In Windows, IO_Read is defined as handleRead, which calls ReadFile.

Taffrail answered 14/12, 2016 at 12:13 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.