----- Original Message -----
From: <[EMAIL PROTECTED]>
To: <inline@perl.org>
Sent: Friday, March 23, 2007 6:19 AM
Subject: structs with Inline::C
Hi everyone,
I am new to inline and am using Inline::C to embed C
in my perl code. I am trying to return a struct from a C subroutine
back to the perl caller. How do I deal with structs when I use
Inline::C? Any help would be appreciated.
You might be able to make use of Inline::Struct from CPAN. It has apparently
been abandoned by its author and, IIRC, there are bugs with its handling of
nested structs - but it should work reliably for simpler cases. See 'perldoc
Inline::Struct' and the module's test scripts for examples of usage.
Also see the "Object Oriented Inline" example in 'perldoc
Inline::C-Cookbook'. Along similar lines is this script which I happened to
have lying around:
------------------------------------
use warnings;
package My_struct;
use Inline (C => Config =>
BUILD_NOISY => 1,
);
use Inline C => <<'EOC';
typedef struct {
char * suit;
int value;
} Card;
SV * create_struct(SV * s, SV * v) {
Card * cptr;
New(123, cptr, sizeof(Card), Card);
if(cptr == NULL) croak("Failed to allocate memory in create_struct
function");
cptr->suit = SvPV_nolen(s);
cptr->value = SvIV(v);
return sv_setref_pv(newSViv(0), "My_struct", cptr);
/*******************************************************
Alternatively, if you don't want to bless the object
into package My_struct (in which case you'll have to
call DESTROY() explicitly):
return sv_setref_pv(newSViv(0), Nullch, cptr);
*******************************************************/
}
void deref_ref(SV * p) {
Inline_Stack_Vars;
Inline_Stack_Reset;
Inline_Stack_Push(newSVpv(((Card *)SvIV(SvRV(p)))->suit, 0));
Inline_Stack_Push(newSViv(((Card *)SvIV(SvRV(p)))->value));
Inline_Stack_Done;
Inline_Stack_Return(2);
}
void DESTROY(SV * p) {
printf("Destroying ...");
Card* c = (Card *)SvIV(SvRV(p));
Safefree(c);
printf("...destroyed\n");
}
EOC
for(1..500) {
$x = ('Hearts', 'Spades', 'Clubs', 'Diamonds')[rand(4)];
$y = int(rand(13)) + 1;
$p = create_struct($x, $y);
@members = deref_ref($p);
print "@members\n";
}
------------------------------------
There are of course, other ways to do it. For example you could have the
struct returned to perl as a hash reference (HV*).
Cheers,
Rob