web-dev-qa-db-ja.com

ログファイルに追加するのが2 >>&1ではなく2>&1である理由

STDOUTとSTDERRを単一のファイルにリダイレクトし、常に拡大しているため、常に「追加」リダイレクトを使用します。これは>>です

私のコマンドはcommand >> logfile 2>&1です

そしてそれは機能します。

ただし、STDERRリダイレクトには>が1つあり、これを使用してファイルを「作成」し、command > outlog 2> errlogのように以前のファイルを消去しました。

この場合、ログファイルが消去されないのはなぜですか?

43
Mikel Vergy

何かを&numberにリダイレクトしても、新しいファイルはまったく開かれません。あなたはすでに開いているファイルを再利用するであり、それが開かれたモードと一緒です。

番号は「オープンファイル」ハンドル(ファイル記述子)を参照します。したがって、>&>>&(および実際には<&)の動作に技術的な違いはありません。これらはすべて「dup()を使用して既存のファイル記述子を複製する」という意味です。

つまり、2>&1は、ファイル記述子#1(以前に開いた追加用>>logfileを使用)が番号#2に複製されていることを示します。はい、2<&1も同様に機能します。

サイドのテクニカルノート:追加と切り捨ては、シェルが行う明示的なアクションではありません。これは実際にはシェルが指定するモードです開くときファイルで、残りはOS自体によって実行されます。たとえば、>を使用すると、シェルは古いコンテンツを消去しませんmanuallyは、open()を呼び出すときにO_TRUNCを追加するだけです。したがって、open()が呼び出されない場合、すべて、以前のモードは変更されません。

54
user1686

シーケンス command >> logfile 2>&1には2つのリダイレクトステージがあります。

  • command >> logfileはログファイルに追加します
  • 2>&1はstderrをstdoutにリダイレクトします(それ自体追加がログファイルに)

そう command >> logfile 2>&1はログファイルを切り捨てませんが、command >>logfile 2>logfileでしょう。

14
Eugen Rieck