Bill the Lizard
Bill the Lizard

Reputation: 405755

How do I call a C++ static library from Perl?

I'm writing a C++ static library that needs to be shared among several applications, one of them written in Perl. Unfortunately, I only barely know the core Perl language (I read the Llama book), and I'm not all that familiar with its libraries. How do you make calls to an external C++ binary from a Perl script?

By Google search, I found information on the Perl Inline module, but if I understand it correctly, that isn't what I need. I'm pretty sure that's for writing C and C++ code directly in your Perl scripts, not for calling external C++ libraries.

The C++ static library is being cross-compiled for an ARM processor, so there will be no C++ compiler on the target machine where the Perl script will be running. (If that makes a difference.)

Upvotes: 11

Views: 9259

Answers (6)

daotoad
daotoad

Reputation: 27183

I'm only starting to wrap my head around XS, so I can't offer much help. But here's what I do know...

There is XSpp, which is XS for C++. It is distributed with WxPerl. WxPerl is under active and responsive development.

Inline:CPP can be used to write your initial interface/wrapper code. Then you can analyze the generated XS. However, it doesn't look so well maintianed. If it works, it may provide you with a good head start.

You might find this short note on XS and C++ by John Keiser helpful, if a bit dated.

Upvotes: 0

dicroce
dicroce

Reputation: 46770

First, it does need to be in a dynamic library, not a static library (unless you'll be re-compiling perl itself and linking it against your static library).

Second, since C++ will mangle the names (one of the most annoying "Features" of C++ if you ask me) you'll need an extern "C" block that contains hook functions. If you were using C++ you could probably get by with a single hook function that returns the C++ object that implements the interface you need to use. Since you're using perl, you may need to wrap an object in an interface like this:

CPPObject object;

extern "C"
{

int InitObject( void )
{
  return object.init();
}

int DoCoolStuff( void )
{
  return object.DoCoolStuff();
}

int DoOtherCoolStuff( int foo )
{
  return object.DoOtherCoolStuff( foo );
}

int DestroyObject( void )
{
  return object.Destroy();
}

}

Upvotes: 4

Corion
Corion

Reputation: 507

You can call code from other libraries via Inline::C (and likely the same via Inline::CPP) - have a look at Inline::C::Cookbook. Most likely you want to start out with Inline and after you're done experimenting use the resulting .XS file to work further.

Upvotes: 8

Adam Bellaire
Adam Bellaire

Reputation: 110489

You want to look at using XS, which is how Perl normally interfaces with C/C++ libraries. It's not quite trivial. A couple of relevant portions of the Perl documentation:

Upvotes: 5

Mr Fooz
Mr Fooz

Reputation: 111856

You need to create a wrapper function that is callable from perl, and AFAIK, you'll need to have this wrapper function be in a dynamic library (unless you're going to rebuild the perl binary and link the static lib to it). I like to use a tool called SWIG (Simple Wrapper Interface Generator) to create the wrappers for me. It can create wrappers for 17 or so other languages too.

Upvotes: 2

Paul Tomblin
Paul Tomblin

Reputation: 182782

Probably not what you're thinking, but how about writing a stand-alone C++ program that the perl program communicates through pipes with?

Upvotes: 1

Related Questions