From 72ba741d1c82fe24dfe94354117db0477636c63c Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 16 Mar 2017 21:04:38 +0000 Subject: [PATCH] Fix wrapping of references/pointers and qualifiers to member pointers Also fix Go wrapping of member const function pointers. --- CHANGES.current | 2 +- Examples/test-suite/member_funcptr_galore.i | 8 +++-- Examples/test-suite/member_pointer.i | 6 ---- Examples/test-suite/member_pointer_const.i | 10 ------- Lib/allegrocl/allegrocl.swg | 2 ++ Lib/cffi/cffi.swg | 2 ++ Lib/chicken/chicken.swg | 2 ++ Lib/csharp/csharp.swg | 9 ++++++ Lib/d/dmemberfunctionpointers.swg | 2 ++ Lib/go/go.swg | 6 ++-- Lib/guile/typemaps.i | 2 ++ Lib/java/java.swg | 2 ++ Lib/lua/luatypemaps.swg | 2 ++ Lib/modula3/modula3.swg | 2 ++ Lib/ocaml/typemaps.i | 2 ++ Lib/php/php.swg | 3 +- Lib/php5/php.swg | 3 +- Lib/pike/pike.swg | 2 ++ Lib/typemaps/swigtype.swg | 3 ++ Source/Modules/go.cxx | 33 +++++++++++++-------- Source/Swig/stype.c | 9 ++---- 21 files changed, 70 insertions(+), 42 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 15e2005d6..b0d9eed6a 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,7 +7,7 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 3.0.13 (in progress) ============================ -2017-03-10: wsfulton +2017-03-16: wsfulton Add support for member const function pointers such as: int fn(short (Funcs::* parm)(bool)) const; diff --git a/Examples/test-suite/member_funcptr_galore.i b/Examples/test-suite/member_funcptr_galore.i index 2592ae563..27d7a386a 100644 --- a/Examples/test-suite/member_funcptr_galore.i +++ b/Examples/test-suite/member_funcptr_galore.i @@ -1,5 +1,11 @@ %module member_funcptr_galore +%warnfilter(SWIGWARN_TYPEMAP_SWIGTYPELEAK_MSG) extra2; +%warnfilter(SWIGWARN_TYPEMAP_SWIGTYPELEAK_MSG) extra3; +%warnfilter(SWIGWARN_TYPEMAP_SWIGTYPELEAK_MSG) pp2; +%warnfilter(SWIGWARN_TYPEMAP_SWIGTYPELEAK_MSG) pp3; +%warnfilter(SWIGWARN_TYPEMAP_SWIGTYPELEAK_MSG) pp5; + %{ #if defined(__SUNPRO_CC) #pragma error_messages (off, badargtype2w) /* Formal argument ... is being passed extern "C" ... */ @@ -185,7 +191,6 @@ int MemberFuncPtrs::qqq5(short (Funcs::* & qq5)(bool)) const { return 0; } int MemberFuncPtrs::qqq6(short (Funcs::* const qq6)(bool)) const { return 0; } int MemberFuncPtrs::qqq7(short (Funcs::* const& qq7)(bool)) const { return 0; } -#if !defined(SWIGGO) // member function pointer variables short (Funcs::* pp1)(bool) = &Funcs::FF; @@ -199,5 +204,4 @@ short (Funcs::* *const& pp4)(bool) = extra4; short (Funcs::* & pp5)(bool) = pp1; short (Funcs::* const pp6)(bool) = &Funcs::FF; short (Funcs::* const& pp7)(bool) = pp1; -#endif %} diff --git a/Examples/test-suite/member_pointer.i b/Examples/test-suite/member_pointer.i index 0784d0e3b..e3b4f85ab 100644 --- a/Examples/test-suite/member_pointer.i +++ b/Examples/test-suite/member_pointer.i @@ -48,24 +48,18 @@ public: typedef double (Shape::*PerimeterFunc_td)(void); extern double do_op(Shape *s, double (Shape::*m)(void)); -#if !defined(SWIGGO) extern double do_op_td(Shape *s, PerimeterFunc_td m); -#endif /* Functions that return member pointers */ extern double (Shape::*areapt())(void); extern double (Shape::*perimeterpt())(void); -#if !defined(SWIGGO) extern PerimeterFunc_td perimeterpt_td(); -#endif /* Global variables that are member pointers */ extern double (Shape::*areavar)(void); extern double (Shape::*perimetervar)(void); -#if !defined(SWIGGO) extern PerimeterFunc_td perimetervar_td; -#endif %} %{ diff --git a/Examples/test-suite/member_pointer_const.i b/Examples/test-suite/member_pointer_const.i index 20299f5f5..4af712f7f 100644 --- a/Examples/test-suite/member_pointer_const.i +++ b/Examples/test-suite/member_pointer_const.i @@ -49,24 +49,18 @@ public: typedef double (Shape::*PerimeterFunc_td)(void) const; extern double do_op(Shape *s, double (Shape::*m)(void) const); -#if !defined(SWIGGO) extern double do_op_td(Shape *s, PerimeterFunc_td m); -#endif /* Functions that return member pointers */ extern double (Shape::*areapt())(void) const; extern double (Shape::*perimeterpt())(void) const; -#if !defined(SWIGGO) extern PerimeterFunc_td perimeterpt_td(); -#endif /* Global variables that are member pointers */ extern double (Shape::*areavar)(void) const; extern double (Shape::*perimetervar)(void) const; -#if !defined(SWIGGO) extern PerimeterFunc_td perimetervar_td; -#endif %} %{ @@ -124,11 +118,9 @@ PerimeterFunc_td perimetervar_td = &Shape::perimeter; /* Some constants */ -#if !defined(SWIGGO) %constant double (Shape::*AREAPT)(void) const = &Shape::area; %constant double (Shape::*PERIMPT)(void) const = &Shape::perimeter; %constant double (Shape::*NULLPT)(void) const = 0; -#endif /* %inline %{ @@ -152,8 +144,6 @@ int call1(int (Funktions::*d)(const int &, int) const, int a, int b) { Funktions //int call3(int & (Funktions::*d)(const int &, int) const, int a, int b) { Funktions f; return (f.*d)(a, b); } %} -#if !defined(SWIGGO) %constant int (Funktions::*ADD_BY_VALUE)(const int &, int) const = &Funktions::addByValue; -#endif //%constant int * (Funktions::*ADD_BY_POINTER)(const int &, int) const = &Funktions::addByPointer; //%constant int & (Funktions::*ADD_BY_REFERENCE)(const int &, int) const = &Funktions::addByReference; diff --git a/Lib/allegrocl/allegrocl.swg b/Lib/allegrocl/allegrocl.swg index 152e5e6f0..524aa7c11 100644 --- a/Lib/allegrocl/allegrocl.swg +++ b/Lib/allegrocl/allegrocl.swg @@ -232,6 +232,8 @@ $body)" /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* name conversion for overloaded operators. */ #ifdef __cplusplus diff --git a/Lib/cffi/cffi.swg b/Lib/cffi/cffi.swg index 3ad767ef8..f7294956f 100644 --- a/Lib/cffi/cffi.swg +++ b/Lib/cffi/cffi.swg @@ -136,6 +136,8 @@ /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } %{ diff --git a/Lib/chicken/chicken.swg b/Lib/chicken/chicken.swg index 17f0d0ac3..571c392ea 100644 --- a/Lib/chicken/chicken.swg +++ b/Lib/chicken/chicken.swg @@ -716,6 +716,8 @@ $result = C_SCHEME_UNDEFINED; /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* ------------------------------------------------------------ * Overloaded operator support diff --git a/Lib/csharp/csharp.swg b/Lib/csharp/csharp.swg index 8dc2ba813..bf1e126d8 100644 --- a/Lib/csharp/csharp.swg +++ b/Lib/csharp/csharp.swg @@ -843,6 +843,13 @@ SWIGINTERN const char * SWIG_UnpackData(const char *c, void *ptr, size_t sz) { $*csclassname ret = (cPtr == global::System.IntPtr.Zero) ? null : new $*csclassname(cPtr, $owner);$excode return ret; } +%typemap(csvarout, excode=SWIGEXCODE) SWIGTYPE *const& %{ + get { + global::System.IntPtr cPtr = $imcall; + $*csclassname ret = (cPtr == global::System.IntPtr.Zero) ? null : new $*csclassname(cPtr, $owner);$excode + return ret; + } %} + %typemap(in) SWIGTYPE *const& ($*1_ltype temp = 0) %{ temp = ($*1_ltype)$input; $1 = ($1_ltype)&temp; %} @@ -1011,6 +1018,8 @@ SWIG_CSBODY_TYPEWRAPPER(internal, protected, internal, SWIGTYPE) /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* csharp keywords */ %include diff --git a/Lib/d/dmemberfunctionpointers.swg b/Lib/d/dmemberfunctionpointers.swg index c63eca23e..a07d0a5d8 100644 --- a/Lib/d/dmemberfunctionpointers.swg +++ b/Lib/d/dmemberfunctionpointers.swg @@ -43,6 +43,8 @@ return ret; } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* * Helper functions to pack/unpack arbitrary binary data (member function diff --git a/Lib/go/go.swg b/Lib/go/go.swg index 53b653f7c..3e1fab2d9 100644 --- a/Lib/go/go.swg +++ b/Lib/go/go.swg @@ -341,8 +341,6 @@ %typemap(directorout) SWIGTYPE * %{ $result = *($&1_ltype)&$input; %} -%apply SWIGTYPE * { SWIGTYPE *const } - /* Pointer references. */ %typemap(gotype) SWIGTYPE *const& @@ -692,6 +690,10 @@ SWIGTYPE (CLASS::*) "" +%apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } + /* Go keywords. */ %include diff --git a/Lib/guile/typemaps.i b/Lib/guile/typemaps.i index a01e73f64..0d130f523 100644 --- a/Lib/guile/typemaps.i +++ b/Lib/guile/typemaps.i @@ -468,5 +468,7 @@ typedef unsigned long SCM; /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* typemaps.i ends here */ diff --git a/Lib/java/java.swg b/Lib/java/java.swg index d173cb627..2ca426675 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1338,6 +1338,8 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* String & length */ %typemap(jni) (char *STRING, size_t LENGTH) "jbyteArray" diff --git a/Lib/lua/luatypemaps.swg b/Lib/lua/luatypemaps.swg index 5d98e6107..c2dfcae41 100644 --- a/Lib/lua/luatypemaps.swg +++ b/Lib/lua/luatypemaps.swg @@ -386,6 +386,8 @@ parameters match which function /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } // size_t (which is just a unsigned long) %apply unsigned long { size_t }; diff --git a/Lib/modula3/modula3.swg b/Lib/modula3/modula3.swg index 262f8ead4..13d06e9c6 100644 --- a/Lib/modula3/modula3.swg +++ b/Lib/modula3/modula3.swg @@ -782,4 +782,6 @@ FROM BlaBla IMPORT Bla; /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } diff --git a/Lib/ocaml/typemaps.i b/Lib/ocaml/typemaps.i index 7602ad629..b70b78928 100644 --- a/Lib/ocaml/typemaps.i +++ b/Lib/ocaml/typemaps.i @@ -368,4 +368,6 @@ SIMPLE_MAP(unsigned long long,caml_val_ulong,caml_long_val); /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } diff --git a/Lib/php/php.swg b/Lib/php/php.swg index c9b9a5217..0ac46e006 100644 --- a/Lib/php/php.swg +++ b/Lib/php/php.swg @@ -525,7 +525,8 @@ /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } - +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* php keywords */ %include diff --git a/Lib/php5/php.swg b/Lib/php5/php.swg index 535c7d347..40854ea61 100644 --- a/Lib/php5/php.swg +++ b/Lib/php5/php.swg @@ -523,7 +523,8 @@ /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } - +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* php keywords */ %include diff --git a/Lib/pike/pike.swg b/Lib/pike/pike.swg index 95cc20835..a36bf3ad2 100644 --- a/Lib/pike/pike.swg +++ b/Lib/pike/pike.swg @@ -273,6 +273,8 @@ extern "C" { /* const pointers */ %apply SWIGTYPE * { SWIGTYPE *const } +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* ------------------------------------------------------------ * Overloaded operator support diff --git a/Lib/typemaps/swigtype.swg b/Lib/typemaps/swigtype.swg index d3633eb49..b21240af8 100644 --- a/Lib/typemaps/swigtype.swg +++ b/Lib/typemaps/swigtype.swg @@ -584,6 +584,9 @@ } #endif +%apply SWIGTYPE (CLASS::*) { SWIGTYPE (CLASS::*const) } +%apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } + /* ------------------------------------------------------------ * --- function ptr typemaps --- * ------------------------------------------------------------ */ diff --git a/Source/Modules/go.cxx b/Source/Modules/go.cxx index 884ae906d..68aba6214 100644 --- a/Source/Modules/go.cxx +++ b/Source/Modules/go.cxx @@ -2806,17 +2806,25 @@ private: return SWIG_NOWRAP; } - String *get = NewString(""); - Printv(get, Swig_cresult_name(), " = ", NULL); - String *rawval = Getattr(n, "rawval"); if (rawval && Len(rawval)) { - if (SwigType_type(type) == T_STRING) { - Printv(get, "(char *)", NULL); + // Based on Swig_VargetToFunction + String *nname = NewStringf("(%s)", rawval); + String *call; + if (SwigType_isclass(type)) { + call = NewStringf("%s", nname); + } else { + call = SwigType_lcaststr(type, nname); } - - Printv(get, rawval, NULL); + String *cres = Swig_cresult(type, Swig_cresult_name(), call); + Setattr(n, "wrap:action", cres); + Delete(nname); + Delete(call); + Delete(cres); } else { + String *get = NewString(""); + Printv(get, Swig_cresult_name(), " = ", NULL); + char quote; if (Getattr(n, "wrappedasconstant")) { quote = '\0'; @@ -2838,12 +2846,13 @@ private: if (quote != '\0') { Printf(get, "%c", quote); } + + Printv(get, ";\n", NULL); + + Setattr(n, "wrap:action", get); + Delete(get); } - Printv(get, ";\n", NULL); - - Setattr(n, "wrap:action", get); - String *sname = Copy(symname); if (class_name) { Append(sname, "_"); @@ -6234,7 +6243,7 @@ private: } } else if (SwigType_isfunctionpointer(type) || SwigType_isfunction(type)) { ret = NewString("_swig_fnptr"); - } else if (SwigType_ismemberpointer(type)) { + } else if (SwigType_ismemberpointer(t)) { ret = NewString("_swig_memberptr"); } else if (SwigType_issimple(t)) { Node *cn = classLookup(t); diff --git a/Source/Swig/stype.c b/Source/Swig/stype.c index 49962af4e..829005cd9 100644 --- a/Source/Swig/stype.c +++ b/Source/Swig/stype.c @@ -439,13 +439,8 @@ SwigType *SwigType_default_deduce(const SwigType *t) { Setitem(l, numitems-2, deduced_subtype); } } else if (SwigType_ismemberpointer(subtype)) { - if (numitems >= 3) { - /* member pointer deduction, eg, r.p.m(CLASS) => r.m(CLASS) */ - Delitem(l, numitems-3); - } else { - /* member pointer deduction, m(CLASS). => p. */ - Setitem(l, numitems-2, NewString("p.")); - } + /* member pointer deduction, m(CLASS). => p. */ + Setitem(l, numitems-2, NewString("p.")); } else if (is_enum && !SwigType_isqualifier(subtype)) { /* enum deduction, enum SWIGTYPE => SWIGTYPE */ Setitem(l, numitems-1, NewString("SWIGTYPE"));