F_GETFL fcntlコマンドのargが必要なのはいつですか?
質問
int fcntl(int fd, int command, ... /* arg */ );
それはポータブルですか: flags = fcntl(fd, F_GETFL);
(注:いいえ。 arg
)?
両方 リナックス と FreeBSD manページはそれを言う arg
は無視されます:
F_GETFL (void)
Get the file access mode and the file status flags; arg
is ignored.
void
Linuxのドキュメントでは、 arg
必須ではありません。
ここにaがあります 関連するPOSIXの使用例 F_GETFD
旗:
#include <unistd.h>
#include <fcntl.h>
...
int flags;
flags = fcntl(fd, F_GETFD);
if (flags == -1)
/* Handle error */;
flags |= FD_CLOEXEC;
if (fcntl(fd, F_SETFD, flags) == -1)
/* Handle error */;"
それはそれを示しています arg
は必須ではありません F_GETFD
(今日)。それからそれは言う:
F_GETFD、F_SETFD、F_GETFL、およびF_SETFLのarg値はすべて次のものを表します 将来の成長を可能にするフラグ値。
それはそれを意味しますか F_GETFL
使用するかもしれない arg
将来的には?
Ohlohコードで"F_GETFL"をすばやく検索すると、次のような印象が得られます ほとんどのオープンソースプロジェクトは合格します arg
(通常は 0
,時々 NULL
, 、あるいは(壊れた?) &fl
).私はなぜ理解していない fcntl(fd, F_GETFL, 0)
が好ましい形態である。 @Wumpus Q.Wumbleyは示唆しています それが原因である可能性があること "UNIX環境での高度なプログラミング"の本 それはまた使用します fcntl(fd, F_GETFL, 0)
フォーム。
3番目の引数を必要とするシステム/コンパイラはありますか: flags = fcntl(fd, F_GETFL, 0);
?できます fcntl(fd, F_GETFL)
と fcntl(fd, F_GETFL, 0)
今日または将来的に異なる結果を生成します(準拠した実装を前提としています)か?
解決
残りのfcntlコマンドを見てください。それらのいくつか(F_DUPFD、F_SETFLなど)が3番目のargが何に使用されているかをどのように教えているかに注意してください。それらのいずれかを使用するときは、3番目の引数を提供する必要があります。F_GETFLまたはF_GETFDを使用している場合はそうではありません。
概要では、fcntlが2つの引数とaを取ることがわかります ...
これは、3番目のargが使用されないときに省略できることを意味します。
いくつかの調査を行った後、私はいくつかの古いmanページ(最初のAPUEの頃から)があり、その中には3つの引数すべてが必要であることが示されています。例を示します。: http://www.freebsd.org/cgi/man.cgi?query=fcntl&manpath=FreeBSD+2.2.7-RELEASE
SYNOPSIS
#include <fcntl.h>
int
fcntl(int fd, int cmd, int arg);
ヘッダーで実際にそのように宣言されたという証拠は見つかりませんが、そうであれば、2つの引数だけで呼び出されたときにコンパイルが失敗しそれはあなたのコードに余分な0引数を含める良い理由でしょう。
私の推測が正しく、これが3-arg F_GETFLの歴史的な使用の実際の理由である場合、関数のプロトタイプが新しくて怖くてOSベンダーが間違っていた時から
他のヒント
FreeBSDベースシステムでは、両方 fcntl(fd, F_GETFL)
と fcntl(fd, F_GETFL, 0)
が使用される。しかし、ほとんどの場合、3番目の引数0が使用されます。これは以来、歴史的な理由のためである可能性があります fcntl
4.2BSDに遡り、4.4BSD-Liteのソースコードを介してFreeBSDにインポートされました。
4.4BSD(およびFreeBSD2.0)では、マニュアルページは引数を次のようにリストしていました 必須: int fcntl(int fd, int cmd, int arg)
, 、実際の古い学校のヘッダーがないにもかかわらず ない: int fcntl(int, int, ...)
.
に関しては... なぜ, 、それは答えるのが難しいでしょう。私たちは、元の著者(複数可)に依頼する必要があります。しかし、元のソース管理タグには(ユーザー)名前が記録されていないため、それらを追跡する方法がわかりません。
余分な0引数は、おそらくFreeBSDコードベースでは削除されなかったでしょう。
これらの2つの呼び出し
flags = fcntl(fd, F_GETFL);
flags = fcntl(fd, F_GETFL, 0);
3番目の可変長引数は無視されるため、等価です。あなたが見てみると fs/fcntl.c
:262 と fs/fcntl.c
:269 あなたはそれを見るでしょう arg
は使用されない。
ただし、値を設定する必要がある場合は、設定する値を渡す必要があります。
あなたは考えることができます fcntl
ゲッターとセッターのOOPに相当するものとして。
3番目の引数を必要とするシステムはありますか:フラグ=fcntl(fd,F_GETFL,0);?
私は何も認識していません。少なくともLinuxはそうではありません。ドキュメントには、以下の使用がないため無視されていることが明確に記載されています arg
.あなたが何かを渡すことができるという事実は、あなたがしなければならないことを意味するものではありません。
できます
fcntl(fd, F_GETFL)
とfcntl(fd, F_GETFL, 0)
いくつかのシステムで異なる結果を返します(過去、今日、および将来(準拠した実装を前提としています))?
lxr
私たちは、linuxの古いバージョンに掘り下げることができ、さらには1991で、Linux2.0.4, fcntl
3番目の引数を渡します。それ以上の議論を受け入れる意味はありません。したがって、その3番目の引数が意味を持つシステムがある場合、それは確かにLinuxではありません。
私はいくつかのさらなる研究をしました、そして私はいくつかの矛盾する結果を見つけました。を見てください ここに:いくつかの本があります(私はそれらへの直接リンクを投稿していません protected
)を提案していますか fcntl
3つの引数関数として。しかし、少なくともに関して GETFL
/GETFD
, 、については言及されていません arg
.
私見、その行動は真剣に取られたことはありません:つまり、何があなたを不思議にさせるのか。さらに、私はその第三の議論を使用することは有害であると考えています:それが意味を持っている/持っている場合はどうなりますか?
私は再びLinuxを通過しましたが、これらのコマンドの3番目の引数は渡されません。
ついに!
3番目の引数を必要とするシステム/コンパイラはありますか:フラグ=fcntl(fd,F_GETFL,0);?Fcntl(fd,F_GETFL)とfcntl(fd,F_GETFL,0)は、今日または将来(準拠した実装を前提とした)異なる結果を生成できますか?
未来は謎です。今日、私はそれを除外するのに十分なことを感じています。しかし、過去には かもしれない そうされています。