Chipmunk and LuaJit FFI

Official forum for the Chipmunk2D Physics Library.
Post Reply
nyanonymous
Posts: 4
Joined: Fri Dec 16, 2011 11:27 pm
Contact:

Chipmunk and LuaJit FFI

Post by nyanonymous »

I'm trying to get chipmunk working thru the LuaJit FFI, but running into problems because many chipmunk functions (cpf* and cpv*) are declared static inline, which the LuaJit FFI can't handle. Is there some way to build chipmunk with the inline functions in the actual .so?

I'm just going to go ahead and patch the source, unless there is an easy way to do this already.

EDIT: oops, i just found chipmunk_ffi.h. I'll probably figure it out eventually, but just in case, how do I use it? I'm guessing recompile chipmunk with `-D CHIPMUNK_FFI`, and then `#define CHIPMUNK_FFI` to get the declarations? The functions will be prefixed with an underscore, right?

EDIT2: ok I put `-DCHIPMUNK_FFI` in the cflags, but that caused error messages:

Code: Select all

[ 12%] Building C object src/CMakeFiles/chipmunk.dir/chipmunk.c.o
In file included from /home/eee/builds/Chipmunk-6.0.1/src/chipmunk.c:170:0:
/home/eee/builds/Chipmunk-6.0.1/include/chipmunk/chipmunk_ffi.h:80:1: error: ‘cpShapeGetIsSensor’ undeclared here (not in a function)
/home/eee/builds/Chipmunk-6.0.1/include/chipmunk/chipmunk_ffi.h:80:1: error: ‘cpShapeSetIsSensor’ undeclared here (not in a function)
make[2]: *** [src/CMakeFiles/chipmunk.dir/chipmunk.c.o] Error 1
make[1]: *** [src/CMakeFiles/chipmunk.dir/all] Error 2
make: *** [all] Error 2
EDIT3: Ok so the problem was that chipmunk_ffi.h had something about IsSensor, when the actual function was just Sensor, so I fxed that and it compiled.

