mirror of https://github.com/swig/swig
553 lines
15 KiB
HTML
553 lines
15 KiB
HTML
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
|
|
<html>
|
|
<head>
|
|
<title>SWIG Preprocessor</title>
|
|
<link rel="stylesheet" type="text/css" href="style.css">
|
|
<meta http-equiv="content-type" content="text/html; charset=UTF-8">
|
|
</head>
|
|
|
|
<body bgcolor="#ffffff">
|
|
<H1><a name="Preprocessor">11 Preprocessing</a></H1>
|
|
<!-- INDEX -->
|
|
<div class="sectiontoc">
|
|
<ul>
|
|
<li><a href="#Preprocessor_nn2">File inclusion</a>
|
|
<li><a href="#Preprocessor_nn3">File imports</a>
|
|
<li><a href="#Preprocessor_condition_compilation">Conditional Compilation</a>
|
|
<li><a href="#Preprocessor_nn5">Macro Expansion</a>
|
|
<li><a href="#Preprocessor_nn6">SWIG Macros</a>
|
|
<li><a href="#Preprocessor_nn7">C99 and GNU Extensions</a>
|
|
<li><a href="#Preprocessor_delimiters">Preprocessing and delimiters</a>
|
|
<ul>
|
|
<li><a href="#Preprocessor_nn8">Preprocessing and %{ ... %} & " ... " delimiters</a>
|
|
<li><a href="#Preprocessor_nn9">Preprocessing and { ... } delimiters</a>
|
|
</ul>
|
|
<li><a href="#Preprocessor_typemap_delimiters">Preprocessor and Typemaps</a>
|
|
<li><a href="#Preprocessor_nn10">Viewing preprocessor output</a>
|
|
<li><a href="#Preprocessor_warning_error">The #error and #warning directives</a>
|
|
</ul>
|
|
</div>
|
|
<!-- INDEX -->
|
|
|
|
|
|
|
|
<p>
|
|
SWIG includes its own enhanced version of the C preprocessor. The preprocessor
|
|
supports the standard preprocessor directives and macro expansion rules.
|
|
However, a number of modifications and enhancements have been made. This
|
|
chapter describes some of these modifications.
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_nn2">11.1 File inclusion</a></H2>
|
|
|
|
|
|
<p>
|
|
To include another file into a SWIG interface, use the <tt>%include</tt> directive
|
|
like this:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%include "cpointer.i"
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
Unlike, <tt>#include</tt>, <tt>%include</tt> includes each file once (and will not
|
|
reload the file on subsequent <tt>%include</tt> declarations). Therefore, it
|
|
is not necessary to use include-guards in SWIG interfaces.
|
|
</p>
|
|
|
|
<p>
|
|
By default, the <tt>#include</tt> is ignored unless you run SWIG with the
|
|
<tt>-includeall</tt> option. The reason for ignoring traditional includes
|
|
is that you often don't want SWIG to try and wrap everything included
|
|
in standard header system headers and auxiliary files.
|
|
|
|
<H2><a name="Preprocessor_nn3">11.2 File imports</a></H2>
|
|
|
|
|
|
<p>
|
|
SWIG provides another file inclusion directive with the <tt>%import</tt> directive.
|
|
For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%import "foo.i"
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
The purpose of <tt>%import</tt> is to collect certain information from another
|
|
SWIG interface file or a header file without actually generating any wrapper code.
|
|
Such information generally includes type declarations (e.g., <tt>typedef</tt>) as well as
|
|
C++ classes that might be used as base-classes for class declarations in the interface.
|
|
The use of <tt>%import</tt> is also important when SWIG is used to generate
|
|
extensions as a collection of related modules. This is an advanced topic and is described
|
|
in later in the <a href="Modules.html#Modules">Working with Modules</a> chapter.
|
|
</p>
|
|
|
|
<P>
|
|
The <tt>-importall</tt> directive tells SWIG to follow all <tt>#include</tt> statements
|
|
as imports. This might be useful if you want to extract type definitions from system
|
|
header files without generating any wrappers.
|
|
|
|
<H2><a name="Preprocessor_condition_compilation">11.3 Conditional Compilation</a></H2>
|
|
|
|
|
|
<p>
|
|
SWIG fully supports the use of <tt>#if</tt>, <tt>#ifdef</tt>,
|
|
<tt>#ifndef</tt>, <tt>#else</tt>, <tt>#endif</tt> to conditionally
|
|
include parts of an interface.
|
|
</p>
|
|
|
|
<p>
|
|
SWIG's preprocessor conditionals support the standard C/C++ preprocessor
|
|
integer expressions. As a SWIG-specific extension, string equality and
|
|
inequality tests are also supported, for example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#if defined __cplusplus && (#__VA_ARGS__ != "" || #TYPE == "void")
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
The following symbols are predefined by SWIG when it is parsing the interface:
|
|
</p>
|
|
|
|
<div class="code"><pre>
|
|
SWIG Always defined when SWIG is processing a file
|
|
SWIGIMPORTED Defined when SWIG is importing a file with <tt>%import</tt>
|
|
SWIG_VERSION Hexadecimal (binary-coded decimal) number containing SWIG version,
|
|
such as 0x010311 (corresponding to SWIG-1.3.11).
|
|
|
|
SWIGCSHARP Defined when using C#
|
|
SWIGD Defined when using D
|
|
SWIGGO Defined when using Go
|
|
SWIGGUILE Defined when using Guile
|
|
SWIGJAVA Defined when using Java
|
|
SWIGJAVASCRIPT Defined when using Javascript
|
|
SWIG_JAVASCRIPT_JSC Defined when using Javascript with -jsc
|
|
SWIG_JAVASCRIPT_V8 Defined when using Javascript with -v8 or -node
|
|
SWIG_JAVASCRIPT_NAPI Defined when using Javascript with -napi
|
|
SWIGLUA Defined when using Lua
|
|
SWIGMZSCHEME Defined when using Mzscheme
|
|
SWIGOCAML Defined when using OCaml
|
|
SWIGOCTAVE Defined when using Octave
|
|
SWIGPERL Defined when using Perl
|
|
SWIGPHP Defined when using PHP (any version)
|
|
SWIGPHP7 Defined when using PHP 7 or later (with a compatible C API)
|
|
SWIGPYTHON Defined when using Python
|
|
SWIGR Defined when using R
|
|
SWIGRUBY Defined when using Ruby
|
|
SWIGSCILAB Defined when using Scilab
|
|
SWIGTCL Defined when using Tcl
|
|
SWIGXML Defined when using XML
|
|
</pre></div>
|
|
|
|
<p>
|
|
SWIG also defines <tt>SWIG_VERSION</tt> and a target language macro in
|
|
the generated wrapper file (since SWIG 4.1.0 - in older versions these
|
|
were defined for some target languages but this wasn't consistent). Best
|
|
practice is to use SWIG-time conditional checks because that results in smaller
|
|
generated wrapper sources.
|
|
</p>
|
|
|
|
<p>
|
|
In addition, SWIG defines the following set of standard C/C++ macros:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
__LINE__ Current line number
|
|
__FILE__ Current file name
|
|
__STDC__ Defined to indicate ISO C
|
|
__cplusplus Defined when -c++ option used
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
Since SWIG 4.2.0, <tt>__STDC__</tt> is defined to <tt>1</tt> to match
|
|
the behaviour of ISO C/C++ compilers. Before this SWIG defined it to
|
|
have an empty value.
|
|
</p>
|
|
|
|
<p>
|
|
Since SWIG 4.2.0, <tt>__cplusplus</tt> is defined to <tt>199711L</tt>
|
|
(the value for C++98) but you can override this by defining it
|
|
explicitly on the SWIG command line if you are wrapping headers
|
|
which have preprocessor checks based on its value (e.g. use
|
|
<tt>-D__cplusplus=201103L</tt> to set it to the value for C++11).
|
|
Before this SWIG always defined it to have the <b>value</b>
|
|
<tt>__cplusplus</tt> and attempting to use <tt>-D__cplusplus</tt>
|
|
to change this gave an error.
|
|
</p>
|
|
|
|
<p>
|
|
The following are language specific symbols that might be defined:
|
|
</p>
|
|
|
|
<div class="code"><pre>
|
|
SWIG_D_VERSION Unsigned integer target version when using D
|
|
SWIGGO_CGO Defined when using Go for cgo
|
|
SWIGGO_GCCGO Defined when using Go for gccgo
|
|
SWIGGO_INTGO_SIZE Size of the Go type int when using Go (32 or 64)
|
|
SWIGPYTHON_BUILTIN Defined when using Python with -builtin
|
|
SWIG_RUBY_AUTORENAME Defined when using Ruby with -autorename
|
|
</pre></div>
|
|
|
|
<p>
|
|
Interface files can look at these symbols as necessary to change the
|
|
way in which an interface is generated or to mix SWIG directives with
|
|
C code.
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_nn5">11.4 Macro Expansion</a></H2>
|
|
|
|
|
|
<p>
|
|
Traditional preprocessor macros can be used in SWIG interfaces. Be aware that the <tt>#define</tt> statement
|
|
is also used to try and detect constants. Therefore, if you have something like this in your file,
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#ifndef FOO_H 1
|
|
#define FOO_H 1
|
|
...
|
|
#endif
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
you may get some extra constants such as <tt>FOO_H</tt> showing up in the scripting interface.
|
|
</p>
|
|
|
|
<p>
|
|
More complex macros can be defined in the standard way. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define EXTERN extern
|
|
#ifdef __STDC__
|
|
#define ISOC_(args) (args)
|
|
#else
|
|
#define ISOC_(args) ()
|
|
#endif
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
The following operators can appear in macro definitions:
|
|
</p>
|
|
|
|
<ul>
|
|
<li><tt>#x</tt><br>
|
|
Converts macro argument <tt>x</tt> to a string surrounded by double quotes ("x").
|
|
</li>
|
|
|
|
<li><tt>x ## y</tt><br>
|
|
Concatenates x and y together to form <tt>xy</tt>.
|
|
</li>
|
|
|
|
<li><tt>`x`</tt><br>
|
|
If <tt>x</tt> is a string surrounded by double quotes, do nothing. Otherwise, turn into a string
|
|
like <tt>#x</tt>. This is a non-standard SWIG extension.
|
|
</li>
|
|
</ul>
|
|
|
|
<H2><a name="Preprocessor_nn6">11.5 SWIG Macros</a></H2>
|
|
|
|
|
|
<p>
|
|
SWIG provides an enhanced macro capability with the <tt>%define</tt> and <tt>%enddef</tt> directives.
|
|
For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%define ARRAYHELPER(type, name)
|
|
%inline %{
|
|
type *new_ ## name (int nitems) {
|
|
return (type *) malloc(sizeof(type)*nitems);
|
|
}
|
|
void delete_ ## name(type *t) {
|
|
free(t);
|
|
}
|
|
type name ## _get(type *t, int index) {
|
|
return t[index];
|
|
}
|
|
void name ## _set(type *t, int index, type val) {
|
|
t[index] = val;
|
|
}
|
|
%}
|
|
%enddef
|
|
|
|
ARRAYHELPER(int, IntArray)
|
|
ARRAYHELPER(double, DoubleArray)
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
The primary purpose of <tt>%define</tt> is to define large macros of code. Unlike normal C preprocessor
|
|
macros, it is not necessary to terminate each line with a continuation character (\)--the macro definition
|
|
extends to the first occurrence of <tt>%enddef</tt>. Furthermore, when such macros are expanded,
|
|
they are reparsed through the C preprocessor. Thus, SWIG macros can contain all other preprocessor
|
|
directives except for nested <tt>%define</tt> statements.
|
|
</p>
|
|
|
|
<p>
|
|
The SWIG macro capability is a very quick and easy way to generate large amounts of code. In fact,
|
|
many of SWIG's advanced features and libraries are built using this mechanism (such as C++ template
|
|
support).
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_nn7">11.6 C99 and GNU Extensions</a></H2>
|
|
|
|
|
|
<p>
|
|
SWIG-1.3.12 and newer releases support variadic preprocessor macros. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define DEBUGF(fmt, ...) fprintf(stderr, fmt, __VA_ARGS__)
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
When used, any extra arguments to <tt>...</tt> are placed into the
|
|
special variable <tt>__VA_ARGS__</tt>. This also works with special SWIG
|
|
macros defined using <tt>%define</tt>.
|
|
</p>
|
|
|
|
<p>
|
|
SWIG allows a variable number of arguments to be empty. However, this often results
|
|
in an extra comma (, ) and syntax error in the resulting expansion. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
DEBUGF("hello"); --> fprintf(stderr, "hello", );
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
To get rid of the extra comma, use <tt>##</tt> like this:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define DEBUGF(fmt, ...) fprintf(stderr, fmt, ##__VA_ARGS__)
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
SWIG also supports GNU-style variadic macros. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define DEBUGF(fmt, args...) fprintf(stdout, fmt, args)
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
<b>Comment:</b> It's not entirely clear how variadic macros might be useful to
|
|
interface building. However, they are used internally to implement a number of
|
|
SWIG directives and are provided to make SWIG more compatible with C99 code.
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_delimiters">11.7 Preprocessing and delimiters</a></H2>
|
|
|
|
|
|
<p>
|
|
The preprocessor handles { }, " " and %{ %} delimiters differently.
|
|
</p>
|
|
|
|
<H3><a name="Preprocessor_nn8">11.7.1 Preprocessing and %{ ... %} & " ... " delimiters</a></H3>
|
|
|
|
|
|
<p>
|
|
The SWIG preprocessor does not process any text enclosed in a code block %{ ... %}. Therefore,
|
|
if you write code like this,
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%{
|
|
#ifdef NEED_BLAH
|
|
int blah() {
|
|
...
|
|
}
|
|
#endif
|
|
%}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
the contents of the <tt>%{ ... %}</tt> block are copied without
|
|
modification to the output (including all preprocessor directives).
|
|
</p>
|
|
|
|
<H3><a name="Preprocessor_nn9">11.7.2 Preprocessing and { ... } delimiters</a></H3>
|
|
|
|
|
|
<p>
|
|
SWIG always runs the preprocessor on text appearing inside <tt>{ ... }</tt>. However,
|
|
sometimes it is desirable to make a preprocessor directive pass through to the output
|
|
file. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%extend Foo {
|
|
void bar() {
|
|
#ifdef DEBUG
|
|
printf("I'm in bar\n");
|
|
#endif
|
|
}
|
|
}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
By default, SWIG will interpret the <tt>#ifdef DEBUG</tt> statement. However, if you really wanted that code
|
|
to actually go into the wrapper file, prefix the preprocessor directives with <tt>%</tt> like this:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
%extend Foo {
|
|
void bar() {
|
|
%#ifdef DEBUG
|
|
printf("I'm in bar\n");
|
|
%#endif
|
|
}
|
|
}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
SWIG will strip the extra <tt>%</tt> and leave the preprocessor directive in the code.
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_typemap_delimiters">11.8 Preprocessor and Typemaps</a></H2>
|
|
|
|
|
|
<p>
|
|
<a href="Typemaps.html#Typemaps">Typemaps</a> support a special attribute called <tt>noblock</tt> where the { ... } delimiters can be used,
|
|
but the delimiters are not actually generated into the code.
|
|
The effect is then similar to using "" or %{ %} delimiters but the code <b>is</b> run through the preprocessor. For example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define SWIG_macro(CAST) (CAST)$input
|
|
%typemap(in) Int {$1= SWIG_macro(int);}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
might generate
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
{
|
|
arg1=(int)jarg1;
|
|
}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
whereas
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define SWIG_macro(CAST) (CAST)$input
|
|
%typemap(in, noblock=1) Int {$1= SWIG_macro(int);}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
might generate
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
arg1=(int)jarg1;
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
and
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#define SWIG_macro(CAST) (CAST)$input
|
|
%typemap(in) Int %{$1=SWIG_macro(int);%}
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
would generate
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
arg1=SWIG_macro(int);
|
|
</pre>
|
|
</div>
|
|
|
|
|
|
<H2><a name="Preprocessor_nn10">11.9 Viewing preprocessor output</a></H2>
|
|
|
|
|
|
<p>
|
|
Like many compilers, SWIG supports a <tt>-E</tt> command line option to display the output from the preprocessor.
|
|
When the <tt>-E</tt> option is used, SWIG will not generate any wrappers.
|
|
Instead the results after the preprocessor has run are displayed.
|
|
This might be useful as an aid to debugging and viewing the results of macro expansions.
|
|
</p>
|
|
|
|
<H2><a name="Preprocessor_warning_error">11.10 The #error and #warning directives</a></H2>
|
|
|
|
|
|
<p>
|
|
SWIG supports the commonly used <tt>#warning</tt> and <tt>#error</tt> preprocessor directives.
|
|
The <tt>#warning</tt> directive will cause SWIG to issue a warning then continue processing.
|
|
The <tt>#error</tt> directive will cause SWIG to exit with a fatal error.
|
|
Example usage:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
#error "This is a fatal error message"
|
|
#warning "This is a warning message"
|
|
</pre>
|
|
</div>
|
|
|
|
<p>
|
|
The <tt>#error</tt> behaviour can be made to work like <tt>#warning</tt> if the <tt>-cpperraswarn</tt>
|
|
commandline option is used. Alternatively, the <tt>#pragma</tt> directive can be used to the same effect, for example:
|
|
</p>
|
|
|
|
<div class="code">
|
|
<pre>
|
|
/* Modified behaviour: #error does not cause SWIG to exit with error */
|
|
#pragma SWIG cpperraswarn=1
|
|
/* Normal behaviour: #error does cause SWIG to exit with error */
|
|
#pragma SWIG cpperraswarn=0
|
|
</pre>
|
|
</div>
|
|
|
|
</body>
|
|
</html>
|