2011-10-20 8 views
1

私は、ファイルを開いて操作中に(通常は一度に何日も)日々書き込むデーモンを持っています。ログのローテーションをサポートするために、ハンドルが参照しているファイルがいつ元の新しい場所にあるのかを識別できるようにしたい。Linuxのファイルハンドルからのファイルパスを確認する

これは可能ですか? fstat()は、この状況に役立つものは何も私に与えません。

私の現在の解決策は、ログ記録機能でログファイルの存在をテストし、存在しない場合は古いハンドルを閉じて新しいハンドルを開くことです。これは動作しますが、ハックであり、制限があります。私の場合、私たちのシステムグループでは、ログを回転させるツールを使用しています。回転ツールは、回転させた後にファイルに触れなければならないため、デーモンはファイルハンドルが正しい場所を指していると考え続けます。

+0

このスレッドを見て、phpマニュアルに相当する機能があるかどうかを確認してください。 http://stackoverflow.com/questions/1188757/getting-filename-from-file-descriptor-in-c – Jake

答えて

3

ここに考えがあります。それは移植性がない、私はそれが動作しているか信頼できるかどうか完全にはわからないが、それは私には少し気になるが、おそらく/proc/%d/fd/%dreadlinkを使用することができ、最初の%dgetpid()の結果であり、ディスクリプタ。

ここにいくつかの注意点があります。まず、「パスを取得+そのパスで何かを行う」というアプローチは、名前の変更が同時に起こっても競合状態になります。また、ログファイルには他のリンクが存在する可能性があります。私は名前の変更に直面して/procのリンクの動作が何であるか分かりません。

+0

procファイルはファイル記述子を取得します。 'fstat'から別の答えを与えるつもりはありません – mkj

+0

@mkjこれは本当ですか?最後に、 'struct stat'には名前フィールドがないことが分かっていました。 – asveikau

+0

これは名前フィールドではなく、inode番号を与える 'st_ino'フィールドです。 – mkj

0

ファイルハンドル(モードa)を定期的に(たとえば24時間ごとに)定期的に再取得できます。これにより、ファイルの名前を変更してから再度タッチする間に避けられない競合条件が存在するため、ログ回転ユーティリティーを使用することによって、馬鹿馬鹿しくてバグの存在にもかかわらずログを継続することができます。

0

fstatは、ログをローテーションするときに変更されるinode番号を示します。

はあなたがlstatからinode番号でfstatからiノード番号を比較することができhttp://php.net/manual/en/function.fstat.phphttp://www.php.net/manual/en/function.lstat.php

を参照してください。それらが異なる場合は、再度開きます。

これをUnixデーモンでこれまで扱ってきた標準的な方法は、SIGHUPをキャッチしてログファイルを再オープンするシグナルとして使用し、ログローテーションスクリプトをSIGHUPに送信することでした。

+0

私のテストでは、ファイルを移動するとiノードは変更されません。良い、信頼できる解決策ではないようだから、私はSIGHUPを扱うことが私のやり方になるかもしれないと思う。 – Mark

+0

正確には、ファイルを移動するとiノード番号は変わりません。あなたのファイル記述子の 'fstat'があなたがそれを開くときにファイルの名前に' lstat'と異なるinode番号を生成すると、あなたがそれを開いてからファイルが移動または削除されました。すべてのことが言った、 'SIGHUP'処理の実装はUnixの方法です。 'lstat'と' fstat'をチェックすることは、誰かが 'SIGHUP'を送ることを忘れた場合のバックアップ戦略です。 – mkj

関連する問題