Basic tech stuff

Programming and Linux administration

Lessons to get embedded Perl to work in C

Posted by Daniel Brahneborg on 2007 March 1

The theme for this week has definitely been “embedding”. First Ruby, then Perl. Ruby was easy. Perl, being much more mature, should have been rather easy as well. Not quite.

First, it really didn’t like having my call perl_alloc() in one thread and using it in another. Well, that was easy to fix.

The documentation contain enough information about all the ENTER, SAVETMPS, PUSHMARK etc to get the stack correct. However, the only data that was sent was integers and strings. I wanted to send a couple of hash tables, some of them as elements in other hash tables. From the perlguts man page I found the newHV() and hv_store() functions, which looked promising. For some reason it just never wanted to work properly. Either the entire application crashed like crazy, or the perl function simply never got the data. I was starting to get a bit annoyed at this point.

Suddenly I found a typo! I had sent a normal C struct instead of an HV*. No wonder it crashed! Now it stopped crashing so much, but the perl function still didn’t get anything.

I went back to basics, trying to pass hash tables in hash tables from perl to perl. That turned out to be a complete mess, since the values in a hash table only can be integers or strings. Jay, great language. Well done, boys. After a while I found “references”. To put a hash table as the value of another hash table, one had to write beautiful code like this:

sms{'MESSAGE'} = "hello plugin";
$request{'sm'} = %sms;

To extract it, I had to use more beautiful code (both versions of syntax work, but I like variety).

my $sms = ${$request}{'sm'};
my $mess = $sms->{'MESSAGE'};

In other words, you can’t put hashes in a hash table, but a reference to a hash table is ok. In C, this would look like this:

hv_store(smsObj, "MESSAGE", 7, value, 0);
hv_store(requestObj, "sms", 3, newRV_noinc((SV*)smsObj), 0);

Now data passed through correctly.

There are still problems, of course. First, I haven’t verified that data can flow back from perl to C. Second, I’m not sure I’ve gotten all reference counts right, so it might leak memory. Third, it crashes like crazy when calling perl_destruct(). It might help calling this from the same thread as perl_construct(), of course.

Andra bloggar om: ,


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

%d bloggers like this: