Provided by: manpages-ja-dev_0.5.0.0.20221215+dfsg-1_all bug

名前

       fcntl - ファイルディスクリプターの操作を行う

書式

       #include <unistd.h>
       #include <fcntl.h>

       int fcntl(int fd, int cmd, ... /* arg */ );

説明

       fcntl()   は、オープンされたファイルディスクリプター fd に関して下記の操作を行う。操作は cmd によって決ま
       る:

       fcntl() はオプションとして第三引数をとることができる。 第三引数が必要 かどうかは cmd により決まる。必要な
       引数の型は cmd 名の後ろの括弧内で 指定されている (ほとんどの場合、必要な型は int であり、この引数を表すの
       に arg という名前を使っている)。引数が必要ない場合には void が指定さ れている。

       下記のいくつかの操作は特定のバージョンの Linux カーネルでのみサポートされている。  ホストカーネルが特定の
       操作をサポートしているかを確認する推奨の方法は、  fcntl() を所望の cmd 値で呼び出し、 EINVAL で失敗するか
       を検査することである。 EINVAL が返った場合、カーネルがこの値を認識していないことを示す。

   ファイルディスクリプターの複製
       F_DUPFD (int)
              Duplicate the file descriptor fd using the lowest-numbered available file descriptor greater  than
              or  equal  to  arg.   This  is  different  from  dup2(2),  which  uses exactly the file descriptor
              specified.

              成功すると、新しいファイルディスクリプターが返される。

              詳細は dup(2)  を参照のこと。

       F_DUPFD_CLOEXEC (int; Linux 2.6.24 以降)
              F_DUPFD と同様だが、それに加えて複製されたファイルディスクリプターに対して close-on-exec  フラグを
              セットする。  このフラグを指定することで、プログラムは FD_CLOEXEC フラグをセットするために fcntl()
              の  F_SETFD  操作を追加で行う必要がなくなる。   このフラグがなぜ有用かについては、   open(2)    の
              O_CLOEXEC の説明を参照のこと。

   ファイルディスクリプターフラグ
       The  following commands manipulate the flags associated with a file descriptor.  Currently, only one such
       flag is defined: FD_CLOEXEC, the close-on-exec flag.  If the FD_CLOEXEC bit is set, the  file  descriptor
       will  automatically  be  closed  during  a  successful  execve(2).   (If  the  execve(2)  fails, the file
       descriptor is left open.)  If the FD_CLOEXEC bit is not set, the file descriptor will remain open  across
       an execve(2).

       F_GETFD (void)
              Return (as the function result) the file descriptor flags; arg is ignored.

       F_SETFD (int)
              ファイルディスクリプターフラグに arg で指定した値を設定する。

       マルチスレッドプログラムでは、  fcntl() の F_SETFD を使って close-on-exec フラグを設定するのと同時に、 別
       のスレッドで execve(2) と fork(2) を実行することは、競合条件次第では、 そのファイルディスクリプターが子プ
       ロセスで実行されるプログラムに意図せず見えてしまうという危険性がある。 詳細とこの問題への対処法については
       open(2) の O_CLOEXEC フラグの議論を参照のこと。

   ファイル状態フラグ
       オープンファイル記述  (open  file  description)  には、  ファイル記述毎に設定される状態フラグがいくつかあ
       る。これらのフラグは   open(2)    によって初期化され、  fcntl(2)   により変更することもできる。これらは、
       (dup(2), fcntl(F_DUPFD), fork(2)  などで) 複製されたファイルディスクリプター同士は 同じオープンファイル記
       述を参照する。 そのため、 同じファイル状態フラグが共有される。

       ファイル状態フラグとその意味は open(2)  で説明されている。

       F_GETFL (void)
              Return (as the function result)  the file access mode and the file status flags; arg is ignored.

       F_SETFL (int)
              ファイル状態フラグに    arg    で指定された値を設定する。   arg   のうち、ファイルのアクセスモード
              (O_RDONLY, O_WRONLY, O_RDWR)  とファイル作成フラグ (すなわち O_CREAT, O_EXCL,  O_NOCTTY,  O_TRUNC)
              に関するビットは無視される。 Linux では、このコマンドで変更できるのは O_APPEND, O_ASYNC, O_DIRECT,
              O_NOATIME, O_NONBLOCK フラグだけである。フラグ O_DSYNC, O_SYNC  を変更することはできない。下記の「
              バグ」を参照。

   アドバイザリーレコードロック
       Linux  は昔からある (「プロセスに関連付けられる」) UNIX のレコードロックを実装している。 このレコードロッ
       クは POSIX で標準化されている。 Linux  固有のより良い動作を行うロックについては、下記のオープンファイル記
       述ロックの議論を参照のこと。

       F_SETLK, F_SETLKW, F_GETLK は、レコードロックの獲得/解放/テストのために使用する (レコードロックは、バイ
       ト範囲ロック、ファイルセグメントロック、ファイル領域ロックとも呼ばれる)。 三番目の引数 lock  は、以下に示
       すフィールドを含む構造体へのポインターである  (フィールドの順序は関係なく、構造体に他のフィールドがあって
       もよい)。

           struct flock {
               ...
               short l_type;    /* Type of lock: F_RDLCK,
                                   F_WRLCK, F_UNLCK */
               short l_whence;  /* How to interpret l_start:
                                   SEEK_SET, SEEK_CUR, SEEK_END */
               off_t l_start;   /* Starting offset for lock */
               off_t l_len;     /* Number of bytes to lock */
               pid_t l_pid;     /* PID of process blocking our lock
                                   (set by F_GETLK and F_OFD_GETLK) */
               ...
           };

       この構造体の l_whence, l_start, l_len フィールドで、ロックを行いたいバイト範囲を指定する。 ファイルの末尾
       より後ろのバイトをロックすることはできるが、 ファイルの先頭より前のバイトをロックすることはできない。

       l_start はロックを行う領域の開始オフセットである。 その意味は l_whence により異なる: l_whenceSEEK_SET
       の場合はファイルの先頭からのオフセット、 l_whenceSEEK_CUR  の場合は現在のファイルオフセットからのオフ
       セット、 l_whenceSEEK_END の場合はファイルの末尾からのオフセットと解釈される。 後ろの2つの場合には、
       ファイルの先頭より前にならない範囲で、 l_start に負の値を指定することができる。

       l_len   はロックしたいバイト数を示す。   l_len    が正の場合、ロックされるバイト範囲は    l_start    以上
       l_start+l_len-1 以下となる。 l_len に 0 を指定した場合は特別な意味を持つ: l_whence and l_start で指定され
       る位置からファイルの末尾までの全てのバイトをロックする  (ファイルがどんなに大きくなったとしてもファイルの
       末尾までロックする)。

       POSIX.1-2001  では、負の値の l_len をサポートする実装を認めている (必須ではない)。 l_len が負の場合、ロッ
       クされるバイト範囲は l_start+l_len  以上  l_start-1  以下となる。  この動作はカーネル  2.4.21  以降および
       2.5.49 以降の Linux で サポートされている。

       l_type  フィールドは、ファイルに対して読み出しロック (F_RDLCK)  と書き込みロック (F_WRLCK)  のどちらを 設
       定するかを指定する。 ファイルのある領域に対して、読み出しロック (共有ロック) を保持できる  プロセス数に制
       限はないが、書き込みロック  (排他ロック)  を保持できる のは一つのプロセスだけである。排他ロックを設定する
       と、(共有ロックか 排他ロックにかかわらず) 他のロックは何も設定できない。 一つのプロセスは、ファイルのある
       領域に対して一種類のロックしか保持できない。   新規のロックがロックが設定されている領域に対して適用される
       と、既存のロック は新規のロックの種別に変換される (新規のロックで指定されたバイト範囲が既存ロックの範囲と
       一致する場合以外では、 変換の過程で既存のロックの分割、縮小、結合が行われることがある)。

       F_SETLK (struct flock *)
              (l_typeF_RDLCKF_WRLCK の場合は) ロックの獲得を、 (F_UNLCK の場合は) ロックの解放を、 flock
              構造体のフィールド l_whence, l_start, l_len で指定された範囲のバイトに対して行う。  指定されたロッ
              クが他のプロセスが設定しているロックと衝突する場合は、  -1 を返し、 errnoEACCESEAGAIN を設
              定する。 (この場合に返されるエラーは実装により異なる。 そのため、  POSIX  では移植性が必要なアプリ
              ケーションでは、 これらの両方のエラーをチェックすることが必要としている。)

       F_SETLKW (struct flock *)
              F_SETLK  と同様だが、こちらではそのファイルに対して衝突するロックが 適用されていた場合に、そのロッ
              クが解放されるのを待つ点が異なる。    待っている間にシグナルを受けた場合は、システムコールは中断さ
              れ、  (シグナルハンドラーが戻った直後に)  返り値  -1  を返す  (また  errnoEINTR が設定される;
              signal(7)  参照)。

       F_GETLK (struct flock *)
              このコールの呼び出し時には、  lock  にはそのファイルに適用しようとするロックに関する情報が入ってい
              る。 ロックを適用できる場合には、 fcntl()  は実際にはロックを行わず、 構造体 lockl_type フィー
              ルドに F_UNLCK を返し、 他のフィールドは変更しない。

              違う種別のロックが (一つもしくは複数)  適用されていてロックを適用できないような場合には、  fcntl()
              は、 原因となったロックの一つについての詳細を、 lock のフィールド l_type, l_whence, l_start, l_len
              で返す。 衝突するロックが昔からある (プロセスに関連付けられる) レコードロックの場合、 l_pid フィー
              ルドにロックを保持しているプロセスの PID が設定される。 衝突するロックがオープンファイル記述ロック
              の場合、 l_pid に -1 が設定される。 呼び出し元がその内容を参照した時点では、  返された情報はすでに
              古いものとなっている可能性がある点に注意すること。

       読み出しロックを適用するには、 fd は読み出し用にオープンされていなければならない。 書き込みロックを適用す
       るには、 fd は書き込み用にオープンされていなければならない。 読み書き両方のロックを適用するには、読み書き
       両用で ファイルをオープンしなければならない。

       F_SETLKW  でロックを適用する際、 カーネルはデッドロックの検出を行う。 2 つ以上のプロセスが、 他のプロセス
       が保持するロックにより互いにブロックされるようなロック要求を行っているかを検査する。 例えば、 プロセス  A
       があるファイルのバイト  100 に対して書き込みロックを保持していて、 プロセス B がバイト 200 に対して書き込
       みロックを保持しているとする。 各プロセスが F_SETLKW を使って他のプロセスによるすでにロックされているバイ
       トをロックしようとすると、 デッドロック検出がない場合、 両方のプロセスが無限に停止することになる。 カーネ
       ルはこのようなデッドロックを検出すると、  停止していたロック要求の一つをエラー  EDEADLK  ですぐに失敗させ
       る。  このエラーを受け取ったアプリケーションは、  必要なロックを再度獲得しようとする前に、 他のアプリケー
       ションが実行できるように自分が保持するロックのいくつかを解放する必要がある。 3 つ以上のプロセスが関連する
       循環するデッドロックも検出される。  ただし、 カーネルのデッドロック検出アルゴリズムには制限がある点に注意
       すること。 「バグ」を参照。

       レコードロックは  F_UNLCK  で明示的に削除されるだけでなく、  そのプロセスが終了した際には自動的に解放され
       る。

       レコードのロックは fork(2)  で作成された子プロセスには継承されないが、 execve(2)  の前後では保存される。

       stdio(3)  ではバッファーリングが行われるので、 stdio 関連の関数ではレコードのロックの使用は回避される; 代
       わりに read(2)  や write(2)  を使用すること。

       上記で説明したレコードロックはプロセスと関連付けられる  (以下で説明するオープンファイル記述ロックと異なる
       点である)。 そのため、 残念ながら以下のようなことが起こる。

       *  プロセスがロックが適用されているファイルを参照しているファイルディスクリプターの「いずれか」をクローズ
          した場合、 そのファイルに対するそのプロセスのすべてのロックが解放される。 この動作はまずい。  あるプロ
          セスが  /etc/passwd/etc/mtab といったファイルにロックを適用しているときに、 あるライブラリ関数が何
          かの理由で同じファイルを open, read, close すると、そのファイルへのロックが失われることになる。

       *  1 つのプロセス内のスレッドはロックを共有する。 言い換えると、 マルチスレッドのプログラムで、  レコード
          ロックを使って、 複数のスレッドが同時に 1 つのファイルの同じ領域にアクセスしないようにすることはできな
          いということだ。

       オープンファイル記述ロックを使うとこれらの問題が解決できる。

   オープンファイル記述ロック (非 POSIX)
       Open file description locks are advisory byte-range locks whose operation is in most  respects  identical
       to  the  traditional record locks described above.  This lock type is Linux-specific, and available since
       Linux 3.15.  (There is a proposal with the Austin Group to include this lock type in the next revision of
       POSIX.1.)  For an explanation of open file descriptions, see open(2).

       2  つのロック種別の主な違いは、  昔からあるレコードロックはプロセスに関連付けられるのに対して、  オープン
       ファイル記述ロックはロックが獲得されるオープンファイル記述に関連付けられる点である。 この動作は  flock(2)
       で獲得されるロックによく似ている。  結果として  (昔からあるアドバイザリーレコードロックと違い)、 オープン
       ファイル記述ロックは fork(2) (や CLONE_FILES 付きの clone(2)) の前後で継承され、 ファイルのクローズ時に解
       放されるのではなく、 オープンファイル記述の最後のクローズ時にのみ自動的に解放される。

       Conflicting  lock combinations (i.e., a read lock and a write lock or two write locks)  where one lock is
       an open file description lock and the other is a traditional record lock  conflict  even  when  they  are
       acquired by the same process on the same file descriptor.

       同じオープンファイル記述経由  (同じファイルディスクリプター経由や fork(2), dup(2), fcntl() F_DUPFD などで
       作成されたファイルディスクリプターの複製経由)  で適用されたオープンファイル記述ロックは常に互換性がある。
       つまり、  すでにロックされている領域に対して新しいロックが適用された場合、 既存のロックは新しいロック種別
       に変換される。 (上記で説明した通り、 このような変換の結果、 既存のロックの分割、 縮小、  結合が行われるこ
       とがある。)

       一方、  異なるオープンファイル記述経由で獲得されると、  オープンファイル記述ロックは互いに競合する。 した
       がって、 マルチスレッドプログラムのスレッドは、 各スレッドがそれぞれ自分で  open(2)  を実行し、  得られた
       ファイルディスクリプター経由でロックを適用することで、 オープンファイル記述ロックを使って一つのファイル領
       域えのアクセスを同期させることができる。

       昔からあるレコードロックの場合と同様、 fcntl() の第 3 引数 lockflock 構造体へのポインターである。  昔
       からあるレコードロックと違い、  下記で説明するコマンドを使う際には、 この構造体のフィールド l_pid に 0 を
       設定しなければならない。

       オープンファイル記述ロックで使用できるコマンドは、 昔からあるロックのコマンドと同じである。

       F_OFD_SETLK (struct flock *)
              (l_typeF_RDLCKF_WRLCK の場合は) オープンファイル記述のロックの獲得を、 (F_UNLCK  の場合は)
              オープンファイル記述のロックの解放を、  flock 構造体のフィールド l_whence, l_start, l_len で指定さ
              れた範囲のバイトに対して行う。    指定されたロックが他のプロセスが設定しているロックと衝突する場合
              は、 -1 を返し、 errnoEAGAIN を設定する。

       F_OFD_SETLKW (struct flock *)
              F_OFD_SETLK  と同様だが、こちらではそのファイルに対して衝突するロックが 適用されていた場合に、その
              ロックが解放されるのを待つ点が異なる。  待っている間にシグナルを受けた場合は、システムコールは中断
              され、  (シグナルハンドラーが戻った直後に)  返り値  -1  を返す  (また errnoEINTR が設定される;
              signal(7) 参照)。

       F_OFD_GETLK (struct flock *)
              このコールの呼び出し時には、  lock  にはそのファイルに適用しようとするロックに関する情報が入ってい
              る。 ロックを適用できる場合には、 fcntl()  は実際にはロックを行わず、 構造体 lockl_type フィー
              ルドで F_UNLCK を返し、 他のフィールドは変更しない。 違う種別のロックが (一つもしくは複数)  適用さ
              れていてロックを適用できないような場合には、  原因となったロックの一つについての詳細が lock で返さ
              れる。 詳細は上記の F_GETLK を参照。

       現在の実装では、 オープンファイル記述ロクではデッドロックの検出は行われない。 (これがプロセスと関連付けら
       れるレコードロックとは異なる点である。 プロセスと関連付けられるレコードロックではカーネルはデッドロックの
       検出を行う。)

   強制ロック (mandatory locking)
       Warning: the Linux implementation of mandatory locking is unreliable.  See BUGS below.  Because of  these
       bugs, and the fact that the feature is believed to be little used, since Linux 4.5, mandatory locking has
       been made an optional feature, governed by a configuration option (CONFIG_MANDATORY_FILE_LOCKING).   This
       is an initial step toward removing this feature completely.

       デフォルトでは、  昔からある (プロセスに関連付けられる) レコードロックも、 オープンファイル記述のレコード
       ロックも、 アドバイザリーロックである。  アドバイザリーロックに強制力はなく、協調して動作するプロセス間で
       のみ有効である。

       両方のタイプのロックも強制ロックにすることもできる。  強制ロックは全てのプロセスに対して効果がある。 ある
       プロセスが互換性のない強制ロックが適用されたファイル領域に対して (read(2)  や write(2)  により)  互換性の
       ないアクセスを実行しようとした場合、  アクセスの結果は そのファイルのオープンファイル記述で O_NONBLOCK フ
       ラグが有効になっているかにより決まる。  O_NONBLOCK   フラグが有効になっていないときは、ロックが削除される
       か、   ロックがアクセスと互換性のあるモードに変換されるまで、   システムコールは停止   (block)   される。
       O_NONBLOCK フラグが有効になっているときは、システムコールはエラー EAGAIN で失敗する。

       強制ロックを使用するためには、ロック対象のファイルが含まれるファイルシステム と、ロック対象のファイル自身
       の両方について、強制ロックが有効になっていなけれ ばならない。ファイルシステムについて強制ロックを有効にす
       るには、 mount(8)  に "-o mand" オプションを渡すか、 mount(2)  に MS_MANDLOCK  フラグを指定する。ファイル
       について強制ロックを有効にするには、  そのファイルのグループ実行許可  (group execute permission) を無効と
       し、 かつ set-group-ID 許可ビットを有効にする (chmod(1)  と chmod(2)  を参照)。

       強制ロックは POSIX では規定されていない。 他のいくつかのシステムでも強制ロックはサポートされているが、 強
       制ロックをどのようにして有効にするかの詳細はシステムより異なる。

   Lost locks
       When  an  advisory  lock  is  obtained on a networked filesystem such as NFS it is possible that the lock
       might get lost.  This may happen due to administrative  action  on  the  server,  or  due  to  a  network
       partition (i.e., loss of network connectivity with the server)  which lasts long enough for the server to
       assume that the client is no longer functioning.

       When the filesystem determines that a lock has been lost, future read(2) or write(2)  requests  may  fail
       with  the error EIO.  This error will persist until the lock is removed or the file descriptor is closed.
       Since Linux 3.12, this happens at least for NFSv4 (including all minor versions).

       Some versions of UNIX send a signal (SIGLOST)  in this circumstance.  Linux does not define this  signal,
       and does not provide any asynchronous notification of lost locks.

   シグナルの管理
       F_GETOWN, F_SETOWN, F_GETOWN_EX, F_SETOWN_EX, F_GETSIG, F_SETSIG は、I/O が利用可能になったことを示すシグ
       ナルを管理するために使用される。

       F_GETOWN (void)
              ファイルディスクリプター fd のイベントに対するシグナル SIGIO および SIGURG  を受けているプロセスの
              プロセス  ID  かプロセスグループ  ID を (関数の結果として) 返す。 プロセス ID は正の値として返され
              る。 プロセスグループ ID は負の値として返される (下記のバグの章を参照)。 arg は無視される。

       F_SETOWN (int)
              Set the process ID or process group ID that will receive SIGIO and SIGURG signals  for  events  on
              the file descriptor fd.  The target process or process group ID is specified in arg.  A process ID
              is specified as a positive value; a process group ID is  specified  as  a  negative  value.   Most
              commonly,  the  calling  process  specifies  itself  as  the  owner  (that is, arg is specified as
              getpid(2)).

              As well as setting the file descriptor owner, one must also enable generation of  signals  on  the
              file  descriptor.   This  is  done  by  using the fcntl()  F_SETFL command to set the O_ASYNC file
              status flag on the file descriptor.  Subsequently, a SIGIO signal is sent whenever input or output
              becomes  possible  on  the  file  descriptor.  The fcntl()  F_SETSIG command can be used to obtain
              delivery of a signal other than SIGIO.

              Sending a signal to the owner process (group)  specified  by  F_SETOWN  is  subject  to  the  same
              permissions checks as are described for kill(2), where the sending process is the one that employs
              F_SETOWN (but see BUGS below).  If this permission  check  fails,  then  the  signal  is  silently
              discarded.   Note:  The  F_SETOWN  operation  records  the caller's credentials at the time of the
              fcntl()  call, and it is these saved credentials that are used for the permission checks.

              ファイルディスクリプターがソケットを参照している場合は、   F_SETOWN   を使用して、ソケットに帯域外
              (out-of-band)  データが届いた時に SIGURG シグナルを配送する相手を選択することもできる (SIGURG が送
              られた場合には select(2) がソケットが「特別な状態」にあると報告することだろう)。

              バージョン 2.6.11 以前の 2.6.x カーネルでは、以下に示す動作であった。

                     スレッドグループをサポートしているスレッドライブラリ (例えば NPTL) を  使って動作しているマ
                     ルチスレッドプロセスで F_SETSIG に 0 以外の値を指定した場合、 F_SETOWN に正の値を渡すと、そ
                     の意味が違ってくる: プロセス全体を示すプロセスID ではなく、プロセス内の特定の  スレッドを示
                     すスレッドID  と解釈される。 したがって、 F_SETSIG を使う場合には、きちんと結果を受け取るに
                     は、 F_SETOWN に渡す値を getpid(2)  ではなく gettid(2) の返り値にする必要があるだろう。 (現
                     状の  Linux スレッド実装では、メインスレッドのスレッドID は そのスレッドのプロセスID と同じ
                     である。つまり、 シグナルスレッドのプログラムではこの場合 gettid(2)  と getpid(2)  は全く同
                     じように使うことができる。)   ただし、注意すべき点として、この段落で述べたことは、 ソケット
                     の帯域外データが届いたときに生成される SIGURG シグナルにはあてはまらない。 このシグナルは常
                     にプロセスかプロセスグループに送られ、  送信先は  F_SETOWN に渡された値にしたがって決められ
                     る。

              上記の動作は、Linux 2.6.12 で図らずも削除され、 元に戻されない予定である。 Linux 2.6.32 以降で、特
              定のスレッド宛にシグナル SIGIOSIGURG を送るには F_SETOWN_EX を使うこと。

       F_GETOWN_EX (struct f_owner_ex *) (Linux 2.6.32 以降)
              直前の  F_SETOWN_EX  操作で定義された現在のファイルディスクリプターの所有者設定 を返す。情報は arg
              が指す構造体に格納されて返される。構造体は以下の通りである。

                  struct f_owner_ex {
                      int   type;
                      pid_t pid;
                  };

              type フィールドは、 F_OWNER_TID , F_OWNER_PID , F_OWNER_PGRP のいずれか一つの値となる。 pid フィー
              ルドは、スレッド ID、プロセス ID、プロセスグループ ID を 表す正の整数である。詳細は F_SETOWN_EX を
              参照。

       F_SETOWN_EX (struct f_owner_ex *) (Linux 2.6.32 以降)
              この操作は F_SETOWN と同様の処理を行う。 この操作を使うと、I/O  が利用可能になったことを示すシグナ
              ルを、  特定のスレッド、プロセス、プロセスグループに送ることができる  ようになる。  呼び出し元は、
              arg 経由でシグナルの配送先を指定する。 argf_owner_ex 構造体へのポインターである。 type  フィー
              ルドは以下のいずれかの値を取り、 この値により pid がどのように解釈されるかが規定される。

              F_OWNER_TID
                     スレッド  ID  が  pid で指定された値のスレッドにそのシグナルを送る (スレッド ID は clone(2)
                     や gettid(2)  の呼び出しで返される値である)。

              F_OWNER_PID
                     ID が pid で指定された値のプロセスにそのシグナルを送る。

              F_OWNER_PGRP
                     ID が pid で指定された値のプロセスグループにそのシグナルを送る。 (F_SETOWN と異なり、プロセ
                     スグループ ID には正の値を指定する点に注意すること。)

       F_GETSIG (void)
              入力や出力が可能になった場合に送るシグナルを (関数の結果として) 返す。 値ゼロは SIGIO を送ることを
              意味する。 (SIGIO を含む)  他の値はいずれも、  SIGIO  の代わりに送るシグナル番号を表す。  後者の場
              合、シグナルハンドラーを SA_SIGINFO フラグ付きで設定すれば、ハンドラーで追加の情報を得ることができ
              る。 arg は無視される。

       F_SETSIG (int)
              入力や出力が可能になった場合に送るシグナルを arg に指定された値に設定する。 値ゼロは SIGIO  を送る
              ことを意味する。 (SIGIO を含む) 他の値はいずれも、 SIGIO の代わりに送るシグナル番号を表す。 後者の
              場合、シグナルハンドラーを SA_SIGINFO フラグ付きで設定すれば、  ハンドラーで追加の情報を得ることが
              できる。

              F_SETSIG      にゼロ以外の値を設定し、シグナルハンドラーに     SA_SIGINFO     フラグを設定すると、
              (sigaction(2) を参照) I/O イベントに関する追加の情報が siginfo_t  構造体でシグナルハンドラーへ渡さ
              れる。 si_code フィールドが示すシグナルの原因が SI_SIGIO である場合、 si_fd フィールドにはイベント
              に対応するファイルディスクリプターが入っている。  それ以外の場合は、どのファイルディスクリプターが
              利用可能かを示す情報は  ないので、どのファイルディスクリプターで I/O が可能かを判断するためには 通
              常の機構 (select(2), poll(2), O_NONBLOCK を設定した read(2)  など) を使用しなければならない。

              Note that the file descriptor provided in si_fd is the one that was specified during the  F_SETSIG
              operation.  This can lead to an unusual corner case.  If the file descriptor is duplicated (dup(2)
              or similar), and the original file descriptor is closed, then  I/O  events  will  continue  to  be
              generated, but the si_fd field will contain the number of the now closed file descriptor.

              リアルタイムシグナル  (値が SIGRTMIN 以上) を選択している場合は、 同じシグナル番号を持つ複数の I/O
              イベントがキューに入ることがある (キューに入れるかどうかは利用可能なメモリーに依存している)。 上記
              と同様、 SA_SIGINFO が設定されている場合、シグナルハンドラーのための追加の情報が得られる。

              以下の点に注意すること。 Linux では一つのプロセスに対してキューに入れられるリアルタイム シグナルの
              数に上限が設けられており (getrlimit(2)  と signal(7)  を参照)、この上限に達するとカーネルは  SIGIO
              シグナルを配送する。この SIGIO シグナルは、指定されたスレッドではなくプロセス全体に送られる。

       これらの機構を使用することで、ほとんどの場合で select(2)  や poll(2)  を使用せずに完全な非同期 I/O を実装
       することができる。

       O_ASYNC の使用方法は BSD と Linux に特有である。 POSIX.1 で規定されている F_GETOWNF_SETOWN の使用方法
       は、ソケットに対する  SIGURG シグナルとの組み合わせだけである (POSIX は SIGIO シグナルは規定していない)。
       F_GETOWN_EX, F_SETOWN_EX, F_GETSIG, F_SETSIG は Linux 固有である。POSIX  には、同様のことを行うために、非
       同期 I/O と aio_sigevent 構造体がある。Linux では、GNU C ライブラリ (Glibc) の一部として これらも利用可能
       である。

   リース (leases)
       (Linix 2.4 以降で利用可能)  F_SETLEASE は、 fd が参照するオープンファイル記述に対して新しいリースを設定す
       るのに使用される。 F_GETLEASE は、 fd が参照するオープンファイル記述に対して設定されている 現在のリースを
       取得するのに使用される。 ファイルのリースにより、 あるプロセス ("lease breaker") がそのファイルディスクリ
       プターが参照  しているファイルに対して open(2)  や truncate(2) を行おうとした際に、リースを保持しているプ
       ロセス ("lease holder") へ (シグナルの配送による) 通知が行われるという機構が提供される。

       F_SETLEASE (int)
              arg の内容に基いてファイルのリースの設定、削除を行う。整数 arg には以下の値が指定できる:

              F_RDLCK
                     読み出しリースを取得する。これにより、 そのファイルが書き込み用にオープンされたり、ファイル
                     が切り詰められた場合に、  呼び出し元のプロセスに通知が行われるようになる。 読み出しリースを
                     設定できるのは、読み出し専用でオープンされている   ファイルディスクリプターに対してのみであ
                     る。

              F_WRLCK
                     書き込みリースを取得する。これにより、  (読み出し用か書き込み用にかかわらず) そのファイルが
                     オープンされたり、 ファイルが切り詰められた場合に、呼び出し元のプロセスに通知が行われるよう
                     になる。  書き込みリースは、そのファイルに対するオープンされたファイルディスクリプターが 他
                     にない場合にのみ設定できる。

              F_UNLCK
                     そのファイルからリースを削除する。

       リースはオープンファイル記述に対して関連付けられる (open(2)  参照)。 つまり、 (fork(2)  や dup(2)  などに
       より作成された) ファイルディスクリプターの複製は同じリースを参照し、 複製も含めたどのファイルディスクリプ
       ターを使ってもこのリースを変更したり 解放したりできる。  また、これらのファイルディスクリプターのいずれか
       に対して   F_UNLCK   操作が明示的に実行された場合や、すべてのファイルディスクリプターが  閉じられた場合に
       も、リースは解放される。

       リースの取得は通常のファイル (regular file) に対してのみ可能である。 非特権プロセスがリースを取得できるの
       は、UID  (所有者) がプロセスの ファイルシステム UID と一致するファイルに対してだけである。 CAP_LEASE ケー
       パビリティを持つプロセスは任意のファイルに対してリースを取得できる。

       F_GETLEASE (void)
              ファイルディスクリプター  fd  に対して設定されているリースの種別を取得する。   F_RDLCK,   F_WRLCK,
              F_UNLCK のいずれかが返される。 F_RDLCK, F_WRLCK はそれぞれ、読み出しリース、書き込みリースが設定さ
              れていることを示し、 F_UNLCK はリースが何も設定されていないことを示す。 arg は無視される。

       あるプロセス ("lease breaker") が F_SETLEASE で設定されたリースと矛 盾するような open(2)  や  truncate(2)
       を実行した場合、  そのシステム  コールはカーネルによって停止され、 カーネルは lease holder にシグナル (デ
       フォルトでは SIGIO) を送って通知を行う。 lease holder はこのシグ ナルを受信したときにはきちんと対応すべき
       である。  具体的には、別のプロセ  スがそのファイルにアクセスするための準備として 必要な後片付け (例えば、
       キャッシュされたバッファーのフラッシュ) を すべて行ってから、そのファイル  のリースの削除または格下げを行
       う。リースを削除をするには、  argF_UNLCK を指定して F_SETLEASE を実行する。lease holder がファイル に
       書き込みリースを保持していて、 lease breaker  が読み出し用にそのファイ  ルをオープンしている場合、  lease
       holder が保持しているリースを読み出し リースに格下げすれば 十分である。これをするには、 argF_RDLCK を
       指定して F_SETLEASE を実行する。

       If the lease holder fails to downgrade or remove the lease within the  number  of  seconds  specified  in
       /proc/sys/fs/lease-break-time, then the kernel forcibly removes or downgrades the lease holder's lease.

       いったん  lease  break  が開始されると、  lease holder が自発的にそのリース の格下げか削除を行うか、lease
       break timer の満了後にカーネルが強制的に リースの格下げか削除を行うまで、 F_GETLEASE は対象となるリースの
       型を 返す (リースの型は F_RDLCKF_UNLCK のどちらであり、lease breaker と互換性のある型となる)。

       一度リースの削除か格下げが自発的もしくは強制的に行われると、 lease breaker がまだシステムコールを再開して
       いない場合には、 カーネルが lease breaker のシステムコールの続行を許可する。

       lease breaker が実行した open(2)  や truncate(2)  が停止中にシグナルハンドラーにより中断された場合、 その
       システムコールは    EINTR   エラーで失敗するが、上で述べた他の処理は   そのまま行われる。   open(2)    や
       truncate(2)  が停止中に lease breaker がシグナルにより kill された場合、 上で述べた他の処理はそのまま行わ
       れる。   lease  breaker  が  open(2)   を呼ぶ際に  O_NONBLOCK  フラグを指定した場合、そのシステムコールは
       EWOULDBLOCK エラーで直ちに失敗するが、上で述べた他の処理はそのまま行われる。

       lease holder への通知に使われるデフォルトのシグナルは SIGIO だが、 fcntl()  の F_SETSIG  コマンドで変更す
       ることができる。 F_SETSIG コマンドが実行され (SIGIO を指定された場合も含む)、 SA_SIGINFO フラグ付きでシグ
       ナルハンドラーが設定されている場合には、 ハンドラーの第二引数として siginfo_t  構造体が渡され、この引数の
       si_fd  フィールドには別のプロセスがアクセスしたリース設定済みファイルのファイルディスクリプターが入ってい
       る (この機能は複数のファイルに対してリースを設定する場合に有用である)。

   ファイルやディレクトリの変更の通知 (dnotify)
       F_NOTIFY (int)
              (Linux 2.4 以降)  fd で参照されるディレクトリか、その中にあるファイルに変更があった場合に 通知を行
              う。どのイベントを通知するかは arg で指定する。 arg はビットマスクで、以下のビットの 0個以上の論理
              和をとったものを指定する。

              DN_ACCESS
                     ファイルへのアクセスがあった (read(2), pread(2), readv(2) や同様のシステムコール)
              DN_MODIFY
                     ファイルの内容が変更された (write(2), pwrite(2), writev(2), truncate(2), ftruncate(2)  や同
                     様のシステムコール)
              DN_CREATE
                     ファイルが作成された  (open(2),  creat(2), mknod(2), mkdir(2), " "link(2), symlink(2), この
                     ディレクトリへの rename(2))
              DN_DELETE
                     ファイルが削除 (unlink) された (unlink(2), 別のディレクトリへの rename(2), rmdir(2))
              DN_RENAME
                     ディレクトリ内でのファイル名の変更があった (rename(2))
              DN_ATTRIB
                     ファイル属性が変更された (chown(2), chmod(2), utime(2),  utimensat(2)  や同様のシステムコー
                     ル)

              (上記の定義を利用するには、どの  ヘッダーファイルをインクルードするより前に、 _GNU_SOURCE 機能検査
              マクロを定義しなければならない。)

              ディレクトリの変更通知は通常「一回限り (one-shot)」であり、 アプリケーション側でその後さらに通知を
              受信したい場合は  再登録しなければならない。 argDN_MULTISHOT が含まれていた場合には、 変更通知
              は明示的に解除されるまで有効状態が継続する。

              F_NOTIFY 要求は積算されていく。つまり、 arg で指定されたイベントがすでにモニタされている  イベント
              集合に加算される形になる。  すべてのイベントの通知を無効にするには、  arg に 0 を指定して F_NOTIFY
              を呼び出す必要がある。

              通知はシグナルの配送で行われる。 デフォルトのシグナルは SIGIO だが、 fcntl()  の F_SETSIG コマンド
              で変更することができる。  (SIGIO はキューイングされない標準のシグナルの一つである点に注意。 リアル
              タイムシグナルを使うように変更すると、  複数の通知がそのプロセス宛のキューに入ることがあることを意
              味する。) 後者の場合には、 (SA_SIGINFO フラグ付きでシグナルハンドラーが設定されている場合には)  ハ
              ンドラーの第二引数として siginfo_t 構造体が渡され、この構造体の si_fd フィールドには通知の行われた
              ファイルディスクリプターが入っている (この機能は複数のディレクトリに対して通知を設定する場合に有用
              である)。

              特に DN_MULTISHOT を使う場合は、通知にはリアルタイムシグナルを使うべきである。  それは、リアルタイ
              ムシグナルを使うことで、複数の通知をキューに入れる ことができるからである。

              注意:  新しくアプリケーションを書く際には、(カーネル  2.6.13 以降で利用可能となった)  inotify イン
              ターフェースを使用すべきである。 inotify はファイルシステムイベントの通知を取得するための ずっと優
              れたインターフェースである。 inotify(7)  を参照。

   パイプの容量の変更
       F_SETPIPE_SZ (int; Linux 2.6.35 以降)
              fd  が参照するパイプの容量を少なくとも  arg  バイトに変更する。 非特権プロセスは、パイプの容量とし
              て、 システムのページサイズと /proc/sys/fs/pipe-max-size で定義される 上限値 (proc(5) 参照) の間の
              任意の値を設定できる。 パイプの容量をページサイズよりも小さな値に設定しようとした場合は、 暗黙のう
              ちにページサイズに切り上げられる。 非特権プロセスがパイプの容量を /proc/sys/fs/pipe-max-size  で定
              義    された上限より大きな値に設定しようとした場合は、エラー   EPERM   が   発生する。特権プロセス
              (CAP_SYS_RESOURCE ケーパビリティを持つ プロセス) はこの上限を上書きできる。

              When allocating the buffer for the pipe, the kernel may use a capacity larger than arg, if that is
              convenient  for  the  implementation.   (In the current implementation, the allocation is the next
              higher power-of-two page-size multiple of the requested size.)  The  actual  capacity  (in  bytes)
              that is set is returned as the function result.

              パイプの容量を現在データを格納するのに使用されているバッファーのサイズよりも小さくしようとした場合
              は、エラー EBUSY が発生する。

              Note that because of the way the pages of the pipe buffer are employed when data is written to the
              pipe,  the number of bytes that can be written may be less than the nominal size, depending on the
              size of the writes.

       F_GETPIPE_SZ (void; Linux 2.6.35 以降)
              fd が参照するパイプの容量を (関数の結果として) 返す。

   File Sealing
       file seal は指定されたファイルで許可される操作の集合を制限する。 ファイルに設定される seal 毎に対応する操
       作の集合が規定されており、 それ以降のそのファイルに対する対応する操作は EPERM で失敗する。 このようなファ
       イルは sealed (seal が適用されている) と呼ばれる。 デフォルトの seal の集合は、適用されるファイルやファイ
       ルシステムに依存する。 file seal の概要、 その目的、 サンプルコードについては memfd_create(2) を参照。

       Currently,  file  seals  can  be  applied  only to a file descriptor returned by memfd_create(2)  (if the
       MFD_ALLOW_SEALING was employed).  On other filesystems, all fcntl()  operations  that  operate  on  seals
       will return EINVAL.

       seal は inode の属性である。 したがって、 同じ inode を参照するすべてのオープンされたファイルディスクリプ
       ターは、 同じ seal の集合を共有する。 さらに、 seal は削除することはできず、 追加のみ可能である。

       F_ADD_SEALS (int; Linux 3.17 以降)
              ビットマスク引数 arg で指定された seal を、 ファイルディスクリプター fd が参照する inode  の  seal
              の集合に追加する。 一度追加した seal を削除することはできない。 この呼び出しが成功すると、 seal は
              ただちにカーネルにより適用される。 現在の seal の集合に  F_SEAL_SEAL  (下記参照)  が含まれている場
              合、 この呼び出しは EPERM で拒否される。 すでに設定されている seal を追加した場合、 F_SEAL_SEAL が
              まだ設定されていない場合は no-op (何もしない) となる。 seal を設定するには、  ファイルディスクリプ
              ター fd が書き込み可能でなければならない。

       F_GET_SEALS (void; Linux 3.17 以降)
              (関数の結果として)  fd が参照する inode の seal の現在の集合を返す。 seal が何も設定されていない場
              合、 0 が返される。 ファイルが sealing をサポートしていない場合、 -1 が返され、 errnoEINVAL が
              設定される。

       以下の seal が利用できる。

       F_SEAL_SEAL
              この  seal が設定されると、  これ以降の F_ADD_SEALS を指定した fcntl() の呼び出しはすべて EPERM エ
              ラーで失敗する。 したがって、 この seal を設定すると seal の集合自身の変更を防止できる。  ファイル
              の最初の seal の集合に F_SEAL_SEAL が含まれていた場合、 結果的に seal の集合が定数になりロックされ
              ることになる。

       F_SEAL_SHRINK
              この seal が設定されると、 設定されたファイルのサイズを小さくできなくなる。 この seal  は  open(2)
              の  O_TRUNC フラグに影響する。 truncate(2) と ftruncate(2) についても同様である。 対象のファイルの
              サイズを小さくしようとした場合、 これらの呼び出しは EPERM で失敗する。  ファイルサイズを増やすこと
              はこの場合でも可能である。

       F_SEAL_GROW
              この seal が設定されると、 設定されたファイルのサイズを増やせなくなる。 この seal はファイルの末尾
              を超えての write(2) や truncate(2), ftruncate(2), fallocate(2) に影響する。 対象のファイルのサイズ
              を大きくしようとした場合、  これらの呼び出しは EPERM で失敗する。 ファイルサイズが変わらない場合、
              小さくなる場合は、 これらの呼び出しはそのまま動作する。

       F_SEAL_WRITE
              この seal が設定されていると、 ファイルの内容を変更できない。 ファイルのサイズを縮小したり伸張した
              りすることは可能で許可されている。 したがって、 この seal は通常は他の seal のいずれかと組み合わせ
              て使用される。 この seal は write(2) と fallocate(2) (FALLOC_FL_PUNCH_HOLE  フラグとの組み合わせの
              場合のみ)  に影響する。  この  seal  が設定されると、 これらの呼び出しは EPERM で失敗する。 また、
              mmap(2) による新しい書き込み可能な共有メモリーマッピングの作成も EPERM で失敗する。

              F_SEAL_WRITE seal を設定するのに F_ADD_SEALS  操作を使った場合、書き込み可能な共有マッピングが存在
              すると  EBUSY で失敗する。 このようなマッピングは、 この seal を追加する前にアンマップしなければな
              らない。 また、 ファイルに対して処理待ちの非同期 I/O 操作 (io_submit(2) がある場合、  処理されてい
              ない書き込みは破棄される。

       F_SEAL_FUTURE_WRITE (Linux 5.1 以降)
              The  effect  of  this  seal  is similar to F_SEAL_WRITE, but the contents of the file can still be
              modified via shared writable mappings that were created prior to the seal being set.  Any  attempt
              to  create  a  new  writable  mapping on the file via mmap(2)  will fail with EPERM.  Likewise, an
              attempt to write to the file via write(2)  will fail with EPERM.

              Using this seal, one process can create a memory buffer that  it  can  continue  to  modify  while
              sharing that buffer on a "read-only" basis with other processes.

   File read/write hints
       Write lifetime hints can be used to inform the kernel about the relative expected lifetime of writes on a
       given inode or via a particular open file description.  (See open(2)  for an  explanation  of  open  file
       descriptions.)   In this context, the term "write lifetime" means the expected time the data will live on
       media, before being overwritten or erased.

       An application may use the different hint values specified below to separate writes into different  write
       classes,  so that multiple users or applications running on a single storage back-end can aggregate their
       I/O patterns in a consistent manner.  However, there are no functional semantics implied by these  flags,
       and  different  I/O  classes can use the write lifetime hints in arbitrary ways, so long as the hints are
       used consistently.

       The following operations can be applied to the file descriptor, fd:

       F_GET_RW_HINT (uint64_t *; Linux 4.13 以降)
              Returns the value of the read/write hint associated with the underlying inode referred to by fd.

       F_SET_RW_HINT (uint64_t *; Linux 4.13 以降)
              Sets the read/write hint value associated with the underlying inode referred to by fd.  This  hint
              persists until either it is explicitly modified or the underlying filesystem is unmounted.

       F_GET_FILE_RW_HINT (uint64_t *; Linux 4.13 以降)
              Returns  the value of the read/write hint associated with the open file description referred to by
              fd.

       F_SET_FILE_RW_HINT (uint64_t *; Linux 4.13 以降)
              Sets the read/write hint value associated with the open file description referred to by fd.

       If an open file description has not been assigned a read/write hint, then it shall use the value assigned
       to the inode, if any.

       The following read/write hints are valid since Linux 4.13:

       RWH_WRITE_LIFE_NOT_SET
              No specific hint has been set.  This is the default value.

       RWH_WRITE_LIFE_NONE
              No specific write lifetime is associated with this file or inode.

       RWH_WRITE_LIFE_SHORT
              Data written to this inode or via this open file description is expected to have a short lifetime.

       RWH_WRITE_LIFE_MEDIUM
              Data written to this inode or via this open file description is expected to have a lifetime longer
              than data written with RWH_WRITE_LIFE_SHORT.

       RWH_WRITE_LIFE_LONG
              Data written to this inode or via this open file description is expected to have a lifetime longer
              than data written with RWH_WRITE_LIFE_MEDIUM.

       RWH_WRITE_LIFE_EXTREME
              Data written to this inode or via this open file description is expected to have a lifetime longer
              than data written with RWH_WRITE_LIFE_LONG.

       All the write-specific hints are relative to each other, and no individual  absolute  meaning  should  be
       attributed to them.

返り値

       成功した場合の返り値は操作の種類により違う:

       F_DUPFD
              新規のファイルディスクリプター。

       F_GETFD
              ファイルディスクリプターフラグの値

       F_GETFL
              ファイル状態フラグの値

       F_GETLEASE
              ファイルディスクリプターに対して保持されているリースの種別を返す。

       F_GETOWN
              ファイルディスクリプターの所有者。

       F_GETSIG
              読み込みや書き出しが可能になった時に送られるシグナルの値、もしくは 伝統的な SIGIO 動作の場合にはゼ
              ロを返す。

       F_GETPIPE_SZ, F_SETPIPE_SZ
              パイプの容量。

       F_GET_SEALS
              fd が参照する inode に設定されている seal を示すビットマスク。

       他の全てのコマンド
              0 を返す。

       エラーの時は -1 が返され、 errno に適切な値が設定される。

エラー

       EACCESEAGAIN
              他のプロセスが保持しているロックによって操作が禁止されている。

       EAGAIN そのファイルは他のプロセスによってメモリーマップされているため、 操作が禁止されている。

       EBADF  fd がオープンされたファイルディスクリプターではない。

       EBADF  cmdF_SETLK または F_SETLKW だったが、対象のファイルディスクリプターのオープンモードが 必要とな
              るロックの型にマッチしていない。

       EBUSY  cmdF_SETPIPE_SZ で、 arg で指定されたパイプの新しい容量がパイプが、 現在パイプにあるデータを格
              納するのに使用されているバッファー容量よりも小さい。

       EBUSY  cmdF_ADD_SEALS で、 argF_SEAL_WRITE が含まれており、 fd が参照するファイルに対する書き込み
              可能な共有マッピングが存在する。

       EDEADLK
              指定された F_SETLKW コマンドを実行した場合にはデッドロックになることが検出された。

       EFAULT lock が利用可能なアドレス空間の外部にある。

       EINTR  cmdF_SETLKWF_OFD_SETLKW で、 操作がシグナルにより割り込まれた。 signal(7) 参照。

       EINTR  cmdF_GETLK, F_SETLK, F_OFD_GETLK, F_OFD_SETLK で、 操作がシグナルにより割り込まれた (signal(7)
              参照)。 F_GETLKF_SETLK  の場合、ロックを確認したり取得したりする前にシグナルによって割り込まれ
              た。  これはたいていリモートのファイルをロックする場合  (例えば NFS 上でロックする場合) に起こる。
              しかしローカルでも起こる場合がある。

       EINVAL カーネルが認識しない値が cmd で指定された。

       EINVAL cmdF_ADD_SEALS で、 arg に認識できない seal を示すビットが含まれている。

       EINVAL cmdF_ADD_SEALSF_GET_SEALS で、 fd が参照している inode  が格納されているファイルシステムが
              sealing をサポートしていない。

       EINVAL cmdF_DUPFD で、 arg が負か、もしくは許される最大値よりも大きい (getrlimit(2) の RLIMIT_NOFILE
              の議論を参照)。

       EINVAL cmdF_SETSIG で、 arg が許可されたシグナル番号ではない。

       EINVAL cmdF_OFD_SETLK, F_OFD_SETLKW, F_OFD_GETLK のいずれかで、 l_pid に 0 が指定されなかった。

       EMFILE cmdF_DUPFDで、オープンされているファイルディスクリプターの数がプロセス単位の上限に達していた。

       ENOLCK オープンされているロックの数が多過ぎて、ロックテーブルがいっぱいである。  または  remote   locking
              protocol (例えば NFS 上のロック) が失敗した。

       ENOTDIR
              F_NOTIFYcmd に指定されたが、 fd がディレクトリを参照していない。

       EPERM  cmd is F_SETPIPE_SZ and the soft or hard user pipe limit has been reached; see pipe(7).

       EPERM  追加専用属性が設定されたファイルの O_APPEND フラグをクリアしようと試みた。

       EPERM  cmdF_ADD_SEALS だが、 fd が書き込み用にオープンされていないか、 ファイルの現在の seal の集合に
              すでに F_SEAL_SEAL が含まれている。

準拠

       SVr4, 4.3BSD, POSIX.1-2001.  POSIX.1-2001 で規定されている操作は、 F_DUPFD,  F_GETFD,  F_SETFD,  F_GETFL,
       F_SETFL, F_GETLK, F_SETLK, F_SETLKW だけである。

       F_GETOWNF_SETOWN は POSIX.1-2001 で規定されている。 (これら定義するには、 _XOPEN_SOURCE を 500 以上の
       値で定義するか、 _POSIX_C_SOURCE を 200809L 以上の値で定義するか、 のいずれが必要である。)

       F_DUPFD_CLOEXEC は POSIX.1-2008 で規定されている。 (これら定義するには、 _POSIX_C_SOURCE を 200809L  以上
       の値で定義するか、 _XOPEN_SOURCE を 700 以上の値で定義すること。)

       F_GETOWN_EX,   F_SETOWN_EX,   F_SETPIPE_SZ,   F_GETPIPE_SZ,  F_GETSIG,  F_SETSIG,  F_NOTIFY,  F_GETLEASE,
       F_SETLEASE は Linux 固有である (これらの定義を有効にするには _GNU_SOURCE マクロを定義すること)。

       F_OFD_SETLK, F_OFD_SETLKW, F_OFD_GETLK は Linux 固有だが (これらの定義を得るには _GNU_SOURCE を定義しなけ
       ればならない)、 POSIX.1 の次のバージョンに含めようという活動が進められている。

       F_ADD_SEALSF_GET_SEALS は Linux 固有である。

注意

       エラーの際の返り値が dup2(2)  と F_DUPFD では異なっている。

   ファイルロック
       元々の Linux の fcntl() システムコールは (flock 構造体で) 大きな ファイルオフセットを扱えるように設計され
       ていなかった。 その結果、Linux 2.4  で  fcntl64()  システムコールが追加された。  この新しいシステムコール
       は、ファイルのロックに   flock64   という別の   構造体を利用し、これに対応するコマンドとして   F_GETLK64,
       F_SETLK64, F_SETLKW64 を使用する。 しかし、 glibc  を使うアプリケーションではこれらの詳細を無視することが
       できる。 glibc の fcntl のラッパー関数は新しいシステムコールが 利用できる場合はそれを利用するようになって
       いるからである。

   レコードロック
       カーネル 2.0 以降では、 flock(2)  と fcntl()  が設定するロック種別の間に相互作用はない。

       Several systems have more fields in struct flock such as, for example, l_sysid (to identify  the  machine
       where  the lock is held).  Clearly, l_pid alone is not going to be very useful if the process holding the
       lock may live on a different machine; on Linux, while present on some  architectures  (such  as  MIPS32),
       this field is not used.

       元々の Linux の fcntl() システムコールは (flock 構造体で) 大きな ファイルオフセットを扱えるように設計され
       ていなかった。 その結果、Linux 2.4  で  fcntl64()  システムコールが追加された。  この新しいシステムコール
       は、ファイルのロックに   flock64   という別の   構造体を利用し、これに対応するコマンドとして   F_GETLK64,
       F_SETLK64, F_SETLKW64 を使用する。 しかし、 glibc  を使うアプリケーションではこれらの詳細を無視することが
       できる。 glibc の fcntl のラッパー関数は新しいシステムコールが 利用できる場合はそれを利用するようになって
       いるからである。

   レコードロックと NFS
       Linux 3.12 より前では、 NFSv4 クライアントが一定時間サーバーと通信がなかった場合 (90 秒間通信がない場合と
       定義されている)、  クライアントが気付かずにロックを失い再獲得する場合がある。 (通信がなくなったみなす時間
       は NFSv4 leastime と呼ばれる。 Linux NFS サーバーでは、 この値は /proc/fs/nfsd/nfsv4leasetime  を見て決定
       される。  このファイルの値の単位は秒であり、 このファイルのデフォルト値は 90 である。) この状況では潜在的
       にデータ破壊が起こる危険性がある。 通信がなかった間に他のプロセスがロックを獲得しファイル入出力を行う場合
       があるからである。

       Linux 3.12 以降、 NFSv4 クライアントがサーバーと通信がなかった場合、 ロックを持っていると「思っている」プ
       ロセスがそのファイルに入出力を行うと失敗する。 そのプロセスがそのファイルをいったんクローズし再オープンす
       るまでは入出力は失敗する。  カーネルパラメーター nfs.recover_lost_locks を 1 に設定すると、 Linux 3.12 よ
       り前の動作にすることができる。 この場合、  サーバーとの通信が再確立された場合、  クライアントがは失われた
       ロックを回復しようとする。 データ破壊が起こる危険性があるため、 このパラメーターはデフォルトでは 0 (無効)
       になっている。

バグ

   F_SETFL
       F_SETFL を使って、 フラグ O_DSYNCO_SYNC  の状態を変更することはできない。これらのフラグの状態を変更し
       ようとした場合には、黙って無視される。

   F_GETOWN
       いくつかのアーキテクチャー  (特に  i386) における Linux システムコールの慣習 のため以下の制限が存在する。
       F_GETOWN が返す (負の) プロセスグループID が -1 から -4095 の範囲に入った場合、 glibc  はこの返り値をシス
       テムコールでエラーが起こったと間違って解釈してしまう。 つまり、 fcntl() の返り値は -1 となり、 errno には
       (正の) プロセスグループID  が設定されることになる。Linux  固有の  F_GETOWN_EX  ではこの問題を回避できる。
       glibc  バージョン  2.11  以降では、glibc  では F_GETOWN_EX を使って F_GETOWN を実装することで、カーネルの
       F_GETOWN の問題を見えないようにしている。

   F_SETOWN
       Linux 2.4 以前では、非特権プロセスが F_SETOWN を使って、ソケットのファイルディスクリプターの所有者に 呼び
       出し元以外のプロセス  (やプロセスグループ) を指定すると 発生するバグがある。この場合、 呼び出し元が所有者
       として指定したプロセス (やプロセスグループ) に シグナルを送る許可を持っていたとしても、 fcntl()  が -1 を
       返し errnoEPERM を設定することがある。 このエラーが返ったにもかかわらず、ファイルディスクリプターの所
       有者 は設定され、シグナルはその所有者に送られる。

   デッドロックの検出
       F_SETLKW 要求を処理する際にカーネルが使用するデッドロック検出アルゴリズムは、 false  negative  になる場合
       (デッドロックを検出できず、  デッドロックになったプロセスは無限に停止する)  も  false positive になる場合
       (デッドロックがない場合でも EDEADLK エラーとなる) もある。 例えば、  カーネルは依存関係の検索を行うロック
       の深さを  10 ステップに限定しているが、 このためこれよりも長い循環するデッドロックは検出されない。 また、
       clone(2) の CLONE_FILES フラグを使って作成された 2 つ以上のプロセスが (カーネルにとって) 衝突するように見
       えるロックを適用した場合、 カーネルはデッドロックを誤って検出する。

   強制ロック (mandatory locking)
       Linux  の強制ロックの実装は、 競合条件下で強制ロックが不完全になるような場合がある。 ロックと重なって実行
       された write(2) の呼び出しは強制ロックが獲得された後にもデータを変更することができる。 ロックと重なって実
       行された  read(2)  の呼び出しは強制ロックが獲得された後になって行われたデータの変更を  検出することができ
       る。  同様の競合条件が強制ロックと  mmap(2)  の間にも存在する。それゆえ、強制ロックに頼るのはお薦めできな
       い。

関連項目

        dup2(2), flock(2), open(2), socket(2), lockf(3), capabilities(7), feature_test_macros(7), lslocks(8)

       Linux  カーネルソースの  Documentation/filesystems/  ディレクトリ内の  locks.txt,  mandatory-locking.txt,
       dnotify.txt     (以前のカーネルでは、これらのファイルは      Documentation/      ディレクトリ直下にあり、
       mandatory-locking.txtmandatory.txt という名前であった)

この文書について

       この  man ページは Linux man-pages プロジェクトのリリース 5.10 の一部である。プロジェクトの説明とバグ報告
       に関する情報は https://www.kernel.org/doc/man-pages/ に書かれている。