大量のゴミを印刷するツール(openocd
)を使用しています。次に、基本的なプログレスバーで単純なドットをゆっくりと印刷し、次にゴミを印刷します。
この出力をgrep
でフィルタリングして、プログレスバーのある行のみをリアルタイムで表示したいと思います(つまり、openocd
によって出力された各ドットはすぐに端末に出力されます):
openocd <args> |& grep '^\.'
問題は、grep
が(せいぜい)行バッファリングされているため、終了するまで進行状況バーが表示されないことです。
grep
を使用するにはどうすればよいですか、またはこれを実現するための標準的な代替手段はありますか? openocd
構成を使用する方法がある場合、これは便利ですが、より一般的な解決策を使用します。
これは一種のハック/異常な答えです。これは、あまりクリーンでない方法で可能性が高いという事実です。
grep
自体は、改行文字が検出された場合にのみ出力を出力するようです。プログレスバーは、更新時に改行文字を導入しない可能性が高いため、問題が発生します。
strace
は、コマンドが呼び出しているシステムコールを表示するために使用されるツールです。これには、メモリ/ストレージへの読み取りや書き込み、ファイル記述子の開閉などが含まれます。
strace
を使用すると、プロセスがアクセスしているものを表示できます。パイプの場合、stout
がgrep
に渡されているため、strace
を使用すると、grep
にフィードされているテキストを表示できます。 strace
には、pipedコマンドからの出力が定期的に送信され、その出力をスニッフィングして表示できます。私はrsync --progress
でテストしていましたが、これは同様のシナリオに遭遇したようです。 ##%
でgrep
を使用しました。これは、rsync
が進行状況を表示するために使用するためです。
rsync --progress file1 file2 | strace -e trace=read grep "[0-9]*%"
このコマンドを実行すると、strace
にNiceの出力がないことがわかりますが、strace
はread
からrsync
をいくつかキャッチしましたが、grep
は通常write
ではなく、read
sの0%、21%、45を示しています%、68%、91%、100%は、ほぼ毎秒更新されているようです(おそらく、rsync
が進行状況を更新する頻度に基づいています)。
そのため、同じgrep
を再度呼び出すことで、strace
出力をgrep
できますが、これはあまり良いことではありません。
rsync --progress file1 file2 | strace -e trace=read grep "[0-9]*%" 2>&1 > /dev/null | grep -o "[0-9]*%"
strace
はstderr
に出力されるため、2>&1
は重要です。 > /dev/null
はstdout
を/dev/null
にリダイレクトして、最初のgrep
の出力が報告されないようにします。これの最終結果は次の出力でした:
0%
21%
45%
68%
91%
100%
grep
を交換する必要がありますが、これでうまくいくようです。きれいではありませんが、機能し、grep
の制限を回避します。 grep -f
のように機能するtail -f
は便利だと思われます(grep -f
はすでに使用されています)。
最初のgrep
は、strace
がread
ingになるテキストをフィルタリングするだけです。これは、strace
s read
呼び出しに一致する行のみがリストされるためですが、strace
がそれを監視できるようにテキストを移動するための何かも必要です。