bitrush has asked for the wisdom of the Perl Monks concerning the following question:

I've made an attempt at trying to embed one of my perl applications in a C script, but that didnt work. So, I went for something simpler, and simpler, but alas; none of them worked. When I run the program generated by the following scripts, I recieve a segfault.

Any advice or tips would be greatly appreciated. Thanks in advance.

Here goes:

malkavian:~/code/engine2$ ls
ex.c  make.sh*  script.pl
-------------------------------------------------------
malkavian:~/code/engine2$ cat ex.c
#include <EXTERN.h>
#include <perl.h>
static PerlInterpreter *foo;
main(int argc, char **argv, char **env) {
    foo = perl_alloc();
    perl_construct(foo);
    perl_parse(foo, NULL, argc, argv, env);
    perl_call_argv("printme", G_DISCARD, "geh");
perl_destruct(foo);
perl_free(foo);
}
-------------------------------------------------------
malkavian:~/code/engine2$ cat make.sh
#!/bin/sh
gcc -o ex -I/usr/lib/perl5/i386-linux/CORE \
              -L/usr/lib/perl5/i386-linux/CORE \
              -Dbool=char -DHAS_BOOL           \
       ex.c -lperl -lm -lcrypt
--------------------------------------------------------
malkavian:~/code/engine2$ cat script.pl
sub printme { print $_ };

Replies are listed 'Best First'.
Re: Embedding perl in C.
by perlmonkey (Hermit) on Apr 25, 2000 at 09:29 UTC
    This is the first time I have done anything in C with perl, but this seems to work:
    #include <EXTERN.h> #include <perl.h> static PerlInterpreter *foo; main(int argc, char **argv, char **env) { char * args[] = { NULL, NULL}; args[0] = "geh\n"; foo = perl_alloc(); perl_construct(foo); perl_parse(foo, NULL, argc, argv, env); perl_call_argv("printme", G_DISCARD, args); perl_destruct(foo); perl_free(foo); }
    Then for my script I used:
    printme(); sub printme { print $_[0] };
    The results:
    prompt% myperl script.pl geh
    So one of your problems was the last argument in perl_call_argv. You need to pass it an array of (char *) or a (char **) not just a single (char*). Also the last element in that char * array apparently needs to be NULL. So that is why I created a two element array, but only populated the first element.

    For more goods see perlcall and perlembed

    I hope this helps get you started. I am glad you asked this question. I was also curious about the perl/C interface.

      Ahh, thanks a bunch. That did work.

      Hi I am Sumit . Trying to use the same concept .I was trying to compile this example on Sun-solaris . Could you please tell what will be the gcc option . thanks Sumit
        The options should be the same that your perl binary was complied with. Those options should be saved in the Config module.

        Read the perlembed manpage.

        You can use ExtUtils::Embed module to get at these options easier. This is in the above manpage:
        cc -o interp interp.c `perl -MExtUtils::Embed -e ccopts -e ldopts`