Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

C# Tcl and reference counting

21 views
Skip to first unread message

stephen...@yahoo.com

unread,
Apr 21, 2008, 8:29:47 AM4/21/08
to
Hi.

I'm working on integrating c# and tcl 8.5. I'm able to use the
standard C interface to access the various TCL commands, however I'm
concerned about leaking memory on Tcl_Objs (Lists, Strings etc) that
I've 'created' in C# and then passed to the interpreter, for example
SetObjectResult.

I notice that I should be calling Tcl_IncrRefCount when I create the
object and Tcl_DecrRefCount when I'm done. However as these are
implemented as macro's I can't just import them into C#.

Is is just a case of converting the macro's into C# code to create the
same effect (with the possiblity of breaking forward compatibility) or
is there another method?

Alexandre Ferrieux

unread,
Apr 21, 2008, 9:02:49 AM4/21/08
to

You might also write a small C stub defining them as functions (with a
slightly different name). The stub reuses the macros, so there is no
risk of incompatibility:

void func_Tcl_IncrRefCount(Tcl_Obj *obj) {Tcl_IncrRefCount(obj);}

-Alex


Neil Madden

unread,
Apr 21, 2008, 10:09:28 AM4/21/08
to
stephen...@yahoo.com wrote:
> Hi.
>
> I'm working on integrating c# and tcl 8.5. I'm able to use the
> standard C interface to access the various TCL commands, however I'm
> concerned about leaking memory on Tcl_Objs (Lists, Strings etc) that
> I've 'created' in C# and then passed to the interpreter, for example
> SetObjectResult.

Tcl_SetObjResult will increment the reference count for you, so you
don't need to explicitly increment in this case. As a rule of thumb you
should always be able to match up Tcl_IncrRefCounts and
Tcl_DecrRefCounts in your source code. So, e.g. if you have code like:

Tcl_Obj *result = ...
Tcl_IncrRefCount(result);
Tcl_SetObjResult(interp, result);
return TCL_OK;

This should ring a bell as an error as there is no matching
Tcl_DecrRefCount. On the other hand, if you have a temporary Tcl_Obj
that you pass to several Tcl library calls:

Tcl_Obj *tmp = ...
Tcl_FooBar(tmp);
Tcl_BarFoo(tmp);
...

It should always be safe to wrap an incr/decr pair around this (and is a
wise thing to do):

Tcl_Obj *tmp = ...
Tcl_IncrRefCount(tmp);
Tcl_FooBar(tmp);
Tcl_BarFoo(tmp);
Tcl_DecrRefCount(tmp);

If you store a persistent reference to a Tcl_Obj then you should
*always* incr the count on store and decr on release.

-- Neil

0 new messages