質問
私は、Oracleプロセスをトレースし、それが最初のファイルハンドル/etc/netconfig
としてファイル11
を開き、パラメータ256
でfcntl
を呼び出すことにより、F_DUPFD
としてそれを複製し、元のファイルハンドルclose
を11
見つけます。その後、それはファイルハンドル256
を使用して読み取ります。だから、ファイルハンドルを複製するポイントは何ですか?なぜ、元のファイルハンドルでないだけで動作しますか?
12931: 0.0006 open("/etc/netconfig", O_RDONLY|O_LARGEFILE) = 11
12931: 0.0002 fcntl(11, F_DUPFD, 0x00000100) = 256
12931: 0.0001 close(11) = 0
12931: 0.0002 read(256, " # p r a g m a i d e n".., 1024) = 1024
12931: 0.0003 read(256, " t s t p i _ c".., 1024) = 215
12931: 0.0002 read(256, 0x106957054, 1024) = 0
12931: 0.0001 lseek(256, 0, SEEK_SET) = 0
12931: 0.0002 read(256, " # p r a g m a i d e n".., 1024) = 1024
12931: 0.0003 read(256, " t s t p i _ c".., 1024) = 215
12931: 0.0003 read(256, 0x106957054, 1024) = 0
12931: 0.0001 close(256) = 0
解決
はさておき、彼らはしているファイルの記述子のではなく、ファイルのハンドルのよう。後者は、記述子はfopen
らと共に使用するための、よりUNIXy、でありながらopen
その兄弟と共に使用Cの特徴である。
興味深いです。頭に浮かぶ唯一の理由は、コードのいくつかの他の作品は、私が唯一のOracleはそのための奇妙な理由を知っているだろう疑う256するファイルディスクリプタのための具体的なニーズを持っていることです。いずれにせよ、あなたが256を取得することを保証していない、あなたは最初に使用可能なファイルディスクリプタを超えるファイルを取得するか、その数に等しいます。
<時間> 調査のビットから(私は知らない。のすべてのの私の頭の上からUNIXの内臓についてはほとんどのもの)のような重複した記述子のグループに属し、属性がありますファイル位置とアクセスモード。このようGNULibでクローズ(close-on-exec)フラグと重複した場合でも、のシングルのファイルディスクリプタに所属する他の属性は、あります。
(どちらかdup
、dup2
たりfcntl
で)複製を行うと、2つのディスクリプタ、異なるファイルディスクリプタ属性を持つものを作成するための方法かもしれないが、私は最初の記述があるので、あなたの質問にケースされていることを見ることができませんとにかく閉じました。あなたが言うように、なぜ単に低記述子を使用していない?
あなたがnetconfig f_dupfd
のためのgoogle場合興味深いことに、fcntl
が失敗したところ、あなたは同様のトレースが表示され、それが問題に関する私の考えは、このような低いファイル記述子を保存しようとする試みであるとされているので、低記述とそのファイルを読むために続けて可能な限り。たとえばます:
4327: open("/etc/netconfig", O_RDONLY|O_LARGEFILE) = 4
4327: fcntl(4, F_DUPFD, 0x00000100) Err#22 EINVAL
4327: read(4, " # p r a g m a i d e n".., 1024) = 1024
4327: read(4, " t s t p i _ c".., 1024) = 215
4327: read(4, 0x00296B80, 1024) = 0
4327: lseek(4, 0, SEEK_SET) = 0
4327: read(4, " # p r a g m a i d e n".., 1024) = 1024
4327: read(4, " t s t p i _ c".., 1024) = 215
4327: read(4, 0x00296B80, 1024) = 0
4327: close(4) = 0
はたぶんソフトウェアは、それは255-限界以上の他のファイルを移動しようそれでは、制限することをどこかにファイルディスクリプタのバイト配列を持っています。
しかし、実際に、それはちょうど(私はそれが比較的知的な当て推量だと思うしたいと思いますが)私の部分に当て推量です。また、それは、Oracle自身がこれを行うことではないかもしれないことに注意してください。それは、特に前述のウェブヒットのほとんどはないOracle固有(ftp
、remsh
など)だったという事実に照らして、それを行う、いくつかの基本的なライブラリーでもよいので、netconfigのものは、多くの場所で使用されています。
他のヒント
一部のシステムでは、Solarisのように、FILEの標準I / Oは、ファイルディスクリプタ0〜255で動作します。プログラムは、ファイル記述子の多くを使用している場合、それはfnctl(FD、F_DUPFD、256)を使用して、3から255予備ファイルディスクリプタに便利です。それ以外の場合は、関数fopen()、freopenは()とのfdopen()などの関数を使用すると、256個のファイルが開いている場合は失敗します。
ここ低い番号のファイル記述子を確保する技術が必要とされるときに、別の例である。
プロセスは、例えば、ファイルディスクリプタの多数を開くと仮定それは1024以上の同時ソケット接続を受け付けます。同時に、プロセスは、ソケット接続と用途はソケットが読み取りまたは書き込みの準備ができているかどうかを確認するためにselect()
開き、サードパーティのライブラリを使用しています。さらに、サードパーティのライブラリは1024(デフォルト値)に__FD_SETSIZE
を設定してコンパイルされました。
それはselect()
および関連FD_ *マクロは対応できないという記述を取得します。これは、プロセスがクラッシュまたは未定義の動作になります。