명명된 파이프의 버퍼 크기 변경

명명된 파이프의 버퍼 크기 변경

명명된 파이프의 경우 512바이트보다 작은 쓰기는 원자적이라고 들었습니다(쓰기는 인터리브되지 않음).

특정 명명된 파이프 수를 늘리는 방법이 있습니까?

그것은 다음과 같습니다:

mkfifo mynamedpipe --buf=2500

이것은 완전한 문서라고 합니다: http://www.gnu.org/software/coreutils/manual/html_node/mkfifo-invocable.html#mkfifo-inspiration

man mkfifo해당 페이지로 이동해 주세요.

답변1

파일은 fifo단순한 파일 형식이며 읽기 및 쓰기를 위해 열리면 파이프라인() 시스템 호출처럼 파이프가 인스턴스화됩니다.

적어도 Linux에서는 이 파이프를 통해 전송된 데이터가 파일 시스템에 전혀 저장되지 않습니다(커널 메모리로 커널에만 저장됨). 게다가크기fifo 파일의 속성은 관련이 없으며 항상 0입니다.

Linux에서는 파이프 버퍼의 크기를 변경할 수 있습니다(파이프가 pipe()인스턴스화를 사용하여 인스턴스화되는지 또는 fifo 파일을 열어 파이프가 인스턴스화되는지 여부) F_SETPIPE_SZ fcntl(). 그러나 권한이 없는 사용자의 경우 제약 조건이 적용됩니다 /proc/sys/fs/pipe-max-size. 파이프의 작성자나 리더는 누구나 이 명령을 실행할 수 있지만 fcntl()작성자가 그렇게 하는 것이 더 합리적입니다. 명명된 파이프의 경우 fifo 파일을 통해 인스턴스화된 각 파이프에 대해 이 작업을 수행해야 합니다.

$ mkfifo fifo
$ exec 3<> fifo # instantiate the pipe
$ seq 20000 > fifo
^C  # seq hangs because it's trying to write more than 64KiB
$ exec 3<&- 3<> fifo # close the first pipe and instantiate a new one
$ (perl -MFcntl -e 'fcntl(STDOUT, 1031, 1048576)'; seq 20000) > fifo
$ # went through this time

위에서는 (내 시스템에서는 1031) 값을 인코딩하여 perl을 발행 했습니다 . fcntl()F_SETPIPE_SZ

답변2

변경하는 대신 processus를 F_SETPIPE_SZ다음과 같은 표현식으로 대체하여 동일한 효과를 갖는 bash 쉘 구현이 있습니다. (런타임에 파일 설명자로 대체됩니다)fifo>(stdbuf -o100M grep -a '^' > fifo)/dev/fd/63

mkfifo fifo
exec 3<> fifo
seq 12000000 > >(stdbuf -o100M grep -a '^' > fifo)

모든 필터가 버퍼링 모드 변경에 민감한 것은 아닙니다 stdbuf. 예를 들어 단순히 사용할 수는 없습니다 cat. 같은 이유로 역시 말할 수 없습니다 stdbuf -o100M seq 12000000 > fifo. 내가 아는 한, sed grep그냥 awk클래식을 하자.

단점은 하나 이상의 프로세스를 시작해야 한다는 것입니다. 장점은 거대한 버퍼 크기를 자유롭게 구현할 수 있다는 것입니다.

관련 정보