| Table of contents of this page | |
|
|
Wrap a simple function in C
This example is based on the example given for other languages in the distribution of SWIG.
Problems
There is a problem with the naming of the function. I have not been able to get the wrapper code to compile unless the name of the C function and the name given in D are different. Here I have changed the name of the C function from gcd to gcdc.
There is also a problem with the file names, in that if there is a file called example.d and one called example.c they will both have the same object file name. As both of these files have to be linked into the executable program, I have renamed the C one as examplec.c. The file example.d is generated automatically.
The C function to be wrapped
| /* File : examplec.c */
/* Compute the greatest common divisor of positive integers */
int gcdc(int x, int y) {
int g;
g = y;
while (x > 0) {
g = x;
x = y % x;
y = g;
}
return g;
} |
|
|
The Interface file
The interface file is the input data for SWIG. This and the code to be wrapped are the only things which should have to be edited by the person implementing the interface. The user will then write the application code in the target language.
The module name in the wrapper file will be used as the name for the files which will be generated.
| /* File : example.i */
%module example
/* rename is needed to change the name of the function */
%rename(gcd) gcdc;
extern int gcdc(int x, int y); |
|
|
There are a lot more SWIG commands.
Run SWIG
In this case three files are generated called example.d, examplePINVOKE.d and example_wrap.c
Generated files
example.d
| private import examplePINVOKE;
/* ----------------------------------------------------------------------------
* This file was automatically generated by SWIG (http://www.swig.org).
* Version: 1.3.19
*
* Do not make changes to this file unless you know what you are doing--modify
* the SWIG interface file instead.
* ----------------------------------------------------------------------------- */
// Module level imports should go here
// use: (percent)pragma(dmd) moduleimports="importname"
public static int gcd(int x, int y) {
return examplePINVOKE.gcd(x, y);
} |
|
|
examplePINVOKE.d
| /* ----------------------------------------------------------------------------
* This file was automatically generated by SWIG (http://www.swig.org).
* Version: 1.3.19
*
* Do not make changes to this file unless you know what you are doing--modify
* the SWIG interface file instead.
* ----------------------------------------------------------------------------- */
static extern(C):
int gcd(int jarg1, int jarg2); |
|
|
example_wrap.c
| /* ----------------------------------------------------------------------------
* This file was automatically generated by SWIG (http://www.swig.org).
* Version 1.3.19
*
* This file is not intended to be easily readable and contains a number of
* coding conventions designed to improve portability and efficiency. Do not make
* changes to this file unless you know what you are doing--modify the SWIG
* interface file instead.
* ----------------------------------------------------------------------------- */
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#ifdef WIN32
# define DllExport __declspec( dllexport )
#else
# define DllExport
#endif
extern int gcdc(int,int);
#ifdef __cplusplus
extern "C" {
#endif
DllExport int gcd(int jarg1, int jarg2) {
int jresult = 0 ;
int arg1 ;
int arg2 ;
int result;
arg1 = (int)jarg1;
arg2 = (int)jarg2;
result = (int)gcdc(arg1,arg2);
jresult = result;
return jresult;
}
#ifdef __cplusplus
}
#endif |
|
|
These files should not need to be edited. If the C function is changed, or more functions added, expand the interface and regenerate the files.
Comment
These may not be the most efficient interface possible, but they are generated automatically.
Example application
helloex.d
| private import example;
/* hello.d from the dmd distribution adapted as an example for D SWIG */
int main(char[][] args)
{
printf("hello world\n");
printf("int y = gcd(5,50); calls a C function\n");
int y = gcd(5,50);
printf("The result is y = %d\n",y);
return 0;
} |
|
|
Linux
| gcc -c examplec.c
gcc -c example_wrap.c
dmd helloex.d example.d example_wrap.o examplec.o |
|
|
Windows Note that for this I copied the files unchanged from Linux to Windows.
| dmc -c examplec.c
dmc -c example_wrap.c
dmd helloex.d example.d example_wrap.obj examplec.obj |
|
|
Output
| hello world
int y = gcd(5,50); calls a C function
The result is y = 5 |
|
|
I have given considerable detail on this to help those unfamiliar with SWIG. For more extended examples I will not give the full wrapped files.
JohnFletcher