views:

981

answers:

10

I have a C application and I want to include a Scripting Language to put certain functionality into scripts. I just have no experience with that and don't know exactly where to start (Still learning C and trying to understand the application).

How does embedding and communication between my app and the scripts actually work? I think I need the interpreter for the scripting language as a library (.dll on Windows or C Source Code that can be compiled into my application)? And then can I do something like

interpreter->run("myscript", some_object);

How would the script know about the properties of the object? Say my script wants to read or modify some_object->some_field?

Are there any scripting languages that are optimized for that sort of embedding? I know that there is Lua which is popular in game dev, and languages like Python, Perl, PHP or Ruby which seem to be more targeted as stand-alone applications, but my knowledge in the deep architecture does not allow more educated guesses :) (Tagged Lua and Python because they would be my favorites, but as long as it runs on x86 Windows, Linux and Mac OS X, I'm open for other scripting languages as long as they are easy to implement into a C application)

A: 

You'll need to use an object type (struct in C) specifically designed for interop with the scripting language. The method of embedding varies per language, but IIRC lua is particularly easy to embed, though python works fine too. In short, from the C-side you'll be working with objects that contain a bunch of meta-information in addition to the actual data, which when passed to (or from) the scripting language will be used to inform the engine about runtime specifics.

There are language specific tutorials for this kind of interop - just take your pick. I presume that perf. isn't an issue, so just pick whichever language you prefer.

Eamon Nerbonne
+12  A: 

Lua. It has a very small footprint, is rather fast, and I found it (subjectively) to have the most pleasant API to interact with C.

If you want to touch the Lua objects from C - it's quite easy using the built-in APIs. If you want to touch C data from Lua - it's a bit more work, typically you'd need to make wrapper methods to expose what you want to allow the Lua to modify.

Small code base and tight control over the amount of default libraries introduced into your embeded interpreter also means that you can make reasonable assumptions over the security.

The only odd part is the 1-based array numbering, however, it was not that big of a deal compared to what I thought, given the existence of the iterators.

How to integrate with C: the distribution tarball for Lua has a directory "etc" with a few very good useful examples that should quickly get you started. Specifically - etc/min.c shows how to start up an interpreter, make it interpret the file, and make it call the C function ('print' in that case). From there on you can go by reading the Lua documentation and the source of the standard libraries included with the distribution.

Andrew Y
I've used Lua for this, and it's extremely good at it. It's designed for embedding in other systems. Concur with the 1-based arrays, of course; every language has its little bits of braindamage, and this is one of Lua's, but it's copable.
Glenn Maynard
+2  A: 

Lua is designed for exactly this purpose, and fairly easy to work with.

Another thing worth looking at would be QtScript, which is Javascript based, although this would involve some work to "qt-ify" your app.

Paul Dixon
+4  A: 

Here's the document from the Python website for embedding Python 2.6...

http://docs.python.org/extending/embedding.html

Anon
I found the integration to Python to be really simple to use, FWIW. I was able to build something useful and functioning (including calling custom routines in my C code) in half a day.
Joe
My experience in embedding scripting languages in C only includes Perl, Python, Lua, and Tcl. In terms of learning curve (time from scratch to having a working program), I would give Lua a 1, Tcl a 2, Python a 5, and Perl a 359,000. But then, I worked with Lua and Tcl after having worked with Python, whereas I learned Python embedding knowing only Perl, so my experience may have made both Lua and Tcl seem easier than they are. But I concur with Joe--it takes about half a day to figure it out with Python, and about 20 minutes to figure in out with Lua. Lua is very easy to embed.
William Pursell
I'm accepting this above all the "Use Lua!" answers because I can kill two birds with one stone (I wanted to learn Python anyway) and because it does work. Dear Anonymous Reader that came to this question from Google: Read all the other answers as well, they are all excellent.
Michael Stum
+1  A: 

Most scripting language allow embedding in C and usually allow you to expose certain objects or even functions from your C code to the script so it can manipulate the objects and call the functions.

As said Lua is designed for this purpose embedding, using the interpreter you can expose objects to the script and call lua functions from C, search for embedding lua in C and you should find a lot of information, also don't miss the lua manual section "The Application Programming Interface"

Although Python is more suitable for stand-alone usage, it can also be embedded, it can be useful in case your scripts use the vast amount libraries provided with Python.

Diaa Sami
+10  A: 

Some useful links:

I am familiar with Python. Python is a very rich language, and has a huge number of libraries available.

codeape
+3  A: 

You may also want to take a look at SWIG, the Simplified Wrapper and Interface Generator. As one would guess, it generates much of the boiler plate code to interface your C/C++ code to the scripting engine (which can be quite cumbersome to do manually).

It supports Python and Lua (your preferences) and many other languages. It is quite easy to generate a module that extends the scripting language. Extending and embedding, which is what you desire, takes a bit more effort.

erichui
A: 

If you would like to execute scripts from C Program , for that you can use system function to execute the scripts.

Example [ Executing Php script from C Program]

printf("calling php function\n");
system("/usr/bin/php -q /var/www/html/phpinfo.php");
printf("End php function\n");

Refer related link

Webrsk
He wants the script to modify data within his C program.
Kieveli
+1  A: 

You might take a look at Game Scripting Mastery. As i am interested in the high level aspect of computer games aswell this book has been recommended to me very often.

Unfortunately the book seems to be out of print (at least in Europe).

tr9sh
+5  A: 

Lua is totally optimized for exactly this sort of embedding. A good starting point is Roberto Ierusalimschy's book Programming in Lua; you can get the previous edition free online.

How does your script know about the properties of your C object?

Imagine for a moment your object is defined like this:

typedef struct my_object *Object;
Object some_object;

What does your C code know about the properties of that object? Almost nothing, that's what. All you can do is

  • Pass around pointers to an object, put them in data structures, etc.

  • Call functions that actually know what's inside a struct my_object.

Lua gets access to C objects in exactly the same way: indirectly through functions:

  • You make API calls to put a pointer to the object on Lua's stack, from which it can go into Lua data structures, variables, or anywhere else in the Lua universe.

  • You define functions that know about the object's internals, and you export those functions to Lua.

  • There is a lot of stuff in the "auxiliary library" to help you. Don't overlook it!

All of this is explained with crystal clarity in the third part of Roberto's book, which includes examples. One fine point is

  • You have the choice of allocating the memory yourself ("light userdata") or having Lua allocate the memory. It's generally better to have Lua allocate the memory because it can then free the object automatically when it's no longer needed, and you can also associated a Lua metatable, which allows you (among other tricks) to allow the object to participate in standard Lua operations like looking up fields, not just function calls.

A final note: althought it's possible to use SWIG or toLua or other tools to try to generate code to connect C and Lua, I urge you to write the code yourself, by hand. It's actually quite easy to to, and it's the only way to understand what's really going on.

Norman Ramsey