1. Callback problem
- Posted by kbochert at copper.net Oct 12, 2002
- 391 views
>From: Andy Serpa <renegade at earthling.net> >Subject: RE: Wrapping C - Callback troubles Bernie Ryan wrote: > > Andy Serpa wrote: > > Here's another problem. I'm making the Berkeley DB wrapper= which allows > > for certain callback functions to be used. One particular= one I'm > > trying to set up is supposed to be a void function. The= callback works > > (my function is called), but when it returns a value (any= value) it > > crashes. (Callback functions are required to return= something.) >But that's not the problem. Setting the callback function is no= >problem, and my Euphoria function is being called with the= correct >args. >The problem is when my function exits (returns a value) the= whole >thing >crashes with an exception. I was just wondering is that because= it >is a >supposed to be void function? (It seems like I should be able= to >return >anything in that case, but maybe it wants me to return nothing?)= >Anybody know anything about that? This sounds like the cdecl-stdcall problem. Many packages that= come from the unix world expect the callback function to be cdecl= rather than the windows standard stdcall. If the callback is of the= wrong variety, the stack gets messed up. I modified Bach to accept cdecl callbacks -- under Euphoria I= think the easiest option is to modify the calling convention in the= source and re-compile the package. There probably is a way to fix it by poking assembly. Karl Bochert
2. Re: Callback problem
- Posted by stabmaster_ at hotmail.com Oct 13, 2002
- 354 views
>This sounds like the cdecl-stdcall problem. >... >There probably is a way to fix it by poking assembly. > >Karl Bochert I did just that in Glue, my GLUT wrapper for Euphoria. In glue.e there is a function called cdecl_callback that takes a routine_id and a sequence of parameter sizes (in bytes). E.g. if you have a function foo that takes 3 integer parameters, you'd do something like: atom my_callback my_callback = cdecl_callback(routine_id("foo"),{4,4,4,4}) Note that i passed 4 4's, this is intentionally. You see, there's a small problem: Since EIP is pushed on the stack after the parameters, you'll get the return address in the first parameter of your function. To get around this you must prepend a dummy argument to your function. I.e. if you had: function foo(integer a,integer b,integer c) You'd have to change it to: function foo(integer dummy,integer a,integer b,integer b)