ATTENTION: You are viewing a page formatted for mobile devices; to view the full web page, click HERE.

Other Software > Developer's Corner

Anyone ever used Swig or other c++ wrapping tools? recommendations

(1/3) > >>

mouser:
Anyone ever used Swig to automatically create wrappers around C++ class?

Swig: http://www.swig.org/

I know there are some others and i'd be interested in hearing any comparisons or experiences.

NeilS:
SWIG is pretty amazing. I've only used it with Ruby (see Screenshot Captor scripting thread), although I did use a fair chunk of its features and I was constantly impressed by how flexible it was.

One of its best features is that the C++ parser is really pretty good, so you don't have to "sanitise" your code that much for SWIG to accept it, although you'll probably always end up generating a separate interface file anyway, just to make use of some of SWIG's extra features.

It also has a really flexible "typemap" system which allows you to control how types in C++ map to your scripting language. It comes with a decent set of defaults that will cover a lot of stuff for you, but having the ability to define your own mappings is extremely useful. The last project I did with Ruby integration would have been virtually impossible without this feature. It's not particularly easy to get your head round at first, but there's enough examples and documentation to get by.

Robustness wasn't an issue either. I was using it to generate a binding from an 16,000+ line interface file (several hundred classes) which resulted in a ~120,000 line binding implementation, and never had any problems with it. In fact, the only problem I had dealing at this scale was that Visual Studio really didn't like the 120,000 line source file (even though every other text editor I tried was quite happy with it).

One thing to note about SWIG is that it's really designed to build extensions for scripting languages, and not for embedding a scripting language into a C++ program, so the instructions are kind of geared towards extending. Having said that, you can use it for embedding (which is what I was doing) and it works very well for that.

It's also worth noting that it only deals with the scripting language's view onto the C++ program, and not the other way round. You can use some of the stuff it provides to access the scripting language from C++, but you'll probably need to write some sort of C++ wrapper for the scripting language yourself. Fortunately, this is normally pretty easy and doesn't usually require anything like the code generation required for the other direction.

Documentation: I really don't want to say anything negative about SWIG's documentation, because it really is a brilliant effort and clearly a lot of work has gone into it. The problem is that SWIG is so flexible that even the best documentation is going to leave you scratching your head on occasion, and this happened to me a few times. However, I think it's fair to say that I would have been scratching my head a lot more if the documentation wasn't as good as it was. It's certainly amongst the best documentation I've seen in an open source project.

All in all, I can happily say that if I ever decide to switch from embedding Ruby to some other language, then I'll be heading straight to SWIG again.

Oh, I've also use toLua in the past for Lua integration. It was small, simple and worked pretty well, but nowhere near as flexible as SWIG (although probably more than enough for many purposes). This was quite a few years ago, so I've no idea if it's still supported, or if it's more advanced now, or what.

I also know a few people who swear by Boost Python for Python integration, although I've never had any direct experience with it, so I can't really say much more than that.

HTH.

mouser:
i used Swig yesterday to wrap a DLL.
I have to say I was very impressed with it for the most part,
and at the same time terribly dissappointed at the lack of some mappings.

for example, if you look at their newsgroups youll see a bunch of people saying "hey can you use Swig to wrap c++ code for use in a c api" or ".. for a delphi api" or ".. for a vb.net api" and the response is usually "people have been asking for this for a year fairly regularly, it would be easy to do but no one has done it."

i may give it a try myself but it's kind of depressing that *the* wrapping tool above all others is missing some targets that would seem to me kinda obvious.  Wrapping c++ code for a plain vanilla c-interface DLL is sort of what i would consider the base case.  I don't understand why it doesn't exist.  It never ocurred to me that it wouldnt.

Of course it's not hard to get around this, by using Swig to output stuff for a dif language and stripping unnesc. stuff, and rewriting some simple stuff on the produced output, but it's annoying.

NeilS:
You're a hard man to please, Mouser. ;)

Yes, I can see it being disappointing for someone if it doesn't provide support for the language they want to use, but it can't support them all.

I'm a bit confused by your C DLL example though. If you want to wrap a C++ interface so that you can access it from C code, then you're talking about new C code, aren't you? What I mean by this is that you won't have an interface to the C++ code yet, so any C code which would use this interface cannot exist yet.

If that's the case, couldn't you just write a C++ DLL instead?

mouser:
I can see how what i said wasn't all that clear.
What I meant was that I have some classes with member functions that I wasn to expose as a standard DLL.
Because class datatypes are not safe accross languages, the solution is to basically create functions for creating objects and returning void* to them, and then creating new "proxy" functions that are called and passed the pointer to the function to work on.

Essentially this is what Swig does already.  It converts class member functions to global exported functions in a DLL that each have an additional variable that takes an object pointer to operate one.

so where in C++ you would do:

Cat* mycat = new Cat();
mycat.feed();

The wrapped C DLL would look like:

void *mycat = DLL->Cat_new();
DLL->Cat_feed(mycat);

Basically I can use Swig to create these wrapper/proxy classes by selecting a target language like C# and throwing away most of what gets produced, and changing some names and stuff, but it's confusing to me that no one has written a standard C DLL output emitter for Swig.  more than confusing.

Navigation

[0] Message Index

[#] Next page

Go to full version