Beefy Boxes and Bandwidth Generously Provided by pair Networks
more useful options
 
PerlMonks  

Re^2: Perl XS

by revendar (Novice)
on Nov 18, 2013 at 19:50 UTC ( #1063189=note: print w/ replies, xml ) Need Help??


in reply to Re: Perl XS
in thread Perl XS

Thanks!. I have seen Inline::C. I wanted to give XS a try. I still wanted to use XS as it keeps an abstraction.


Comment on Re^2: Perl XS
Replies are listed 'Best First'.
Re^3: Perl XS
by syphilis (Canon) on Nov 19, 2013 at 00:11 UTC
    Inline::C can still be helpful - as a quick way of discovering what's going wrong and testing proposed fixes.

    For example, I placed (copy'n'paste') your 2 functions in an Inline::C script:
    use warnings; use strict; use Inline C => Config => BUILD_NOISY => 1; use Inline C => <<'EOC'; void print_array_char(char * array) { int l; int i; l=strlen(array); printf("Length of array is %d\n",l); for(i=0;i < l;i++) { printf("Element array[%d] = %c\n",i,array[i]); } } void print_array_int(int array[], int l) { int i; for(i=0;i < l;i++) { printf("Element array[%d] = %d\n",i,array[i]); } } EOC print_array_char( "revendar" ); print_array_int (-1,12,23,3);
    When I run that script, it compiles, then outputs:
    Length of array is 8 Element array[0] = r Element array[1] = e Element array[2] = v Element array[3] = e Element array[4] = n Element array[5] = d Element array[6] = a Element array[7] = r Undefined subroutine &main::print_array_int_alt called at try.pl line +....
    The problem is that, although there's nothing syntactically wrong with print_array_int(), perl doesn't know how to pass the 'int array[]' type to XS.
    For a working solution, you need to know a little bit about the perl API. I suggest perlxs, perlxstut, and perlapi docs, though you'll perhaps also find some useful tips in the Inline::C cookbook and, no doubt, many other places.
    Anyway, here's one solution:
    void print_array_int(int x, ...) { dXSARGS; int i; for(i=0;i < items - 1; i++) { printf("Element array[%d] = %d\n",i,SvIV(ST(i))); } XSRETURN(0); }
    "items" is the number of elements on the stack - so there's really no need to pass the length of the array to the function. You could remove that arg and rewrite the for loop condition as (i=0; i<items; i++)

    Two things to note about Inline::C:
    1) It's really just XS - it takes your C code, autogenerates the XS code, then compiles and runs your program.
    2) Inline::C defines its own stack macros, all of which begin with "Inline_Stack_" and are defined in the Inline.h file that it also autogenerates. Other than that, it's the same as XS, and you don't *have* to use its stack macros. You can just use the normal XS terms - as I did above when I declared "dXSARGS" instead of "Inline_Stack_Vars" (and used "XSRETURN(0)" instead of "Inline_Stack_Void").

    Cheers,
    Rob

      I second this!

      Here's one way to do it...

      1. Prototype in Perl, thinking "This will be reimplemented in XS/C." (which will encourage you to keep the prototype simple.)
      2. Re-implement using Inline::C
      3. If there's some additional tweekery that isn't available when using Inline::C, grab the XS file that Inline::C generates, and tweak to your heart's content.

      It's really so much more convenient. One thing to keep in mind: Passing a char* string around is simple until you start dealing with Unicode. Eventually it becomes easier to pass an SV*, and avoid touching the internal PV string except with proper XS macros/functions, and even then with extreme care.

      Also, write your unit tests either as step zero, or in conjunction with step one. That way when you've re-implemented in Inline::C/XS you can verify behavior.


      Dave

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: note [id://1063189]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others surveying the Monastery: (6)
As of 2015-08-01 01:56 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (285 votes), past polls