GNU/Linux >> Linux の 問題 >  >> Linux

パイプバッファの大きさはどれくらいですか?

のコメントとして、なぜ「| makefileの「true」は「||」と同じ効果がありますtrue」ユーザーcjmは次のように書いています:

| true コマンドがパイプバッファをいっぱいにするのに十分な出力を生成した場合、trueがそれを読み取るのを待つのをブロックするということです。

パイプバッファのサイズを確認する方法はありますか?

承認された回答:

パイプバッファの容量はシステムによって異なります(同じシステムでも異なる場合があります)。パイプの容量を調べるだけの、すばやく簡単なクロスプラットフォームの方法があるかどうかはわかりません。

たとえば、Mac OS Xはデフォルトで16384バイトの容量を使用しますが、パイプに大量の書き込みが行われた場合は65336バイトの容量に切り替えることができ、カーネルメモリが多すぎる場合は単一のシステムページの容量に切り替えることができますパイプバッファによって使用されています(xnu/bsd/sys/pipe.hを参照) 、およびxnu/bsd/kern/sys_pipe.c;これらはFreeBSDからのものであるため、同じ動作がそこでも発生する可能性があります。

1つのLinuxpipe(7) マニュアルページには、Linux 2.6.11以降のパイプ容量は65536バイトであり、それ以前の単一のシステムページ(たとえば、(32ビット)x86システムでは4096バイト)と記載されています。コード(include/linux/pipe_fs_i.h 、およびfs/pipe.c )は16のシステムページを使用しているようです(つまり、システムページが4KiBの場合は64KiB)が、各パイプのバッファは fcntlを介して調整できます。 パイプ上(最大容量はデフォルトで1048576バイトですが、/proc/sys/fs/pipe-max-sizeで変更できます。 ))。

これが少しbash / perl システムのパイプ容量をテストするために使用した組み合わせ:

#!/bin/bash
test $# -ge 1 || { echo "usage: $0 write-size [wait-time]"; exit 1; }
test $# -ge 2 || set -- "[email protected]" 1
bytes_written=$(
{
    exec 3>&1
    {
        perl -e '
            $size = $ARGV[0];
            $block = q(a) x $size;
            $num_written = 0;
            sub report { print STDERR $num_written * $size, qq(n); }
            report; while (defined syswrite STDOUT, $block) {
                $num_written++; report;
            }
        ' "$1" 2>&3
    } | (sleep "$2"; exec 0<&-);
} | tail -1
)
printf "write size: %10d; bytes successfully before error: %dn" 
    "$1" "$bytes_written"

Mac OS X 10.6.7システムでさまざまな書き込みサイズで実行していることがわかりました(16KiBを超える書き込みの変更に注意してください):

% /bin/bash -c 'for p in {0..18}; do /tmp/ts.sh $((2 ** $p)) 0.5; done'
write size:          1; bytes successfully before error: 16384
write size:          2; bytes successfully before error: 16384
write size:          4; bytes successfully before error: 16384
write size:          8; bytes successfully before error: 16384
write size:         16; bytes successfully before error: 16384
write size:         32; bytes successfully before error: 16384
write size:         64; bytes successfully before error: 16384
write size:        128; bytes successfully before error: 16384
write size:        256; bytes successfully before error: 16384
write size:        512; bytes successfully before error: 16384
write size:       1024; bytes successfully before error: 16384
write size:       2048; bytes successfully before error: 16384
write size:       4096; bytes successfully before error: 16384
write size:       8192; bytes successfully before error: 16384
write size:      16384; bytes successfully before error: 16384
write size:      32768; bytes successfully before error: 65536
write size:      65536; bytes successfully before error: 65536
write size:     131072; bytes successfully before error: 0
write size:     262144; bytes successfully before error: 0

Linux 3.19での同じスクリプト:

/bin/bash -c 'for p in {0..18}; do /tmp/ts.sh $((2 ** $p)) 0.5; done'
write size:          1; bytes successfully before error: 65536
write size:          2; bytes successfully before error: 65536
write size:          4; bytes successfully before error: 65536
write size:          8; bytes successfully before error: 65536
write size:         16; bytes successfully before error: 65536
write size:         32; bytes successfully before error: 65536
write size:         64; bytes successfully before error: 65536
write size:        128; bytes successfully before error: 65536
write size:        256; bytes successfully before error: 65536
write size:        512; bytes successfully before error: 65536
write size:       1024; bytes successfully before error: 65536
write size:       2048; bytes successfully before error: 65536
write size:       4096; bytes successfully before error: 65536
write size:       8192; bytes successfully before error: 65536
write size:      16384; bytes successfully before error: 65536
write size:      32768; bytes successfully before error: 65536
write size:      65536; bytes successfully before error: 65536
write size:     131072; bytes successfully before error: 0
write size:     262144; bytes successfully before error: 0

注:PIPE_BUF Cヘッダーファイル(および pathconf )で定義された値 _PC_PIPE_BUFの値 )、パイプの容量を指定しませんが、アトミックに書き込むことができる最大バイト数を指定します(POSIX write(2)を参照)。 。

関連:Linux –ビデオから抽出されたffmpegパイプ画像?

include/linux/pipe_fs_i.hからの引用 :

/* Differs from PIPE_BUF in that PIPE_SIZE is the length of the actual
   memory allocation, whereas PIPE_BUF makes atomicity guarantees.  */

Linux
  1. Bashでループを作成する方法

  2. クラウドがビッグデータの分析をより効率的にする方法

  3. curl -v の出力をパイプまたはリダイレクトするにはどうすればよいですか?

  1. BusyBox シェルで乱数を生成する方法

  2. Linuxのソケットバッファサイズを見つける方法

  3. GNU Screen コピー バッファをクリップボードにコピーするには?

  1. 「タブ完了」によって表示されるコマンドのリストをパイプする方法は?

  2. 8G RAM と SSD - スワップの大きさはどれくらいですか?

  3. スワップ パーティションのサイズはどれくらいですか?