Started making changes to Python.html to document support for multithreaded Python SWIG applications.

This commit is contained in:
Todd Leonhardt 2017-02-28 20:53:30 -05:00
commit 52d12bc415

View file

@ -133,6 +133,10 @@
<li><a href="#Python_nn77">Byte string output conversion</a> <li><a href="#Python_nn77">Byte string output conversion</a>
<li><a href="#Python_2_unicode">Python 2 Unicode</a> <li><a href="#Python_2_unicode">Python 2 Unicode</a>
</ul> </ul>
<li><a href="#Python_multithreaded">Support for Multithreaded Applications</a>
<ul>
<li><a href="#Python_thread_UI">UI for Enabling Multithreading Support</a>
</ul>
</ul> </ul>
</div> </div>
<!-- INDEX --> <!-- INDEX -->
@ -162,7 +166,7 @@ Basics</a>" chapter.
<p> <p>
To build Python extension modules, SWIG uses a layered approach in which To build Python extension modules, SWIG uses a layered approach in which
parts of the extension module are defined in C and other parts are parts of the extension module are defined in C and other parts are
defined in Python. The C layer contains low-level wrappers whereas Python code defined in Python. The C layer contains low-level wrappers whereas Python code
is used to define high-level features. is used to define high-level features.
</p> </p>
@ -395,9 +399,9 @@ $ gcc -shared example.o example_wrap.o -o _example.so
</pre></div> </pre></div>
<p> <p>
The exact commands for doing this vary from platform to platform. The exact commands for doing this vary from platform to platform.
However, SWIG tries to guess the right options when it is installed. Therefore, However, SWIG tries to guess the right options when it is installed. Therefore,
you may want to start with one of the examples in the <tt>SWIG/Examples/python</tt> you may want to start with one of the examples in the <tt>SWIG/Examples/python</tt>
directory. If that doesn't work, you will need to read the man-pages for directory. If that doesn't work, you will need to read the man-pages for
your compiler and linker to get the right set of options. You might also your compiler and linker to get the right set of options. You might also
check the <a href="https://github.com/swig/swig/wiki">SWIG Wiki</a> for check the <a href="https://github.com/swig/swig/wiki">SWIG Wiki</a> for
@ -409,7 +413,7 @@ When linking the module, <b>the name of the output file has to match the name
of the module prefixed by an underscore</b>. If the name of your module is "<tt>example</tt>", then the of the module prefixed by an underscore</b>. If the name of your module is "<tt>example</tt>", then the
name of the corresponding object file should be name of the corresponding object file should be
"<tt>_example.so</tt>" or "<tt>_examplemodule.so</tt>". "<tt>_example.so</tt>" or "<tt>_examplemodule.so</tt>".
The name of the module is specified using the <tt>%module</tt> directive or the The name of the module is specified using the <tt>%module</tt> directive or the
<tt>-module</tt> command line option. <tt>-module</tt> command line option.
</p> </p>
@ -433,7 +437,7 @@ An alternative approach to dynamic linking is to rebuild the Python
interpreter with your extension module added to it. In the past, interpreter with your extension module added to it. In the past,
this approach was sometimes necessary due to limitations in dynamic loading this approach was sometimes necessary due to limitations in dynamic loading
support on certain machines. However, the situation has improved greatly support on certain machines. However, the situation has improved greatly
over the last few years and you should not consider this approach over the last few years and you should not consider this approach
unless there is really no other option. unless there is really no other option.
</p> </p>
@ -493,7 +497,7 @@ linking if possible. Some programmers may be inclined
to use static linking in the interest of getting better performance. to use static linking in the interest of getting better performance.
However, the performance gained by static linking tends to be rather However, the performance gained by static linking tends to be rather
minimal in most situations (and quite frankly not worth the extra minimal in most situations (and quite frankly not worth the extra
hassle in the opinion of this author). hassle in the opinion of this author).
</p> </p>
<p> <p>
@ -552,13 +556,13 @@ Another possible error is the following:
Traceback (most recent call last): Traceback (most recent call last):
File "&lt;stdin&gt;", line 1, in ? File "&lt;stdin&gt;", line 1, in ?
ImportError: dynamic module does not define init function (init_example) ImportError: dynamic module does not define init function (init_example)
&gt;&gt;&gt; &gt;&gt;&gt;
</pre> </pre>
</div> </div>
<p> <p>
This error is almost always caused when a bad name is given to the shared object file. This error is almost always caused when a bad name is given to the shared object file.
For example, if you created a file <tt>example.so</tt> instead of <tt>_example.so</tt> you would For example, if you created a file <tt>example.so</tt> instead of <tt>_example.so</tt> you would
get this error. Alternatively, this error could arise if the name of the module is get this error. Alternatively, this error could arise if the name of the module is
inconsistent with the module name supplied with the <tt>%module</tt> directive. inconsistent with the module name supplied with the <tt>%module</tt> directive.
Double-check the interface to make sure the module name and the shared object Double-check the interface to make sure the module name and the shared object
@ -584,7 +588,7 @@ This error usually indicates that you forgot to include some object
files or libraries in the linking of the shared library file. Make files or libraries in the linking of the shared library file. Make
sure you compile both the SWIG wrapper file and your original program sure you compile both the SWIG wrapper file and your original program
into a shared library file. Make sure you pass all of the required libraries into a shared library file. Make sure you pass all of the required libraries
to the linker. to the linker.
</p> </p>
<p> <p>
@ -619,7 +623,7 @@ problem when you try to use your module:
Traceback (most recent call last): Traceback (most recent call last):
File "&lt;stdin&gt;", line 1, in ? File "&lt;stdin&gt;", line 1, in ?
ImportError: libfoo.so: cannot open shared object file: No such file or directory ImportError: libfoo.so: cannot open shared object file: No such file or directory
&gt;&gt;&gt; &gt;&gt;&gt;
</pre> </pre>
</div> </div>
@ -642,7 +646,7 @@ $ gcc -shared example.o example_wrap.o -L/home/beazley/projects/lib -lfoo \
<p> <p>
Alternatively, you can set the <tt>LD_LIBRARY_PATH</tt> environment variable to Alternatively, you can set the <tt>LD_LIBRARY_PATH</tt> environment variable to
include the directory with your shared libraries. include the directory with your shared libraries.
If setting <tt>LD_LIBRARY_PATH</tt>, be aware that setting this variable can introduce If setting <tt>LD_LIBRARY_PATH</tt>, be aware that setting this variable can introduce
a noticeable performance impact on all other applications that you run. a noticeable performance impact on all other applications that you run.
To set it only for Python, you might want to do this instead: To set it only for Python, you might want to do this instead:
@ -707,7 +711,7 @@ $ CC -G example.o example_wrap.o -L/opt/SUNWspro/lib -o _example.so -lCrun
</pre></div> </pre></div>
<p> <p>
Of course, the extra libraries to use are completely non-portable---you will Of course, the extra libraries to use are completely non-portable---you will
probably need to do some experimentation. probably need to do some experimentation.
</p> </p>
@ -715,8 +719,8 @@ probably need to do some experimentation.
Sometimes people have suggested that it is necessary to relink the Sometimes people have suggested that it is necessary to relink the
Python interpreter using the C++ compiler to make C++ extension modules work. Python interpreter using the C++ compiler to make C++ extension modules work.
In the experience of this author, this has never actually appeared to be In the experience of this author, this has never actually appeared to be
necessary. Relinking the interpreter with C++ really only includes the necessary. Relinking the interpreter with C++ really only includes the
special run-time libraries described above---as long as you link your extension special run-time libraries described above---as long as you link your extension
modules with these libraries, it should not be necessary to rebuild Python. modules with these libraries, it should not be necessary to rebuild Python.
</p> </p>
@ -760,7 +764,7 @@ might want to investigate using a more formal standard such as COM.
On platforms that support 64-bit applications (Solaris, Irix, etc.), On platforms that support 64-bit applications (Solaris, Irix, etc.),
special care is required when building extension modules. On these special care is required when building extension modules. On these
machines, 64-bit applications are compiled and linked using a different machines, 64-bit applications are compiled and linked using a different
set of compiler/linker options. In addition, it is not generally possible to mix set of compiler/linker options. In addition, it is not generally possible to mix
32-bit and 64-bit code together in the same application. 32-bit and 64-bit code together in the same application.
</p> </p>
@ -814,10 +818,10 @@ If you need to build it on your own, the following notes are provided:
</p> </p>
<p> <p>
You will need to create a DLL that can be loaded into the interpreter. You will need to create a DLL that can be loaded into the interpreter.
This section briefly describes the use of SWIG with Microsoft Visual This section briefly describes the use of SWIG with Microsoft Visual
C++. As a starting point, many of SWIG's examples include project C++. As a starting point, many of SWIG's examples include project
files (.dsp files) for Visual C++ 6. These can be opened by more files (.dsp files) for Visual C++ 6. These can be opened by more
recent versions of Visual Studio. recent versions of Visual Studio.
You might want to take a quick look at these examples in addition to You might want to take a quick look at these examples in addition to
reading this section. reading this section.
@ -852,7 +856,7 @@ settings, select the "Custom Build" option.
"C++:Preprocessor". Add the include directories for your Python "C++:Preprocessor". Add the include directories for your Python
installation under "Additional include directories". installation under "Additional include directories".
<li>Define the symbol __WIN32__ under preprocessor options. <li>Define the symbol __WIN32__ under preprocessor options.
<li>Finally, select the settings for the entire project and go to <li>Finally, select the settings for the entire project and go to
"Link Options". Add the Python library file to your link libraries. "Link Options". Add the Python library file to your link libraries.
@ -866,7 +870,7 @@ match the name of your Python module, ie. _example.pyd - Note that _example.dll
If all went well, SWIG will be automatically invoked whenever If all went well, SWIG will be automatically invoked whenever
you build your project. Any changes made to the interface file will you build your project. Any changes made to the interface file will
result in SWIG being automatically executed to produce a new version of result in SWIG being automatically executed to produce a new version of
the wrapper file. the wrapper file.
</p> </p>
<p> <p>
@ -885,9 +889,9 @@ $ python
<p> <p>
If you get an <tt>ImportError</tt> exception when importing the module, you may If you get an <tt>ImportError</tt> exception when importing the module, you may
have forgotten to include additional library files when you built your module. have forgotten to include additional library files when you built your module.
If you get an access violation or some kind of general protection fault If you get an access violation or some kind of general protection fault
immediately upon import, you have a more serious problem. This immediately upon import, you have a more serious problem. This
is often caused by linking your extension module against the wrong is often caused by linking your extension module against the wrong
set of Win32 debug or thread libraries. You will have to fiddle around with set of Win32 debug or thread libraries. You will have to fiddle around with
the build options of project to try and track this down. the build options of project to try and track this down.
</p> </p>
@ -938,7 +942,7 @@ wrapped into a Python '<tt>example</tt>' module. Underneath the covers,
this module consists of a Python source file <tt>example.py</tt> and a low-level this module consists of a Python source file <tt>example.py</tt> and a low-level
extension module <tt>_example.so</tt>. When choosing a extension module <tt>_example.so</tt>. When choosing a
module name, make sure you don't use the same name as a built-in module name, make sure you don't use the same name as a built-in
Python command or standard module name. Python command or standard module name.
</p> </p>
<H3><a name="Python_nn15">36.3.2 Functions</a></H3> <H3><a name="Python_nn15">36.3.2 Functions</a></H3>
@ -991,8 +995,8 @@ then "a" and "b" are both names for the object containing the value
3.4. Thus, there is only one object containing 3.4 and "a" 3.4. Thus, there is only one object containing 3.4 and "a"
and "b" are both names that refer to it. This is quite and "b" are both names that refer to it. This is quite
different than C where a variable name refers to a memory location in which different than C where a variable name refers to a memory location in which
a value is stored (and assignment copies data into that location). a value is stored (and assignment copies data into that location).
Because of this, there is no direct way to map variable Because of this, there is no direct way to map variable
assignment in C to variable assignment in Python. assignment in C to variable assignment in Python.
</p> </p>
@ -1038,7 +1042,7 @@ error message. For example:
Traceback (most recent call last): Traceback (most recent call last):
File "&lt;stdin&gt;", line 1, in ? File "&lt;stdin&gt;", line 1, in ?
TypeError: C variable 'density (double )' TypeError: C variable 'density (double )'
&gt;&gt;&gt; &gt;&gt;&gt;
</pre></div> </pre></div>
<p> <p>
@ -1188,7 +1192,7 @@ simply represented as opaque values using an especial python container object:
<p> <p>
This pointer value can be freely passed around to different C functions that This pointer value can be freely passed around to different C functions that
expect to receive an object of type <tt>FILE *</tt>. The only thing you can't do is expect to receive an object of type <tt>FILE *</tt>. The only thing you can't do is
dereference the pointer from Python. Of course, that isn't much of a concern in this example. dereference the pointer from Python. Of course, that isn't much of a concern in this example.
</p> </p>
@ -1309,7 +1313,7 @@ is used as follows:
&gt;&gt;&gt; v.y = 7.2 &gt;&gt;&gt; v.y = 7.2
&gt;&gt;&gt; print v.x, v.y, v.z &gt;&gt;&gt; print v.x, v.y, v.z
7.8 -4.5 0.0 7.8 -4.5 0.0
&gt;&gt;&gt; &gt;&gt;&gt;
</pre></div> </pre></div>
<p> <p>
@ -1368,7 +1372,7 @@ struct Foo {
<p> <p>
When <tt>char *</tt> members of a structure are wrapped, the contents are assumed to be When <tt>char *</tt> members of a structure are wrapped, the contents are assumed to be
dynamically allocated using <tt>malloc</tt> or <tt>new</tt> (depending on whether or not dynamically allocated using <tt>malloc</tt> or <tt>new</tt> (depending on whether or not
SWIG is run with the -c++ option). When the structure member is set, the old contents will be SWIG is run with the -c++ option). When the structure member is set, the old contents will be
released and a new value created. If this is not the behavior you want, you will have to use released and a new value created. If this is not the behavior you want, you will have to use
a typemap (described later). a typemap (described later).
</p> </p>
@ -1395,7 +1399,7 @@ If accessed in Python, you will see behavior like this:
&gt;&gt;&gt; b = example.Bar() &gt;&gt;&gt; b = example.Bar()
&gt;&gt;&gt; print b.x &gt;&gt;&gt; print b.x
_801861a4_p_int _801861a4_p_int
&gt;&gt;&gt; &gt;&gt;&gt;
</pre> </pre>
</div> </div>
@ -1460,7 +1464,7 @@ Foo *x = &amp;b-&gt;f; /* Points inside b */
</div> </div>
<p> <p>
Because the pointer points inside the structure, you can modify the contents and Because the pointer points inside the structure, you can modify the contents and
everything works just like you would expect. For example: everything works just like you would expect. For example:
</p> </p>
@ -1468,7 +1472,7 @@ everything works just like you would expect. For example:
<pre> <pre>
&gt;&gt;&gt; b = Bar() &gt;&gt;&gt; b = Bar()
&gt;&gt;&gt; b.f.a = 3 # Modify attribute of structure member &gt;&gt;&gt; b.f.a = 3 # Modify attribute of structure member
&gt;&gt;&gt; x = b.f &gt;&gt;&gt; x = b.f
&gt;&gt;&gt; x.a = 3 # Modifies the same structure &gt;&gt;&gt; x.a = 3 # Modifies the same structure
</pre> </pre>
</div> </div>
@ -1510,13 +1514,13 @@ you can use it in Python like this:
</pre></div> </pre></div>
<p> <p>
Class data members are accessed in the same manner as C structures. Class data members are accessed in the same manner as C structures.
</p> </p>
<p> <p>
Static class members present a special problem for Python. Prior to Python-2.2, Static class members present a special problem for Python. Prior to Python-2.2,
Python classes had no support for static methods and no version of Python Python classes had no support for static methods and no version of Python
supports static member variables in a manner that SWIG can utilize. Therefore, supports static member variables in a manner that SWIG can utilize. Therefore,
SWIG generates wrappers that try to work around some of these issues. To illustrate, SWIG generates wrappers that try to work around some of these issues. To illustrate,
suppose you have a class like this: suppose you have a class like this:
</p> </p>
@ -1669,10 +1673,10 @@ const Foo &amp;spam9();
<p> <p>
then all three functions will return a pointer to some <tt>Foo</tt> object. then all three functions will return a pointer to some <tt>Foo</tt> object.
Since the third function (spam8) returns a value, newly allocated memory is used Since the third function (spam8) returns a value, newly allocated memory is used
to hold the result and a pointer is returned (Python will release this memory to hold the result and a pointer is returned (Python will release this memory
when the return value is garbage collected). The fourth case (spam9) when the return value is garbage collected). The fourth case (spam9)
which returns a const reference, in most of the cases will be which returns a const reference, in most of the cases will be
treated as a returning value, and it will follow the same treated as a returning value, and it will follow the same
allocation/deallocation process. allocation/deallocation process.
</p> </p>
@ -1771,7 +1775,7 @@ To fix this, you either need to ignore or rename one of the methods. For exampl
<pre> <pre>
%rename(spam_short) spam(short); %rename(spam_short) spam(short);
... ...
void spam(int); void spam(int);
void spam(short); // Accessed as spam_short void spam(short); // Accessed as spam_short
</pre> </pre>
</div> </div>
@ -1784,7 +1788,7 @@ or
<pre> <pre>
%ignore spam(short); %ignore spam(short);
... ...
void spam(int); void spam(int);
void spam(short); // Ignored void spam(short); // Ignored
</pre> </pre>
</div> </div>
@ -1797,7 +1801,7 @@ first declaration takes precedence.
</p> </p>
<p> <p>
Please refer to the "SWIG and C++" chapter for more information about overloading. Please refer to the "SWIG and C++" chapter for more information about overloading.
</p> </p>
<H3><a name="Python_nn24">36.3.11 C++ operators</a></H3> <H3><a name="Python_nn24">36.3.11 C++ operators</a></H3>
@ -1823,7 +1827,7 @@ public:
Complex operator-(const Complex &amp;c) const; Complex operator-(const Complex &amp;c) const;
Complex operator*(const Complex &amp;c) const; Complex operator*(const Complex &amp;c) const;
Complex operator-() const; Complex operator-() const;
double re() const { return rpart; } double re() const { return rpart; }
double im() const { return ipart; } double im() const { return ipart; }
}; };
@ -2005,7 +2009,7 @@ In Python:
<p> <p>
Obviously, there is more to template wrapping than shown in this example. Obviously, there is more to template wrapping than shown in this example.
More details can be found in the <a href="SWIGPlus.html#SWIGPlus">SWIG and C++</a> chapter. More details can be found in the <a href="SWIGPlus.html#SWIGPlus">SWIG and C++</a> chapter.
Some more complicated Some more complicated
examples will appear later. examples will appear later.
</p> </p>
@ -2188,7 +2192,7 @@ These wrappers can be found in the low-level extension module (e.g., <tt>_exampl
</p> </p>
<p> <p>
Using these wrappers, SWIG generates a high-level Python proxy class (also known as a shadow class) like this (shown Using these wrappers, SWIG generates a high-level Python proxy class (also known as a shadow class) like this (shown
for Python 2.2): for Python 2.2):
</p> </p>
@ -2210,7 +2214,7 @@ class Foo(object):
</div> </div>
<p> <p>
This class merely holds a pointer to the underlying C++ object (<tt>.this</tt>) and dispatches methods and This class merely holds a pointer to the underlying C++ object (<tt>.this</tt>) and dispatches methods and
member variable access to that object using the low-level accessor functions. From a user's point of member variable access to that object using the low-level accessor functions. From a user's point of
view, it makes the class work normally: view, it makes the class work normally:
</p> </p>
@ -2254,7 +2258,7 @@ class Foo(object):
</div> </div>
<p>When a <tt>Foo</tt> instance is created, the call to <tt>_example.new_Foo()</tt> <p>When a <tt>Foo</tt> instance is created, the call to <tt>_example.new_Foo()</tt>
creates a new C++ <tt>Foo</tt> instance; wraps that C++ instance inside an instance of creates a new C++ <tt>Foo</tt> instance; wraps that C++ instance inside an instance of
a python built-in type called <tt>SwigPyObject</tt>; and stores the <tt>SwigPyObject</tt> a python built-in type called <tt>SwigPyObject</tt>; and stores the <tt>SwigPyObject</tt>
instance in the 'this' field of the python Foo object. Did you get all that? So, the instance in the 'this' field of the python Foo object. Did you get all that? So, the
python <tt>Foo</tt> object is composed of three parts:</p> python <tt>Foo</tt> object is composed of three parts:</p>
@ -2545,7 +2549,7 @@ public:
</div> </div>
<p> <p>
If you examine the generated code, the supplied hash function will now be If you examine the generated code, the supplied hash function will now be
the function callback in the tp_hash slot for the builtin type for <tt>MyClass</tt>: the function callback in the tp_hash slot for the builtin type for <tt>MyClass</tt>:
</p> </p>
@ -2609,7 +2613,7 @@ when the <tt>-builtin</tt> option is used.</p>
<p> <p>
Associated with proxy object, is an ownership flag <tt>.thisown</tt> The value of this Associated with proxy object, is an ownership flag <tt>.thisown</tt> The value of this
flag determines who is responsible for deleting the underlying C++ object. If set to 1, flag determines who is responsible for deleting the underlying C++ object. If set to 1,
the Python interpreter will destroy the C++ object when the proxy class is the Python interpreter will destroy the C++ object when the proxy class is
garbage collected. If set to 0 (or if the attribute is missing), then the destruction garbage collected. If set to 0 (or if the attribute is missing), then the destruction
of the proxy class has no effect on the C++ object. of the proxy class has no effect on the C++ object.
</p> </p>
@ -2712,7 +2716,7 @@ is assigned to a global variable. For example:
&gt;&gt;&gt; f = example.Foo() &gt;&gt;&gt; f = example.Foo()
&gt;&gt;&gt; f.thisown &gt;&gt;&gt; f.thisown
1 1
&gt;&gt;&gt; example.cvar.head = f &gt;&gt;&gt; example.cvar.head = f
&gt;&gt;&gt; f.thisown &gt;&gt;&gt; f.thisown
0 0
&gt;&gt;&gt; &gt;&gt;&gt;
@ -2813,7 +2817,7 @@ To address differences between Python versions, SWIG currently emits
dual-mode proxy class wrappers. In Python-2.2 and newer releases, dual-mode proxy class wrappers. In Python-2.2 and newer releases,
these wrappers encapsulate C++ objects in new-style classes that take these wrappers encapsulate C++ objects in new-style classes that take
advantage of new features (static methods and properties). However, advantage of new features (static methods and properties). However,
if these very same wrappers are imported into an older version of Python, if these very same wrappers are imported into an older version of Python,
old-style classes are used instead. old-style classes are used instead.
</p> </p>
@ -2883,18 +2887,18 @@ option to the %module directive, like this:
<p> <p>
Without this option no director code will be generated. Second, you Without this option no director code will be generated. Second, you
must use the %feature("director") directive to tell SWIG which classes must use the %feature("director") directive to tell SWIG which classes
and methods should get directors. The %feature directive can be applied and methods should get directors. The %feature directive can be applied
globally, to specific classes, and to specific methods, like this: globally, to specific classes, and to specific methods, like this:
</p> </p>
<div class="code"> <div class="code">
<pre> <pre>
// generate directors for all classes that have virtual methods // generate directors for all classes that have virtual methods
%feature("director"); %feature("director");
// generate directors for all virtual methods in class Foo // generate directors for all virtual methods in class Foo
%feature("director") Foo; %feature("director") Foo;
</pre> </pre>
</div> </div>
@ -2912,11 +2916,11 @@ directors for specific classes or methods. So for example,
<p> <p>
will generate directors for all virtual methods of class Foo except will generate directors for all virtual methods of class Foo except
bar(). bar().
</p> </p>
<p> <p>
Directors can also be generated implicitly through inheritance. Directors can also be generated implicitly through inheritance.
In the following, class Bar will get a director class that handles In the following, class Bar will get a director class that handles
the methods one() and two() (but not three()): the methods one() and two() (but not three()):
</p> </p>
@ -2961,7 +2965,7 @@ class MyFoo(mymodule.Foo):
<H3><a name="Python_nn34">36.5.2 Director classes</a></H3> <H3><a name="Python_nn34">36.5.2 Director classes</a></H3>
<p> <p>
@ -3224,7 +3228,7 @@ be able to use std::vector, std::string, etc., as you would any other type.
<p> <p>
<b>Note:</b> The director typemaps for return types based in const <b>Note:</b> The director typemaps for return types based in const
references, such as references, such as
<div class="code"> <div class="code">
<pre> <pre>
@ -3498,7 +3502,7 @@ def bar(*args):
$action $action
#do something after #do something after
%} %}
class Foo { class Foo {
public: public:
int bar(int x); int bar(int x);
@ -3507,7 +3511,7 @@ public:
</div> </div>
<p> where <tt>$action</tt> will be replaced by the call to <p> where <tt>$action</tt> will be replaced by the call to
the C/C++ proper method. the C/C++ proper method.
</p> </p>
<p> <p>
@ -3525,7 +3529,7 @@ proxy, just before the return statement.
<pre> <pre>
%module example %module example
// Add python code to bar() // Add python code to bar()
%feature("pythonprepend") Foo::bar(int) %{ %feature("pythonprepend") Foo::bar(int) %{
#do something before C++ call #do something before C++ call
@ -3535,7 +3539,7 @@ proxy, just before the return statement.
#do something after C++ call #do something after C++ call
%} %}
class Foo { class Foo {
public: public:
int bar(int x); int bar(int x);
@ -3554,7 +3558,7 @@ SWIG version 1.3.28 you can use the directive forms
<pre> <pre>
%module example %module example
// Add python code to bar() // Add python code to bar()
%pythonprepend Foo::bar(int) %{ %pythonprepend Foo::bar(int) %{
#do something before C++ call #do something before C++ call
@ -3564,7 +3568,7 @@ SWIG version 1.3.28 you can use the directive forms
#do something after C++ call #do something after C++ call
%} %}
class Foo { class Foo {
public: public:
int bar(int x); int bar(int x);
@ -3658,7 +3662,7 @@ Vector(2, 3, 4)
</div> </div>
<p> <p>
<tt>%extend</tt> can be used for many more tasks than this. <tt>%extend</tt> can be used for many more tasks than this.
For example, if you wanted to overload a Python operator, you might do this: For example, if you wanted to overload a Python operator, you might do this:
</p> </p>
@ -3687,7 +3691,7 @@ Use it like this:
&gt;&gt;&gt; w = example.Vector(10, 11, 12) &gt;&gt;&gt; w = example.Vector(10, 11, 12)
&gt;&gt;&gt; print v+w &gt;&gt;&gt; print v+w
Vector(12, 14, 16) Vector(12, 14, 16)
&gt;&gt;&gt; &gt;&gt;&gt;
</pre> </pre>
</div> </div>
@ -3991,7 +3995,7 @@ int send_message(char *text, int *success);
</div> </div>
<p> <p>
When used in Python, the function will return multiple values. When used in Python, the function will return multiple values.
</p> </p>
<div class="targetlang"> <div class="targetlang">
@ -4142,7 +4146,7 @@ int sumitems(int *first, int nitems) {
</div> </div>
<p> <p>
To wrap this into Python, you need to pass an array pointer as the first argument. To wrap this into Python, you need to pass an array pointer as the first argument.
A simple way to do this is to use the <tt>carrays.i</tt> library file. For example: A simple way to do this is to use the <tt>carrays.i</tt> library file. For example:
</p> </p>
@ -4219,13 +4223,13 @@ using the <tt>cstring.i</tt> library file described in the <a href="Library.html
</p> </p>
<p> <p>
When functions return a <tt>char *</tt>, it is assumed to be a NULL-terminated string. When functions return a <tt>char *</tt>, it is assumed to be a NULL-terminated string.
Data is copied into a new Python string and returned. Data is copied into a new Python string and returned.
</p> </p>
<p> <p>
If your program needs to work with binary data, you can use a typemap If your program needs to work with binary data, you can use a typemap
to expand a Python string into a pointer/length argument pair. As luck would have it, to expand a Python string into a pointer/length argument pair. As luck would have it,
just such a typemap is already defined. Just do this: just such a typemap is already defined. Just do this:
</p> </p>
@ -4260,7 +4264,7 @@ also be used to extra binary data from arbitrary pointers.
<p> <p>
C++ default argument code generation is documented in the main C++ default argument code generation is documented in the main
<a href="SWIGPlus.html#SWIGPlus_default_args">Default arguments</a> section. <a href="SWIGPlus.html#SWIGPlus_default_args">Default arguments</a> section.
There is also an optional Python specific feature that can be used called the <tt>python:cdefaultargs</tt> There is also an optional Python specific feature that can be used called the <tt>python:cdefaultargs</tt>
<a href="Customization.html#Customization_feature_flags">feature flag</a>. <a href="Customization.html#Customization_feature_flags">feature flag</a>.
By default, SWIG attempts to convert C++ default argument values By default, SWIG attempts to convert C++ default argument values
into Python values and generates code into the Python layer containing these values. into Python values and generates code into the Python layer containing these values.
@ -4303,7 +4307,7 @@ class CDA(object):
<p> <p>
Adding the feature: Adding the feature:
</p> </p>
<div class="code"> <div class="code">
<pre> <pre>
%feature("python:cdefaultargs") CDA::fff; %feature("python:cdefaultargs") CDA::fff;
@ -4364,7 +4368,7 @@ as the material in the "<a href="Typemaps.html#Typemaps">Typemaps</a>" chapter.
</p> </p>
<p> <p>
Before proceeding, it should be stressed that typemaps are not a required Before proceeding, it should be stressed that typemaps are not a required
part of using SWIG---the default wrapping behavior is enough in most cases. part of using SWIG---the default wrapping behavior is enough in most cases.
Typemaps are only used if you want to change some aspect of the primitive Typemaps are only used if you want to change some aspect of the primitive
C-Python interface or if you want to elevate your guru status. C-Python interface or if you want to elevate your guru status.
@ -4374,7 +4378,7 @@ C-Python interface or if you want to elevate your guru status.
<p> <p>
A typemap is nothing more than a code generation rule that is attached to A typemap is nothing more than a code generation rule that is attached to
a specific C datatype. For example, to convert integers from Python to C, a specific C datatype. For example, to convert integers from Python to C,
you might define a typemap like this: you might define a typemap like this:
</p> </p>
@ -4506,7 +4510,7 @@ like this:
<p> <p>
A detailed list of available methods can be found in the "<a A detailed list of available methods can be found in the "<a
href="Typemaps.html#Typemaps">Typemaps</a>" chapter. href="Typemaps.html#Typemaps">Typemaps</a>" chapter.
</p> </p>
<p> <p>
@ -4568,7 +4572,7 @@ A <tt>PyObject *</tt> that holds the result to be returned to Python.
</p> </p>
<div class="indent"> <div class="indent">
The parameter name that was matched. The parameter name that was matched.
</div> </div>
<p> <p>
@ -4812,7 +4816,7 @@ In the example, two different typemaps are used. The "in" typemap is
used to receive an input argument and convert it to a C array. Since dynamic used to receive an input argument and convert it to a C array. Since dynamic
memory allocation is used to allocate memory for the array, the memory allocation is used to allocate memory for the array, the
"freearg" typemap is used to later release this memory after the execution of "freearg" typemap is used to later release this memory after the execution of
the C function. the C function.
</p> </p>
<H3><a name="Python_nn60">36.9.2 Expanding a Python object into multiple arguments</a></H3> <H3><a name="Python_nn60">36.9.2 Expanding a Python object into multiple arguments</a></H3>
@ -4878,7 +4882,7 @@ previous example:
</div> </div>
<p> <p>
When writing a multiple-argument typemap, each of the types is referenced by a variable such When writing a multiple-argument typemap, each of the types is referenced by a variable such
as <tt>$1</tt> or <tt>$2</tt>. The typemap code simply fills in the appropriate values from as <tt>$1</tt> or <tt>$2</tt>. The typemap code simply fills in the appropriate values from
the supplied Python object. the supplied Python object.
</p> </p>
@ -4960,7 +4964,7 @@ A typemap can be used to handle this case as follows :
%module outarg %module outarg
// This tells SWIG to treat an double * argument with name 'OutValue' as // This tells SWIG to treat an double * argument with name 'OutValue' as
// an output value. We'll append the value to the current result which // an output value. We'll append the value to the current result which
// is guaranteed to be a List object by SWIG. // is guaranteed to be a List object by SWIG.
%typemap(argout) double *OutValue { %typemap(argout) double *OutValue {
@ -5312,7 +5316,7 @@ example:
<div class="code"> <div class="code">
<pre> <pre>
%define DOCSTRING %define DOCSTRING
"The `XmlResource` class allows program resources defining menus, "The `XmlResource` class allows program resources defining menus,
layout of controls on a panel, etc. to be loaded from an XML file." layout of controls on a panel, etc. to be loaded from an XML file."
%enddef %enddef
@ -5607,7 +5611,7 @@ Packages</a> for more information.
<p> <p>
If you place a SWIG generated module into a Python package then there If you place a SWIG generated module into a Python package then there
are details concerning the way SWIG are details concerning the way SWIG
<a href="#Python_package_search">searches for the wrapper module</a> <a href="#Python_package_search">searches for the wrapper module</a>
that you may want to familiarize yourself with. that you may want to familiarize yourself with.
</p> </p>
@ -6378,7 +6382,7 @@ In Python:
&gt;&gt;&gt; snprintf(buf, "Hello world!") &gt;&gt;&gt; snprintf(buf, "Hello world!")
&gt;&gt;&gt; print(buf) &gt;&gt;&gt; print(buf)
bytearray(b'Hello\x00') bytearray(b'Hello\x00')
&gt;&gt;&gt; &gt;&gt;&gt;
</pre></div> </pre></div>
</div> </div>
@ -6414,7 +6418,7 @@ bytearray(b'FOO\x00')
<p> <p>
Both <tt>%pybuffer_mutable_binary</tt> and <tt>%pybuffer_mutable_string</tt> Both <tt>%pybuffer_mutable_binary</tt> and <tt>%pybuffer_mutable_string</tt>
require the provided buffer to be mutable, eg. they can accept a require the provided buffer to be mutable, eg. they can accept a
<tt>bytearray</tt> type but can't accept an immutable <tt>byte</tt> <tt>bytearray</tt> type but can't accept an immutable <tt>byte</tt>
type. type.
</p> </p>
@ -6730,6 +6734,38 @@ the first is allowing unicode conversion and the second is explicitly
prohibiting it. prohibiting it.
</p> </p>
<H2><a name="Python_multithreaded">36.13 Support for Multithreaded Applications</a></H2>
<p>By default, SWIG does not enable support for multithreaded Python applications. More
specifically, the Python wrappers generated by SWIG will not release the
Python's interpreter's Global Interpreter Lock (GIL) when wrapped C/C++ code is
entered. Hence, while any of the wrapped C/C++ code is executing, the Python interpreter
will not be able to run any other threads, even if the wrapped C/C++ code is waiting
in a blocking call for something like network or disk IO.
Fortunately, SWIG does have the ability to enable multithreaded support and automatic
release of the GIL either for all wrapped code in a module or on a more selective basis. The user
interface for this is described in the next section.
</p>
<H3><a name="Python_thread_UI">36.13.1 UI for Enabling Multithreading Support</a></H3>
<p>The user interface is as follows:</p>
<ol>
<li>Module thread support can be enabled in two ways:
<ul>
<li>
The <b>-threads</b> swig python option at the command line (or in <tt>setup.py</tt>):
<div class="shell">$ swig -python -threads example.i</div>
</li>
<li>
The <b>threads</b> module option in the *.i template file:
<div class="code">%module("threads"=1)</div>
</li>
</ul>
</li>
</ol>
</body> </body>
</html> </html>