{-# LANGUAGE GeneralizedNewtypeDeriving, FlexibleContexts #-}
-- |various common data-passing conventions
module Foreign.Ptr.Conventions where

-- TODO: make these all exception-safe
-- TODO: reverse order of 'out' returns
-- TODO: bytestring versions?  versions allocating by byte but using vectors?
import Foreign.C.Types
import Foreign.Marshal
import Foreign.Ptr
import Foreign.ForeignPtr
import Foreign.Storable

import Control.Monad.IO.Class
import Control.Monad.Trans.Control
import Control.Exception.Lifted

import qualified Data.ByteString as BS
import qualified Data.Vector.Storable as SV
import qualified Data.Vector.Storable.Mutable as SVM

class WrappedPtr p where
    wrapPtr         :: Ptr a -> p a
    unwrapPtr       :: p a -> Ptr a
    nullWrappedPtr  :: p a
    nullWrappedPtr = Ptr a -> p a
forall a. Ptr a -> p a
forall (p :: * -> *) a. WrappedPtr p => Ptr a -> p a
wrapPtr Ptr a
forall a. Ptr a
nullPtr
    castWrappedPtr  :: p a -> p b
    castWrappedPtr = Ptr b -> p b
forall a. Ptr a -> p a
forall (p :: * -> *) a. WrappedPtr p => Ptr a -> p a
wrapPtr (Ptr b -> p b) -> (p a -> Ptr b) -> p a -> p b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> Ptr b
forall a b. Ptr a -> Ptr b
castPtr (Ptr a -> Ptr b) -> (p a -> Ptr a) -> p a -> Ptr b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. p a -> Ptr a
forall a. p a -> Ptr a
forall (p :: * -> *) a. WrappedPtr p => p a -> Ptr a
unwrapPtr

instance WrappedPtr Foreign.Ptr.Ptr where
    wrapPtr :: forall a. Ptr a -> Ptr a
wrapPtr         = Ptr a -> Ptr a
forall a. a -> a
id
    unwrapPtr :: forall a. Ptr a -> Ptr a
unwrapPtr       = Ptr a -> Ptr a
forall a. a -> a
id
    nullWrappedPtr :: forall a. Ptr a
nullWrappedPtr  = Ptr a
forall a. Ptr a
nullPtr
    castWrappedPtr :: forall a b. Ptr a -> Ptr b
castWrappedPtr  = Ptr a -> Ptr b
forall a b. Ptr a -> Ptr b
castPtr

-- * Input pointers

-- |In by-ref parameter; memory is allocated and freed by caller
newtype In       a = In       (Ptr a) deriving (In a -> In a -> Bool
(In a -> In a -> Bool) -> (In a -> In a -> Bool) -> Eq (In a)
forall a. In a -> In a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. In a -> In a -> Bool
== :: In a -> In a -> Bool
$c/= :: forall a. In a -> In a -> Bool
/= :: In a -> In a -> Bool
Eq, Eq (In a)
Eq (In a) =>
(In a -> In a -> Ordering)
-> (In a -> In a -> Bool)
-> (In a -> In a -> Bool)
-> (In a -> In a -> Bool)
-> (In a -> In a -> Bool)
-> (In a -> In a -> In a)
-> (In a -> In a -> In a)
-> Ord (In a)
In a -> In a -> Bool
In a -> In a -> Ordering
In a -> In a -> In a
forall a. Eq (In a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. In a -> In a -> Bool
forall a. In a -> In a -> Ordering
forall a. In a -> In a -> In a
$ccompare :: forall a. In a -> In a -> Ordering
compare :: In a -> In a -> Ordering
$c< :: forall a. In a -> In a -> Bool
< :: In a -> In a -> Bool
$c<= :: forall a. In a -> In a -> Bool
<= :: In a -> In a -> Bool
$c> :: forall a. In a -> In a -> Bool
> :: In a -> In a -> Bool
$c>= :: forall a. In a -> In a -> Bool
>= :: In a -> In a -> Bool
$cmax :: forall a. In a -> In a -> In a
max :: In a -> In a -> In a
$cmin :: forall a. In a -> In a -> In a
min :: In a -> In a -> In a
Ord, Int -> In a -> ShowS
[In a] -> ShowS
In a -> String
(Int -> In a -> ShowS)
-> (In a -> String) -> ([In a] -> ShowS) -> Show (In a)
forall a. Int -> In a -> ShowS
forall a. [In a] -> ShowS
forall a. In a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> In a -> ShowS
showsPrec :: Int -> In a -> ShowS
$cshow :: forall a. In a -> String
show :: In a -> String
$cshowList :: forall a. [In a] -> ShowS
showList :: [In a] -> ShowS
Show, Ptr (In a) -> IO (In a)
Ptr (In a) -> Int -> IO (In a)
Ptr (In a) -> Int -> In a -> IO ()
Ptr (In a) -> In a -> IO ()
In a -> Int
(In a -> Int)
-> (In a -> Int)
-> (Ptr (In a) -> Int -> IO (In a))
-> (Ptr (In a) -> Int -> In a -> IO ())
-> (forall b. Ptr b -> Int -> IO (In a))
-> (forall b. Ptr b -> Int -> In a -> IO ())
-> (Ptr (In a) -> IO (In a))
-> (Ptr (In a) -> In a -> IO ())
-> Storable (In a)
forall b. Ptr b -> Int -> IO (In a)
forall b. Ptr b -> Int -> In a -> IO ()
forall a. Ptr (In a) -> IO (In a)
forall a. Ptr (In a) -> Int -> IO (In a)
forall a. Ptr (In a) -> Int -> In a -> IO ()
forall a. Ptr (In a) -> In a -> IO ()
forall a. In a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (In a)
forall a b. Ptr b -> Int -> In a -> IO ()
$csizeOf :: forall a. In a -> Int
sizeOf :: In a -> Int
$calignment :: forall a. In a -> Int
alignment :: In a -> Int
$cpeekElemOff :: forall a. Ptr (In a) -> Int -> IO (In a)
peekElemOff :: Ptr (In a) -> Int -> IO (In a)
$cpokeElemOff :: forall a. Ptr (In a) -> Int -> In a -> IO ()
pokeElemOff :: Ptr (In a) -> Int -> In a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (In a)
peekByteOff :: forall b. Ptr b -> Int -> IO (In a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> In a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> In a -> IO ()
$cpeek :: forall a. Ptr (In a) -> IO (In a)
peek :: Ptr (In a) -> IO (In a)
$cpoke :: forall a. Ptr (In a) -> In a -> IO ()
poke :: Ptr (In a) -> In a -> IO ()
Storable, (forall a. Ptr a -> In a)
-> (forall a. In a -> Ptr a)
-> (forall a. In a)
-> (forall a b. In a -> In b)
-> WrappedPtr In
forall a. In a
forall a. Ptr a -> In a
forall a. In a -> Ptr a
forall a b. In a -> In b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> In a
wrapPtr :: forall a. Ptr a -> In a
$cunwrapPtr :: forall a. In a -> Ptr a
unwrapPtr :: forall a. In a -> Ptr a
$cnullWrappedPtr :: forall a. In a
nullWrappedPtr :: forall a. In a
$ccastWrappedPtr :: forall a b. In a -> In b
castWrappedPtr :: forall a b. In a -> In b
WrappedPtr)

-- |In by-ref array; memory is allocated and freed by caller
newtype InArray  a = InArray  (Ptr a) deriving (InArray a -> InArray a -> Bool
(InArray a -> InArray a -> Bool)
-> (InArray a -> InArray a -> Bool) -> Eq (InArray a)
forall a. InArray a -> InArray a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. InArray a -> InArray a -> Bool
== :: InArray a -> InArray a -> Bool
$c/= :: forall a. InArray a -> InArray a -> Bool
/= :: InArray a -> InArray a -> Bool
Eq, Eq (InArray a)
Eq (InArray a) =>
(InArray a -> InArray a -> Ordering)
-> (InArray a -> InArray a -> Bool)
-> (InArray a -> InArray a -> Bool)
-> (InArray a -> InArray a -> Bool)
-> (InArray a -> InArray a -> Bool)
-> (InArray a -> InArray a -> InArray a)
-> (InArray a -> InArray a -> InArray a)
-> Ord (InArray a)
InArray a -> InArray a -> Bool
InArray a -> InArray a -> Ordering
InArray a -> InArray a -> InArray a
forall a. Eq (InArray a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. InArray a -> InArray a -> Bool
forall a. InArray a -> InArray a -> Ordering
forall a. InArray a -> InArray a -> InArray a
$ccompare :: forall a. InArray a -> InArray a -> Ordering
compare :: InArray a -> InArray a -> Ordering
$c< :: forall a. InArray a -> InArray a -> Bool
< :: InArray a -> InArray a -> Bool
$c<= :: forall a. InArray a -> InArray a -> Bool
<= :: InArray a -> InArray a -> Bool
$c> :: forall a. InArray a -> InArray a -> Bool
> :: InArray a -> InArray a -> Bool
$c>= :: forall a. InArray a -> InArray a -> Bool
>= :: InArray a -> InArray a -> Bool
$cmax :: forall a. InArray a -> InArray a -> InArray a
max :: InArray a -> InArray a -> InArray a
$cmin :: forall a. InArray a -> InArray a -> InArray a
min :: InArray a -> InArray a -> InArray a
Ord, Int -> InArray a -> ShowS
[InArray a] -> ShowS
InArray a -> String
(Int -> InArray a -> ShowS)
-> (InArray a -> String)
-> ([InArray a] -> ShowS)
-> Show (InArray a)
forall a. Int -> InArray a -> ShowS
forall a. [InArray a] -> ShowS
forall a. InArray a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> InArray a -> ShowS
showsPrec :: Int -> InArray a -> ShowS
$cshow :: forall a. InArray a -> String
show :: InArray a -> String
$cshowList :: forall a. [InArray a] -> ShowS
showList :: [InArray a] -> ShowS
Show, Ptr (InArray a) -> IO (InArray a)
Ptr (InArray a) -> Int -> IO (InArray a)
Ptr (InArray a) -> Int -> InArray a -> IO ()
Ptr (InArray a) -> InArray a -> IO ()
InArray a -> Int
(InArray a -> Int)
-> (InArray a -> Int)
-> (Ptr (InArray a) -> Int -> IO (InArray a))
-> (Ptr (InArray a) -> Int -> InArray a -> IO ())
-> (forall b. Ptr b -> Int -> IO (InArray a))
-> (forall b. Ptr b -> Int -> InArray a -> IO ())
-> (Ptr (InArray a) -> IO (InArray a))
-> (Ptr (InArray a) -> InArray a -> IO ())
-> Storable (InArray a)
forall b. Ptr b -> Int -> IO (InArray a)
forall b. Ptr b -> Int -> InArray a -> IO ()
forall a. Ptr (InArray a) -> IO (InArray a)
forall a. Ptr (InArray a) -> Int -> IO (InArray a)
forall a. Ptr (InArray a) -> Int -> InArray a -> IO ()
forall a. Ptr (InArray a) -> InArray a -> IO ()
forall a. InArray a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (InArray a)
forall a b. Ptr b -> Int -> InArray a -> IO ()
$csizeOf :: forall a. InArray a -> Int
sizeOf :: InArray a -> Int
$calignment :: forall a. InArray a -> Int
alignment :: InArray a -> Int
$cpeekElemOff :: forall a. Ptr (InArray a) -> Int -> IO (InArray a)
peekElemOff :: Ptr (InArray a) -> Int -> IO (InArray a)
$cpokeElemOff :: forall a. Ptr (InArray a) -> Int -> InArray a -> IO ()
pokeElemOff :: Ptr (InArray a) -> Int -> InArray a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (InArray a)
peekByteOff :: forall b. Ptr b -> Int -> IO (InArray a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> InArray a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> InArray a -> IO ()
$cpeek :: forall a. Ptr (InArray a) -> IO (InArray a)
peek :: Ptr (InArray a) -> IO (InArray a)
$cpoke :: forall a. Ptr (InArray a) -> InArray a -> IO ()
poke :: Ptr (InArray a) -> InArray a -> IO ()
Storable, (forall a. Ptr a -> InArray a)
-> (forall a. InArray a -> Ptr a)
-> (forall a. InArray a)
-> (forall a b. InArray a -> InArray b)
-> WrappedPtr InArray
forall a. InArray a
forall a. Ptr a -> InArray a
forall a. InArray a -> Ptr a
forall a b. InArray a -> InArray b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> InArray a
wrapPtr :: forall a. Ptr a -> InArray a
$cunwrapPtr :: forall a. InArray a -> Ptr a
unwrapPtr :: forall a. InArray a -> Ptr a
$cnullWrappedPtr :: forall a. InArray a
nullWrappedPtr :: forall a. InArray a
$ccastWrappedPtr :: forall a b. InArray a -> InArray b
castWrappedPtr :: forall a b. InArray a -> InArray b
WrappedPtr)

withIn :: (Storable a, MonadBaseControl IO m) => a -> (In a -> m b) -> m b
withIn :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m) =>
a -> (In a -> m b) -> m b
withIn a
x In a -> m b
f = ((Ptr a -> IO (StM m b)) -> IO (StM m b)) -> (Ptr a -> m b) -> m b
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (a -> (Ptr a -> IO (StM m b)) -> IO (StM m b)
forall a b. Storable a => a -> (Ptr a -> IO b) -> IO b
with a
x) (In a -> m b
f (In a -> m b) -> (Ptr a -> In a) -> Ptr a -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> In a
forall a. Ptr a -> In a
In)

withInList :: (Storable a, MonadBaseControl IO m) => [a] -> (InArray a -> m b) -> m b
withInList :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m) =>
[a] -> (InArray a -> m b) -> m b
withInList [a]
xs InArray a -> m b
f = ((Ptr a -> IO (StM m b)) -> IO (StM m b)) -> (Ptr a -> m b) -> m b
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp ([a] -> (Ptr a -> IO (StM m b)) -> IO (StM m b)
forall a b. Storable a => [a] -> (Ptr a -> IO b) -> IO b
withArray [a]
xs) (InArray a -> m b
f (InArray a -> m b) -> (Ptr a -> InArray a) -> Ptr a -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> InArray a
forall a. Ptr a -> InArray a
InArray)

withInVector :: (Storable a, MonadBaseControl IO m) => SV.Vector a -> (InArray a -> m b) -> m b
withInVector :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m) =>
Vector a -> (InArray a -> m b) -> m b
withInVector Vector a
vec InArray a -> m b
f = ((Ptr a -> IO (StM m b)) -> IO (StM m b)) -> (Ptr a -> m b) -> m b
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Vector a -> (Ptr a -> IO (StM m b)) -> IO (StM m b)
forall a b. Storable a => Vector a -> (Ptr a -> IO b) -> IO b
SV.unsafeWith Vector a
vec) (InArray a -> m b
f (InArray a -> m b) -> (Ptr a -> InArray a) -> Ptr a -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> InArray a
forall a. Ptr a -> InArray a
InArray)

withInMVector :: (Storable a, MonadBaseControl IO m) => SVM.IOVector a -> (InArray a -> m b) -> m b
withInMVector :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m) =>
IOVector a -> (InArray a -> m b) -> m b
withInMVector IOVector a
vec InArray a -> m b
f = ((Ptr a -> IO (StM m b)) -> IO (StM m b)) -> (Ptr a -> m b) -> m b
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (IOVector a -> (Ptr a -> IO (StM m b)) -> IO (StM m b)
forall a b. Storable a => IOVector a -> (Ptr a -> IO b) -> IO b
SVM.unsafeWith IOVector a
vec) (InArray a -> m b
f (InArray a -> m b) -> (Ptr a -> InArray a) -> Ptr a -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> InArray a
forall a. Ptr a -> InArray a
InArray)

