From: Javier D. C. <jav...@fo...> - 2014-09-19 13:39:51
|
This could be refactored as: How can I correctly apply argument handling without having to include one by one all the functions in the library. Example, I have read http://www.swig.org/Doc3.0/SWIGDocumentation.html#Arguments And therefore, tried with: ===== %include aj_status.i %include aj_bus.i %include "typemaps.i" %apply uint32_t *OUTPUT { uint32_t* sessionId }; %inline %{ AJ_EXPORT AJ_Status AJ_StartClient(AJ_BusAttachment* bus, const char* daemonName, uint32_t timeout, uint8_t connected, const char* name, uint16_t port, uint32_t* sessionId, const AJ_SessionOpts* opts); %} %{ #include "aj_helper.h" %} %include aj_helper.h ===== But I can't get it working. Any way to make it work? Because at the moment, this wrapper code gets generated for uint32_t * OUTPUT one: ===== res7 = SWIG_ConvertPtr(obj6, &argp7,SWIGTYPE_p_uint32_t, 0 | 0 ); if (!SWIG_IsOK(res7)) { SWIG_exception_fail(SWIG_ArgError(res7), "in method '" "AJ_StartClient" "', argument " "7"" of type '" "uint32_t *""'"); } arg7 = (uint32_t *)(argp7); ===== Javier Domingo Cansino Research & Development Junior Engineer Fon Labs Workgroup, Getxo - Spain. On Fri, Sep 19, 2014 at 1:10 PM, Javier Domingo Cansino <jav...@fo...> wrote: > More information, the output with debug option: > > swig/aj_helper.i:21: Searching for a suitable 'in' typemap for: uint32_t *OUTPUT > Looking for: uint32_t *OUTPUT > Looking for: uint32_t * > Looking for: SWIGTYPE *OUTPUT > Looking for: SWIGTYPE * > Using: %typemap(in) SWIGTYPE * > > in theory, acording to the docs, OUTPUT should be mapped to out > typemap, shouldn't it? > > Just in case someone wonders, I included typemaps.in in the higher level header > > > Javier Domingo Cansino > Research & Development Junior Engineer > Fon Labs Workgroup, Getxo - Spain. > > > On Fri, Sep 19, 2014 at 12:54 PM, Javier Domingo Cansino > <jav...@fo...> wrote: >> Seems that this is caused because SWIG does return by reference >> different from what I thought. >> >> Anyone knows how to override just one function to mark a function's >> argument as OUTPUT using >> http://www.swig.org/Doc3.0/SWIGDocumentation.html#Arguments_nn5 but I >> don't know how to make it in a bigger file. >> >> I have tried copying the header file, etc. but nothing worked. My >> header file atm is: >> >> ===== >> %include aj_status.i >> %include aj_bus.i >> >> %{ >> AJ_EXPORT AJ_Status AJ_StartClient(AJ_BusAttachment* bus, >> const char* daemonName, >> uint32_t timeout, >> uint8_t connected, >> const char* name, >> uint16_t port, >> uint32_t* OUTPUT, >> const AJ_SessionOpts* opts); >> %} >> >> AJ_EXPORT AJ_Status AJ_StartClient(AJ_BusAttachment* bus, >> const char* daemonName, >> uint32_t timeout, >> uint8_t connected, >> const char* name, >> uint16_t port, >> uint32_t* OUTPUT, >> const AJ_SessionOpts* opts); >> >> >> %{ >> #include "aj_helper.h" >> %} >> >> %include aj_helper.h >> ===== >> >> But doesn't seem to get overriden >> >> Javier Domingo Cansino >> Research & Development Junior Engineer >> Fon Labs Workgroup, Getxo - Spain. >> >> >> On Fri, Sep 12, 2014 at 3:44 PM, Javier Domingo Cansino >> <jav...@fo...> wrote: >>> Hi, >>> >>> I am struggling against how to map different well known and C standard >>> data types, such as uint32, etc. I have found that %apply unsigned >>> long {uint32_t} works like a charm, and maps correctly values. >>> >>> The problem comes when I want to use a uint32_t *. In that case, SWIG >>> doesn't interpret it correctly. >>> >>> The output error message is (once modified the SWIG_ConvertPtr): >>> ``` >>> No type cast needed >>> sobj >>> Argument 7 about to be parsed >>> Traceback (most recent call last): >>> File "test.py", line 15, in <module> >>> None) >>> TypeError: in method 'AJ_StartClient', argument 7 of type 'uint32_t *' >>> No type cast needed >>> sobj >>> ``` >>> >>> The code generated is like this: >>> ``` >>> res7 = SWIG_ConvertPtr(obj6, &argp7,SWIGTYPE_p_uint32_t, 0 | 0 ); >>> if (!SWIG_IsOK(res7)) { >>> SWIG_exception_fail(SWIG_ArgError(res7), "in method '" >>> "AJ_StartClient" "', argument " "7"" of type '" "uint32_t *""'"); >>> } >>> arg7 = (uint32_t *)(argp7); >>> ``` >>> >>> If I follow the code execution through SWIG_ConvertPtr() and it >>> doesn't seem to qualify for (!SWIG_IsOK(res7)), so I am unable to know >>> what if failing here: >>> ``` >>> SWIGRUNTIME int >>> SWIG_Python_ConvertPtrAndOwn(PyObject *obj, void **ptr, swig_type_info >>> *ty, int flags, int *own) { >>> int res; >>> SwigPyObject *sobj; >>> int implicit_conv = (flags & SWIG_POINTER_IMPLICIT_CONV) != 0; >>> >>> if (!obj){ >>> printf("No obj\n"); >>> return SWIG_ERROR; >>> } >>> if (obj == Py_None && !implicit_conv) { >>> if (ptr) >>> *ptr = 0; >>> return SWIG_OK; >>> } >>> >>> res = SWIG_ERROR; >>> >>> sobj = SWIG_Python_GetSwigThis(obj); >>> if (own) >>> *own = 0; >>> while (sobj) { >>> void *vptr = sobj->ptr; >>> if (ty) { >>> swig_type_info *to = sobj->ty; >>> if (to == ty) { >>> printf("No type cast needed\n"); >>> /* no type cast needed */ >>> if (ptr) *ptr = vptr; >>> break; >>> } else { >>> printf("Type cast needed\n"); >>> swig_cast_info *tc = SWIG_TypeCheck(to->name,ty); >>> if (!tc) { >>> printf("No tc\n"); >>> sobj = (SwigPyObject *)sobj->next; >>> } else { >>> printf("Typcast yes\n"); >>> if (ptr) { >>> printf("If pointer\n"); >>> int newmemory = 0; >>> *ptr = SWIG_TypeCast(tc,vptr,&newmemory); >>> if (newmemory == SWIG_CAST_NEW_MEMORY) { >>> printf("newmemory\n"); >>> assert(own); /* badly formed typemap which will lead to >>> a memory leak - it must set and use own to delete *ptr */ >>> if (own) >>> *own = *own | SWIG_CAST_NEW_MEMORY; >>> } >>> } >>> break; >>> } >>> } >>> } else { >>> printf("pointer\n"); >>> if (ptr) *ptr = vptr; >>> break; >>> } >>> } >>> if (sobj) { >>> if (own) >>> *own = *own | sobj->own; >>> if (flags & SWIG_POINTER_DISOWN) { >>> sobj->own = 0; >>> } >>> printf("sobj\n"); >>> res = SWIG_OK; >>> } else { >>> if (implicit_conv) { >>> printf("implicit_conv\n"); >>> SwigPyClientData *data = ty ? (SwigPyClientData *) ty->clientdata : 0; >>> if (data && !data->implicitconv) { >>> printf("data && !data->implicitconv\n"); >>> PyObject *klass = data->klass; >>> if (klass) { >>> printf("klass\n"); >>> PyObject *impconv; >>> data->implicitconv = 1; /* avoid recursion and call >>> 'explicit' constructors*/ >>> impconv = SWIG_Python_CallFunctor(klass, obj); >>> data->implicitconv = 0; >>> if (PyErr_Occurred()) { >>> printf("PyErr_Occurred()\n"); >>> PyErr_Clear(); >>> impconv = 0; >>> } >>> if (impconv) { >>> printf("impconv\n"); >>> SwigPyObject *iobj = SWIG_Python_GetSwigThis(impconv); >>> if (iobj) { >>> printf("iobj\n"); >>> void *vptr; >>> res = SWIG_Python_ConvertPtrAndOwn((PyObject*)iobj, >>> &vptr, ty, 0, 0); >>> if (SWIG_IsOK(res)) { >>> printf("SWIG_IsOK(res)\n"); >>> if (ptr) { >>> printf("ptr\n"); >>> *ptr = vptr; >>> /* transfer the ownership to 'ptr' */ >>> iobj->own = 0; >>> res = SWIG_AddCast(res); >>> res = SWIG_AddNewMask(res); >>> } else { >>> printf("else ptr\n"); >>> res = SWIG_AddCast(res); >>> } >>> } >>> } >>> Py_DECREF(impconv); >>> } >>> } >>> } >>> } >>> if (!SWIG_IsOK(res) && obj == Py_None) { >>> printf("!SWIG_IsOK(res) && obj == Py_None\n"); >>> if (ptr) >>> *ptr = 0; >>> if (PyErr_Occurred()) >>> PyErr_Clear(); >>> res = SWIG_OK; >>> } >>> } >>> return res; >>> } >>> ``` >>> >>> I hope someone can help with something... Just in case, you have code >>> available in github: >>> https://github.com/fonlabs/ajtcl/blob/33bd4ba03556c5afafb447cdc4667e4f3faaf782/swig/alljoyn.i >>> >>> Cheers, >>> >>> Javier Domingo Cansino >>> Research & Development Junior Engineer >>> Fon Labs Workgroup, Getxo - Spain. |