Tcl_SetObjResult(interp,Tcl_NewStringObj(result,-1));
As I understand it, this creates a new copy of the string as part of
the newly created Tcl object. While Tcl's memory management handles the
copy, the string created by my C function will not be garbage collected
by Tcl, so as it stands, this is a memory leak.
Things seem to work just fine if I add to the code generated by swig:
free((void *) result);
after the call to TclSetObjResult.
My questions are:
(a) have I misunderstood anything here?
(b) is there a way to get swig to free the C string so that I don't
have to do it by editing the output of swig?
(c) if I distribute my edited version of the wrapper file generated by
swig, will it be portable? That is, is the code generated by swig
system-dependent? I can't find anything in the swig documentation about
this.
George
>
> I am using swig to provide a Tcl interface to a C library. One function
> returns a dynamically allocated string
> which is assigned to "result" below. Swig returns this in Tcl as
> follows:
>
>
> Tcl_SetObjResult(interp,Tcl_NewStringObj(result,-1));
>
>
> As I understand it, this creates a new copy of the string as part of
> the newly created Tcl object. While Tcl's memory management handles the
> copy, the string created by my C function will not be garbage collected
> by Tcl, so as it stands, this is a memory leak.
>
> Things seem to work just fine if I add to the code generated by swig:
>
>
> free((void *) result);
>
>
> after the call to TclSetObjResult.
>
>
> My questions are:
>
> (a) have I misunderstood anything here?
No.
>
> (b) is there a way to get swig to free the C string so that I don't
> have to do it by editing the output of swig?
>
Yes. You need to write a typemap for this case. This will allow you to
include some special handling.
> (c) if I distribute my edited version of the wrapper file generated by
> swig, will it be portable? That is, is the code generated by swig
> system-dependent? I can't find anything in the swig documentation about
> this.
The code generated by swig is cross-platform. Any code you insert
(manually or via a typemap) might or might not be. If you are using
autoconf and/or TEA you should make sure all the generated -D<mumble>
flags are passed to your swig call (in your Makefile.in) and then you
can test them with #ifdef's (in the typemap code) to be sure you
generate portable code. Presumbably, your C library is doing this, in
terms of it calling the proper flavor of malloc()/calloc(), etc. and
you can use these flags to call the matching flavor of free().
>
>
--
Robert Heller -- 978-544-6933
Deepwoods Software -- Linux Installation and Administration
http://www.deepsoft.com/ -- Web Hosting, with CGI and Database
hel...@deepsoft.com -- Contract Programming: C/C++, Tcl/Tk
Tcl_SetObjResult(interp,Tcl_NewStringObj(result,-1));
As I understand it, this creates a new copy of the string as part of
the newly created Tcl object. While Tcl's memory management handles the
copy, the string created by my C function will not be garbage collected
by Tcl, so as it stands, this is a memory leak: every call to the Tcl
function will cause my C function to allocate a new string that will
not be garbage collected by Tcl.
Things seem to work just fine if I add to the code generated
by swig:
free((void *) result);
after the call to TclSetObjResult.
My questions are:
(a) have I misunderstood anything here?
(b) is there a way to get swig to free the C string so that I don't
have to do it by editing the output of swig?
(c) if I distribute my edited version of the wrapper file generated by
swig, will it be portable? That is, is the code generated by swig
system-dependent? Or must I write a script to insert the free()into the
code generated by swig?
%{
typedef char * malloced_str;
%}
%typemap(out) malloced_str %{
if ($1 == NULL) {
/* Assumes NULL return is a failure */
Tcl_SetResult(interp, ........);
SWIG_fail;
}
else {
Tcl_SetObjResult(interp, Tcl_NewStringObj($1, -1));
}
%}
%typemap(ret) malloced_str "if ($1) free($1);"
malloced_str my_function();
Note this assumes the function returns the string as a return value. If
it is passed out through a parameter poiunter, you will need a
typemap(argout) that does something similar
/Ashok
%newobject UNStrToWNStr;
That tells Swig that the function returns newly allocated memory and
induces it to add a free by itself in the _wrap.c file.
Incidentally, the reason I posted twice is that the first one didn't
appear for a very long time, over an hour, so I mistakenly concluded
that something had gone wrong. After it appeared, I was unable to
respond to posts in this thread. Every time I clicked on the "Reply"
button I got an error message. Anyone know what was wrong?
Bill