-- * Output pointers

-- |Out by-ref parameter; memory is allocated and freed by caller
newtype Out      a = Out      (Ptr a) deriving (Out a -> Out a -> Bool
(Out a -> Out a -> Bool) -> (Out a -> Out a -> Bool) -> Eq (Out a)
forall a. Out a -> Out a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. Out a -> Out a -> Bool
== :: Out a -> Out a -> Bool
$c/= :: forall a. Out a -> Out a -> Bool
/= :: Out a -> Out a -> Bool
Eq, Eq (Out a)
Eq (Out a) =>
(Out a -> Out a -> Ordering)
-> (Out a -> Out a -> Bool)
-> (Out a -> Out a -> Bool)
-> (Out a -> Out a -> Bool)
-> (Out a -> Out a -> Bool)
-> (Out a -> Out a -> Out a)
-> (Out a -> Out a -> Out a)
-> Ord (Out a)
Out a -> Out a -> Bool
Out a -> Out a -> Ordering
Out a -> Out a -> Out a
forall a. Eq (Out a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. Out a -> Out a -> Bool
forall a. Out a -> Out a -> Ordering
forall a. Out a -> Out a -> Out a
$ccompare :: forall a. Out a -> Out a -> Ordering
compare :: Out a -> Out a -> Ordering
$c< :: forall a. Out a -> Out a -> Bool
< :: Out a -> Out a -> Bool
$c<= :: forall a. Out a -> Out a -> Bool
<= :: Out a -> Out a -> Bool
$c> :: forall a. Out a -> Out a -> Bool
> :: Out a -> Out a -> Bool
$c>= :: forall a. Out a -> Out a -> Bool
>= :: Out a -> Out a -> Bool
$cmax :: forall a. Out a -> Out a -> Out a
max :: Out a -> Out a -> Out a
$cmin :: forall a. Out a -> Out a -> Out a
min :: Out a -> Out a -> Out a
Ord, Int -> Out a -> ShowS
[Out a] -> ShowS
Out a -> String
(Int -> Out a -> ShowS)
-> (Out a -> String) -> ([Out a] -> ShowS) -> Show (Out a)
forall a. Int -> Out a -> ShowS
forall a. [Out a] -> ShowS
forall a. Out a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> Out a -> ShowS
showsPrec :: Int -> Out a -> ShowS
$cshow :: forall a. Out a -> String
show :: Out a -> String
$cshowList :: forall a. [Out a] -> ShowS
showList :: [Out a] -> ShowS
Show, Ptr (Out a) -> IO (Out a)
Ptr (Out a) -> Int -> IO (Out a)
Ptr (Out a) -> Int -> Out a -> IO ()
Ptr (Out a) -> Out a -> IO ()
Out a -> Int
(Out a -> Int)
-> (Out a -> Int)
-> (Ptr (Out a) -> Int -> IO (Out a))
-> (Ptr (Out a) -> Int -> Out a -> IO ())
-> (forall b. Ptr b -> Int -> IO (Out a))
-> (forall b. Ptr b -> Int -> Out a -> IO ())
-> (Ptr (Out a) -> IO (Out a))
-> (Ptr (Out a) -> Out a -> IO ())
-> Storable (Out a)
forall b. Ptr b -> Int -> IO (Out a)
forall b. Ptr b -> Int -> Out a -> IO ()
forall a. Ptr (Out a) -> IO (Out a)
forall a. Ptr (Out a) -> Int -> IO (Out a)
forall a. Ptr (Out a) -> Int -> Out a -> IO ()
forall a. Ptr (Out a) -> Out a -> IO ()
forall a. Out a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (Out a)
forall a b. Ptr b -> Int -> Out a -> IO ()
$csizeOf :: forall a. Out a -> Int
sizeOf :: Out a -> Int
$calignment :: forall a. Out a -> Int
alignment :: Out a -> Int
$cpeekElemOff :: forall a. Ptr (Out a) -> Int -> IO (Out a)
peekElemOff :: Ptr (Out a) -> Int -> IO (Out a)
$cpokeElemOff :: forall a. Ptr (Out a) -> Int -> Out a -> IO ()
pokeElemOff :: Ptr (Out a) -> Int -> Out a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (Out a)
peekByteOff :: forall b. Ptr b -> Int -> IO (Out a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> Out a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> Out a -> IO ()
$cpeek :: forall a. Ptr (Out a) -> IO (Out a)
peek :: Ptr (Out a) -> IO (Out a)
$cpoke :: forall a. Ptr (Out a) -> Out a -> IO ()
poke :: Ptr (Out a) -> Out a -> IO ()
Storable, (forall a. Ptr a -> Out a)
-> (forall a. Out a -> Ptr a)
-> (forall a. Out a)
-> (forall a b. Out a -> Out b)
-> WrappedPtr Out
forall a. Out a
forall a. Ptr a -> Out a
forall a. Out a -> Ptr a
forall a b. Out a -> Out b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> Out a
wrapPtr :: forall a. Ptr a -> Out a
$cunwrapPtr :: forall a. Out a -> Ptr a
unwrapPtr :: forall a. Out a -> Ptr a
$cnullWrappedPtr :: forall a. Out a
nullWrappedPtr :: forall a. Out a
$ccastWrappedPtr :: forall a b. Out a -> Out b
castWrappedPtr :: forall a b. Out a -> Out b
WrappedPtr)

-- |Out by-ref array; length is specified by caller, memory is allocated
-- and freed by caller
newtype OutArray a = OutArray (Ptr a) deriving (OutArray a -> OutArray a -> Bool
(OutArray a -> OutArray a -> Bool)
-> (OutArray a -> OutArray a -> Bool) -> Eq (OutArray a)
forall a. OutArray a -> OutArray a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. OutArray a -> OutArray a -> Bool
== :: OutArray a -> OutArray a -> Bool
$c/= :: forall a. OutArray a -> OutArray a -> Bool
/= :: OutArray a -> OutArray a -> Bool
Eq, Eq (OutArray a)
Eq (OutArray a) =>
(OutArray a -> OutArray a -> Ordering)
-> (OutArray a -> OutArray a -> Bool)
-> (OutArray a -> OutArray a -> Bool)
-> (OutArray a -> OutArray a -> Bool)
-> (OutArray a -> OutArray a -> Bool)
-> (OutArray a -> OutArray a -> OutArray a)
-> (OutArray a -> OutArray a -> OutArray a)
-> Ord (OutArray a)
OutArray a -> OutArray a -> Bool
OutArray a -> OutArray a -> Ordering
OutArray a -> OutArray a -> OutArray a
forall a. Eq (OutArray a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. OutArray a -> OutArray a -> Bool
forall a. OutArray a -> OutArray a -> Ordering
forall a. OutArray a -> OutArray a -> OutArray a
$ccompare :: forall a. OutArray a -> OutArray a -> Ordering
compare :: OutArray a -> OutArray a -> Ordering
$c< :: forall a. OutArray a -> OutArray a -> Bool
< :: OutArray a -> OutArray a -> Bool
$c<= :: forall a. OutArray a -> OutArray a -> Bool
<= :: OutArray a -> OutArray a -> Bool
$c> :: forall a. OutArray a -> OutArray a -> Bool
> :: OutArray a -> OutArray a -> Bool
$c>= :: forall a. OutArray a -> OutArray a -> Bool
>= :: OutArray a -> OutArray a -> Bool
$cmax :: forall a. OutArray a -> OutArray a -> OutArray a
max :: OutArray a -> OutArray a -> OutArray a
$cmin :: forall a. OutArray a -> OutArray a -> OutArray a
min :: OutArray a -> OutArray a -> OutArray a
Ord, Int -> OutArray a -> ShowS
[OutArray a] -> ShowS
OutArray a -> String
(Int -> OutArray a -> ShowS)
-> (OutArray a -> String)
-> ([OutArray a] -> ShowS)
-> Show (OutArray a)
forall a. Int -> OutArray a -> ShowS
forall a. [OutArray a] -> ShowS
forall a. OutArray a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> OutArray a -> ShowS
showsPrec :: Int -> OutArray a -> ShowS
$cshow :: forall a. OutArray a -> String
show :: OutArray a -> String
$cshowList :: forall a. [OutArray a] -> ShowS
showList :: [OutArray a] -> ShowS
Show, Ptr (OutArray a) -> IO (OutArray a)
Ptr (OutArray a) -> Int -> IO (OutArray a)
Ptr (OutArray a) -> Int -> OutArray a -> IO ()
Ptr (OutArray a) -> OutArray a -> IO ()
OutArray a -> Int
(OutArray a -> Int)
-> (OutArray a -> Int)
-> (Ptr (OutArray a) -> Int -> IO (OutArray a))
-> (Ptr (OutArray a) -> Int -> OutArray a -> IO ())
-> (forall b. Ptr b -> Int -> IO (OutArray a))
-> (forall b. Ptr b -> Int -> OutArray a -> IO ())
-> (Ptr (OutArray a) -> IO (OutArray a))
-> (Ptr (OutArray a) -> OutArray a -> IO ())
-> Storable (OutArray a)
forall b. Ptr b -> Int -> IO (OutArray a)
forall b. Ptr b -> Int -> OutArray a -> IO ()
forall a. Ptr (OutArray a) -> IO (OutArray a)
forall a. Ptr (OutArray a) -> Int -> IO (OutArray a)
forall a. Ptr (OutArray a) -> Int -> OutArray a -> IO ()
forall a. Ptr (OutArray a) -> OutArray a -> IO ()
forall a. OutArray a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (OutArray a)
forall a b. Ptr b -> Int -> OutArray a -> IO ()
$csizeOf :: forall a. OutArray a -> Int
sizeOf :: OutArray a -> Int
$calignment :: forall a. OutArray a -> Int
alignment :: OutArray a -> Int
$cpeekElemOff :: forall a. Ptr (OutArray a) -> Int -> IO (OutArray a)
peekElemOff :: Ptr (OutArray a) -> Int -> IO (OutArray a)
$cpokeElemOff :: forall a. Ptr (OutArray a) -> Int -> OutArray a -> IO ()
pokeElemOff :: Ptr (OutArray a) -> Int -> OutArray a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (OutArray a)
peekByteOff :: forall b. Ptr b -> Int -> IO (OutArray a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> OutArray a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> OutArray a -> IO ()
$cpeek :: forall a. Ptr (OutArray a) -> IO (OutArray a)
peek :: Ptr (OutArray a) -> IO (OutArray a)
$cpoke :: forall a. Ptr (OutArray a) -> OutArray a -> IO ()
poke :: Ptr (OutArray a) -> OutArray a -> IO ()
Storable, (forall a. Ptr a -> OutArray a)
-> (forall a. OutArray a -> Ptr a)
-> (forall a. OutArray a)
-> (forall a b. OutArray a -> OutArray b)
-> WrappedPtr OutArray
forall a. OutArray a
forall a. Ptr a -> OutArray a
forall a. OutArray a -> Ptr a
forall a b. OutArray a -> OutArray b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> OutArray a
wrapPtr :: forall a. Ptr a -> OutArray a
$cunwrapPtr :: forall a. OutArray a -> Ptr a
unwrapPtr :: forall a. OutArray a -> Ptr a
$cnullWrappedPtr :: forall a. OutArray a
nullWrappedPtr :: forall a. OutArray a
$ccastWrappedPtr :: forall a b. OutArray a -> OutArray b
castWrappedPtr :: forall a b. OutArray a -> OutArray b
WrappedPtr)

withOut :: (Storable a, MonadBaseControl IO m, MonadIO m) => (Out a -> m b) -> m (a,b)
withOut :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m, MonadIO m) =>
(Out a -> m b) -> m (a, b)
withOut Out a -> m b
f = ((Ptr a -> IO (StM m (a, b))) -> IO (StM m (a, b)))
-> (Ptr a -> m (a, b)) -> m (a, b)
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Ptr a -> IO (StM m (a, b))) -> IO (StM m (a, b))
forall a b. Storable a => (Ptr a -> IO b) -> IO b
alloca ((Ptr a -> m (a, b)) -> m (a, b))
-> (Ptr a -> m (a, b)) -> m (a, b)
forall a b. (a -> b) -> a -> b
$ \Ptr a
p -> do
    b <- Out a -> m b
f (Ptr a -> Out a
forall a. Ptr a -> Out a
Out Ptr a
p)
    a <- liftIO (peek p)
    return (a,b)

withMaybeOut :: (Storable a, MonadBaseControl IO m, MonadIO m) => (Out a -> m Bool) -> m (Maybe a)
withMaybeOut :: forall a (m :: * -> *).
(Storable a, MonadBaseControl IO m, MonadIO m) =>
(Out a -> m Bool) -> m (Maybe a)
withMaybeOut Out a -> m Bool
f = ((Ptr a -> IO (StM m (Maybe a))) -> IO (StM m (Maybe a)))
-> (Ptr a -> m (Maybe a)) -> m (Maybe a)
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Ptr a -> IO (StM m (Maybe a))) -> IO (StM m (Maybe a))
forall a b. Storable a => (Ptr a -> IO b) -> IO b
alloca ((Ptr a -> m (Maybe a)) -> m (Maybe a))
-> (Ptr a -> m (Maybe a)) -> m (Maybe a)
forall a b. (a -> b) -> a -> b
$ \Ptr a
p -> do
    success <- Out a -> m Bool
f (Ptr a -> Out a
forall a. Ptr a -> Out a
Out Ptr a
p)
    if success
        then do
            a <- liftIO (peek p)
            return (Just a)
        else return Nothing

withOut_ :: (Storable a, MonadBaseControl IO m, MonadIO m) => (Out a -> m b) -> m a
withOut_ :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m, MonadIO m) =>
(Out a -> m b) -> m a
withOut_ Out a -> m b
f = ((Ptr a -> IO (StM m a)) -> IO (StM m a)) -> (Ptr a -> m a) -> m a
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Ptr a -> IO (StM m a)) -> IO (StM m a)
forall a b. Storable a => (Ptr a -> IO b) -> IO b
alloca ((Ptr a -> m a) -> m a) -> (Ptr a -> m a) -> m a
forall a b. (a -> b) -> a -> b
$ \Ptr a
p -> do
    _ <- Out a -> m b
f (Ptr a -> Out a
forall a. Ptr a -> Out a
Out Ptr a
p)
    liftIO (peek p)

withOutMVector :: (Storable a, MonadBaseControl IO m) => SVM.IOVector a -> (Int -> OutArray a -> m b) -> m b
withOutMVector :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m) =>
IOVector a -> (Int -> OutArray a -> m b) -> m b
withOutMVector IOVector a
vec Int -> OutArray a -> m b
f =
    ((Ptr a -> IO (StM m b)) -> IO (StM m b)) -> (Ptr a -> m b) -> m b
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (IOVector a -> (Ptr a -> IO (StM m b)) -> IO (StM m b)
forall a b. Storable a => IOVector a -> (Ptr a -> IO b) -> IO b
SVM.unsafeWith IOVector a
vec) (Int -> OutArray a -> m b
f (IOVector a -> Int
forall a s. Storable a => MVector s a -> Int
SVM.length IOVector a
vec) (OutArray a -> m b) -> (Ptr a -> OutArray a) -> Ptr a -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ptr a -> OutArray a
forall a. Ptr a -> OutArray a
OutArray)

withOutVector :: (Storable a, MonadBaseControl IO m, MonadIO m) => Int -> (OutArray a -> m b) -> m (SV.Vector a, b)
withOutVector :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m, MonadIO m) =>
Int -> (OutArray a -> m b) -> m (Vector a, b)
withOutVector Int
n OutArray a -> m b
f = do
    p <- IO (ForeignPtr a) -> m (ForeignPtr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (ForeignPtr a)
forall a. Storable a => Int -> IO (ForeignPtr a)
mallocForeignPtrArray Int
n)
    b <- liftBaseOp (withForeignPtr p) (f . OutArray)
    return (SV.unsafeFromForeignPtr p 0 n, b)


-- NOTE: withOutVector_ and withOutVector' don't typecheck unless you specify the monad type as IO

withOutVector_ :: (Storable a) => Int -> (OutArray a -> IO b) -> IO (SV.Vector a)
withOutVector_ :: forall a b.
Storable a =>
Int -> (OutArray a -> IO b) -> IO (Vector a)
withOutVector_ Int
n OutArray a -> IO b
f = do
    p <- IO (ForeignPtr a) -> IO (ForeignPtr a)
forall a. IO a -> IO a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (ForeignPtr a)
forall a. Storable a => Int -> IO (ForeignPtr a)
mallocForeignPtrArray Int
n)
    _ <- liftBaseOp (withForeignPtr p) (f . OutArray)
    return (SV.unsafeFromForeignPtr p 0 n)

withOutVector' :: (Storable a, Integral b) => Int -> (OutArray a -> IO b) -> IO (SV.Vector a)
withOutVector' :: forall a b.
(Storable a, Integral b) =>
Int -> (OutArray a -> IO b) -> IO (Vector a)
withOutVector' Int
sz OutArray a -> IO b
f = do
    p <- IO (ForeignPtr a) -> IO (ForeignPtr a)
forall a. IO a -> IO a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (ForeignPtr a)
forall a. Storable a => Int -> IO (ForeignPtr a)
mallocForeignPtrArray Int
sz)
    n <- liftBaseOp (withForeignPtr p) (f . OutArray)
    return (SV.unsafeFromForeignPtr p 0 (fromIntegral n))

withOutList :: (Storable a, MonadIO m) => Int -> (OutArray a -> m b) -> m ([a],b)
withOutList :: forall a (m :: * -> *) b.
(Storable a, MonadIO m) =>
Int -> (OutArray a -> m b) -> m ([a], b)
withOutList Int
n OutArray a -> m b
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray Int
n)
    b <- f (OutArray p)
    a <- liftIO (peekArray n p)
    liftIO (free p)
    return (a, b)

withOutList_ :: (Storable a, MonadIO m) => Int -> (OutArray a -> m b) -> m [a]
withOutList_ :: forall a (m :: * -> *) b.
(Storable a, MonadIO m) =>
Int -> (OutArray a -> m b) -> m [a]
withOutList_ Int
n OutArray a -> m b
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray Int
n)
    _ <- f (OutArray p)
    a <- liftIO (peekArray n p)
    liftIO (free p)
    return a

withOutList' :: (Storable a, MonadIO m) => Int -> (OutArray a -> m Int) -> m ([a], Int)
withOutList' :: forall a (m :: * -> *).
(Storable a, MonadIO m) =>
Int -> (OutArray a -> m Int) -> m ([a], Int)
withOutList' Int
sz OutArray a -> m Int
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray Int
sz)
    n <- f (OutArray p)
    a <- liftIO (peekArray n p)
    liftIO (free p)
    return (a, n)

-- | @withOutList0 zero n f@: allocate an array large enough to hold @n@ elements,
-- plus one extra spot for a terminator.  Calls @f@ with that buffer, which is
-- expected to fill it with up to @n@ elements, followed by @zero@.  The
-- elements are then read out into a list.
withOutList0 :: (Storable a, Eq a, MonadIO m) => a -> Int -> (OutArray a -> m b) -> m ([a], b)
withOutList0 :: forall a (m :: * -> *) b.
(Storable a, Eq a, MonadIO m) =>
a -> Int -> (OutArray a -> m b) -> m ([a], b)
withOutList0 a
zero Int
n OutArray a -> m b
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray0 Int
n)
    b <- f (OutArray p)
    a <- liftIO (peekArray0 zero p)
    liftIO (free p)
    return (a, b)

-- |Get a 'BS.ByteString' from a function using the common \"buffer and size in,
-- bytes written out\" convention.
--
-- Calls the function twice; once with a null pointer to discover the length
-- needed and once more to actually read out the string.
withOutByteString :: (MonadBaseControl IO m, MonadIO m, Integral a, Integral b) => (OutArray CChar -> a -> m b) -> m BS.ByteString
withOutByteString :: forall (m :: * -> *) a b.
(MonadBaseControl IO m, MonadIO m, Integral a, Integral b) =>
(OutArray CChar -> a -> m b) -> m ByteString
withOutByteString OutArray CChar -> a -> m b
f = do
    bufSz <- OutArray CChar -> a -> m b
f OutArray CChar
forall a. OutArray a
forall (p :: * -> *) a. WrappedPtr p => p a
nullWrappedPtr a
0

    bracket (liftIO (mallocBytes (fromIntegral bufSz))) (liftIO . free) $ \Ptr CChar
buf -> do
        sz <- OutArray CChar -> a -> m b
f (Ptr CChar -> OutArray CChar
forall a. Ptr a -> OutArray a
OutArray Ptr CChar
buf) (b -> a
forall a b. (Integral a, Num b) => a -> b
fromIntegral b
bufSz)

        liftIO (BS.packCStringLen (buf, fromIntegral sz))

-- | Variant of withOutByteString which expects the discovered length to be one byte less than
--   the required buffer size.  As required for H5Fget_name
withOutByteString' :: (MonadBaseControl IO m, MonadIO m, Integral a, Integral b) => (OutArray CChar -> a -> m b) -> m BS.ByteString
withOutByteString' :: forall (m :: * -> *) a b.
(MonadBaseControl IO m, MonadIO m, Integral a, Integral b) =>
(OutArray CChar -> a -> m b) -> m ByteString
withOutByteString' OutArray CChar -> a -> m b
f = do
    bufSz <- OutArray CChar -> a -> m b
f OutArray CChar
forall a. OutArray a
forall (p :: * -> *) a. WrappedPtr p => p a
nullWrappedPtr a
0
    -- bufSz should be 1 minus the length of the buffer which needs allocating
    let bufSz' = b
bufSz b -> b -> b
forall a. Num a => a -> a -> a
+ b
1

    bracket (liftIO (mallocBytes (fromIntegral bufSz'))) (liftIO . free) $ \Ptr CChar
buf -> do
        sz <- OutArray CChar -> a -> m b
f (Ptr CChar -> OutArray CChar
forall a. Ptr a -> OutArray a
OutArray Ptr CChar
buf) (b -> a
forall a b. (Integral a, Num b) => a -> b
fromIntegral b
bufSz')

        liftIO (BS.packCStringLen (buf, fromIntegral sz))


-- * Bidirectional pointers

-- |In-out parameter.  Memory is allocated and freed by caller.
newtype InOut    a = InOut    (Ptr a) deriving (InOut a -> InOut a -> Bool
(InOut a -> InOut a -> Bool)
-> (InOut a -> InOut a -> Bool) -> Eq (InOut a)
forall a. InOut a -> InOut a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. InOut a -> InOut a -> Bool
== :: InOut a -> InOut a -> Bool
$c/= :: forall a. InOut a -> InOut a -> Bool
/= :: InOut a -> InOut a -> Bool
Eq, Eq (InOut a)
Eq (InOut a) =>
(InOut a -> InOut a -> Ordering)
-> (InOut a -> InOut a -> Bool)
-> (InOut a -> InOut a -> Bool)
-> (InOut a -> InOut a -> Bool)
-> (InOut a -> InOut a -> Bool)
-> (InOut a -> InOut a -> InOut a)
-> (InOut a -> InOut a -> InOut a)
-> Ord (InOut a)
InOut a -> InOut a -> Bool
InOut a -> InOut a -> Ordering
InOut a -> InOut a -> InOut a
forall a. Eq (InOut a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. InOut a -> InOut a -> Bool
forall a. InOut a -> InOut a -> Ordering
forall a. InOut a -> InOut a -> InOut a
$ccompare :: forall a. InOut a -> InOut a -> Ordering
compare :: InOut a -> InOut a -> Ordering
$c< :: forall a. InOut a -> InOut a -> Bool
< :: InOut a -> InOut a -> Bool
$c<= :: forall a. InOut a -> InOut a -> Bool
<= :: InOut a -> InOut a -> Bool
$c> :: forall a. InOut a -> InOut a -> Bool
> :: InOut a -> InOut a -> Bool
$c>= :: forall a. InOut a -> InOut a -> Bool
>= :: InOut a -> InOut a -> Bool
$cmax :: forall a. InOut a -> InOut a -> InOut a
max :: InOut a -> InOut a -> InOut a
$cmin :: forall a. InOut a -> InOut a -> InOut a
min :: InOut a -> InOut a -> InOut a
Ord, Int -> InOut a -> ShowS
[InOut a] -> ShowS
InOut a -> String
(Int -> InOut a -> ShowS)
-> (InOut a -> String) -> ([InOut a] -> ShowS) -> Show (InOut a)
forall a. Int -> InOut a -> ShowS
forall a. [InOut a] -> ShowS
forall a. InOut a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> InOut a -> ShowS
showsPrec :: Int -> InOut a -> ShowS
$cshow :: forall a. InOut a -> String
show :: InOut a -> String
$cshowList :: forall a. [InOut a] -> ShowS
showList :: [InOut a] -> ShowS
Show, Ptr (InOut a) -> IO (InOut a)
Ptr (InOut a) -> Int -> IO (InOut a)
Ptr (InOut a) -> Int -> InOut a -> IO ()
Ptr (InOut a) -> InOut a -> IO ()
InOut a -> Int
(InOut a -> Int)
-> (InOut a -> Int)
-> (Ptr (InOut a) -> Int -> IO (InOut a))
-> (Ptr (InOut a) -> Int -> InOut a -> IO ())
-> (forall b. Ptr b -> Int -> IO (InOut a))
-> (forall b. Ptr b -> Int -> InOut a -> IO ())
-> (Ptr (InOut a) -> IO (InOut a))
-> (Ptr (InOut a) -> InOut a -> IO ())
-> Storable (InOut a)
forall b. Ptr b -> Int -> IO (InOut a)
forall b. Ptr b -> Int -> InOut a -> IO ()
forall a. Ptr (InOut a) -> IO (InOut a)
forall a. Ptr (InOut a) -> Int -> IO (InOut a)
forall a. Ptr (InOut a) -> Int -> InOut a -> IO ()
forall a. Ptr (InOut a) -> InOut a -> IO ()
forall a. InOut a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (InOut a)
forall a b. Ptr b -> Int -> InOut a -> IO ()
$csizeOf :: forall a. InOut a -> Int
sizeOf :: InOut a -> Int
$calignment :: forall a. InOut a -> Int
alignment :: InOut a -> Int
$cpeekElemOff :: forall a. Ptr (InOut a) -> Int -> IO (InOut a)
peekElemOff :: Ptr (InOut a) -> Int -> IO (InOut a)
$cpokeElemOff :: forall a. Ptr (InOut a) -> Int -> InOut a -> IO ()
pokeElemOff :: Ptr (InOut a) -> Int -> InOut a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (InOut a)
peekByteOff :: forall b. Ptr b -> Int -> IO (InOut a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> InOut a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> InOut a -> IO ()
$cpeek :: forall a. Ptr (InOut a) -> IO (InOut a)
peek :: Ptr (InOut a) -> IO (InOut a)
$cpoke :: forall a. Ptr (InOut a) -> InOut a -> IO ()
poke :: Ptr (InOut a) -> InOut a -> IO ()
Storable, (forall a. Ptr a -> InOut a)
-> (forall a. InOut a -> Ptr a)
-> (forall a. InOut a)
-> (forall a b. InOut a -> InOut b)
-> WrappedPtr InOut
forall a. InOut a
forall a. Ptr a -> InOut a
forall a. InOut a -> Ptr a
forall a b. InOut a -> InOut b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> InOut a
wrapPtr :: forall a. Ptr a -> InOut a
$cunwrapPtr :: forall a. InOut a -> Ptr a
unwrapPtr :: forall a. InOut a -> Ptr a
$cnullWrappedPtr :: forall a. InOut a
nullWrappedPtr :: forall a. InOut a
$ccastWrappedPtr :: forall a b. InOut a -> InOut b
castWrappedPtr :: forall a b. InOut a -> InOut b
WrappedPtr)

newtype InOutArray a = InOutArray (Ptr a) deriving (InOutArray a -> InOutArray a -> Bool
(InOutArray a -> InOutArray a -> Bool)
-> (InOutArray a -> InOutArray a -> Bool) -> Eq (InOutArray a)
forall a. InOutArray a -> InOutArray a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. InOutArray a -> InOutArray a -> Bool
== :: InOutArray a -> InOutArray a -> Bool
$c/= :: forall a. InOutArray a -> InOutArray a -> Bool
/= :: InOutArray a -> InOutArray a -> Bool
Eq, Eq (InOutArray a)
Eq (InOutArray a) =>
(InOutArray a -> InOutArray a -> Ordering)
-> (InOutArray a -> InOutArray a -> Bool)
-> (InOutArray a -> InOutArray a -> Bool)
-> (InOutArray a -> InOutArray a -> Bool)
-> (InOutArray a -> InOutArray a -> Bool)
-> (InOutArray a -> InOutArray a -> InOutArray a)
-> (InOutArray a -> InOutArray a -> InOutArray a)
-> Ord (InOutArray a)
InOutArray a -> InOutArray a -> Bool
InOutArray a -> InOutArray a -> Ordering
InOutArray a -> InOutArray a -> InOutArray a
forall a. Eq (InOutArray a)
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. InOutArray a -> InOutArray a -> Bool
forall a. InOutArray a -> InOutArray a -> Ordering
forall a. InOutArray a -> InOutArray a -> InOutArray a
$ccompare :: forall a. InOutArray a -> InOutArray a -> Ordering
compare :: InOutArray a -> InOutArray a -> Ordering
$c< :: forall a. InOutArray a -> InOutArray a -> Bool
< :: InOutArray a -> InOutArray a -> Bool
$c<= :: forall a. InOutArray a -> InOutArray a -> Bool
<= :: InOutArray a -> InOutArray a -> Bool
$c> :: forall a. InOutArray a -> InOutArray a -> Bool
> :: InOutArray a -> InOutArray a -> Bool
$c>= :: forall a. InOutArray a -> InOutArray a -> Bool
>= :: InOutArray a -> InOutArray a -> Bool
$cmax :: forall a. InOutArray a -> InOutArray a -> InOutArray a
max :: InOutArray a -> InOutArray a -> InOutArray a
$cmin :: forall a. InOutArray a -> InOutArray a -> InOutArray a
min :: InOutArray a -> InOutArray a -> InOutArray a
Ord, Int -> InOutArray a -> ShowS
[InOutArray a] -> ShowS
InOutArray a -> String
(Int -> InOutArray a -> ShowS)
-> (InOutArray a -> String)
-> ([InOutArray a] -> ShowS)
-> Show (InOutArray a)
forall a. Int -> InOutArray a -> ShowS
forall a. [InOutArray a] -> ShowS
forall a. InOutArray a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Int -> InOutArray a -> ShowS
showsPrec :: Int -> InOutArray a -> ShowS
$cshow :: forall a. InOutArray a -> String
show :: InOutArray a -> String
$cshowList :: forall a. [InOutArray a] -> ShowS
showList :: [InOutArray a] -> ShowS
Show, Ptr (InOutArray a) -> IO (InOutArray a)
Ptr (InOutArray a) -> Int -> IO (InOutArray a)
Ptr (InOutArray a) -> Int -> InOutArray a -> IO ()
Ptr (InOutArray a) -> InOutArray a -> IO ()
InOutArray a -> Int
(InOutArray a -> Int)
-> (InOutArray a -> Int)
-> (Ptr (InOutArray a) -> Int -> IO (InOutArray a))
-> (Ptr (InOutArray a) -> Int -> InOutArray a -> IO ())
-> (forall b. Ptr b -> Int -> IO (InOutArray a))
-> (forall b. Ptr b -> Int -> InOutArray a -> IO ())
-> (Ptr (InOutArray a) -> IO (InOutArray a))
-> (Ptr (InOutArray a) -> InOutArray a -> IO ())
-> Storable (InOutArray a)
forall b. Ptr b -> Int -> IO (InOutArray a)
forall b. Ptr b -> Int -> InOutArray a -> IO ()
forall a. Ptr (InOutArray a) -> IO (InOutArray a)
forall a. Ptr (InOutArray a) -> Int -> IO (InOutArray a)
forall a. Ptr (InOutArray a) -> Int -> InOutArray a -> IO ()
forall a. Ptr (InOutArray a) -> InOutArray a -> IO ()
forall a. InOutArray a -> Int
forall a.
(a -> Int)
-> (a -> Int)
-> (Ptr a -> Int -> IO a)
-> (Ptr a -> Int -> a -> IO ())
-> (forall b. Ptr b -> Int -> IO a)
-> (forall b. Ptr b -> Int -> a -> IO ())
-> (Ptr a -> IO a)
-> (Ptr a -> a -> IO ())
-> Storable a
forall a b. Ptr b -> Int -> IO (InOutArray a)
forall a b. Ptr b -> Int -> InOutArray a -> IO ()
$csizeOf :: forall a. InOutArray a -> Int
sizeOf :: InOutArray a -> Int
$calignment :: forall a. InOutArray a -> Int
alignment :: InOutArray a -> Int
$cpeekElemOff :: forall a. Ptr (InOutArray a) -> Int -> IO (InOutArray a)
peekElemOff :: Ptr (InOutArray a) -> Int -> IO (InOutArray a)
$cpokeElemOff :: forall a. Ptr (InOutArray a) -> Int -> InOutArray a -> IO ()
pokeElemOff :: Ptr (InOutArray a) -> Int -> InOutArray a -> IO ()
$cpeekByteOff :: forall a b. Ptr b -> Int -> IO (InOutArray a)
peekByteOff :: forall b. Ptr b -> Int -> IO (InOutArray a)
$cpokeByteOff :: forall a b. Ptr b -> Int -> InOutArray a -> IO ()
pokeByteOff :: forall b. Ptr b -> Int -> InOutArray a -> IO ()
$cpeek :: forall a. Ptr (InOutArray a) -> IO (InOutArray a)
peek :: Ptr (InOutArray a) -> IO (InOutArray a)
$cpoke :: forall a. Ptr (InOutArray a) -> InOutArray a -> IO ()
poke :: Ptr (InOutArray a) -> InOutArray a -> IO ()
Storable, (forall a. Ptr a -> InOutArray a)
-> (forall a. InOutArray a -> Ptr a)
-> (forall a. InOutArray a)
-> (forall a b. InOutArray a -> InOutArray b)
-> WrappedPtr InOutArray
forall a. InOutArray a
forall a. Ptr a -> InOutArray a
forall a. InOutArray a -> Ptr a
forall a b. InOutArray a -> InOutArray b
forall (p :: * -> *).
(forall a. Ptr a -> p a)
-> (forall a. p a -> Ptr a)
-> (forall a. p a)
-> (forall a b. p a -> p b)
-> WrappedPtr p
$cwrapPtr :: forall a. Ptr a -> InOutArray a
wrapPtr :: forall a. Ptr a -> InOutArray a
$cunwrapPtr :: forall a. InOutArray a -> Ptr a
unwrapPtr :: forall a. InOutArray a -> Ptr a
$cnullWrappedPtr :: forall a. InOutArray a
nullWrappedPtr :: forall a. InOutArray a
$ccastWrappedPtr :: forall a b. InOutArray a -> InOutArray b
castWrappedPtr :: forall a b. InOutArray a -> InOutArray b
WrappedPtr)

withInOut :: (Storable a, MonadBaseControl IO m, MonadIO m) => a -> (InOut a -> m b) -> m (a,b)
withInOut :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m, MonadIO m) =>
a -> (InOut a -> m b) -> m (a, b)
withInOut a
a InOut a -> m b
f = ((Ptr a -> IO (StM m (a, b))) -> IO (StM m (a, b)))
-> (Ptr a -> m (a, b)) -> m (a, b)
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Ptr a -> IO (StM m (a, b))) -> IO (StM m (a, b))
forall a b. Storable a => (Ptr a -> IO b) -> IO b
alloca ((Ptr a -> m (a, b)) -> m (a, b))
-> (Ptr a -> m (a, b)) -> m (a, b)
forall a b. (a -> b) -> a -> b
$ \Ptr a
p -> do
    IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Ptr a -> a -> IO ()
forall a. Storable a => Ptr a -> a -> IO ()
poke Ptr a
p a
a)
    b <- InOut a -> m b
f (Ptr a -> InOut a
forall a. Ptr a -> InOut a
InOut Ptr a
p)
    a_ <- liftIO (peek p)
    return (a_,b)

withInOut_ :: (Storable a, MonadBaseControl IO m, MonadIO m) => a -> (InOut a -> m b) -> m a
withInOut_ :: forall a (m :: * -> *) b.
(Storable a, MonadBaseControl IO m, MonadIO m) =>
a -> (InOut a -> m b) -> m a
withInOut_ a
a InOut a -> m b
f = ((Ptr a -> IO (StM m a)) -> IO (StM m a)) -> (Ptr a -> m a) -> m a
forall (b :: * -> *) (m :: * -> *) a c d.
MonadBaseControl b m =>
((a -> b (StM m c)) -> b (StM m d)) -> (a -> m c) -> m d
liftBaseOp (Ptr a -> IO (StM m a)) -> IO (StM m a)
forall a b. Storable a => (Ptr a -> IO b) -> IO b
alloca ((Ptr a -> m a) -> m a) -> (Ptr a -> m a) -> m a
forall a b. (a -> b) -> a -> b
$ \Ptr a
p -> do
    IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Ptr a -> a -> IO ()
forall a. Storable a => Ptr a -> a -> IO ()
poke Ptr a
p a
a)
    _ <- InOut a -> m b
f (Ptr a -> InOut a
forall a. Ptr a -> InOut a
InOut Ptr a
p)
    liftIO (peek p)

withInOutList :: (Storable a, MonadIO m) => Int -> [a] -> (InOutArray a -> m (Int, b)) -> m ([a], b)
withInOutList :: forall a (m :: * -> *) b.
(Storable a, MonadIO m) =>
Int -> [a] -> (InOutArray a -> m (Int, b)) -> m ([a], b)
withInOutList Int
sz [a]
xs InOutArray a -> m (Int, b)
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray Int
sz)
    liftIO $ sequence_
        [ pokeElemOff p i x
        | (i,x) <- zip [0..] (take sz xs)
        ]

    (n, y) <- f (InOutArray p)

    xs' <- liftIO $ sequence
        [ peekElemOff p i
        | i <- [0..n-1]
        ]

    return (xs', y)

withInOutList_ :: (Storable a, MonadIO m) => Int -> [a] -> (InOutArray a -> m Int) -> m [a]
withInOutList_ :: forall a (m :: * -> *).
(Storable a, MonadIO m) =>
Int -> [a] -> (InOutArray a -> m Int) -> m [a]
withInOutList_ Int
sz [a]
xs InOutArray a -> m Int
f = do
    p <- IO (Ptr a) -> m (Ptr a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (Int -> IO (Ptr a)
forall a. Storable a => Int -> IO (Ptr a)
mallocArray Int
sz)
    liftIO $ sequence_
        [ pokeElemOff p i x
        | (i,x) <- zip [0..] (take sz xs)
        ]

    n <- f (InOutArray p)

    liftIO $ sequence
        [ peekElemOff p i
        | i <- [0..n-1]
        ]