Now how do I get the include (#include "chipmunk/chipmunk.h") to have the correct declarations?

EDIT4: Neato! it worked:

Code: Select all

ffi.cdef[[
    double (*_cpfclamp)(double f, double min, double max);
]]
cp=ffi.load 'chipmunk'
print(cp._cpfclamp(5, -1, 2))
prints 2, as expected. Still have to do something about the header file declarations so I don't have to declare manually like this.
nyanonymous
Posts: 4
Joined: Fri Dec 16, 2011 11:27 pm
Contact:

Re: Chipmunk and LuaJit FFI

Post by nyanonymous »

I tried to get a luajit parsable header out of chipmunk, but it doesn't seem possible without a lot of manual work.

With SDL for example, it basically just works; you make a little stub that includes SDL.h, use cpp on it, remove a bunch of junk with grep, and then luaJit can eat it right up.

Trying the same with chipmunk hits quite a few bumps:
  • the little number suffixes (eg 1.0f) that chipmunk likes so much trip up luajit ffi.
  • luajit ffi doesn't like static constants like static const cpVect cpvzero = {0,0};
  • luajit ffi doesn't like the extra semicolons that seem to end up placed after one-liner inlines and inline-fixing MAKE_REF() macro expansions (I don't know why those are even there, because they aren't in the header code)
  • there's no clean way to get proper declarations for the CHIPMUNK_FFI inline function references (because __typeof__ is never going to work with luajit ffi), (also on this point, I think the global-function-pointer approach to dealing with the inlines actually ends up preventing luajit from inlining those functions (it might be able do that))
So I'm going to keep trying to get a .so with the inline functions and a header that luajit ffi can handle, but the result is probably going to be an ugly hack. When I get it all figured out, I'll post it, but in the future, there is a lot that chipmunk can do to make this easier.
Last edited by nyanonymous on Sat Dec 17, 2011 1:51 pm, edited 1 time in total.
nyanonymous
Posts: 4
Joined: Fri Dec 16, 2011 11:27 pm
Contact:

Re: Chipmunk and LuaJit FFI

Post by nyanonymous »

okie dokie. I got my ugly hack working!

First we generate a flattened header file. Then we generate a compileable C source file for the former inlines by removing the static inline part of the definitions. Also, we edit the flattened header to make declarations for luajit ffi and fix up some stuff that luajit doesn't like:

Code: Select all

echo '#include "chipmunk/chipmunk.h"' | cpp | grep -v '^#' > rawcpffi.h
sed -e 's/static inline //g' rawcpffi.h > cpinlines.c
cat rawcpffi.h | grep -v '^#' | grep -v 'static const'| sed -e 's/0f/0/g' | lua ffichipmunk.lua > cpffi.h
#we still have to edit cpffi.h to get rid of some spare semicolons that luajit doesn't like
#I'd like to figure out how to get rid of these automatically
The little lua program adds declarations for the former inlines to the header:

Code: Select all

ffiheader = io.input():read('*a')
print(ffiheader)
for decl in ffiheader:gmatch 'inline (.-%))' do
    print(decl..';')
end
And then we put cpinlines.c in with the other chipmunk source files and recompile. We give cpffi.h to the luajit ffi, and now we can finally use chipmunk thru the ffi:

Code: Select all

local ffi = require 'ffi'
ffi.cdef(io.open('cpffi.h', 'r'):read('*a'))
cp=ffi.load 'chipmunk'
print(cp.cpfclamp(5, -1, 2))
Again this just works. Yay!
Last edited by nyanonymous on Sat Dec 17, 2011 3:15 pm, edited 2 times in total.
User avatar
slembcke
Site Admin
Posts: 4166
Joined: Tue Aug 14, 2007 7:13 pm
Contact:

Re: Chipmunk and LuaJit FFI

Post by slembcke »

Wow. That's a lot to digest at the moment. I did change some of the formatting in the headers in Git a couple weeks ago to make the headers easier to parse with a regex to extract all the function prototypes. Maybe some of the changes I made will be beneficial to you. Send me a pull request if there are additional formatting changes you want me to consider.

Anyway, very cool! I've been eyeing LuaJIT for a while, it seems pretty neat. I keep bouncing back and forth between that and Chibi Scheme for what I want to use to script my next desktop game. LuaJIT is faster and possibly easier to set up the FFI stuff, but Scheme is just such a cool language. :D Again, very cool. If you get a project set up for it somewhere I can link to you from the Chipmunk website.
Can't sleep... Chipmunks will eat me...
Check out our latest projects! -> http://howlingmoonsoftware.com/wordpress/
nyanonymous
Posts: 4
Joined: Fri Dec 16, 2011 11:27 pm
Contact:

Re: Chipmunk and LuaJit FFI

Post by nyanonymous »

slembcke wrote:Anyway, very cool! I've been eyeing LuaJIT for a while, it seems pretty neat. I keep bouncing back and forth between that and Chibi Scheme for what I want to use to script my next desktop game. LuaJIT is faster and possibly easier to set up the FFI stuff, but Scheme is just such a cool language. :D Again, very cool. If you get a project set up for it somewhere I can link to you from the Chipmunk website.
For a long time I was looking for a sane scheme, that chibi scheme seems worth looking into. I'm now happily married to Lua, tho. I was going back and forth between lua and C for a while, but then the luajit ffi means I no longer need C for either libraries or speed, given that I can hack the headers well enough for the ffi (which is easier now, the semicolon and number issues were just fixed in luajit).

From my perspective, Luajit 2 + ffi looks like just about the best general purpose language you can get right now.

I imagine I'll eventually get this luajit-chipmunk thing more refined and tested and then I'll post it publicly and let you know. By that point I think it will be a nearly general ffi header generator, rather than a chipmunk specific thing. Anyways, I'll let you know.
User avatar
slembcke
Site Admin
Posts: 4166
Joined: Tue Aug 14, 2007 7:13 pm
Contact:

Re: Chipmunk and LuaJit FFI

Post by slembcke »

Ok. Well let me know. :)
Can't sleep... Chipmunks will eat me...
Check out our latest projects! -> http://howlingmoonsoftware.com/wordpress/
Post Reply

Who is online

Users browsing this forum: No registered users and 32 guests