zoukankan      html  css  js  c++  java
  • 在扩展模块中对python的GIL进行解锁

    在多线程环境下,python虚拟机按照以下方式运行:
       1. 设置GIL(全局解释器锁)
       2. 切换到一个线程中去
       3. 运行
            a. 指定数量的字节码的指令,或者
            b. 线程主动让出控制(可以条用time.sleep(0) )
       4. 把线程设置为睡眠模式
       5. 解锁GIL
       6. 再次重复以上步骤
    调用C/C++扩展函数的时候,GIL会被锁定,直到这个函数结束。由于这期间没有python的字节码被运行,所以线程不会切换

    如果我在扩展模块中调用阻塞式地I/O函数,那么就会发生比较糟糕的事情。

    比如说,我在扩展模块中接受网络数据,如果对端机器没有发送数据,那么我的整个Python程序就会阻塞到这一点,而且不会进行线程的切换。

    如果发生这样的事情,python中的多线程机制就形同虚设了。 

     不过,python允许扩展模块自己对GIL进行解锁,方法如下: 

     解锁GIL的代码结构

    Save the thread state in a local variable. 
    Release the global interpreter lock. 
    ... Do some blocking I/O operation ... 
    Reacquire the global interpreter lock. 
    Restore the thread state from the local variable. 

     由于这个步骤十分通用,Python提供了宏以简化代码,如下:

    Py_BEGIN_ALLOW_THREADS
    ... Do some blocking I/O operation ...
    Py_END_ALLOW_THREADS

    例如,如果我们在代码中使用了 getch 这个函数,那么我们的代码可以这么写:

    # getch test
    Py_BEGIN_ALLOW_THREADS
    int key = getch();
    Py_END_ALLOW_THREADS

    这段代码会被扩展为如下:

     # getch test

    PyThreadState *_save;

    _save = PyEval_SaveThread();
    int key = getch();
    PyEval_RestoreThread(_save);
     
  • 相关阅读:
    apache http 403 Forbidden error
    Python dictionary
    Python The standard programe tructure
    SVN server setup 2
    SVN Server setup 3
    Cent OS下中文乱码的解决方法
    Start to enjoin python
    Linux Client RapidSVN
    使用 F12 开发人员工具调试 HTML 和 CSS(IE浏览器)
    十条不错的编程观点
  • 原文地址:https://www.cnblogs.com/hdtianfu/p/2743799.html
Copyright © 2011-2022 走看看