{-# LANGUAGE ScopedTypeVariables #-} -- These are replacements for the broken equivalents in Foreign.*. -- The functions in Foreign.* do not obey the required alignment. module LLVM.Util.Foreign where import Foreign.Ptr(alignPtr, Ptr) import Foreign.Storable(Storable(poke, sizeOf, alignment)) import Foreign.Marshal.Alloc(allocaBytes) import Foreign.Marshal.Array(allocaArray, pokeArray) with :: Storable a => a -> (Ptr a -> IO b) -> IO b with x act = alloca $ \ p -> do poke p x act p alloca :: forall a b . Storable a => (Ptr a -> IO b) -> IO b alloca act = allocaBytes (2 * sizeOf (undefined :: a)) $ \ p -> act $ alignPtr p (alignment (undefined :: a)) withArrayLen :: (Storable a) => [a] -> (Int -> Ptr a -> IO b) -> IO b withArrayLen xs act = let l = length xs in allocaArray (l+1) $ \ p -> do let p' = alignPtr p (alignment (head xs)) pokeArray p' xs act l p'