これらの関数は他のPython呼び出し可能オブジェクトと同じように呼び出すことができます。
この例ではtime()
関数(Unixエポックからのシステム時間を秒単位で返す)と、
GetModuleHandleA()
関数(win32モジュールハンドルを返す)を使います。
この例は両方の関数をNULLポインタとともに呼び出します
(None
をNULLポインタとして使う必要があります):
>>> print libc.time(None) # doctest: +SKIP 1150640792 >>> print hex(windll.kernel32.GetModuleHandleA(None)) # doctest: +WINDOWS 0x1d000000 >>>
ctypes
は引数の数を間違えたり、あるいは呼び出し規約を間違えた関数呼び出しから
あなたを守ろうとします。残念ながら、これはWindowsでしか機能しません。
関数が返った後にスタックを調べることでこれを行います。したがって、
エラーは発生しますが、その関数は呼び出された後です:
>>> windll.kernel32.GetModuleHandleA() # doctest: +WINDOWS Traceback (most recent call last): File "<stdin>", line 1, in ? ValueError: Procedure probably called with not enough arguments (4 bytes missing) >>> windll.kernel32.GetModuleHandleA(0, 0) # doctest: +WINDOWS Traceback (most recent call last): File "<stdin>", line 1, in ? ValueError: Procedure probably called with too many arguments (4 bytes in excess) >>>
同じ例外がcdecl
呼び出し規約を使ってstdcall
関数を呼び出したときに発生しますし、
逆の場合も同様です。
>>> cdll.kernel32.GetModuleHandleA(None) # doctest: +WINDOWS Traceback (most recent call last): File "<stdin>", line 1, in ? ValueError: Procedure probably called with not enough arguments (4 bytes missing) >>> >>> windll.msvcrt.printf("spam") # doctest: +WINDOWS Traceback (most recent call last): File "<stdin>", line 1, in ? ValueError: Procedure probably called with too many arguments (4 bytes in excess) >>>
正しい呼び出し規約を知るためには、呼び出したい関数についてのCヘッダファイル もしくはドキュメントを見なければなりません。
Windowsでは、関数が無効な引数とともに呼び出された場合の一般保護例外による
クラッシュを防ぐために、ctypes
はwin32構造化例外処理を使います:
>>> windll.kernel32.GetModuleHandleA(32) # doctest: +WINDOWS Traceback (most recent call last): File "<stdin>", line 1, in ? WindowsError: exception: access violation reading 0x00000020 >>>
しかし、ctypes
を使ってPythonをクラッシュさせる方法は十分なほどあるので、
よく注意すべきです。
None
、整数、長整数、バイト文字列およびユニコード文字列だけが、
こうした関数呼び出しにおいてパラメータとして直接使えるネイティブの
Pythonオブジェクトです。None
はCのNULL
ポインタとして
渡され、バイト文字列とユニコード文字列はそのデータを含むメモリブロックへの
ポインタ(char *
または wchar_t *
)として渡されます。
Python整数とPython長整数はプラットホームのデフォルトのC int
型として渡され、
その値はC int
型に合うようにマスクされます。
他のパラメータ型をもつ関数呼び出しに移る前に、
ctypes
データ型についてさらに学ぶ必要があります。
ご意見やご指摘をお寄せになりたい方は、 このドキュメントについて... をご覧ください。