simonmar at microsoft.com
Fri Dec 1 10:43:15 EST 2000
> I don't want to talk about [Char] -> [CChar] specifically, but the
> mention of efficiency reminds me of something that has been bothering
> me for a little while.
> In the current design of the FFI, it is assumed that most of the
> marshalling work is going to be done in Haskell. For example, to
> return more than one result from a C function, the results
> are packaged
> as a C struct, passed as an Addr (or Ptr) to Haskell, which then
> dereferences from the Addr to each individual component of the struct.
> Now in GHC, the treatment of the IO monad may make this acceptably
> fast, but in other implementations (like nhc98 (of course)), this
> is just horribly inefficient, and can slow up FFI calls by an order
> of magnitude or more. (Comparing to previous implementations using
> either the builtin 'primitive' mechanism or GreenCard.) I agree that
> it is better in principle to have the marshalling code in Haskell
> because it has much better type-safety than C. But in practice,
> I have found other ways to do the marshalling, mainly because of the
> efficiency question.
> Do other people have any thoughts about the efficiency of the current
The one thing that concerns me is the overhead of the malloc/free for
allocating the memory into which we marshal structs. This and the
overhead of installing an exception handler to free the memory in case
of an error.
GHC has ByteArrays which are more efficient (no explicit free, no need
for an exception handler), but they have the problem that they can move
around and therefore can only be passed to unsafe foreign calls.
However, I'd really like a way to integrate them into the current FFI
An alternative is to write our own memory allocator - we can't use
thread stacks, because they tend to move around too, but we could use a
static area of memory allocated in a stack-like fashion. This won't be
a huge win over malloc/free though.
I'm not too worried about the IO monad overhead, which is allegedly zero
in GHC and in fact speeds things up by virtue of being strict. Perhaps
the right thing to do in nhc98 is to make the IO monad more efficient?
More information about the FFI