\section{\module{fcntl} ---
         \function{fcntl()} および \function{ioctl()} システムコール}

\declaremodule{builtin}{fcntl}
  \platform{Unix}
\modulesynopsis{\function{fcntl()} および \function{ioctl()} システム
コール。}
\sectionauthor{Jaap Vermeulen}{}

\indexii{UNIX@\UNIX}{file control}
\indexii{UNIX@\UNIX}{I/O control}

このモジュールでは、ファイル記述子 (file descriptor) に基づいた
ファイル制御および I/O 制御を実現します。
このモジュールは、 \UNIX{} のルーチンである \cfunction{fcntl()} 
および \cfunction{ioctl()} へのインタフェースです。

このモジュール内の全ての関数はファイル記述子 \var{fd} を最初の引数に
取ります。この値は \code{sys.stdin.fileno()} が返すような
整数のファイル記述子でも、\code{sys.stdin} 自体のような、純粋に
ファイル記述子だけを返す \method{fileno()} メソッドを提供している
ファイルオブジェクトでもかまいません。

このモジュールでは以下の関数を定義しています:


\begin{funcdesc}{fcntl}{fd, op\optional{, arg}}
要求された操作をファイル記述子 \var{fd} (または \method{fileno()} 
メソッドを提供しているファイルオブジェクト) に対して実行します。
操作は \var{op} で定義され、オペレーティングシステム依存です。
これらの操作コードは \module{fcntl} モジュール内にもあります。
引数 \var{arg} はオプションで、標準では整数値 \code{0} です。
この引数を与える場合、整数か文字列の値をとります。
引数が無いか整数値の場合、この関数の戻り値は C 言語の
\cfunction{fcntl()} を呼び出した際の整数の戻り値になります。
引数が文字列の場合には、\function{\refmodule{struct}.pack()} で作られる
ようなバイナリの構造体を表します。
バイナリデータはバッファにコピーされ、そのアドレスが
C 言語の \cfunction{fcntl()} 呼び出しに渡されます。
呼び出しが成功した後に戻される値はバッファの内容で、文字列
オブジェクトに変換されています。返される文字列は \var{arg} 引数
と同じ長さになます。この値は 1024 バイトに制限されています。
オペレーティングシステムからバッファに返される情報の長さが 1024 
バイトよりも大きい場合、大抵はセグメンテーション違反となるか、
より不可思議なデータの破損を引き起こします。

\cfunction{fcntl()} が失敗した場合、\exception{IOError} が
送出されます。
\end{funcdesc}

\begin{funcdesc}{ioctl}{fd, op, arg}
この関数は \function{fcntl()} 関数と同じですが、操作が通常ライブラリ
モジュール \refmodule{termios} で定義されており、引数の扱いがより
複雑であるところが異なります。
  
パラメタ \var{arg} は整数か、存在しない (整数 \code{0} と等価なもの
として扱われます) か、(通常の Python 文字列のような) 読み出し専用の
バッファインタフェースをサポートするオブジェクトか、読み書き
バッファインタフェースをサポートするオブジェクトです。

最後の型のオブジェクトを除き、動作は \function{fcntl()} 関数と
同じです。

可変なバッファが渡された場合、動作は \var{mutate_flag} 引数の
値で決定されます。

この値が偽の場合、バッファの可変性は無視され、動作は読み出しバッファ
の場合と同じになりますが、上で述べた 1024 バイトの制限は回避されます
-- 従って、オペレーティングシステムが希望するバッファ長までで
あれば正しく動作します。

\var{mutate_flag} が真の場合、バッファは (実際には) 根底にある
\function{ioctl()} システムコールに渡され、後者の戻り値が
呼び出し側の Python に引き渡され、バッファの新たな内容は 
\function{ioctl()} の動作を反映します。
この説明はやや単純化されています。というのは、与えられたバッファが
1024 バイト長よりも短い場合、バッファはまず 1024 バイト長の
静的なバッファにコピーされてから \function{ioctl()} に渡され、
その後引数で与えたバッファに戻しコピーされるからです。
  
