1/* 2 Fragments 3 ========= 4 See the "Typemap fragments" section in the documentation for understanding 5 fragments. Below is some info on how fragments and automatic type 6 specialization is used. 7 8 Macros that make the automatic generation of typemaps easier are provided. 9 10 Consider the following code: 11 12 %fragment(SWIG_From_frag(bool), "header") { 13 static PyObject* 14 SWIG_From_dec(bool)(bool value) 15 { 16 PyObject *obj = value ? Py_True : Py_False; 17 Py_INCREF(obj); 18 return obj; 19 } 20 } 21 22 %typemap(out, fragment=SWIG_From_frag(bool)) bool { 23 $result = SWIG_From(bool)($1)); 24 } 25 26 Here the macros 27 28 SWIG_From_frag => fragment 29 SWIG_From_dec => declaration 30 SWIG_From => call 31 32 allow you to define/include a fragment, and declare and call the 33 'from-bool' method as needed. In the simpler case, these macros 34 just return something like 35 36 SWIG_From_frag(bool) => "SWIG_From_bool" 37 SWIG_From_dec(bool) => SWIG_From_bool 38 SWIG_From(bool) => SWIG_From_bool 39 40 But they are specialized for the different languages requirements, 41 such as perl or tcl that requires passing the interpreter pointer, 42 and also they can manage C++ ugly types, for example: 43 44 SWIG_From_frag(std::complex<double>) => "SWIG_From_std_complex_Sl_double_Sg_" 45 SWIG_From_dec(std::complex<double>) => SWIG_From_std_complex_Sl_double_Sg_ 46 SWIG_From(std::complex<double>) => SWIG_From_std_complex_Sl_double_Sg_ 47 48 49 Hence, to declare methods to use with typemaps, always use the 50 SWIG_From* macros. In the same way, the SWIG_AsVal* and SWIG_AsPtr* 51 set of macros are provided. 52 53*/ 54 55 56/* ----------------------------------------------------------------------------- 57 * Define the basic macros to 'normalize' the type fragments 58 * ----------------------------------------------------------------------------- */ 59 60#ifndef SWIG_AS_DECL_ARGS 61#define SWIG_AS_DECL_ARGS 62#endif 63 64#ifndef SWIG_FROM_DECL_ARGS 65#define SWIG_FROM_DECL_ARGS 66#endif 67 68#ifndef SWIG_AS_CALL_ARGS 69#define SWIG_AS_CALL_ARGS 70#endif 71 72#ifndef SWIG_FROM_CALL_ARGS 73#define SWIG_FROM_CALL_ARGS 74#endif 75 76#define %fragment_name(Name, Type...) %string_name(Name) "_" {Type} 77 78#define SWIG_Traits_frag(Type...) %fragment_name(Traits, Type) 79#define SWIG_AsPtr_frag(Type...) %fragment_name(AsPtr, Type) 80#define SWIG_AsVal_frag(Type...) %fragment_name(AsVal, Type) 81#define SWIG_From_frag(Type...) %fragment_name(From, Type) 82 83#define SWIG_AsVal_name(Type...) %symbol_name(AsVal, Type) 84#define SWIG_AsPtr_name(Type...) %symbol_name(AsPtr, Type) 85#define SWIG_From_name(Type...) %symbol_name(From, Type) 86 87#define SWIG_AsVal_dec(Type...) SWIG_AsVal_name(Type) SWIG_AS_DECL_ARGS 88#define SWIG_AsPtr_dec(Type...) SWIG_AsPtr_name(Type) SWIG_AS_DECL_ARGS 89#define SWIG_From_dec(Type...) SWIG_From_name(Type) SWIG_FROM_DECL_ARGS 90 91#define SWIG_AsVal(Type...) SWIG_AsVal_name(Type) SWIG_AS_CALL_ARGS 92#define SWIG_AsPtr(Type...) SWIG_AsPtr_name(Type) SWIG_AS_CALL_ARGS 93#define SWIG_From(Type...) SWIG_From_name(Type) SWIG_FROM_CALL_ARGS 94 95/* ------------------------------------------------------------ 96 * common fragments 97 * ------------------------------------------------------------ */ 98 99%fragment("SWIG_isfinite","header",fragment="<math.h>,<float.h>") %{ 100/* Getting isfinite working pre C99 across multiple platforms is non-trivial. Users can provide SWIG_isfinite on older platforms. */ 101#ifndef SWIG_isfinite 102/* isfinite() is a macro for C99 */ 103# if defined(isfinite) 104# define SWIG_isfinite(X) (isfinite(X)) 105# elif defined(__cplusplus) && __cplusplus >= 201103L 106/* Use a template so that this works whether isfinite() is std::isfinite() or 107 * in the global namespace. The reality seems to vary between compiler 108 * versions. 109 * 110 * Make sure namespace std exists to avoid compiler warnings. 111 * 112 * extern "C++" is required as this fragment can end up inside an extern "C" { } block 113 */ 114namespace std { } 115extern "C++" template<typename T> 116inline int SWIG_isfinite_func(T x) { 117 using namespace std; 118 return isfinite(x); 119} 120# define SWIG_isfinite(X) (SWIG_isfinite_func(X)) 121# elif defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 2)) 122# define SWIG_isfinite(X) (__builtin_isfinite(X)) 123# elif defined(__clang__) && defined(__has_builtin) 124# if __has_builtin(__builtin_isfinite) 125# define SWIG_isfinite(X) (__builtin_isfinite(X)) 126# endif 127# elif defined(_MSC_VER) 128# define SWIG_isfinite(X) (_finite(X)) 129# elif defined(__sun) && defined(__SVR4) 130# include <ieeefp.h> 131# define SWIG_isfinite(X) (finite(X)) 132# endif 133#endif 134%} 135 136%fragment("SWIG_Float_Overflow_Check","header",fragment="<float.h>,SWIG_isfinite") %{ 137/* Accept infinite as a valid float value unless we are unable to check if a value is finite */ 138#ifdef SWIG_isfinite 139# define SWIG_Float_Overflow_Check(X) ((X < -FLT_MAX || X > FLT_MAX) && SWIG_isfinite(X)) 140#else 141# define SWIG_Float_Overflow_Check(X) ((X < -FLT_MAX || X > FLT_MAX)) 142#endif 143%} 144 145/* ----------------------------------------------------------------------------- 146 * special macros for fragments 147 * ----------------------------------------------------------------------------- */ 148 149/* Macros to derive numeric types */ 150 151%define %numeric_type_from(Type, Base) 152%fragment(SWIG_From_frag(Type),"header", 153 fragment=SWIG_From_frag(Base)) { 154SWIGINTERNINLINE SWIG_Object 155SWIG_From_dec(Type)(Type value) 156{ 157 return SWIG_From(Base)(value); 158} 159} 160%enddef 161 162%define %numeric_type_asval(Type, Base, Frag, OverflowCond) 163%fragment(SWIG_AsVal_frag(Type),"header", 164 fragment=Frag, 165 fragment=SWIG_AsVal_frag(Base)) { 166SWIGINTERN int 167SWIG_AsVal_dec(Type)(SWIG_Object obj, Type *val) 168{ 169 Base v; 170 int res = SWIG_AsVal(Base)(obj, &v); 171 if (SWIG_IsOK(res)) { 172 if (OverflowCond) { 173 return SWIG_OverflowError; 174 } else { 175 if (val) *val = %numeric_cast(v, Type); 176 } 177 } 178 return res; 179} 180} 181%enddef 182 183#define %numeric_signed_type_asval(Type, Base, Frag, Min, Max) \ 184%numeric_type_asval(Type, Base, Frag, (v < Min || v > Max)) 185 186#define %numeric_unsigned_type_asval(Type, Base, Frag, Max) \ 187%numeric_type_asval(Type, Base, Frag, (v > Max)) 188 189 190/* Macro for 'signed long' derived types */ 191 192%define %numeric_slong(Type, Frag, Min, Max) 193%numeric_type_from(Type, long) 194%numeric_signed_type_asval(Type, long, Frag , Min, Max) 195%enddef 196 197/* Macro for 'unsigned long' derived types */ 198 199%define %numeric_ulong(Type, Frag, Max) 200%numeric_type_from(Type, unsigned long) 201%numeric_unsigned_type_asval(Type, unsigned long, Frag, Max) 202%enddef 203 204 205/* Macro for floating point derived types (original macro) */ 206 207%define %numeric_double(Type, Frag, Min, Max) 208%numeric_type_from(Type, double) 209%numeric_signed_type_asval(Type, double, Frag , Min, Max) 210%enddef 211 212/* Macro for floating point derived types */ 213 214%define %numeric_float(Type, Frag, OverflowCond) 215%numeric_type_from(Type, double) 216%numeric_type_asval(Type, double, Frag, OverflowCond) 217%enddef 218 219 220/* Macros for missing fragments */ 221 222%define %ensure_fragment(Fragment) 223%fragment(`Fragment`,"header") { 224%#error "SWIG language implementation must provide the Fragment fragment" 225} 226%enddef 227 228%define %ensure_type_fragments(Type) 229%fragment(SWIG_From_frag(Type),"header") { 230%#error "SWIG language implementation must provide a SWIG_From_frag(Type) fragment" 231} 232%fragment(SWIG_AsVal_frag(Type),"header") { 233%#error "SWIG language implementation must provide a SWIG_AsVal_frag(Type) fragment" 234} 235%enddef 236