|
감사합니다. 마지막에 파일 처리론이란 책을 추천해 주셨는뎅....
음 열심히 읽어 보겠씁니다.
그럼
열씸! 님이 쓰신 글 :
: Buffered I/O 와 Non-Buffered I/O를 이야기 하시는 것 같군요.
: Buffered I/O 함수들은, 버퍼가 가득 차거나, 별도의 END_OF_LINE으로써의 개행코드,
: END_OF_FILE(EOF) 등의 특정 심볼에 반응하여 버퍼된 데이타를 Update하는 식,
: 혹은 그밖에 Half Duplex 구조일 경우 입력스트림과 출력스트림을 스위칭 해야 할 때 등의 경우
: 입출력을 일단락 짓도록 설계되어 있기 때문에, 당장 입출력을 보내고 싶을 때 fflush 함수를 사용하는 것이죠.
: GDI 함수들 중의 Update 와 Invalidate 의 경우와도 유사한 형식이라 볼 수 있습니다.
:
: 반면, 저수준 입출력이라고 말씀하신 open, close, lseek, read, write 등의 함수들은
: C/C++ 의 Library Function(대부분 Buffered I/O) 이 아닌
: 운영체제가 제공해 주는 함수(API)로써, 의도 되지 않은 버퍼링이나 메모리 낭비를 줄이기 위해
: 즉시 반응하게 되어 있습니다.
:
: 조금 여담이지만 getc, putc의 경우는 마치 API함수인것 처럼 생겼지만, fgetc, fputc의 매크로 형식입니다.
: 단지 Buffered I/O 함수명들과 Non-Buffered I/O 함수명들이 pair를 이루는것 처럼 보이기 위한 것이죠.
: 반면, fflush의 경우는 Non-buffered 의 경우 flushing 할 일이 없으니 당연히 존재할 필요가 없구요.
:
: HDD 의 구조를 Block Device 라고 합니다.
: 그 이유는, 한번에 1byte씩 I/O할 수 있는 구조가 아니라(Flash Memory도 Block Device죠),
: 512byte씩 혹은 그의 배수를 최소 단위로 I/O할 수 있는 Device이기 때문입니다.
: 코딩의 편의를 위해 한 바이트씩 읽을 필요가 있어 getc / putc / fgetc / fputc 등의 함수를
: 구현해 놓긴 했지만,
: Non-buffered인 read 함수를 이용해 1byte씩 읽는다 칩시다. (혹은 그걸 getc 라고 매크로 해 놓고 사용했다 칩시다)
: 그런 경우, 연속한 100byte를 1byte씩 읽어오기 위해서는
: 512바이트를 하드에서 읽어오고 1바이트를 취한 다음 나머진 버리고
: 다시 512바이트를 하드에서 읽어 또 1바이트를 버리는 식이니 엄청난 낭비이겠죠?
: 그래서 파일 입출력에 Buffered I/O 함수들이 구현된 것이고,
: 실제 fgetc(getc) 등을 연속적으로 호출 할 때, 하드디스크에서 매번 읽어오는게 아니라,
: 한꺼번에 하드디스크의 Block 크기만큼 읽어놓은 메모리(버퍼)에서 1바이트씩 가지고 오니
: 효율적이고 빠른 I/O가 가능하게 되는겁니다.
:
: CPU와 Memory는 Local Bus 형태로 고속으로 입출력이 가능하게 되어 있습니다.
: 반대로, 주변 장치들의 I/O는 CPU점유율이 높고(당연하게도 I/O명령은 기본적으로 CPU가 내리는데다,
: Mainboard 의 주파수는 CPU의 주파수 보다 훨씬 느리기때문에 쓸데없이 CPU가 기다려야 하죠)
: CPU를 경유해 다시 Memory로 전송되어야 하는 경우가 태반이라 잦은 외부 I/O는 시스템을 느려지게 합니다.
: 이를 극복하기 위해 크게 Multi-programming, DMA Channel 같은 기술을 사용하고 있지만,
: DMA(Direct Memory Access) Channel 방식을 지원하는 장치는 많지 않습니다.
: 이는 CPU를 거치지 않고 메모리에 확보된 영역에 외부 I/O들이 바로 써 넣는 기법이므로,
: 별도의 프로토콜을 가져야 함이죠.
:
: 정리하자면,
: 버퍼 관리를 멋지게 해 낼 자신이 있다면, 저수준 함수를 사용해 별도의 고수준 함수들을 만들어도 좋습니다.
: 각각의 외부 H/W I/O들에 대한 배경지식이 부족하여 잘 해 낼 자신이 없다면,
: 잘 만들어진 fopen, fclose, fread, fwrite, fseek, fgetc, fputc 등의 buffered I/O 함수를 쓰는게
: 성능에 도움이 되는 것입니다.
:
: 파일처리론 책을 숙독하시면 쉽게 알 수 있는 이야기들이었군요.
: 그럼 이만.
:
: 김상면 님이 쓰신 글 :
: : 고 수준의 파일 입출력은 fflush함수로 입출력을 동기화 하는 걸로 알고 있는데...
: : 저수준의 파일 입출력은 이런 동기화가 필요 없나요? 왜 flush가 없징....
: :
: : 고수님의 답을 구합니다.
: : 그럼
|