\var{mutate_flag} が与えられなかった場合、2.3 ではこの値は偽となります。
この仕様は今後のいくつかのバージョンを経た Python で変更される予定
です: 2.4 では、 \var{mutate_flag} を提供し忘れると警告が出されますが
同じ動作を行い、2.5 ではデフォルトの値が真となるはずです。

以下に例を示します:

\begin{verbatim}
>>> import array, fcntl, struct, termios, os
>>> os.getpgrp()
13341
>>> struct.unpack('h', fcntl.ioctl(0, termios.TIOCGPGRP, "  "))[0]
13341
>>> buf = array.array('h', [0])
>>> fcntl.ioctl(0, termios.TIOCGPGRP, buf, 1)
0
>>> buf
array('h', [13341])
\end{verbatim}
\end{funcdesc}




\begin{funcdesc}{flock}{fd, op}
ファイル記述子 \var{fd} (\method{fileno()} メソッドを提供している
ファイルオブジェクトも含む) に対してロック操作 \var{op} を実行します。
詳細は \UNIX{} マニュアルの \manpage{flock}{3} を参照してください
(システムによっては、この関数は \cfunction{fcntl()} を使って
エミュレーションされています)。
\end{funcdesc}

\begin{funcdesc}{lockf}{fd, operation,
    \optional{length, \optional{start, \optional{whence}}}}
本質的に \function{fcntl()} によるロッキングの呼び出しをラップ
したものです。\var{fd} はロックまたはアンロックするファイルの
ファイル記述子で、\var{operation} は以下の値:

\begin{itemize}
\item \constant{LOCK_UN} -- アンロック
\item \constant{LOCK_SH} -- 共有ロックを取得
\item \constant{LOCK_EX} -- 排他的ロックを取得
\end{itemize}

のうちいずれかになります。

\var{operation} が \constant{LOCK_SH} または \constant{LOCK_EX}
の場合、\constant{LOCK_NB} とビット OR にすることでロック取得時に
ブロックしないようにすることができます。\constant{LOCK_NB} が
使われ、ロックが取得できなかった場合、\exception{IOError} が送出
され、例外は \var{errno} 属性を持ち、その値は \constant{EACCESS}
または \constant{EAGAIN} になります (オペレーティングシステムに
依存します; 可搬性のため、両方の値をチェックしてください)。
少なくともいくつかのシステムでは、 ファイル記述子が参照している
ファイルが書き込みのために開かれている場合、\constant{LOCK_EX}
だけしか使うことができません。

\var{length} はロックを行いたいバイト数、\var{start} は
ロック領域先頭の \var{whence} からの相対的なバイトオフセット、
\var{whence} は \function{fileobj.seek()} と同じで、具体的には:

\begin{itemize}
\item \constant{0} -- ファイル先頭からの相対位置
      (\constant{SEEK_SET})
\item \constant{1} -- 現在のバッファ位置からの相対位置
      (\constant{SEEK_CUR})
\item \constant{2} -- ファイルの末尾からの相対位置
      (\constant{SEEK_END})
\end{itemize}

\var{start} の標準の値は 0 で、ファイルの先頭から開始することを
意味します。\var{whence} の標準の値も 0 です。
\end{funcdesc}

以下に (全ての SVR4 互換システムでの) 例を示します:

\begin{verbatim}
import struct, fcntl, os

f = open(...)
rv = fcntl.fcntl(f, fcntl.F_SETFL, os.O_NDELAY)

lockdata = struct.pack('hhllhh', fcntl.F_WRLCK, 0, 0, 0, 0, 0)
rv = fcntl.fcntl(f, fcntl.F_SETLKW, lockdata)
\end{verbatim}

最初の例では、戻り値 \var{rv} は整数値を保持しています; 二つ目の
例では文字列値を保持しています。\var{lockdata} 変数の構造体
レイアウトはシステム依存です --- 従って \function{flock()} を
呼ぶ方がベターです。

\begin{seealso}
  \seemodule{os}{もし　\constant{O_SHLOCK} と \constant{O_EXLOCK}が　
  \module{os}モジュールに存在する場合、
  \function{os.open()} 関数は
  \function{lockf()} や \function{flock()}関数よりも
  よりプラットフォーム独立なロック機構を提供します。}
\end{seealso}
