[Haskell-cafe] Calling C function in Mac OS X
stefanor at cox.net
Sat Apr 14 12:06:31 EDT 2007
On Sat, Apr 14, 2007 at 07:58:25PM +0400, Sergey Perminov wrote:
> I wish to optimize Haskell code using ByteString, direct reading
> Doubles form it, direct writing Doubles to it.
> I've tried Don Stewart's code http://hpaste.org/26
> that uses calling to C functions to implement necessary readDouble &
> readDouble works ok.
> showDouble always return "nan" in Mac OS X (but works well in Windows).
> I'm using GHC 6.6 in Mac
> and in Windows (http://www.haskell.org/ghc/download_ghc_66.html#windows).
> I've made showInt based on showDouble: http://hpaste.org/1390
> It works well in Mac OS X.
> It seems that problem happens only when I send CDouble (or CLDouble)
> to C function.
> My conf: PowerBook G4, Mac OS X 10.4.9, powerpc-apple-darwin8-gcc-4.0.1
foreign import ccall unsafe "static stdio.h snprintf"
c_printf_double :: Ptr CChar -> CSize -> Ptr CChar -> CInt -> IO CInt
is illegal (and slow).
snprintf is a varargs function, and varargs functions are allowed to
use a completely different calling convention from non-varargs
functions. I'm pretty sure the FFI allows nasal demons for what you
just did, using a non-varargs call for a varargs function... In any
case the fundamental issue is i386 vs. ppc. i386 has so few registers
that everything is passed on the stack, and the ordinary convention
supports varargs too. ppc normally puts things in registers, but does
different stuff for varargs. There is no way to use varargs functions
from the FFI.
Also, snprintf is an INTERPRETER - you won't gain much if every time
you need to print a double you do a dynamic dispatch on the format
string! If you care about performance enough to be using the FFI at
all, you probably ought to hand-code the printer, not call snprintf.
More information about the Haskell-Cafe