Home | History | Annotate | Download | only in chicken
      1 /* -----------------------------------------------------------------------------
      2  * typemaps.i
      3  *
      4  * Pointer handling
      5  *
      6  * These mappings provide support for input/output arguments and
      7  * common uses for C/C++ pointers.  INOUT mappings allow for C/C++
      8  * pointer variables in addition to input/output arguments.
      9  * ----------------------------------------------------------------------------- */
     10 
     11 // INPUT typemaps.
     12 // These remap a C pointer to be an "INPUT" value which is passed by value
     13 // instead of reference.
     14 
     15 /*
     16 The following methods can be applied to turn a pointer into a simple
     17 "input" value.  That is, instead of passing a pointer to an object,
     18 you would use a real value instead.
     19 
     20          int            *INPUT
     21          short          *INPUT
     22          long           *INPUT
     23 	 long long      *INPUT
     24          unsigned int   *INPUT
     25          unsigned short *INPUT
     26          unsigned long  *INPUT
     27          unsigned long long *INPUT
     28          unsigned char  *INPUT
     29          char           *INPUT
     30          bool           *INPUT
     31          float          *INPUT
     32          double         *INPUT
     33 
     34 To use these, suppose you had a C function like this :
     35 
     36         double fadd(double *a, double *b) {
     37                return *a+*b;
     38         }
     39 
     40 You could wrap it with SWIG as follows :
     41 
     42         %include <typemaps.i>
     43         double fadd(double *INPUT, double *INPUT);
     44 
     45 or you can use the %apply directive :
     46 
     47         %include <typemaps.i>
     48         %apply double *INPUT { double *a, double *b };
     49         double fadd(double *a, double *b);
     50 
     51 */
     52 
     53 // OUTPUT typemaps.   These typemaps are used for parameters that
     54 // are output only.   The output value is appended to the result as
     55 // a list element.
     56 
     57 /*
     58 The following methods can be applied to turn a pointer into an "output"
     59 value.  When calling a function, no input value would be given for
     60 a parameter, but an output value would be returned.  In the case of
     61 multiple output values, they are returned in the form of a Scheme list.
     62 
     63          int            *OUTPUT
     64          short          *OUTPUT
     65          long           *OUTPUT
     66          long long      *OUTPUT
     67          unsigned int   *OUTPUT
     68          unsigned short *OUTPUT
     69          unsigned long  *OUTPUT
     70          unsigned long long *OUTPUT
     71          unsigned char  *OUTPUT
     72          char           *OUTPUT
     73          bool           *OUTPUT
     74          float          *OUTPUT
     75          double         *OUTPUT
     76 
     77 For example, suppose you were trying to wrap the modf() function in the
     78 C math library which splits x into integral and fractional parts (and
     79 returns the integer part in one of its parameters).K:
     80 
     81         double modf(double x, double *ip);
     82 
     83 You could wrap it with SWIG as follows :
     84 
     85         %include <typemaps.i>
     86         double modf(double x, double *OUTPUT);
     87 
     88 or you can use the %apply directive :
     89 
     90         %include <typemaps.i>
     91         %apply double *OUTPUT { double *ip };
     92         double modf(double x, double *ip);
     93 
     94 */
     95 
     96 //----------------------------------------------------------------------
     97 //
     98 // T_OUTPUT typemap (and helper function) to return multiple argouts as
     99 // a tuple instead of a list.
    100 //
    101 //----------------------------------------------------------------------
    102 
    103 // Simple types
    104 
    105 %define INOUT_TYPEMAP(type_, from_scheme, to_scheme, checker, convtype, storage_)
    106 
    107 %typemap(in) type_ *INPUT($*1_ltype temp), type_ &INPUT($*1_ltype temp)
    108 %{  if (!checker ($input)) {
    109     swig_barf (SWIG_BARF1_BAD_ARGUMENT_TYPE, "Argument #$argnum is not of type 'type_'");
    110   }
    111   temp = ($*1_ltype) from_scheme ($input);
    112   $1 = &temp; %}
    113 
    114 %typemap(typecheck) type_ *INPUT = type_;
    115 %typemap(typecheck) type_ &INPUT = type_;
    116 
    117 %typemap(in, numinputs=0) type_ *OUTPUT($*1_ltype temp), type_ &OUTPUT($*1_ltype temp)
    118 "  $1 = &temp;"
    119 
    120 #if "storage_" == "0"
    121 
    122 %typemap(argout) type_ *OUTPUT, type_ &OUTPUT
    123 %{
    124   if ($1 == NULL) {
    125     swig_barf (SWIG_BARF1_ARGUMENT_NULL, "Argument #$argnum must be non-null");
    126   }
    127   SWIG_APPEND_VALUE(to_scheme (convtype (*$1)));
    128 %}
    129 
    130 #else
    131 
    132 %typemap(argout) type_ *OUTPUT, type_ &OUTPUT
    133 %{
    134   {
    135     C_word *known_space = C_alloc(storage_);
    136     if ($1 == NULL) {
    137       swig_barf (SWIG_BARF1_ARGUMENT_NULL, "Variable '$1' must be non-null");
    138     }
    139     SWIG_APPEND_VALUE(to_scheme (&known_space, convtype (*$1)));
    140   }
    141 %}
    142 
    143 #endif
    144 
    145 %enddef
    146 
    147 INOUT_TYPEMAP(int, C_num_to_int, C_fix, C_swig_is_number, (int), 0);
    148 INOUT_TYPEMAP(enum SWIGTYPE, C_num_to_int, C_fix, C_swig_is_number, (int), 0);
    149 INOUT_TYPEMAP(short, C_num_to_int, C_fix, C_swig_is_number, (int), 0);
    150 INOUT_TYPEMAP(long, C_num_to_long, C_long_to_num, C_swig_is_long, (long), C_SIZEOF_FLONUM);
    151 INOUT_TYPEMAP(long long, C_num_to_long, C_long_to_num, C_swig_is_long, (long), C_SIZEOF_FLONUM);
    152 INOUT_TYPEMAP(unsigned int, C_num_to_unsigned_int, C_unsigned_int_to_num, C_swig_is_number, (int), C_SIZEOF_FLONUM);
    153 INOUT_TYPEMAP(unsigned short, C_num_to_unsigned_int, C_fix, C_swig_is_number, (unsigned int), 0);
    154 INOUT_TYPEMAP(unsigned long, C_num_to_unsigned_long, C_unsigned_long_to_num, C_swig_is_long, (unsigned long), C_SIZEOF_FLONUM);
    155 INOUT_TYPEMAP(unsigned long long, C_num_to_unsigned_long, C_unsigned_long_to_num, C_swig_is_long, (unsigned long), C_SIZEOF_FLONUM);
    156 INOUT_TYPEMAP(unsigned char, C_character_code, C_make_character, C_swig_is_char, (unsigned int), 0);
    157 INOUT_TYPEMAP(signed char, C_character_code, C_make_character, C_swig_is_char, (int), 0);
    158 INOUT_TYPEMAP(char, C_character_code, C_make_character, C_swig_is_char, (char), 0);
    159 INOUT_TYPEMAP(bool, C_truep, C_mk_bool, C_swig_is_bool, (bool), 0);
    160 INOUT_TYPEMAP(float, C_c_double, C_flonum, C_swig_is_number, (double), C_SIZEOF_FLONUM);
    161 INOUT_TYPEMAP(double, C_c_double, C_flonum, C_swig_is_number, (double), C_SIZEOF_FLONUM);
    162 
    163 // INOUT
    164 // Mappings for an argument that is both an input and output
    165 // parameter
    166 
    167 /*
    168 The following methods can be applied to make a function parameter both
    169 an input and output value.  This combines the behavior of both the
    170 "INPUT" and "OUTPUT" methods described earlier.  Output values are
    171 returned in the form of a CHICKEN tuple.
    172 
    173          int            *INOUT
    174          short          *INOUT
    175          long           *INOUT
    176          long long      *INOUT
    177          unsigned int   *INOUT
    178          unsigned short *INOUT
    179          unsigned long  *INOUT
    180          unsigned long long *INOUT
    181          unsigned char  *INOUT
    182          char           *INOUT
    183          bool           *INOUT
    184          float          *INOUT
    185          double         *INOUT
    186 
    187 For example, suppose you were trying to wrap the following function :
    188 
    189         void neg(double *x) {
    190              *x = -(*x);
    191         }
    192 
    193 You could wrap it with SWIG as follows :
    194 
    195         %include <typemaps.i>
    196         void neg(double *INOUT);
    197 
    198 or you can use the %apply directive :
    199 
    200         %include <typemaps.i>
    201         %apply double *INOUT { double *x };
    202         void neg(double *x);
    203 
    204 As well, you can wrap variables with :
    205 
    206         %include <typemaps.i>
    207         %apply double *INOUT { double *y };
    208         extern double *y;
    209 
    210 Unlike C, this mapping does not directly modify the input value (since
    211 this makes no sense in CHICKEN).  Rather, the modified input value shows
    212 up as the return value of the function.  Thus, to apply this function
    213 to a CHICKEN variable you might do this :
    214 
    215        x = neg(x)
    216 
    217 Note : previous versions of SWIG used the symbol 'BOTH' to mark
    218 input/output arguments.   This is still supported, but will be slowly
    219 phased out in future releases.
    220 
    221 */
    222 
    223 %typemap(in) int *INOUT = int *INPUT;
    224 %typemap(in) enum SWIGTYPE *INOUT = enum SWIGTYPE *INPUT;
    225 %typemap(in) short *INOUT = short *INPUT;
    226 %typemap(in) long *INOUT = long *INPUT;
    227 %typemap(in) long long *INOUT = long long *INPUT;
    228 %typemap(in) unsigned *INOUT = unsigned *INPUT;
    229 %typemap(in) unsigned short *INOUT = unsigned short *INPUT;
    230 %typemap(in) unsigned long *INOUT = unsigned long *INPUT;
    231 %typemap(in) unsigned long long *INOUT = unsigned long long *INPUT;
    232 %typemap(in) unsigned char *INOUT = unsigned char *INPUT;
    233 %typemap(in) char *INOUT = char *INPUT;
    234 %typemap(in) bool *INOUT = bool *INPUT;
    235 %typemap(in) float *INOUT = float *INPUT;
    236 %typemap(in) double *INOUT = double *INPUT;
    237 
    238 %typemap(in) int &INOUT = int &INPUT;
    239 %typemap(in) enum SWIGTYPE &INOUT = enum SWIGTYPE &INPUT;
    240 %typemap(in) short &INOUT = short &INPUT;
    241 %typemap(in) long &INOUT = long &INPUT;
    242 %typemap(in) long long &INOUT = long long &INPUT;
    243 %typemap(in) unsigned &INOUT = unsigned &INPUT;
    244 %typemap(in) unsigned short &INOUT = unsigned short &INPUT;
    245 %typemap(in) unsigned long &INOUT = unsigned long &INPUT;
    246 %typemap(in) unsigned long long &INOUT = unsigned long long &INPUT;
    247 %typemap(in) unsigned char &INOUT = unsigned char &INPUT;
    248 %typemap(in) char &INOUT = char &INPUT;
    249 %typemap(in) bool &INOUT = bool &INPUT;
    250 %typemap(in) float &INOUT = float &INPUT;
    251 %typemap(in) double &INOUT = double &INPUT;
    252 
    253 %typemap(argout) int *INOUT = int *OUTPUT;
    254 %typemap(argout) enum SWIGTYPE *INOUT = enum SWIGTYPE *OUTPUT;
    255 %typemap(argout) short *INOUT = short *OUTPUT;
    256 %typemap(argout) long *INOUT = long *OUTPUT;
    257 %typemap(argout) long long *INOUT = long long *OUTPUT;
    258 %typemap(argout) unsigned *INOUT = unsigned *OUTPUT;
    259 %typemap(argout) unsigned short *INOUT = unsigned short *OUTPUT;
    260 %typemap(argout) unsigned long *INOUT = unsigned long *OUTPUT;
    261 %typemap(argout) unsigned long long *INOUT = unsigned long long *OUTPUT;
    262 %typemap(argout) unsigned char *INOUT = unsigned char *OUTPUT;
    263 %typemap(argout) bool *INOUT = bool *OUTPUT;
    264 %typemap(argout) float *INOUT = float *OUTPUT;
    265 %typemap(argout) double *INOUT = double *OUTPUT;
    266 
    267 %typemap(argout) int &INOUT = int &OUTPUT;
    268 %typemap(argout) enum SWIGTYPE &INOUT = enum SWIGTYPE &OUTPUT;
    269 %typemap(argout) short &INOUT = short &OUTPUT;
    270 %typemap(argout) long &INOUT = long &OUTPUT;
    271 %typemap(argout) long long &INOUT = long long &OUTPUT;
    272 %typemap(argout) unsigned &INOUT = unsigned &OUTPUT;
    273 %typemap(argout) unsigned short &INOUT = unsigned short &OUTPUT;
    274 %typemap(argout) unsigned long &INOUT = unsigned long &OUTPUT;
    275 %typemap(argout) unsigned long long &INOUT = unsigned long long &OUTPUT;
    276 %typemap(argout) unsigned char &INOUT = unsigned char &OUTPUT;
    277 %typemap(argout) char &INOUT = char &OUTPUT;
    278 %typemap(argout) bool &INOUT = bool &OUTPUT;
    279 %typemap(argout) float &INOUT = float &OUTPUT;
    280 %typemap(argout) double &INOUT = double &OUTPUT;
    281 
    282 /* Overloading information */
    283 
    284 %typemap(typecheck) double *INOUT = double;
    285 %typemap(typecheck) bool *INOUT = bool;
    286 %typemap(typecheck) char *INOUT = char;
    287 %typemap(typecheck) signed char *INOUT = signed char;
    288 %typemap(typecheck) unsigned char *INOUT = unsigned char;
    289 %typemap(typecheck) unsigned long *INOUT = unsigned long;
    290 %typemap(typecheck) unsigned long long *INOUT = unsigned long long;
    291 %typemap(typecheck) unsigned short *INOUT = unsigned short;
    292 %typemap(typecheck) unsigned int *INOUT = unsigned int;
    293 %typemap(typecheck) long *INOUT = long;
    294 %typemap(typecheck) long long *INOUT = long long;
    295 %typemap(typecheck) short *INOUT = short;
    296 %typemap(typecheck) int *INOUT = int;
    297 %typemap(typecheck) enum SWIGTYPE *INOUT = enum SWIGTYPE;
    298 %typemap(typecheck) float *INOUT = float;
    299 
    300 %typemap(typecheck) double &INOUT = double;
    301 %typemap(typecheck) bool &INOUT = bool;
    302 %typemap(typecheck) char &INOUT = char;
    303 %typemap(typecheck) signed char &INOUT = signed char;
    304 %typemap(typecheck) unsigned char &INOUT = unsigned char;
    305 %typemap(typecheck) unsigned long &INOUT = unsigned long;
    306 %typemap(typecheck) unsigned long long &INOUT = unsigned long long;
    307 %typemap(typecheck) unsigned short &INOUT = unsigned short;
    308 %typemap(typecheck) unsigned int &INOUT = unsigned int;
    309 %typemap(typecheck) long &INOUT = long;
    310 %typemap(typecheck) long long &INOUT = long long;
    311 %typemap(typecheck) short &INOUT = short;
    312 %typemap(typecheck) int &INOUT = int;
    313 %typemap(typecheck) enum SWIGTYPE &INOUT = enum SWIGTYPE;
    314 %typemap(typecheck) float &INOUT = float;
    315