IO Systems

CPU -> IO Controller

  1. Direct IO vs Memory-mapped IO: CPU가 메모리장치에게 명령을 내리는 방식의 차이
  2. IR&DR: CPU가 IO컨트롤러에게 명령을 전달할때 IO 컨트롤러에는 CPU가 내리는 명령을 저장하는 IR레지스터 와 데이터를 저장할 수 있는 DR이 존재한다.
  3. graphics controller, SCSI controller, disk controller, memory controller등이 빠른 i/o를 위해서 PCI버스와 연결 되어있고 키보드 등의 느린 IO장치는 expansion버스에 연결되어있다.

IO디바이스 명령어 수행

  1. Programmed IO: IO장치에서 처리한 결과를 CPU레지스터에 직접 전달하는 방식. IO의 결과 입출력이 적은 키 보드, 마우스 같은 경우 사용한다.
  2. Interrupt: IO장치가 처리가 완료되었을때 CPU에게 알려주는 방법
  3. DMA: 디스크에서 많은 데이터를 메모리로 로드해야하는 경우 사용. 디스크에 존재하는 DMA컨트롤러가 CPU에게 허락을 받고 이후에는 CPU를 거치지 않고 버스를 통해서 바로 메모리로 데이터를 로드하는 방식

Direct IO

  1. Intel CPU에서 사용하는 방식. 다양한 IO디바이스 각각에 적합한 Instruction을 CPU에 전부 따로 넣고 명령을 처리하는 레지스터도 별도로 구현. CPU입장에서는 메모리도 IO장치이다. CPU설계상에 Instruction이 핀 형태로 구현되어 수행되기 때문에 IO처리에 불필요한 메모리 사용이 없고 빠른 처리가 가능하다. 하지만 Instruction의 수가 늘어나면 각 IO디바이스 대상으로 명령을 수행하는 버스를 따로 둬야 하고 CPU의 복잡도가 증가하며 생 산가격도 증가한다.

Memory Mapped IO

  1. ARM코어에서 사용하는 방식. Instruction의 개수가 많아져서 CPU가 복잡해지는것을 방지하기 위해서 가장 많이 사용하는 IO명령인 메모리의 Input Output방식을 다른 디바이스의 IO에도 활용한다. 특정 메모리 영역을 컨트롤러와 연결해놓고 CPU가 디스크 IO를 수행하면 메모리의 특정 영역에 write을 수행하고 그 데이터가 메모리를 거쳐서 디스크에 저장된다. Direct IO보다 느리지만 MEMR MEMW 명령어 한 세트만 가지고 메모리와 IO명령을 관리할 수 있어서 하드웨어 복잡도가 떨어지고 전력소모도 줄어든다. 어떤 방식을 쓰느냐는 CPU 아키텍쳐가 CISC인지 RISC인지에 따라서 다르다.

Kernel IO Structure

  1. 하드웨어 단에 IO디바이스들이 존재하고 각각의 디바이스들의 컨트롤러가 존재한다. 컨트롤러를 소프트웨어적으로 제어하기 위해서 드라이버라는 시스템 소프트웨어를 컨트롤러마다 제조사에서 제공한다. 드라이버는 특정 하드웨어 dependent한 내용을 다루는 소프트웨어이다. 요즘에는 복잡한 IO장치가 아니라면 Universal Drive가 존재하지만 기능이 많거나 처리할 데이터가 많으면 제조사에서 드라이브를 제공한다. 드라이버들은 IO컨트롤러에 일대일 매핑된다. Kernel IO서브시스템은 드라이버들의 공통적인 부분들을 표준화하여 처리한다. 프리징 된 상태에서 클릭 명령이 여러번 중복되어 들어가서 오버헤드가 발생하면 Kernel IO Subsystem은 이미 요청한 것에 대해서 처리가 되었는지 확인하고 동일한 명령을 무시하도록 처리한다. 이러한 빈번한 IO를 중재하고 커널에서 어떤 드라이버에 명령을 전달할지, 드라이버에서 전달받은 데이터를 어떤 앱에 전달할지 등을 통합해서 관리하는 시스템이다. Device Independent IO Software라고 한다.

IO 요청 순서

  1. user어플리케이션에서 system call로 요청이 들어오면 커널이 올라오고 커널은 IO서브시스템 함수를 호출한다. 버퍼 캐시에 요청이 캐싱되어있다면 바로 시스템 콜 요청결과로 전달한다. 캐싱되어 있지 않으면 어떤 드라이버에 요청을 보낼지 확인해서 요청을 보내고 드라이버는 컨트롤러가 이해할 수 있는 형태로 명령을 내린다. IO처리가 완료되면 컨트롤러가 인터럽트를 발생시키고 인터럽트 핸들러가 동작하고 인터럽트 핸들러가 드라이버로 정보를 전달한다. 드라이버는 IO서브시스템 거치지 않고 요청한 어플리케이션에 결과를 전달한다.
  2. 채팅 어플리케이션 예시: 키보드로 들어온 데이터로 인해 Programmed IO로 인터럽트가 걸리고 인터럽트 핸들러가 동작한다. 그다음 드라이버로 데이터를 넘겨주고 유저 프로세스로 넘겨준다. 엔터가 입력되면 네트워크 어뎁터에게 데이터를 보내고 받는 쪽에서도 데이터를 네트워크 데몬에게 보내서 IPC를 통해 유저 프로세스에 전달한다.