1 /* ----------------------------------------------------------------------------- 2 * arrays_csharp.i 3 * 4 * This file contains a two approaches to marshaling arrays. The first uses 5 * default p/invoke marshaling and the second uses pinning of the arrays. 6 * 7 * Default marshaling approach 8 * ---------------------------- 9 * Array typemaps using default p/invoke marshaling. The data is copied to a separately 10 * allocated buffer when passing over the managed-native boundary. 11 * 12 * There are separate typemaps for in, out and inout arrays to enable avoiding 13 * unnecessary copying. 14 * 15 * Example usage: 16 * 17 * %include "arrays_csharp.i" 18 * %apply int INPUT[] { int* sourceArray } 19 * %apply int OUTPUT[] { int* targetArray } 20 * void myArrayCopy( int* sourceArray, int* targetArray, int nitems ); 21 * 22 * %apply int INOUT[] { int* array1, int *array2 } 23 * void myArraySwap( int* array1, int* array2, int nitems ); 24 * 25 * If handling large arrays you should consider using the pinning array typemaps 26 * described next. 27 * 28 * Pinning approach 29 * ---------------- 30 * Array typemaps using pinning. These typemaps pin the managed array given 31 * as parameter and pass a pointer to it to the c/c++ side. This is very 32 * efficient as no copying is done (unlike in the default array marshaling), 33 * but it makes garbage collection more difficult. When considering using 34 * these typemaps, think carefully whether you have callbacks that may cause 35 * the control to re-enter the managed side from within the call (and produce 36 * garbage for the gc) or whether other threads may produce enough garbage to 37 * trigger gc while the call is being executed. In those cases it may be 38 * wiser to use the default marshaling typemaps. 39 * 40 * Please note that when using fixed arrays, you have to mark your corresponding 41 * module class method unsafe using 42 * %csmethodmodifiers "public unsafe" 43 * (the visibility of the method is up to you). 44 * 45 * Example usage: 46 * 47 * %include "arrays_csharp.i" 48 * %apply int FIXED[] { int* sourceArray, int *targetArray } 49 * %csmethodmodifiers myArrayCopy "public unsafe"; 50 * void myArrayCopy( int *sourceArray, int* targetArray, int nitems ); 51 * 52 * ----------------------------------------------------------------------------- */ 53 54 %define CSHARP_ARRAYS( CTYPE, CSTYPE ) 55 56 // input only arrays 57 58 %typemap(ctype) CTYPE INPUT[] "CTYPE*" 59 %typemap(cstype) CTYPE INPUT[] "CSTYPE[]" 60 %typemap(imtype, inattributes="[In, MarshalAs(UnmanagedType.LPArray)]") CTYPE INPUT[] "CSTYPE[]" 61 %typemap(csin) CTYPE INPUT[] "$csinput" 62 63 %typemap(in) CTYPE INPUT[] "$1 = $input;" 64 %typemap(freearg) CTYPE INPUT[] "" 65 %typemap(argout) CTYPE INPUT[] "" 66 67 // output only arrays 68 69 %typemap(ctype) CTYPE OUTPUT[] "CTYPE*" 70 %typemap(cstype) CTYPE OUTPUT[] "CSTYPE[]" 71 %typemap(imtype, inattributes="[Out, MarshalAs(UnmanagedType.LPArray)]") CTYPE OUTPUT[] "CSTYPE[]" 72 %typemap(csin) CTYPE OUTPUT[] "$csinput" 73 74 %typemap(in) CTYPE OUTPUT[] "$1 = $input;" 75 %typemap(freearg) CTYPE OUTPUT[] "" 76 %typemap(argout) CTYPE OUTPUT[] "" 77 78 // inout arrays 79 80 %typemap(ctype) CTYPE INOUT[] "CTYPE*" 81 %typemap(cstype) CTYPE INOUT[] "CSTYPE[]" 82 %typemap(imtype, inattributes="[In, Out, MarshalAs(UnmanagedType.LPArray)]") CTYPE INOUT[] "CSTYPE[]" 83 %typemap(csin) CTYPE INOUT[] "$csinput" 84 85 %typemap(in) CTYPE INOUT[] "$1 = $input;" 86 %typemap(freearg) CTYPE INOUT[] "" 87 %typemap(argout) CTYPE INOUT[] "" 88 89 %enddef // CSHARP_ARRAYS 90 91 CSHARP_ARRAYS(signed char, sbyte) 92 CSHARP_ARRAYS(unsigned char, byte) 93 CSHARP_ARRAYS(short, short) 94 CSHARP_ARRAYS(unsigned short, ushort) 95 CSHARP_ARRAYS(int, int) 96 CSHARP_ARRAYS(unsigned int, uint) 97 // FIXME - on Unix 64 bit, long is 8 bytes but is 4 bytes on Windows 64 bit. 98 // How can this be handled sensibly? 99 // See e.g. http://www.xml.com/ldd/chapter/book/ch10.html 100 CSHARP_ARRAYS(long, int) 101 CSHARP_ARRAYS(unsigned long, uint) 102 CSHARP_ARRAYS(long long, long) 103 CSHARP_ARRAYS(unsigned long long, ulong) 104 CSHARP_ARRAYS(float, float) 105 CSHARP_ARRAYS(double, double) 106 107 108 %define CSHARP_ARRAYS_FIXED( CTYPE, CSTYPE ) 109 110 %typemap(ctype) CTYPE FIXED[] "CTYPE*" 111 %typemap(imtype) CTYPE FIXED[] "IntPtr" 112 %typemap(cstype) CTYPE FIXED[] "CSTYPE[]" 113 %typemap(csin, 114 pre= " fixed ( CSTYPE* swig_ptrTo_$csinput = $csinput ) {", 115 terminator=" }") 116 CTYPE FIXED[] "(IntPtr)swig_ptrTo_$csinput" 117 118 %typemap(in) CTYPE FIXED[] "$1 = $input;" 119 %typemap(freearg) CTYPE FIXED[] "" 120 %typemap(argout) CTYPE FIXED[] "" 121 122 123 %enddef // CSHARP_ARRAYS_FIXED 124 125 CSHARP_ARRAYS_FIXED(signed char, sbyte) 126 CSHARP_ARRAYS_FIXED(unsigned char, byte) 127 CSHARP_ARRAYS_FIXED(short, short) 128 CSHARP_ARRAYS_FIXED(unsigned short, ushort) 129 CSHARP_ARRAYS_FIXED(int, int) 130 CSHARP_ARRAYS_FIXED(unsigned int, uint) 131 CSHARP_ARRAYS_FIXED(long, int) 132 CSHARP_ARRAYS_FIXED(unsigned long, uint) 133 CSHARP_ARRAYS_FIXED(long long, long) 134 CSHARP_ARRAYS_FIXED(unsigned long long, ulong) 135 CSHARP_ARRAYS_FIXED(float, float) 136 CSHARP_ARRAYS_FIXED(double, double) 137 138