[プログラミングステップ]ctypesのPythonプログラミングにおける奇光異彩


一、What is ctypes?ctypesはPythonの外部関数ライブラリです.Cと互換性のあるデータ型を提供し、DLLまたは共有ライブラリの関数を呼び出すことができます.このモジュールを使用して、これらのライブラリを純粋なPython形式でカプセル化できます.
「入門から精通まで」という文章だと思うかもしれません.もちろんそうではありませんnei~私は私が価値があると思っていることを覚えています.あなたもきっと使えます.そして、私の仲間たちに注目して、私たちがなぜctypesを使うのか、にこにこしています.
詳細は次のとおりです.https://docs.python.org/zh-cn/3.7/library/ctypes.html
二、階段を上る道は足元にある
1.動的接続ライブラリの読み込みctypesはcdllオブジェクトをエクスポートし、Windowsシステムではwindllオブジェクトとoledllオブジェクトをエクスポートして動的接続ライブラリをロードします.
  • cdllは、標準のcdecl呼び出しプロトコルによって導出関数
  • をロードする.
  • windllインポートライブラリstdcall呼び出しプロトコル呼び出し関数
  • oledllも、stdcallに従ってプロトコル呼び出しの関数を呼び出し、Windows HRESULTエラーコードを返し、関数呼び出しに失敗した場合、OSError異常が自動的に呼び出されると仮定する.

  • いくつかの後続工事の原因で、Windowsの下でしか試験を行いませんでした.
    Python 3.7.6 (tags/v3.7.6:43364a7ae0, Dec 19 2019, 00:42:30) [MSC v.1916 64 bit (AMD64)] on win32
    Type "help", "copyright", "credits" or "license" for more information.
    >>> import ctypes
    >>> print(ctypes.windll.kernel32)
    
    >>> print(ctypes.cdll.msvcrt)
    

    2.呼び出し関数
    (1)ctypes.windll.kernel32.VirtualAlloc関数.
    VirtualAllocはWindowsが提供するAPIで、通常は大きなメモリを割り当てるために使用されます.この関数は、例えば、プロセスAとプロセスBとの間でメモリを共有することによって通信を実現する場合に使用することができる.この関数を使用して、通常のメモリ割り当てを実装しないでください.この関数の重要な特性の1つは、アドレスとサイズを指定できる仮想メモリ領域です.たとえば、プロセスのアドレス空間で50 MB目の場所にメモリを割り当てる場合、パラメータ50*1024*`1024=52428800をpvAddressに渡し、必要なメモリサイズをdwSizeに渡します.システムが要求を満たすのに十分な空き領域を持っている場合、システムはブロック領域を予約し、予約メモリのベースアドレスを返します.そうしないとNULLを返します.
    書式:
    LPVOID VirtualAlloc{ 
        LPVOID lpAddress, //             
        DWORD dwSize, //       
        DWORD flAllocationType, //       
        DWORD flProtect //            
    }; 
    ctypesは、Cと互換性のあるいくつかの基本データ型を定義します.
    ctypesタイプ
    Cタイプ
    Pythonタイプc_bool _Bool
    bool (1) c_char char
    シングルバイトオブジェクトc_wchar wchar_t
    単一文字列c_byte char
    せいけいc_ubyte unsigned char
    せいけいc_short short
    せいけいc_ushort unsigned short
    せいけいc_int int
    せいけいc_uint unsigned int
    せいけいc_long long
    せいけいc_ulong unsigned long
    せいけいc_longlong __int64またはlong longせいけいc_ulonglong unsigned __int64またはunsigned long longせいけいc_size_t size_t
    せいけいc_ssize_t ssize_tまたはPy_ssize_tせいけいc_float float
    浮動小数点数c_double double
    浮動小数点数c_longdouble long double
    浮動小数点数c_char_p char *(NULで終わる)
    バイト列オブジェクトまたはNonec_wchar_p wchar_t *(NULで終わる)
    文字列またはNonec_void_p void *
    intまたはNone 
    (2)RtlMoveMemoryは、指定されたメモリから別のメモリにコピーします.構文は次のとおりです.
    VOID RtlMoveMemory(
        VOID UNALIGNED *Destination,
        const VOID UNALIGNED *Source,
        SIZE_T Length
    );

    Destination:移動先アドレスへのポインタ.
    Source:コピーするメモリアドレスへのポインタ.
    Length:コピーするバイト数を指定します.
     
    (3)CreateProcess
    呼び出すと、プロセスとプライマリ・スレッドが作成されます.CreateThreadは、プライマリ・スレッドに基づいて新しいスレッドを作成します.
  • カーネルオブジェクトにスレッドID/ハンドルを割り当て、管理可能であり、CreateThreadによって
  • に戻る.
  • スレッド終了コードをSTILL_に設定ACTIVE、スレッド掛けカウント1
  • 割当context構造
  • は2ページの物理ストレージを割り当ててスタックを準備し、保護ページをPAGE_に設定する.READWRITE,2ページ目をPAGE_とするGUARD
  • lpStartAddrおよびlpvThreadの値はスタックの上部に配置され、StartOfThreadに伝達するパラメータ
  • となる.
  • context構造のスタックポインタをスタックトップに向ける(ステップ5)命令ポインタをstartOfThread関数
  • に向ける.
    構文:
    hThread = CreateThread(&security_attributes, dwStackSize, ThreadProc,pParam, dwFlags, &idThread) ;
    
    HANDLE CreateThread(
      LPSECURITY_ATTRIBUTES lpThreadAttributes,      // pointer to security attributes
      DWORD dwStackSize,                  // initial thread stack size
      LPTHREAD_START_ROUTINE lpStartAddress,       // pointer to thread function
      LPVOID lpParameter,                   // argument for new thread
      DWORD dwCreationFlags,                // creation flags
      LPDWORD lpThreadId                  // pointer to receive thread ID
    );

    最初のパラメータはSECURITY_ATTRIBUTES型の構造の指針.このパラメータはWindows 98では無視される.Windows NTではNULLに設定されています.2番目のパラメータは、新しいスレッドの初期スタックサイズで、デフォルト値は0です.いずれの場合も、Windowsは必要に応じてスタックのサイズを動的に延長します.3番目のパラメータは、スレッド関数を指す指標です.関数名には制限はありませんが、DWORD WINAPI ThreadProc(PVOID pParam);4番目のパラメータは、ThreadProcに渡されるパラメータです.これにより、プライマリ・スレッドとセカンダリ・スレッドがデータを共有できます.5番目のパラメータは通常0ですが、作成したスレッドがすぐに実行されない場合はフラグCREATE_です.SUSPENDED.スレッドは、ResumeThreadを呼び出してスレッドの実行を再開するまで一時停止します.6番目のパラメータは、実行ID値を受け入れる変数を指す指標である.