Re: Sending messages without knowing number of args and types at compile time
Re: Sending messages without knowing number of args and types at compile time
- Subject: Re: Sending messages without knowing number of args and types at compile time
- From: Michael Ash <email@hidden>
- Date: Mon, 1 Feb 2010 14:19:37 -0500
On Mon, Feb 1, 2010 at 6:30 AM, Per Bull Holmen <email@hidden> wrote:
> Hi
>
> I've been playing around with the idea of making a simple bridge between Objective-C (running under Cocoa) and a script language. Not for the API, that is, but for user defined classes and methods. For this reason, I'd like to know whether there are any other ways than NSInvocation to send a message without knowing arg types and numbers at compile time. Non-hackish ways, that is. I see that people used objc_msgSendv earlier, but it is no longer available in Objective-C 2.0. Also, using objc_msgSend doesn't seem to be platform independent (PPC/Intel). So, does this mean that NSInvocation is the only civilised way to go? NSInvocation is great, it's just that there's a lot of overhead, so I assume this is because it has functionality I might not need?
NSInvocation is the only mechanism provided by Cocoa where you can
write code and have it be completely future-proof.
Sending an Objective-C message is equivalent to calling a C function,
and there's no portable way to do that with arbitrary arguments.
NSInvocation handles all the nasty business for you and gives you a
nice API. The downside is that it's really slow, as you've seen.
My first recommendation would be to look at an existing bridge and see
how they do it. Off the top of my head, there's PyObjC, CamelBones,
and RubyCocoa.
I haven't written a bridge, but here are a few ideas anyway.
Since what you ultimately need is fast C function calling with
arbitrary arguments, see what's available to do that. I think that
libffi is probably your best bet here, although I've never used it.
You will have to write more code for this, and possibly encode some
platform-specific conventions as well. For example, you need to call
the _stret version of objc_msgSend if the function (method) uses
struct return calling conventions, but small structs use the normal
calling convention, and the boundary between "small" and regular
depends on the platform you use. Libffi *may* be able to help you
figure out which is which, since it has to know this stuff too.
If you really want to go nuts, you can build trampolines at runtime
using LLVM. This will give you the speed of native code (once you take
the hit of JITting the trampolines), although the complexity of the
code gets pretty intense. (It's not as bad as "JIT" might make it
sound, but a lot worse than NSInvocation....) If you're interested in
this, I have an example where LLVM is put to use for something
somewhat similar here:
http://www.mikeash.com/?page=pyblog/friday-qa-2009-04-24-code-generation-with-llvm-part-2-fast-objective-c-forwarding.html
Mike
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden