module LLVM.ExecutionEngine.Target(TargetData(..), ourTargetData, targetDataFromString) where
import Foreign.C.String
import System.IO.Unsafe(unsafePerformIO)
import LLVM.ExecutionEngine.Engine(runEngineAccess, getExecutionEngineTargetData)
import qualified LLVM.FFI.Core as FFI
import qualified LLVM.FFI.Target as FFI
type Type = FFI.TypeRef
data TargetData = TargetData {
aBIAlignmentOfType :: Type -> Int,
aBISizeOfType :: Type -> Int,
littleEndian :: Bool,
callFrameAlignmentOfType :: Type -> Int,
intPtrType :: Type,
pointerSize :: Int,
preferredAlignmentOfType :: Type -> Int,
sizeOfTypeInBits :: Type -> Int,
storeSizeOfType :: Type -> Int
}
un :: IO a -> a
un = unsafePerformIO
ourEngineTargetDataRef :: FFI.TargetDataRef
ourEngineTargetDataRef = un $
runEngineAccess getExecutionEngineTargetData
makeTargetData :: FFI.TargetDataRef -> TargetData
makeTargetData r = TargetData {
aBIAlignmentOfType = fromIntegral . un . FFI.aBIAlignmentOfType r,
aBISizeOfType = fromIntegral . un . FFI.aBISizeOfType r,
littleEndian = un (FFI.byteOrder r) /= 0,
callFrameAlignmentOfType = fromIntegral . un . FFI.callFrameAlignmentOfType r,
intPtrType = un $ FFI.intPtrType r,
pointerSize = fromIntegral $ un $ FFI.pointerSize r,
preferredAlignmentOfType = fromIntegral . un . FFI.preferredAlignmentOfType r,
sizeOfTypeInBits = fromIntegral . un . FFI.sizeOfTypeInBits r,
storeSizeOfType = fromIntegral . un . FFI.storeSizeOfType r
}
ourTargetData :: TargetData
ourTargetData = makeTargetData ourEngineTargetDataRef
targetDataFromString :: String -> TargetData
targetDataFromString s = makeTargetData $ un $ withCString s FFI.createTargetData