반응형

OIO(Old Input/Output) 와 NIO(Non-blocking Input/Output or New Input/Output) 


 몇 년 사이 두드러진 netty(http://netty.io/) 나 vert.x(http://vertx.io/) 등과 같은 네트워크 라이브러리를 잘 활용하기 위해서는 비동기에 대한 못지 않게 OIO(Old Input Output) 과 NIO(Non-blocking Input Output or New Input Output) 에 대한 개념에 대해 알고 있어야 합니다.


 Java 에서 NIO 는 JDK1.4 에서부터 지원을 하기 시작했는데요. 기존의 Java I/O 는 socket 을 accept() 할 때와, data 를 read() 할 때 해당 Thread 가 Block 이 되는데요. 이런 구조? 때문에 Multi-Thread 를 사용하게 되었으나, 컴퓨터가 처리할 수 없을 정도의 요청이 들어오게 되면 Stack 에 메모리를 할당해야 하는데, 운영체제에 따라 다르지만 보통 64KB 에서 1MB 까지 차지할 수 있다고 합니다. Java는 JVM 을 통해서 많은 수를 처리할 수 있다고 하지만 그럴 경우에는 Context-Switching 에 따른 OverHead 가 크다고 합니다.


Java IO: A classic IO server design - one connection handled by one thread.



 하여튼 Multi-Thread 만으로는 부족하여, polling 과 thread-pool 을 같이 사용하기도 하지만 이또한 완벽한 비동기를 구현하기는 어렵습니다. 그래서 JDK1.4에서는 Non-blocking I/O lib 를 통해서 운영체제 레벨에서 지원되던 것을 Java를 통해서 사용할 수 있도록 했습니다.


Java NIO: A single thread managing multiple connections.


 Java NIO 에 대한 사용을 간단하게 설명하면, Selector 를 생성하여 ServerSocketChannel 에 등록하고 대기상태 없이 Selector의 SelectedSet 에서 ServerSocketChannel 로 들어온 이벤트와 관련된 SelectionKeySet 을 잃어와 이로부터 channel을 구하여 데이터를 처리하게 됩니다. 이 과정에서 Selector 는 Multi-channel 의 작업을 Single-thread 에서 처리할 수 있도록 되어 있는데 이 동작을 Multiplexing 이라 할 수 있습니다. Thread 를 사용하지 않으면서 Thread를 사용하는 효과를 볼 수 있습니다.


Java NIO: Reading data from a channel until all needed datas is in buffer.



 이를 통해, 다수의 클라이언트를 하나 또는 적은 수의 Thread로 처리하게 됨으로써, 메모리 관리와 Context-Switching에 따른 Overhead 가 감소하게 됩니다. 입출력을 처리하지 않을 때는 Thread 를 다른 작업에 활용할 수도 있습니다.




ref) http://tutorials.jenkov.com/java-nio/index.html

ref) http://javacan.tistory.com/entry/87

ref) https://devlearnings.wordpress.com/2010/09/21/tip-use-scheduledexecutor-instead-of-thread-for-polling-or-infinite-loops/

ref) http://www.ibm.com/support/knowledgecenter/SSCRJU_4.0.0/com.ibm.streams.dev.doc/doc/pollingsource.html


반응형

+ Recent posts