mirror of
https://github.com/python/cpython.git
synced 2025-11-02 19:12:55 +00:00
Done with tread state descriptions. Sigh!
This commit is contained in:
parent
86b7db3750
commit
c44d3d6664
2 changed files with 624 additions and 106 deletions
365
Doc/api.tex
365
Doc/api.tex
|
|
@ -653,7 +653,7 @@ e.g., when the object administration appears to be corrupted.
|
||||||
Initialize the \code{__builtin__} module. For internal use only.
|
Initialize the \code{__builtin__} module. For internal use only.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
XXX Other init functions: PyEval_InitThreads, PyOS_InitInterrupts,
|
XXX Other init functions: PyOS_InitInterrupts,
|
||||||
PyMarshal_Init, PySys_Init.
|
PyMarshal_Init, PySys_Init.
|
||||||
|
|
||||||
\chapter{Reference Counting}
|
\chapter{Reference Counting}
|
||||||
|
|
@ -743,14 +743,14 @@ return value to a specific exception; use
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{PyErr_ExceptionMatches}{PyObject *exc}
|
\begin{cfuncdesc}{int}{PyErr_ExceptionMatches}{PyObject *exc}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Equivalent to
|
Equivalent to
|
||||||
\code{PyErr_GivenExceptionMatches(PyErr_Occurred(), \var{exc})}.
|
\code{PyErr_GivenExceptionMatches(PyErr_Occurred(), \var{exc})}.
|
||||||
This should only be called when an exception is actually set.
|
This should only be called when an exception is actually set.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{PyErr_GivenExceptionMatches}{PyObject *given, PyObject *exc}
|
\begin{cfuncdesc}{int}{PyErr_GivenExceptionMatches}{PyObject *given, PyObject *exc}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Return true if the \var{given} exception matches the exception in
|
Return true if the \var{given} exception matches the exception in
|
||||||
\var{exc}. If \var{exc} is a class object, this also returns true
|
\var{exc}. If \var{exc} is a class object, this also returns true
|
||||||
when \var{given} is a subclass. If \var{exc} is a tuple, all
|
when \var{given} is a subclass. If \var{exc} is a tuple, all
|
||||||
|
|
@ -760,7 +760,7 @@ set.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyErr_NormalizeException}{PyObject**exc, PyObject**val, PyObject**tb}
|
\begin{cfuncdesc}{void}{PyErr_NormalizeException}{PyObject**exc, PyObject**val, PyObject**tb}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Under certain circumstances, the values returned by
|
Under certain circumstances, the values returned by
|
||||||
\code{PyErr_Fetch()} below can be ``unnormalized'', meaning that
|
\code{PyErr_Fetch()} below can be ``unnormalized'', meaning that
|
||||||
\var{*exc} is a class object but \var{*val} is not an instance of the
|
\var{*exc} is a class object but \var{*val} is not an instance of the
|
||||||
|
|
@ -871,7 +871,7 @@ raised.
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyErr_NewException}{char *name,
|
\begin{cfuncdesc}{PyObject *}{PyErr_NewException}{char *name,
|
||||||
PyObject *base, PyObject *dict}
|
PyObject *base, PyObject *dict}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
This utility function creates and returns a new exception object. The
|
This utility function creates and returns a new exception object. The
|
||||||
\var{name} argument must be the name of the new exception, a C string
|
\var{name} argument must be the name of the new exception, a C string
|
||||||
of the form \code{module.class}. The \var{base} and \var{dict}
|
of the form \code{module.class}. The \var{base} and \var{dict}
|
||||||
|
|
@ -965,35 +965,17 @@ be created in this case).
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyImport_ImportModuleEx}{char *name, PyObject *globals, PyObject *locals, PyObject *fromlist}
|
\begin{cfuncdesc}{PyObject *}{PyImport_ImportModuleEx}{char *name, PyObject *globals, PyObject *locals, PyObject *fromlist}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Import a module. This is best described by referring to the built-in
|
Import a module. This is best described by referring to the built-in
|
||||||
Python function \code{__import()__}, as the standard
|
Python function \code{__import()__}, as the standard
|
||||||
\code{__import__()} function calls this function directly.
|
\code{__import__()} function calls this function directly.
|
||||||
|
|
||||||
% Should move this para to libfuncs.tex:
|
|
||||||
For example, the statement \code{import spam} results in the following
|
|
||||||
call:
|
|
||||||
\code{__import__('spam', globals(), locals(), [])};
|
|
||||||
the statement \code{from spam.ham import eggs} results in
|
|
||||||
\code{__import__('spam.ham', globals(), locals(), ['eggs'])}.
|
|
||||||
Note that even though \code{locals()} and \code{['eggs']} are passed
|
|
||||||
in as arguments, the \code{__import__()} function does not set the
|
|
||||||
local variable named \code{eggs}; this is done by subsequent code that
|
|
||||||
is generated for the import statement.
|
|
||||||
|
|
||||||
The return value is a new reference to the imported module or
|
The return value is a new reference to the imported module or
|
||||||
top-level package, or \code{NULL} with an exception set on failure
|
top-level package, or \code{NULL} with an exception set on failure
|
||||||
(the module may still be created in this case). When the \var{name}
|
(the module may still be created in this case). Like for
|
||||||
variable is of the form \code{package.module}, normally, the top-level
|
\code{__import__()}, the return value when a submodule of a package
|
||||||
package (the name up till the first dot) is returned, \emph{not} the
|
was requested is normally the top-level package, unless a non-empty
|
||||||
module named by \var{name}. However, when a non-empty \var{fromlist}
|
\var{fromlist} was given.
|
||||||
argument is given, the module named by \var{name} is returned. This
|
|
||||||
is done for compatibility with the bytecode generated for the
|
|
||||||
different kinds of import statement; when using \code{import
|
|
||||||
spam.ham.eggs}, the top-level package \code{spam} must be placed in
|
|
||||||
the importing namespace, but when using \code{from spam.ham import
|
|
||||||
eggs}, the \code{spam.ham} subpackage must be used to find the
|
|
||||||
\code{eggs} variable.
|
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyImport_Import}{PyObject *name}
|
\begin{cfuncdesc}{PyObject *}{PyImport_Import}{PyObject *name}
|
||||||
|
|
@ -1067,7 +1049,7 @@ For internal use only.
|
||||||
Load a frozen module. Return \code{1} for success, \code{0} if the
|
Load a frozen module. Return \code{1} for success, \code{0} if the
|
||||||
module is not found, and \code{-1} with an exception set if the
|
module is not found, and \code{-1} with an exception set if the
|
||||||
initialization failed. To access the imported module on a successful
|
initialization failed. To access the imported module on a successful
|
||||||
load, use \code{PyImport_ImportModule()).
|
load, use \code{PyImport_ImportModule())}.
|
||||||
(Note the misnomer -- this function would reload the module if it was
|
(Note the misnomer -- this function would reload the module if it was
|
||||||
already imported.)
|
already imported.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
@ -1744,8 +1726,6 @@ e.g. to check that an object is a dictionary, use
|
||||||
|
|
||||||
\chapter{Initialization, Finalization, and Threads}
|
\chapter{Initialization, Finalization, and Threads}
|
||||||
|
|
||||||
% XXX Check argument/return type of all these
|
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_Initialize}{}
|
\begin{cfuncdesc}{void}{Py_Initialize}{}
|
||||||
Initialize the Python interpreter. In an application embedding
|
Initialize the Python interpreter. In an application embedding
|
||||||
Python, this should be called before using any other Python/C API
|
Python, this should be called before using any other Python/C API
|
||||||
|
|
@ -1762,7 +1742,7 @@ initialization fails.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{Py_IsInitialized}{}
|
\begin{cfuncdesc}{int}{Py_IsInitialized}{}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Return true (nonzero) when the Python interpreter has been
|
Return true (nonzero) when the Python interpreter has been
|
||||||
initialized, false (zero) if not. After \code{Py_Finalize()} is
|
initialized, false (zero) if not. After \code{Py_Finalize()} is
|
||||||
called, this returns false until \code{Py_Initialize()} is called
|
called, this returns false until \code{Py_Initialize()} is called
|
||||||
|
|
@ -1770,7 +1750,7 @@ again.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_Finalize}{}
|
\begin{cfuncdesc}{void}{Py_Finalize}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Undo all initializations made by \code{Py_Initialize()} and subsequent
|
Undo all initializations made by \code{Py_Initialize()} and subsequent
|
||||||
use of Python/C API functions, and destroy all sub-interpreters (see
|
use of Python/C API functions, and destroy all sub-interpreters (see
|
||||||
\code{Py_NewInterpreter()} below) that were created and not yet
|
\code{Py_NewInterpreter()} below) that were created and not yet
|
||||||
|
|
@ -1802,7 +1782,7 @@ calls \code{Py_Initialize()} and \code{Py_Finalize()} more than once.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyThreadState *}{Py_NewInterpreter}{}
|
\begin{cfuncdesc}{PyThreadState *}{Py_NewInterpreter}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Create a new sub-interpreter. This is an (almost) totally separate
|
Create a new sub-interpreter. This is an (almost) totally separate
|
||||||
environment for the execution of Python code. In particular, the new
|
environment for the execution of Python code. In particular, the new
|
||||||
interpreter has separate, independent versions of all imported
|
interpreter has separate, independent versions of all imported
|
||||||
|
|
@ -1855,7 +1835,7 @@ a hard-to-fix bug that will be addressed in a future release.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_EndInterpreter}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{Py_EndInterpreter}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Destroy the (sub-)interpreter represented by the given thread state.
|
Destroy the (sub-)interpreter represented by the given thread state.
|
||||||
The given thread state must be the current thread state. See the
|
The given thread state must be the current thread state. See the
|
||||||
discussion of thread states below. When the call returns, the current
|
discussion of thread states below. When the call returns, the current
|
||||||
|
|
@ -1867,7 +1847,7 @@ been explicitly destroyed at that point.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_SetProgramName}{char *name}
|
\begin{cfuncdesc}{void}{Py_SetProgramName}{char *name}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
This function should be called before \code{Py_Initialize()} is called
|
This function should be called before \code{Py_Initialize()} is called
|
||||||
for the first time, if it is called at all. It tells the interpreter
|
for the first time, if it is called at all. It tells the interpreter
|
||||||
the value of the \code{argv[0]} argument to the \code{main()} function
|
the value of the \code{argv[0]} argument to the \code{main()} function
|
||||||
|
|
@ -1939,7 +1919,7 @@ platform.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{char *}{Py_GetProgramFullPath}{}
|
\begin{cfuncdesc}{char *}{Py_GetProgramFullPath}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Return the full program name of the Python executable; this is
|
Return the full program name of the Python executable; this is
|
||||||
computed as a side-effect of deriving the default module search path
|
computed as a side-effect of deriving the default module search path
|
||||||
from the program name (set by \code{Py_SetProgramName()} above). The
|
from the program name (set by \code{Py_SetProgramName()} above). The
|
||||||
|
|
@ -2032,41 +2012,320 @@ the variable \code{sys.version}.
|
||||||
|
|
||||||
\section{Thread State and the Global Interpreter Lock}
|
\section{Thread State and the Global Interpreter Lock}
|
||||||
|
|
||||||
|
The Python interpreter is not fully thread safe. In order to support
|
||||||
|
multi-threaded Python programs, there's a global lock that must be
|
||||||
|
held by the current thread before it can safely access Python objects.
|
||||||
|
Without the lock, even the simplest operations could cause problems in
|
||||||
|
a multi-threaded proram: for example, when two threads simultaneously
|
||||||
|
increment the reference count of the same object, the reference count
|
||||||
|
could end up being incremented only once instead of twice.
|
||||||
|
|
||||||
|
Therefore, the rule exists that only the thread that has acquired the
|
||||||
|
global interpreter lock may operate on Python objects or call Python/C
|
||||||
|
API functions. In order to support multi-threaded Python programs,
|
||||||
|
the interpreter regularly release and reacquires the lock -- by
|
||||||
|
default, every ten bytecode instructions (this can be changed with
|
||||||
|
\code{sys.setcheckinterval()}). The lock is also released and
|
||||||
|
reacquired around potentially blocking I/O operations like reading or
|
||||||
|
writing a file, so that other threads can run while the thread that
|
||||||
|
requests the I/O is waiting for the I/O operation to complete.
|
||||||
|
|
||||||
|
The Python interpreter needs to keep some bookkeeping information
|
||||||
|
separate per thread -- for this it uses a data structure called
|
||||||
|
PyThreadState. This is new in Python 1.5; in earlier versions, such
|
||||||
|
state was stored in global variables, and switching threads could
|
||||||
|
cause problems. In particular, exception handling is now thread safe,
|
||||||
|
when the application uses \code{sys.exc_info()} to access the exception
|
||||||
|
last raised in the current thread.
|
||||||
|
|
||||||
|
There's one global variable left, however: the pointer to the current
|
||||||
|
PyThreadState structure. While most thread packages have a way to
|
||||||
|
store ``per-thread global data'', Python's internal platform
|
||||||
|
independent thread abstraction doesn't support this (yet). Therefore,
|
||||||
|
the current thread state must be manipulated explicitly.
|
||||||
|
|
||||||
|
This is easy enough in most cases. Most code manipulating the global
|
||||||
|
interpreter lock has the following simple structure:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
Save the thread state in a local variable.
|
||||||
|
Release the interpreter lock.
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
Reacquire the interpreter lock.
|
||||||
|
Restore the thread state from the local variable.
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
This is so common that a pair of macros exists to simplify it:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
Py_BEGIN_ALLOW_THREADS
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
Py_END_ALLOW_THREADS
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
The BEGIN macro opens a new block and declares a hidden local
|
||||||
|
variable; the END macro closes the block. Another advantage of using
|
||||||
|
these two macros is that when Python is compiled without thread
|
||||||
|
support, they are defined empty, thus saving the thread state and lock
|
||||||
|
manipulations.
|
||||||
|
|
||||||
|
When thread support is enabled, the block above expands to the
|
||||||
|
following code:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
{
|
||||||
|
PyThreadState *_save;
|
||||||
|
_save = PyEval_SaveThread();
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
PyEval_RestoreThread(_save);
|
||||||
|
}
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
Using even lower level primitives, we can get roughly the same effect
|
||||||
|
as follows:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
{
|
||||||
|
PyThreadState *_save;
|
||||||
|
_save = PyThreadState_Swap(NULL);
|
||||||
|
PyEval_ReleaseLock();
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
PyEval_AcquireLock();
|
||||||
|
PyThreadState_Swap(_save);
|
||||||
|
}
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
There are some subtle differences; in particular,
|
||||||
|
\code{PyEval_RestoreThread()} saves and restores the value of the
|
||||||
|
global variable \code{errno}, since the lock manipulation does not
|
||||||
|
guarantee that \code{errno} is left alone. Also, when thread support
|
||||||
|
is disabled, \code{PyEval_SaveThread()} and
|
||||||
|
\code{PyEval_RestoreThread()} don't manipulate the lock; in this case,
|
||||||
|
\code{PyEval_ReleaseLock()} and \code{PyEval_AcquireLock()} are not
|
||||||
|
available. (This is done so that dynamically loaded extensions
|
||||||
|
compiled with thread support enabled can be loaded by an interpreter
|
||||||
|
that was compiled with disabled thread support.)
|
||||||
|
|
||||||
|
The global interpreter lock is used to protect the pointer to the
|
||||||
|
current thread state. When releasing the lock and saving the thread
|
||||||
|
state, the current thread state pointer must be retrieved before the
|
||||||
|
lock is released (since another thread could immediately acquire the
|
||||||
|
lock and store its own thread state in the global variable).
|
||||||
|
Reversely, when acquiring the lock and restoring the thread state, the
|
||||||
|
lock must be acquired before storing the thread state pointer.
|
||||||
|
|
||||||
|
Why am I going on with so much detail about this? Because when
|
||||||
|
threads are created from C, they don't have the global interpreter
|
||||||
|
lock, nor is there a thread state data structure for them. Such
|
||||||
|
threads must bootstrap themselves into existence, by first creating a
|
||||||
|
thread state data structure, then acquiring the lock, and finally
|
||||||
|
storing their thread state pointer, before they can start using the
|
||||||
|
Python/C API. When they are done, they should reset the thread state
|
||||||
|
pointer, release the lock, and finally free their thread state data
|
||||||
|
structure.
|
||||||
|
|
||||||
|
When creating a thread data structure, you need to provide an
|
||||||
|
interpreter state data structure. The interpreter state data
|
||||||
|
structure hold global data that is shared by all threads in an
|
||||||
|
interpreter, for example the module administration
|
||||||
|
(\code{sys.modules}). Depending on your needs, you can either create
|
||||||
|
a new interpreter state data structure, or share the interpreter state
|
||||||
|
data structure used by the Python main thread (to access the latter,
|
||||||
|
you must obtain the thread state and access its \code{interp} member;
|
||||||
|
this must be done by a thread that is created by Python or by the main
|
||||||
|
thread after Python is initialized).
|
||||||
|
|
||||||
|
XXX More?
|
||||||
|
|
||||||
|
\begin{ctypedesc}{PyInterpreterState}
|
||||||
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
This data structure represents the state shared by a number of
|
||||||
|
cooperating threads. Threads belonging to the same interpreter
|
||||||
|
share their module administration and a few other internal items.
|
||||||
|
There are no public members in this structure.
|
||||||
|
|
||||||
|
Threads belonging to different interpreters initially share nothing,
|
||||||
|
except process state like available memory, open file descriptors and
|
||||||
|
such. The global interpreter lock is also shared by all threads,
|
||||||
|
regardless of to which interpreter they belong.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{PyThreadState}
|
||||||
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
This data structure represents the state of a single thread. The only
|
||||||
|
public data member is \code{PyInterpreterState *interp}, which points
|
||||||
|
to this thread's interpreter state.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyEval_InitThreads}{}
|
||||||
|
Initialize and acquire the global interpreter lock. It should be
|
||||||
|
called in the main thread before creating a second thread or engaging
|
||||||
|
in any other thread operations such as \code{PyEval_ReleaseLock()} or
|
||||||
|
\code{PyEval_ReleaseThread(tstate)}. It is not needed before
|
||||||
|
calling \code{PyEval_SaveThread()} or \code{PyEval_RestoreThread()}.
|
||||||
|
|
||||||
|
This is a no-op when called for a second time. It is safe to call
|
||||||
|
this function before calling \code{Py_Initialize()}.
|
||||||
|
|
||||||
|
When only the main thread exists, no lock operations are needed. This
|
||||||
|
is a common situation (most Python programs do not use threads), and
|
||||||
|
the lock operations slow the interpreter down a bit. Therefore, the
|
||||||
|
lock is not created initially. This situation is equivalent to having
|
||||||
|
acquired the lock: when there is only a single thread, all object
|
||||||
|
accesses are safe. Therefore, when this function initializes the
|
||||||
|
lock, it also acquires it. Before the Python \code{thread} module
|
||||||
|
creates a new thread, knowing that either it has the lock or the lock
|
||||||
|
hasn't been created yet, it calls \code{PyEval_InitThreads()}. When
|
||||||
|
this call returns, it is guaranteed that the lock has been created and
|
||||||
|
that it has acquired it.
|
||||||
|
|
||||||
|
It is \strong{not} safe to call this function when it is unknown which
|
||||||
|
thread (if any) currently has the global interpreter lock.
|
||||||
|
|
||||||
|
This function is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_AcquireLock}{}
|
\begin{cfuncdesc}{void}{PyEval_AcquireLock}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
HIRO
|
Acquire the global interpreter lock. The lock must have been created
|
||||||
|
earlier. If this thread already has the lock, a deadlock ensues.
|
||||||
|
This function is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_ReleaseLock}{}
|
\begin{cfuncdesc}{void}{PyEval_ReleaseLock}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
Release the global interpreter lock. The lock must have been created
|
||||||
|
earlier. This function is not available when thread support is
|
||||||
|
disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_AcquireThread}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{PyEval_AcquireThread}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
Acquire the global interpreter lock and then set the current thread
|
||||||
|
state to \var{tstate}, which should not be \code{NULL}. The lock must
|
||||||
|
have been created earlier. If this thread already has the lock,
|
||||||
|
deadlock ensues. This function is not available when thread support
|
||||||
|
is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_ReleaseThread}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{PyEval_ReleaseThread}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
\end{cfuncdesc}
|
Reset the current thread state to \code{NULL} and release the global
|
||||||
|
interpreter lock. The lock must have been created earlier and must be
|
||||||
\begin{cfuncdesc}{void}{PyEval_RestoreThread}{PyThreadState *tstate}
|
held by the current thread. The \var{tstate} argument, which must not
|
||||||
|
be \code{NULL}, is only used to check that it represents the current
|
||||||
|
thread state -- if it isn't, a fatal error is reported. This function
|
||||||
|
is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyThreadState *}{PyEval_SaveThread}{}
|
\begin{cfuncdesc}{PyThreadState *}{PyEval_SaveThread}{}
|
||||||
|
\strong{(Different return type in 1.5a3!)}
|
||||||
|
Release the interpreter lock (if it has been created and thread
|
||||||
|
support is enabled) and reset the thread state to \code{NULL},
|
||||||
|
returning the previous thread state (which is not \code{NULL}). If
|
||||||
|
the lock has been created, the current thread must have acquired it.
|
||||||
|
(This function is available even when thread support is disabled at
|
||||||
|
compile time.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
% XXX These aren't really C functions!
|
\begin{cfuncdesc}{void}{PyEval_RestoreThread}{PyThreadState *tstate}
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_ALLOW_THREADS}{}
|
\strong{(Different argument type in 1.5a3!)}
|
||||||
|
Acquire the interpreter lock (if it has been created and thread
|
||||||
|
support is enabled) and set the thread state to \var{tstate}, which
|
||||||
|
must not be \code{NULL}. If the lock has been created, the current
|
||||||
|
thread must not have acquired it, otherwise deadlock ensues. (This
|
||||||
|
function is available even when thread support is disabled at compile
|
||||||
|
time.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_END_THREADS}{}
|
% XXX These aren't really C types, but the ctypedesc macro is the simplest!
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_ALLOW_THREADS}
|
||||||
|
This macro expands to
|
||||||
|
\code{\{ PyThreadState *_save; _save = PyEval_SaveThread();}.
|
||||||
|
Note that it contains an opening brace; it must be matched with a
|
||||||
|
following \code{Py_END_ALLOW_THREADS} macro. See above for further
|
||||||
|
discussion of this macro. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_END_ALLOW_THREADS}
|
||||||
|
This macro expands to
|
||||||
|
\code{PyEval_RestoreThread(_save); \} }.
|
||||||
|
Note that it contains a closing brace; it must be matched with an
|
||||||
|
earlier \code{Py_BEGIN_ALLOW_THREADS} macro. See above for further
|
||||||
|
discussion of this macro. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_BLOCK_THREADS}
|
||||||
|
This macro expands to \code{PyEval_RestoreThread(_save);} i.e. it
|
||||||
|
is equivalent to \code{Py_END_ALLOW_THREADS} without the closing
|
||||||
|
brace. It is a no-op when thread support is disabled at compile
|
||||||
|
time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_UNBLOCK_THREADS}
|
||||||
|
This macro expands to \code{_save = PyEval_SaveThread();} i.e. it is
|
||||||
|
equivalent to \code{Py_BEGIN_ALLOW_THREADS} without the opening brace
|
||||||
|
and variable declaration. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
All of the following functions are only available when thread support
|
||||||
|
is enabled at compile time, and must be called only when the
|
||||||
|
interpreter lock has been created. They are all new in 1.5a3.
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyInterpreterState *}{PyInterpreterState_New}{}
|
||||||
|
Create a new interpreter state object. The interpreter lock must be
|
||||||
|
held.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_XXX_THREADS}{}
|
\begin{cfuncdesc}{void}{PyInterpreterState_Clear}{PyInterpreterState *interp}
|
||||||
|
Reset all information in an interpreter state object. The interpreter
|
||||||
|
lock must be held.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyInterpreterState_Delete}{PyInterpreterState *interp}
|
||||||
|
Destroy an interpreter state object. The interpreter lock need not be
|
||||||
|
held. The interpreter state must have been reset with a previous
|
||||||
|
call to \code{PyInterpreterState_Clear()}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_New}{PyInterpreterState *interp}
|
||||||
|
Create a new thread state object belonging to the given interpreter
|
||||||
|
object. The interpreter lock must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyThreadState_Clear}{PyThreadState *tstate}
|
||||||
|
Reset all information in a thread state object. The interpreter lock
|
||||||
|
must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyThreadState_Delete}{PyThreadState *tstate}
|
||||||
|
Destroy a thread state object. The interpreter lock need not be
|
||||||
|
held. The thread state must have been reset with a previous
|
||||||
|
call to \code{PyThreadState_Clear()}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_Get}{}
|
||||||
|
Return the current thread state. The interpreter lock must be held.
|
||||||
|
When the current thread state is \code{NULL}, this issues a fatal
|
||||||
|
error (so that the caller needn't check for \code{NULL}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_Swap}{PyThreadState *tstate}
|
||||||
|
Swap the current thread state with the thread state given by the
|
||||||
|
argument \var{tstate}, which may be \code{NULL}. The interpreter lock
|
||||||
|
must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
|
||||||
|
\section{Defining New Object Types}
|
||||||
|
|
||||||
XXX To be done:
|
XXX To be done:
|
||||||
|
|
||||||
|
|
@ -2131,7 +2390,7 @@ This section describes Python type objects and the singleton object
|
||||||
\subsection{The None Object}
|
\subsection{The None Object}
|
||||||
|
|
||||||
\begin{cvardesc}{PyObject *}{Py_None}
|
\begin{cvardesc}{PyObject *}{Py_None}
|
||||||
macro
|
XXX macro
|
||||||
\end{cvardesc}
|
\end{cvardesc}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -2139,7 +2398,7 @@ macro
|
||||||
|
|
||||||
Generic operations on sequence objects were discussed in the previous
|
Generic operations on sequence objects were discussed in the previous
|
||||||
chapter; this section deals with the specific kinds of sequence
|
chapter; this section deals with the specific kinds of sequence
|
||||||
objects that are intrinsuc to the Python language.
|
objects that are intrinsic to the Python language.
|
||||||
|
|
||||||
|
|
||||||
\subsection{String Objects}
|
\subsection{String Objects}
|
||||||
|
|
|
||||||
365
Doc/api/api.tex
365
Doc/api/api.tex
|
|
@ -653,7 +653,7 @@ e.g., when the object administration appears to be corrupted.
|
||||||
Initialize the \code{__builtin__} module. For internal use only.
|
Initialize the \code{__builtin__} module. For internal use only.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
XXX Other init functions: PyEval_InitThreads, PyOS_InitInterrupts,
|
XXX Other init functions: PyOS_InitInterrupts,
|
||||||
PyMarshal_Init, PySys_Init.
|
PyMarshal_Init, PySys_Init.
|
||||||
|
|
||||||
\chapter{Reference Counting}
|
\chapter{Reference Counting}
|
||||||
|
|
@ -743,14 +743,14 @@ return value to a specific exception; use
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{PyErr_ExceptionMatches}{PyObject *exc}
|
\begin{cfuncdesc}{int}{PyErr_ExceptionMatches}{PyObject *exc}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Equivalent to
|
Equivalent to
|
||||||
\code{PyErr_GivenExceptionMatches(PyErr_Occurred(), \var{exc})}.
|
\code{PyErr_GivenExceptionMatches(PyErr_Occurred(), \var{exc})}.
|
||||||
This should only be called when an exception is actually set.
|
This should only be called when an exception is actually set.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{PyErr_GivenExceptionMatches}{PyObject *given, PyObject *exc}
|
\begin{cfuncdesc}{int}{PyErr_GivenExceptionMatches}{PyObject *given, PyObject *exc}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Return true if the \var{given} exception matches the exception in
|
Return true if the \var{given} exception matches the exception in
|
||||||
\var{exc}. If \var{exc} is a class object, this also returns true
|
\var{exc}. If \var{exc} is a class object, this also returns true
|
||||||
when \var{given} is a subclass. If \var{exc} is a tuple, all
|
when \var{given} is a subclass. If \var{exc} is a tuple, all
|
||||||
|
|
@ -760,7 +760,7 @@ set.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyErr_NormalizeException}{PyObject**exc, PyObject**val, PyObject**tb}
|
\begin{cfuncdesc}{void}{PyErr_NormalizeException}{PyObject**exc, PyObject**val, PyObject**tb}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Under certain circumstances, the values returned by
|
Under certain circumstances, the values returned by
|
||||||
\code{PyErr_Fetch()} below can be ``unnormalized'', meaning that
|
\code{PyErr_Fetch()} below can be ``unnormalized'', meaning that
|
||||||
\var{*exc} is a class object but \var{*val} is not an instance of the
|
\var{*exc} is a class object but \var{*val} is not an instance of the
|
||||||
|
|
@ -871,7 +871,7 @@ raised.
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyErr_NewException}{char *name,
|
\begin{cfuncdesc}{PyObject *}{PyErr_NewException}{char *name,
|
||||||
PyObject *base, PyObject *dict}
|
PyObject *base, PyObject *dict}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
This utility function creates and returns a new exception object. The
|
This utility function creates and returns a new exception object. The
|
||||||
\var{name} argument must be the name of the new exception, a C string
|
\var{name} argument must be the name of the new exception, a C string
|
||||||
of the form \code{module.class}. The \var{base} and \var{dict}
|
of the form \code{module.class}. The \var{base} and \var{dict}
|
||||||
|
|
@ -965,35 +965,17 @@ be created in this case).
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyImport_ImportModuleEx}{char *name, PyObject *globals, PyObject *locals, PyObject *fromlist}
|
\begin{cfuncdesc}{PyObject *}{PyImport_ImportModuleEx}{char *name, PyObject *globals, PyObject *locals, PyObject *fromlist}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Import a module. This is best described by referring to the built-in
|
Import a module. This is best described by referring to the built-in
|
||||||
Python function \code{__import()__}, as the standard
|
Python function \code{__import()__}, as the standard
|
||||||
\code{__import__()} function calls this function directly.
|
\code{__import__()} function calls this function directly.
|
||||||
|
|
||||||
% Should move this para to libfuncs.tex:
|
|
||||||
For example, the statement \code{import spam} results in the following
|
|
||||||
call:
|
|
||||||
\code{__import__('spam', globals(), locals(), [])};
|
|
||||||
the statement \code{from spam.ham import eggs} results in
|
|
||||||
\code{__import__('spam.ham', globals(), locals(), ['eggs'])}.
|
|
||||||
Note that even though \code{locals()} and \code{['eggs']} are passed
|
|
||||||
in as arguments, the \code{__import__()} function does not set the
|
|
||||||
local variable named \code{eggs}; this is done by subsequent code that
|
|
||||||
is generated for the import statement.
|
|
||||||
|
|
||||||
The return value is a new reference to the imported module or
|
The return value is a new reference to the imported module or
|
||||||
top-level package, or \code{NULL} with an exception set on failure
|
top-level package, or \code{NULL} with an exception set on failure
|
||||||
(the module may still be created in this case). When the \var{name}
|
(the module may still be created in this case). Like for
|
||||||
variable is of the form \code{package.module}, normally, the top-level
|
\code{__import__()}, the return value when a submodule of a package
|
||||||
package (the name up till the first dot) is returned, \emph{not} the
|
was requested is normally the top-level package, unless a non-empty
|
||||||
module named by \var{name}. However, when a non-empty \var{fromlist}
|
\var{fromlist} was given.
|
||||||
argument is given, the module named by \var{name} is returned. This
|
|
||||||
is done for compatibility with the bytecode generated for the
|
|
||||||
different kinds of import statement; when using \code{import
|
|
||||||
spam.ham.eggs}, the top-level package \code{spam} must be placed in
|
|
||||||
the importing namespace, but when using \code{from spam.ham import
|
|
||||||
eggs}, the \code{spam.ham} subpackage must be used to find the
|
|
||||||
\code{eggs} variable.
|
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyObject *}{PyImport_Import}{PyObject *name}
|
\begin{cfuncdesc}{PyObject *}{PyImport_Import}{PyObject *name}
|
||||||
|
|
@ -1067,7 +1049,7 @@ For internal use only.
|
||||||
Load a frozen module. Return \code{1} for success, \code{0} if the
|
Load a frozen module. Return \code{1} for success, \code{0} if the
|
||||||
module is not found, and \code{-1} with an exception set if the
|
module is not found, and \code{-1} with an exception set if the
|
||||||
initialization failed. To access the imported module on a successful
|
initialization failed. To access the imported module on a successful
|
||||||
load, use \code{PyImport_ImportModule()).
|
load, use \code{PyImport_ImportModule())}.
|
||||||
(Note the misnomer -- this function would reload the module if it was
|
(Note the misnomer -- this function would reload the module if it was
|
||||||
already imported.)
|
already imported.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
@ -1744,8 +1726,6 @@ e.g. to check that an object is a dictionary, use
|
||||||
|
|
||||||
\chapter{Initialization, Finalization, and Threads}
|
\chapter{Initialization, Finalization, and Threads}
|
||||||
|
|
||||||
% XXX Check argument/return type of all these
|
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_Initialize}{}
|
\begin{cfuncdesc}{void}{Py_Initialize}{}
|
||||||
Initialize the Python interpreter. In an application embedding
|
Initialize the Python interpreter. In an application embedding
|
||||||
Python, this should be called before using any other Python/C API
|
Python, this should be called before using any other Python/C API
|
||||||
|
|
@ -1762,7 +1742,7 @@ initialization fails.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{int}{Py_IsInitialized}{}
|
\begin{cfuncdesc}{int}{Py_IsInitialized}{}
|
||||||
\strong{NEW in 1.5a4!}
|
\strong{(NEW in 1.5a4!)}
|
||||||
Return true (nonzero) when the Python interpreter has been
|
Return true (nonzero) when the Python interpreter has been
|
||||||
initialized, false (zero) if not. After \code{Py_Finalize()} is
|
initialized, false (zero) if not. After \code{Py_Finalize()} is
|
||||||
called, this returns false until \code{Py_Initialize()} is called
|
called, this returns false until \code{Py_Initialize()} is called
|
||||||
|
|
@ -1770,7 +1750,7 @@ again.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_Finalize}{}
|
\begin{cfuncdesc}{void}{Py_Finalize}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Undo all initializations made by \code{Py_Initialize()} and subsequent
|
Undo all initializations made by \code{Py_Initialize()} and subsequent
|
||||||
use of Python/C API functions, and destroy all sub-interpreters (see
|
use of Python/C API functions, and destroy all sub-interpreters (see
|
||||||
\code{Py_NewInterpreter()} below) that were created and not yet
|
\code{Py_NewInterpreter()} below) that were created and not yet
|
||||||
|
|
@ -1802,7 +1782,7 @@ calls \code{Py_Initialize()} and \code{Py_Finalize()} more than once.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyThreadState *}{Py_NewInterpreter}{}
|
\begin{cfuncdesc}{PyThreadState *}{Py_NewInterpreter}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Create a new sub-interpreter. This is an (almost) totally separate
|
Create a new sub-interpreter. This is an (almost) totally separate
|
||||||
environment for the execution of Python code. In particular, the new
|
environment for the execution of Python code. In particular, the new
|
||||||
interpreter has separate, independent versions of all imported
|
interpreter has separate, independent versions of all imported
|
||||||
|
|
@ -1855,7 +1835,7 @@ a hard-to-fix bug that will be addressed in a future release.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_EndInterpreter}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{Py_EndInterpreter}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Destroy the (sub-)interpreter represented by the given thread state.
|
Destroy the (sub-)interpreter represented by the given thread state.
|
||||||
The given thread state must be the current thread state. See the
|
The given thread state must be the current thread state. See the
|
||||||
discussion of thread states below. When the call returns, the current
|
discussion of thread states below. When the call returns, the current
|
||||||
|
|
@ -1867,7 +1847,7 @@ been explicitly destroyed at that point.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{Py_SetProgramName}{char *name}
|
\begin{cfuncdesc}{void}{Py_SetProgramName}{char *name}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
This function should be called before \code{Py_Initialize()} is called
|
This function should be called before \code{Py_Initialize()} is called
|
||||||
for the first time, if it is called at all. It tells the interpreter
|
for the first time, if it is called at all. It tells the interpreter
|
||||||
the value of the \code{argv[0]} argument to the \code{main()} function
|
the value of the \code{argv[0]} argument to the \code{main()} function
|
||||||
|
|
@ -1939,7 +1919,7 @@ platform.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{char *}{Py_GetProgramFullPath}{}
|
\begin{cfuncdesc}{char *}{Py_GetProgramFullPath}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
Return the full program name of the Python executable; this is
|
Return the full program name of the Python executable; this is
|
||||||
computed as a side-effect of deriving the default module search path
|
computed as a side-effect of deriving the default module search path
|
||||||
from the program name (set by \code{Py_SetProgramName()} above). The
|
from the program name (set by \code{Py_SetProgramName()} above). The
|
||||||
|
|
@ -2032,41 +2012,320 @@ the variable \code{sys.version}.
|
||||||
|
|
||||||
\section{Thread State and the Global Interpreter Lock}
|
\section{Thread State and the Global Interpreter Lock}
|
||||||
|
|
||||||
|
The Python interpreter is not fully thread safe. In order to support
|
||||||
|
multi-threaded Python programs, there's a global lock that must be
|
||||||
|
held by the current thread before it can safely access Python objects.
|
||||||
|
Without the lock, even the simplest operations could cause problems in
|
||||||
|
a multi-threaded proram: for example, when two threads simultaneously
|
||||||
|
increment the reference count of the same object, the reference count
|
||||||
|
could end up being incremented only once instead of twice.
|
||||||
|
|
||||||
|
Therefore, the rule exists that only the thread that has acquired the
|
||||||
|
global interpreter lock may operate on Python objects or call Python/C
|
||||||
|
API functions. In order to support multi-threaded Python programs,
|
||||||
|
the interpreter regularly release and reacquires the lock -- by
|
||||||
|
default, every ten bytecode instructions (this can be changed with
|
||||||
|
\code{sys.setcheckinterval()}). The lock is also released and
|
||||||
|
reacquired around potentially blocking I/O operations like reading or
|
||||||
|
writing a file, so that other threads can run while the thread that
|
||||||
|
requests the I/O is waiting for the I/O operation to complete.
|
||||||
|
|
||||||
|
The Python interpreter needs to keep some bookkeeping information
|
||||||
|
separate per thread -- for this it uses a data structure called
|
||||||
|
PyThreadState. This is new in Python 1.5; in earlier versions, such
|
||||||
|
state was stored in global variables, and switching threads could
|
||||||
|
cause problems. In particular, exception handling is now thread safe,
|
||||||
|
when the application uses \code{sys.exc_info()} to access the exception
|
||||||
|
last raised in the current thread.
|
||||||
|
|
||||||
|
There's one global variable left, however: the pointer to the current
|
||||||
|
PyThreadState structure. While most thread packages have a way to
|
||||||
|
store ``per-thread global data'', Python's internal platform
|
||||||
|
independent thread abstraction doesn't support this (yet). Therefore,
|
||||||
|
the current thread state must be manipulated explicitly.
|
||||||
|
|
||||||
|
This is easy enough in most cases. Most code manipulating the global
|
||||||
|
interpreter lock has the following simple structure:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
Save the thread state in a local variable.
|
||||||
|
Release the interpreter lock.
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
Reacquire the interpreter lock.
|
||||||
|
Restore the thread state from the local variable.
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
This is so common that a pair of macros exists to simplify it:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
Py_BEGIN_ALLOW_THREADS
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
Py_END_ALLOW_THREADS
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
The BEGIN macro opens a new block and declares a hidden local
|
||||||
|
variable; the END macro closes the block. Another advantage of using
|
||||||
|
these two macros is that when Python is compiled without thread
|
||||||
|
support, they are defined empty, thus saving the thread state and lock
|
||||||
|
manipulations.
|
||||||
|
|
||||||
|
When thread support is enabled, the block above expands to the
|
||||||
|
following code:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
{
|
||||||
|
PyThreadState *_save;
|
||||||
|
_save = PyEval_SaveThread();
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
PyEval_RestoreThread(_save);
|
||||||
|
}
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
Using even lower level primitives, we can get roughly the same effect
|
||||||
|
as follows:
|
||||||
|
|
||||||
|
\bcode\begin{verbatim}
|
||||||
|
{
|
||||||
|
PyThreadState *_save;
|
||||||
|
_save = PyThreadState_Swap(NULL);
|
||||||
|
PyEval_ReleaseLock();
|
||||||
|
...Do some blocking I/O operation...
|
||||||
|
PyEval_AcquireLock();
|
||||||
|
PyThreadState_Swap(_save);
|
||||||
|
}
|
||||||
|
\end{verbatim}\ecode
|
||||||
|
|
||||||
|
There are some subtle differences; in particular,
|
||||||
|
\code{PyEval_RestoreThread()} saves and restores the value of the
|
||||||
|
global variable \code{errno}, since the lock manipulation does not
|
||||||
|
guarantee that \code{errno} is left alone. Also, when thread support
|
||||||
|
is disabled, \code{PyEval_SaveThread()} and
|
||||||
|
\code{PyEval_RestoreThread()} don't manipulate the lock; in this case,
|
||||||
|
\code{PyEval_ReleaseLock()} and \code{PyEval_AcquireLock()} are not
|
||||||
|
available. (This is done so that dynamically loaded extensions
|
||||||
|
compiled with thread support enabled can be loaded by an interpreter
|
||||||
|
that was compiled with disabled thread support.)
|
||||||
|
|
||||||
|
The global interpreter lock is used to protect the pointer to the
|
||||||
|
current thread state. When releasing the lock and saving the thread
|
||||||
|
state, the current thread state pointer must be retrieved before the
|
||||||
|
lock is released (since another thread could immediately acquire the
|
||||||
|
lock and store its own thread state in the global variable).
|
||||||
|
Reversely, when acquiring the lock and restoring the thread state, the
|
||||||
|
lock must be acquired before storing the thread state pointer.
|
||||||
|
|
||||||
|
Why am I going on with so much detail about this? Because when
|
||||||
|
threads are created from C, they don't have the global interpreter
|
||||||
|
lock, nor is there a thread state data structure for them. Such
|
||||||
|
threads must bootstrap themselves into existence, by first creating a
|
||||||
|
thread state data structure, then acquiring the lock, and finally
|
||||||
|
storing their thread state pointer, before they can start using the
|
||||||
|
Python/C API. When they are done, they should reset the thread state
|
||||||
|
pointer, release the lock, and finally free their thread state data
|
||||||
|
structure.
|
||||||
|
|
||||||
|
When creating a thread data structure, you need to provide an
|
||||||
|
interpreter state data structure. The interpreter state data
|
||||||
|
structure hold global data that is shared by all threads in an
|
||||||
|
interpreter, for example the module administration
|
||||||
|
(\code{sys.modules}). Depending on your needs, you can either create
|
||||||
|
a new interpreter state data structure, or share the interpreter state
|
||||||
|
data structure used by the Python main thread (to access the latter,
|
||||||
|
you must obtain the thread state and access its \code{interp} member;
|
||||||
|
this must be done by a thread that is created by Python or by the main
|
||||||
|
thread after Python is initialized).
|
||||||
|
|
||||||
|
XXX More?
|
||||||
|
|
||||||
|
\begin{ctypedesc}{PyInterpreterState}
|
||||||
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
This data structure represents the state shared by a number of
|
||||||
|
cooperating threads. Threads belonging to the same interpreter
|
||||||
|
share their module administration and a few other internal items.
|
||||||
|
There are no public members in this structure.
|
||||||
|
|
||||||
|
Threads belonging to different interpreters initially share nothing,
|
||||||
|
except process state like available memory, open file descriptors and
|
||||||
|
such. The global interpreter lock is also shared by all threads,
|
||||||
|
regardless of to which interpreter they belong.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{PyThreadState}
|
||||||
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
This data structure represents the state of a single thread. The only
|
||||||
|
public data member is \code{PyInterpreterState *interp}, which points
|
||||||
|
to this thread's interpreter state.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyEval_InitThreads}{}
|
||||||
|
Initialize and acquire the global interpreter lock. It should be
|
||||||
|
called in the main thread before creating a second thread or engaging
|
||||||
|
in any other thread operations such as \code{PyEval_ReleaseLock()} or
|
||||||
|
\code{PyEval_ReleaseThread(tstate)}. It is not needed before
|
||||||
|
calling \code{PyEval_SaveThread()} or \code{PyEval_RestoreThread()}.
|
||||||
|
|
||||||
|
This is a no-op when called for a second time. It is safe to call
|
||||||
|
this function before calling \code{Py_Initialize()}.
|
||||||
|
|
||||||
|
When only the main thread exists, no lock operations are needed. This
|
||||||
|
is a common situation (most Python programs do not use threads), and
|
||||||
|
the lock operations slow the interpreter down a bit. Therefore, the
|
||||||
|
lock is not created initially. This situation is equivalent to having
|
||||||
|
acquired the lock: when there is only a single thread, all object
|
||||||
|
accesses are safe. Therefore, when this function initializes the
|
||||||
|
lock, it also acquires it. Before the Python \code{thread} module
|
||||||
|
creates a new thread, knowing that either it has the lock or the lock
|
||||||
|
hasn't been created yet, it calls \code{PyEval_InitThreads()}. When
|
||||||
|
this call returns, it is guaranteed that the lock has been created and
|
||||||
|
that it has acquired it.
|
||||||
|
|
||||||
|
It is \strong{not} safe to call this function when it is unknown which
|
||||||
|
thread (if any) currently has the global interpreter lock.
|
||||||
|
|
||||||
|
This function is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_AcquireLock}{}
|
\begin{cfuncdesc}{void}{PyEval_AcquireLock}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
HIRO
|
Acquire the global interpreter lock. The lock must have been created
|
||||||
|
earlier. If this thread already has the lock, a deadlock ensues.
|
||||||
|
This function is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_ReleaseLock}{}
|
\begin{cfuncdesc}{void}{PyEval_ReleaseLock}{}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
Release the global interpreter lock. The lock must have been created
|
||||||
|
earlier. This function is not available when thread support is
|
||||||
|
disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_AcquireThread}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{PyEval_AcquireThread}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
|
Acquire the global interpreter lock and then set the current thread
|
||||||
|
state to \var{tstate}, which should not be \code{NULL}. The lock must
|
||||||
|
have been created earlier. If this thread already has the lock,
|
||||||
|
deadlock ensues. This function is not available when thread support
|
||||||
|
is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{void}{PyEval_ReleaseThread}{PyThreadState *tstate}
|
\begin{cfuncdesc}{void}{PyEval_ReleaseThread}{PyThreadState *tstate}
|
||||||
\strong{NEW in 1.5a3!}
|
\strong{(NEW in 1.5a3!)}
|
||||||
\end{cfuncdesc}
|
Reset the current thread state to \code{NULL} and release the global
|
||||||
|
interpreter lock. The lock must have been created earlier and must be
|
||||||
\begin{cfuncdesc}{void}{PyEval_RestoreThread}{PyThreadState *tstate}
|
held by the current thread. The \var{tstate} argument, which must not
|
||||||
|
be \code{NULL}, is only used to check that it represents the current
|
||||||
|
thread state -- if it isn't, a fatal error is reported. This function
|
||||||
|
is not available when thread support is disabled at
|
||||||
|
compile time.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{PyThreadState *}{PyEval_SaveThread}{}
|
\begin{cfuncdesc}{PyThreadState *}{PyEval_SaveThread}{}
|
||||||
|
\strong{(Different return type in 1.5a3!)}
|
||||||
|
Release the interpreter lock (if it has been created and thread
|
||||||
|
support is enabled) and reset the thread state to \code{NULL},
|
||||||
|
returning the previous thread state (which is not \code{NULL}). If
|
||||||
|
the lock has been created, the current thread must have acquired it.
|
||||||
|
(This function is available even when thread support is disabled at
|
||||||
|
compile time.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
% XXX These aren't really C functions!
|
\begin{cfuncdesc}{void}{PyEval_RestoreThread}{PyThreadState *tstate}
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_ALLOW_THREADS}{}
|
\strong{(Different argument type in 1.5a3!)}
|
||||||
|
Acquire the interpreter lock (if it has been created and thread
|
||||||
|
support is enabled) and set the thread state to \var{tstate}, which
|
||||||
|
must not be \code{NULL}. If the lock has been created, the current
|
||||||
|
thread must not have acquired it, otherwise deadlock ensues. (This
|
||||||
|
function is available even when thread support is disabled at compile
|
||||||
|
time.)
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_END_THREADS}{}
|
% XXX These aren't really C types, but the ctypedesc macro is the simplest!
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_ALLOW_THREADS}
|
||||||
|
This macro expands to
|
||||||
|
\code{\{ PyThreadState *_save; _save = PyEval_SaveThread();}.
|
||||||
|
Note that it contains an opening brace; it must be matched with a
|
||||||
|
following \code{Py_END_ALLOW_THREADS} macro. See above for further
|
||||||
|
discussion of this macro. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_END_ALLOW_THREADS}
|
||||||
|
This macro expands to
|
||||||
|
\code{PyEval_RestoreThread(_save); \} }.
|
||||||
|
Note that it contains a closing brace; it must be matched with an
|
||||||
|
earlier \code{Py_BEGIN_ALLOW_THREADS} macro. See above for further
|
||||||
|
discussion of this macro. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_BLOCK_THREADS}
|
||||||
|
This macro expands to \code{PyEval_RestoreThread(_save);} i.e. it
|
||||||
|
is equivalent to \code{Py_END_ALLOW_THREADS} without the closing
|
||||||
|
brace. It is a no-op when thread support is disabled at compile
|
||||||
|
time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
\begin{ctypedesc}{Py_BEGIN_UNBLOCK_THREADS}
|
||||||
|
This macro expands to \code{_save = PyEval_SaveThread();} i.e. it is
|
||||||
|
equivalent to \code{Py_BEGIN_ALLOW_THREADS} without the opening brace
|
||||||
|
and variable declaration. It is a no-op when thread support is
|
||||||
|
disabled at compile time.
|
||||||
|
\end{ctypedesc}
|
||||||
|
|
||||||
|
All of the following functions are only available when thread support
|
||||||
|
is enabled at compile time, and must be called only when the
|
||||||
|
interpreter lock has been created. They are all new in 1.5a3.
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyInterpreterState *}{PyInterpreterState_New}{}
|
||||||
|
Create a new interpreter state object. The interpreter lock must be
|
||||||
|
held.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
\begin{cfuncdesc}{}{Py_BEGIN_XXX_THREADS}{}
|
\begin{cfuncdesc}{void}{PyInterpreterState_Clear}{PyInterpreterState *interp}
|
||||||
|
Reset all information in an interpreter state object. The interpreter
|
||||||
|
lock must be held.
|
||||||
\end{cfuncdesc}
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyInterpreterState_Delete}{PyInterpreterState *interp}
|
||||||
|
Destroy an interpreter state object. The interpreter lock need not be
|
||||||
|
held. The interpreter state must have been reset with a previous
|
||||||
|
call to \code{PyInterpreterState_Clear()}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_New}{PyInterpreterState *interp}
|
||||||
|
Create a new thread state object belonging to the given interpreter
|
||||||
|
object. The interpreter lock must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyThreadState_Clear}{PyThreadState *tstate}
|
||||||
|
Reset all information in a thread state object. The interpreter lock
|
||||||
|
must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{void}{PyThreadState_Delete}{PyThreadState *tstate}
|
||||||
|
Destroy a thread state object. The interpreter lock need not be
|
||||||
|
held. The thread state must have been reset with a previous
|
||||||
|
call to \code{PyThreadState_Clear()}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_Get}{}
|
||||||
|
Return the current thread state. The interpreter lock must be held.
|
||||||
|
When the current thread state is \code{NULL}, this issues a fatal
|
||||||
|
error (so that the caller needn't check for \code{NULL}.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
\begin{cfuncdesc}{PyThreadState *}{PyThreadState_Swap}{PyThreadState *tstate}
|
||||||
|
Swap the current thread state with the thread state given by the
|
||||||
|
argument \var{tstate}, which may be \code{NULL}. The interpreter lock
|
||||||
|
must be held.
|
||||||
|
\end{cfuncdesc}
|
||||||
|
|
||||||
|
|
||||||
|
\section{Defining New Object Types}
|
||||||
|
|
||||||
XXX To be done:
|
XXX To be done:
|
||||||
|
|
||||||
|
|
@ -2131,7 +2390,7 @@ This section describes Python type objects and the singleton object
|
||||||
\subsection{The None Object}
|
\subsection{The None Object}
|
||||||
|
|
||||||
\begin{cvardesc}{PyObject *}{Py_None}
|
\begin{cvardesc}{PyObject *}{Py_None}
|
||||||
macro
|
XXX macro
|
||||||
\end{cvardesc}
|
\end{cvardesc}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -2139,7 +2398,7 @@ macro
|
||||||
|
|
||||||
Generic operations on sequence objects were discussed in the previous
|
Generic operations on sequence objects were discussed in the previous
|
||||||
chapter; this section deals with the specific kinds of sequence
|
chapter; this section deals with the specific kinds of sequence
|
||||||
objects that are intrinsuc to the Python language.
|
objects that are intrinsic to the Python language.
|
||||||
|
|
||||||
|
|
||||||
\subsection{String Objects}
|
\subsection{String Objects}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue