# C ext / threading / callback issue, ruby-1.9.1p129

**URL:** <https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041>\
**Category:** Ruby\
**Created:** [July 13, 2009, 6:50pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041 "2009-07-13T18:50:19Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 13, 2009, 6:50pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/1 "2009-07-13T18:50:19Z")

</div>

Hi,

I’ve never written a C extension for Ruby before, and I’m struggling  
with  
some demo code which uses C and/or Ruby pthreads, and a C or Ruby  
callback  
(address passed as an arg into the C lib).

There’s a watcher thread (in C) that waits for an event (the creation of  
a file), then triggers whichever callback is specified.

Triggering the Ruby callback causes MRI to crash. The C callback  
works…  
but when it completes, all Ruby threads appear to suspend (control is  
never returned to Ruby / the threads are never rejoined?)

I’m guessing that the MRI crash is a dereferencing bug?? I haven’t  
figured  
that out obviously, but I have a feeling that the second problem  
(threads  
never rejoin?) will show up after the crash is resolved.

I put the code up on github: [GitHub - reynhout/callme: A simple Ruby 1.9 demo C ext with a callback](http://github.com/reynhout/callme/) . There  
is a bunch more description there, too.

There are two versions, C\_ext (described above), and FFI\_lib which uses  
ruby-ffi to achieve the same goals … but is also failing similarly.  
I worked on the FFI\_lib one first, then backed down to a straight C ext  
trying to simplify it and make the bugs easier to find.

I’m pretty sure that if I can get the C\_ext version working, the FFI\_lib  
one will fall into place. The ultimate goal is a Ruby library for  
Apache  
ZooKeeper. The rest of the code is going great, but many ZK functions  
depend on this sort of mechanism…

I hope the bugs are obvious to anyone who has written a C ext before.  
I’d greatly appreciate any ideas or pointers (no pun intended :)…

> **[GitHub - reynhout/callme: A simple Ruby 1.9 demo C ext with a callback](https://github.com/reynhout/callme/)**
>
> A simple Ruby 1.9 demo C ext with a callback. Contribute to reynhout/callme development by creating an account on GitHub.

Thank you!  
Andrew

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 3:57am UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/2 "2009-07-14T03:57:05Z")

</div>

> There’s a watcher thread (in C) that waits for an event (the creation of  
> a file), then triggers whichever callback is specified.

Hmm. MRI isn’t “used” to other threads running–are you running 1.8.6  
or something else?  
=r

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 2:08pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/3 "2009-07-14T14:08:27Z")

</div>

On Tue, Jul 14, 2009 at 10:57:07AM +0900, Roger P. wrote:

> > There’s a watcher thread (in C) that waits for an event (the creation of  
> > a file), then triggers whichever callback is specified.
> 
> Hmm. MRI isn’t “used” to other threads running–are you running 1.8.6  
> or something else?

I’m using 1.9.1p129, but I tried the FFI version under 1.8.6 too, and  
got similar MRI crashes and/or stuck threads. I did wrap the callback  
invocation inside rb\_thread\_blocking\_region, though I’m not sure it’s  
necessary for this sample code.

I haven’t written a 1.8.6 version of the C ext (the syntax/semantics  
are slightly different than 1.9), but I’d be very surprised to see  
anything change – these failures are consistent with MRI through  
multiple versions and approaches.

This code DOES work correctly under JRuby. JRuby has a different  
threading model, of course, but I don’t understand it well enough to  
determine why it fails under MRI.

Sample code and details at: [GitHub - reynhout/callme: A simple Ruby 1.9 demo C ext with a callback](http://github.com/reynhout/callme/)

Thanks again,  
Andrew

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 3:48pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/4 "2009-07-14T15:48:49Z")

</div>

Roger P. wrote:

> Does the callback use ruby code from within the thread blocking region?

Yes, e.g.:

rb\_thread\_blocking\_region((rb\_blocking\_function\_t \*)w-\>callback, tmp\_x,  
RUBY\_UBF\_IO, 0);

w-\>callback is the address of the Ruby proc. The address is correct  
afaict, but note that this does crash MRI before the callback appears to  
execute (dereferencing failure?). When w-\>callback is the address of  
the C function, the callback runs, but the Ruby threads apparently  
suspend.

Both callbacks in this sample code are very simple – they just print  
the int value of tmp\_x, which is the number of seconds since the watcher  
thread was started.

Thanks,  
Andrew

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 7:35pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/5 "2009-07-14T19:35:44Z")

</div>

On Jul 14, 10:48 am, Andrew R. [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> execute (dereferencing failure?). When w-\>callback is the address of  
> the C function, the callback runs, but the Ruby threads apparently  
> suspend.
> 
> Both callbacks in this sample code are very simple – they just print  
> the int value of tmp\_x, which is the number of seconds since the watcher  
> thread was started.

Ruby-FFI issues, more related to callbacks can be asked at Ruby-ffi  
mailing list:

[http://kenai.com/projects/ruby-ffi/lists](http://kenai.com/projects/ruby-ffi/lists)

If memory plays well, I saw something related to callbacks not long  
ago there:

[http://kenai.com/projects/ruby-ffi/lists/dev/archive](http://kenai.com/projects/ruby-ffi/lists/dev/archive)

Sometimes the API hasn’t been updated across the implementations.

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 7:58pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/6 "2009-07-14T19:58:17Z")

</div>

Luis L. wrote:

> Ruby-FFI issues, more related to callbacks can be asked at Ruby-ffi  
> mailing list:

Sorry, I didn’t mean to confuse the issue by mentioning FFI. I did try  
it with FFI initially (and have been discussing the problem on the  
ruby-ffi list), but I’ve completely removed FFI from the current version  
of the code. It’s a straight C ext with no dependencies except gcc,  
MRI, and mkmf.

Thanks,  
Andrew

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 14, 2009, 2:52pm UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/7 "2009-07-14T14:52:25Z")

</div>

> I’m using 1.9.1p129, but I tried the FFI version under 1.8.6 too, and  
> got similar MRI crashes and/or stuck threads. I did wrap the callback  
> invocation inside rb\_thread\_blocking\_region, though I’m not sure it’s  
> necessary for this sample code.

Does the callback use ruby code from within the thread blocking region?  
=r

---

<div class="post-metadata">

**Author:** ![unknown](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/u/4bbf92/32.png) [@unknown](https://www.ruby-forum.com/u/unknown)\
**Post date:** [July 15, 2009, 5:49am UTC](https://www.ruby-forum.com/t/c-ext-threading-callback-issue-ruby-1-9-1p129/172041/8 "2009-07-15T05:49:41Z")

</div>

> rb\_thread\_blocking\_region((rb\_blocking\_function\_t \*)w-\>callback, tmp\_x,  
> RUBY\_UBF\_IO, 0);

Hmm. This question might be more easily answered by the core folk, but  
perhaps you’re assigning the value of w-\>callback to a ruby proc object,  
when what you wanted was perhaps a pointer to a C method.

So the question is how to call proc objects in C?  
I’ve never done it, but glancing at README.EXT appears to be something  
like rb\_iterate or rb\_block\_call (the latter for 1.9 esp.)

Not sure of that’s right but it’s about as far as my know-how goes.  
GL.  
=r
