{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE FlexibleContexts #-}
module LLVM.Extra.Memory (
   C(load, store, decompose, compose), modify,
   Struct,
   Record, Element, element,
   loadRecord, storeRecord, decomposeRecord, composeRecord,
   loadNewtype, storeNewtype, decomposeNewtype, composeNewtype,
   ) where

import qualified LLVM.Extra.Multi.Vector as MultiVector
import qualified LLVM.Extra.Multi.Value.Private as MultiValue
import qualified LLVM.Extra.Scalar as Scalar
import qualified LLVM.Extra.Tuple as Tuple
import qualified LLVM.Extra.Struct as Struct
import qualified LLVM.Extra.Either as Either
import qualified LLVM.Extra.Maybe as Maybe

import qualified LLVM.Core as LLVM
import LLVM.Core
   (getElementPtr0,
    extractvalue, insertvalue,
    Value, -- valueOf, Vector,
    IsType, IsSized,
    CodeGenFunction, )

import qualified Type.Data.Num.Decimal as TypeNum
import qualified Type.Data.Num.Unary as Unary
import Type.Data.Num.Decimal (d0, d1, d2, d3)
import Type.Base.Proxy (Proxy(Proxy))

import qualified Data.Traversable as Trav
import qualified Data.Foldable as Fold
import qualified Data.FixedLength as FixedLength
import qualified Data.Complex as Complex
import Data.Complex (Complex((:+)))
import Data.Tuple.HT (fst3, snd3, thd3, )
import Data.Word (Word)

import qualified Control.Applicative.HT as App
import Control.Monad (ap, (<=<))
import Control.Applicative (Applicative, pure, liftA2, liftA3, (<*>))

import Prelude2010 hiding (maybe, either, )
import Prelude ()


{- |
An implementation of both 'Tuple.Value' and 'Memory.C'
must ensure that @haskellValue@ is compatible
with @Stored (Struct haskellValue)@ (which we want to call @llvmStruct@).
That is, writing and reading @llvmStruct@ by LLVM
must be the same as accessing @haskellValue@ by 'Storable' methods.
ToDo: In future we may also require Storable constraint for @llvmStruct@.

We use a functional dependency in order to let type inference work nicely.
-}
class (Tuple.Phi llvmValue, Tuple.Undefined llvmValue, IsType (Struct llvmValue), IsSized (Struct llvmValue)) =>
      C llvmValue where
   type Struct llvmValue
   load :: Value (LLVM.Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
   load Value (Ptr (Struct llvmValue))
ptr  =  Value (Struct llvmValue) -> CodeGenFunction r llvmValue
forall r. Value (Struct llvmValue) -> CodeGenFunction r llvmValue
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose (Value (Struct llvmValue) -> CodeGenFunction r llvmValue)
-> CodeGenFunction r (Value (Struct llvmValue))
-> CodeGenFunction r llvmValue
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value (Ptr (Struct llvmValue))
-> CodeGenFunction r (Value (Struct llvmValue))
forall a r.
IsType a =>
Value (Ptr a) -> CodeGenFunction r (Value a)
LLVM.load Value (Ptr (Struct llvmValue))
ptr
   store :: llvmValue -> Value (LLVM.Ptr (Struct llvmValue)) -> CodeGenFunction r ()
   store llvmValue
r Value (Ptr (Struct llvmValue))
ptr  =  (Value (Struct llvmValue)
 -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ())
-> Value (Ptr (Struct llvmValue))
-> Value (Struct llvmValue)
-> CodeGenFunction r ()
forall a b c. (a -> b -> c) -> b -> a -> c
flip Value (Struct llvmValue)
-> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
forall a r.
IsType a =>
Value a -> Value (Ptr a) -> CodeGenFunction r ()
LLVM.store Value (Ptr (Struct llvmValue))
ptr (Value (Struct llvmValue) -> CodeGenFunction r ())
-> CodeGenFunction r (Value (Struct llvmValue))
-> CodeGenFunction r ()
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
forall r. llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose llvmValue
r
   {- |
   In principle it holds:

   > decompose struct = do
   >   ptr <- LLVM.alloca
   >   LLVM.store struct ptr
   >   Memory.load ptr

   but 'LLVM.alloca' will blast your stack when used in a loop.
   -}
   decompose :: Value (Struct llvmValue) -> CodeGenFunction r llvmValue
   {- |
   In principle it holds:

   > compose struct = do
   >   ptr <- LLVM.alloca
   >   Memory.store struct ptr
   >   LLVM.load ptr

   but 'LLVM.alloca' will blast your stack when used in a loop.
   -}
   compose :: llvmValue -> CodeGenFunction r (Value (Struct llvmValue))

modify ::
   (C llvmValue) =>
   (llvmValue -> CodeGenFunction r llvmValue) ->
   Value (LLVM.Ptr (Struct llvmValue)) -> CodeGenFunction r ()
modify :: forall llvmValue r.
C llvmValue =>
(llvmValue -> CodeGenFunction r llvmValue)
-> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
modify llvmValue -> CodeGenFunction r llvmValue
f Value (Ptr (Struct llvmValue))
ptr =
   (llvmValue
 -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ())
-> Value (Ptr (Struct llvmValue))
-> llvmValue
-> CodeGenFunction r ()
forall a b c. (a -> b -> c) -> b -> a -> c
flip llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
forall r.
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
forall llvmValue r.
C llvmValue =>
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
store Value (Ptr (Struct llvmValue))
ptr (llvmValue -> CodeGenFunction r ())
-> CodeGenFunction r llvmValue -> CodeGenFunction r ()
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< llvmValue -> CodeGenFunction r llvmValue
f (llvmValue -> CodeGenFunction r llvmValue)
-> CodeGenFunction r llvmValue -> CodeGenFunction r llvmValue
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
forall r.
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
forall llvmValue r.
C llvmValue =>
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
load Value (Ptr (Struct llvmValue))
ptr


instance C () where
   type Struct () = LLVM.Struct ()
   load :: forall r. Value (Ptr (Struct ())) -> CodeGenFunction r ()
load Value (Ptr (Struct ()))
_ = () -> CodeGenFunction r ()
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
   store :: forall r. () -> Value (Ptr (Struct ())) -> CodeGenFunction r ()
store ()
_ Value (Ptr (Struct ()))
_ = () -> CodeGenFunction r ()
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
   decompose :: forall r. Value (Struct ()) -> CodeGenFunction r ()
decompose Value (Struct ())
_ = () -> CodeGenFunction r ()
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
   compose :: forall r. () -> CodeGenFunction r (Value (Struct ()))
compose ()
_ = Value (Struct ()) -> CodeGenFunction r (Value (Struct ()))
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return (ConstValue (Struct ()) -> Value (Struct ())
forall a. ConstValue a -> Value a
LLVM.value (ConstValue (Struct ()) -> Value (Struct ()))
-> ConstValue (Struct ()) -> Value (Struct ())
forall a b. (a -> b) -> a -> b
$ () -> ConstValue (Struct (ConstStructOf ()))
forall c.
IsConstStruct c =>
c -> ConstValue (Struct (ConstStructOf c))
LLVM.constStruct ())


type Record r o v = Element r o v v

data Element r o v x =
   Element {
      forall r o v x.
Element r o v x -> Value (Ptr o) -> CodeGenFunction r x
loadElement :: Value (LLVM.Ptr o) -> CodeGenFunction r x,
      forall r o v x.
Element r o v x -> Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement :: Value (LLVM.Ptr o) -> v -> CodeGenFunction r (),
      forall r o v x. Element r o v x -> Value o -> CodeGenFunction r x
extractElement :: Value o -> CodeGenFunction r x,
      forall r o v x.
Element r o v x -> v -> Value o -> CodeGenFunction r (Value o)
insertElement :: v -> Value o -> CodeGenFunction r (Value o)
         -- State.Monoid
   }

element ::
   (C x, IsType o,
    LLVM.GetValue o n, LLVM.ValueType o n ~ Struct x,
    LLVM.GetElementPtr o (n, ()), LLVM.ElementPtrType o (n, ()) ~ Struct x) =>
   (v -> x) -> n -> Element r o v x
element :: forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element v -> x
field n
n =
   Element {
      loadElement :: Value (Ptr o) -> CodeGenFunction r x
loadElement = \Value (Ptr o)
ptr -> Value (Ptr (Struct x)) -> CodeGenFunction r x
forall r. Value (Ptr (Struct x)) -> CodeGenFunction r x
forall llvmValue r.
C llvmValue =>
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
load (Value (Ptr (Struct x)) -> CodeGenFunction r x)
-> CodeGenFunction r (Value (Ptr (Struct x)))
-> CodeGenFunction r x
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value (Ptr o)
-> (n, ())
-> CodeGenFunction r (Value (Ptr (ElementPtrType o (n, ()))))
forall o i r.
(GetElementPtr o i, IsType o) =>
Value (Ptr o)
-> i -> CodeGenFunction r (Value (Ptr (ElementPtrType o i)))
getElementPtr0 Value (Ptr o)
ptr (n
n, ()),
      storeElement :: Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement = \Value (Ptr o)
ptr v
v -> x -> Value (Ptr (Struct x)) -> CodeGenFunction r ()
forall r. x -> Value (Ptr (Struct x)) -> CodeGenFunction r ()
forall llvmValue r.
C llvmValue =>
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
store (v -> x
field v
v) (Value (Ptr (Struct x)) -> CodeGenFunction r ())
-> CodeGenFunction r (Value (Ptr (Struct x)))
-> CodeGenFunction r ()
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value (Ptr o)
-> (n, ())
-> CodeGenFunction r (Value (Ptr (ElementPtrType o (n, ()))))
forall o i r.
(GetElementPtr o i, IsType o) =>
Value (Ptr o)
-> i -> CodeGenFunction r (Value (Ptr (ElementPtrType o i)))
getElementPtr0 Value (Ptr o)
ptr (n
n, ()),
      extractElement :: Value o -> CodeGenFunction r x
extractElement = \Value o
o -> Value (Struct x) -> CodeGenFunction r x
forall r. Value (Struct x) -> CodeGenFunction r x
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose (Value (Struct x) -> CodeGenFunction r x)
-> CodeGenFunction r (Value (Struct x)) -> CodeGenFunction r x
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value o -> n -> CodeGenFunction r (Value (ValueType o n))
forall r agg i.
GetValue agg i =>
Value agg -> i -> CodeGenFunction r (Value (ValueType agg i))
extractvalue Value o
o n
n,
      insertElement :: v -> Value o -> CodeGenFunction r (Value o)
insertElement = \v
v Value o
o -> (Value (Struct x) -> n -> CodeGenFunction r (Value o))
-> n -> Value (Struct x) -> CodeGenFunction r (Value o)
forall a b c. (a -> b -> c) -> b -> a -> c
flip (Value o
-> Value (ValueType o n) -> n -> CodeGenFunction r (Value o)
forall r agg i.
GetValue agg i =>
Value agg
-> Value (ValueType agg i) -> i -> CodeGenFunction r (Value agg)
insertvalue Value o
o) n
n (Value (Struct x) -> CodeGenFunction r (Value o))
-> CodeGenFunction r (Value (Struct x))
-> CodeGenFunction r (Value o)
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< x -> CodeGenFunction r (Value (Struct x))
forall r. x -> CodeGenFunction r (Value (Struct x))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose (v -> x
field v
v)
   }

instance Functor (Element r o v) where
   fmap :: forall a b. (a -> b) -> Element r o v a -> Element r o v b
fmap a -> b
f Element r o v a
m =
      Element {
         loadElement :: Value (Ptr o) -> CodeGenFunction r b
loadElement = (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
f (CodeGenFunction r a -> CodeGenFunction r b)
-> (Value (Ptr o) -> CodeGenFunction r a)
-> Value (Ptr o)
-> CodeGenFunction r b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Element r o v a -> Value (Ptr o) -> CodeGenFunction r a
forall r o v x.
Element r o v x -> Value (Ptr o) -> CodeGenFunction r x
loadElement Element r o v a
m,
         storeElement :: Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement = Element r o v a -> Value (Ptr o) -> v -> CodeGenFunction r ()
forall r o v x.
Element r o v x -> Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement Element r o v a
m,
         extractElement :: Value o -> CodeGenFunction r b
extractElement = (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
f (CodeGenFunction r a -> CodeGenFunction r b)
-> (Value o -> CodeGenFunction r a)
-> Value o
-> CodeGenFunction r b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Element r o v a -> Value o -> CodeGenFunction r a
forall r o v x. Element r o v x -> Value o -> CodeGenFunction r x
extractElement Element r o v a
m,
         insertElement :: v -> Value o -> CodeGenFunction r (Value o)
insertElement = Element r o v a -> v -> Value o -> CodeGenFunction r (Value o)
forall r o v x.
Element r o v x -> v -> Value o -> CodeGenFunction r (Value o)
insertElement Element r o v a
m
      }

instance Applicative (Element r o v) where
   pure :: forall a. a -> Element r o v a
pure a
x =
      Element {
         loadElement :: Value (Ptr o) -> CodeGenFunction r a
loadElement = \ Value (Ptr o)
_ptr -> a -> CodeGenFunction r a
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return a
x,
         storeElement :: Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement = \ Value (Ptr o)
_ptr v
_v -> () -> CodeGenFunction r ()
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return (),
         extractElement :: Value o -> CodeGenFunction r a
extractElement = \ Value o
_o -> a -> CodeGenFunction r a
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return a
x,
         insertElement :: v -> Value o -> CodeGenFunction r (Value o)
insertElement = \ v
_v Value o
o -> Value o -> CodeGenFunction r (Value o)
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return Value o
o
      }
   Element r o v (a -> b)
f <*> :: forall a b.
Element r o v (a -> b) -> Element r o v a -> Element r o v b
<*> Element r o v a
x =
      Element {
         loadElement :: Value (Ptr o) -> CodeGenFunction r b
loadElement = \Value (Ptr o)
ptr -> Element r o v (a -> b)
-> Value (Ptr o) -> CodeGenFunction r (a -> b)
forall r o v x.
Element r o v x -> Value (Ptr o) -> CodeGenFunction r x
loadElement Element r o v (a -> b)
f Value (Ptr o)
ptr CodeGenFunction r (a -> b)
-> CodeGenFunction r a -> CodeGenFunction r b
forall (m :: * -> *) a b. Monad m => m (a -> b) -> m a -> m b
`ap` Element r o v a -> Value (Ptr o) -> CodeGenFunction r a
forall r o v x.
Element r o v x -> Value (Ptr o) -> CodeGenFunction r x
loadElement Element r o v a
x Value (Ptr o)
ptr,
         storeElement :: Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement = \Value (Ptr o)
ptr v
y -> Element r o v (a -> b)
-> Value (Ptr o) -> v -> CodeGenFunction r ()
forall r o v x.
Element r o v x -> Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement Element r o v (a -> b)
f Value (Ptr o)
ptr v
y CodeGenFunction r ()
-> CodeGenFunction r () -> CodeGenFunction r ()
forall a b.
CodeGenFunction r a -> CodeGenFunction r b -> CodeGenFunction r b
forall (m :: * -> *) a b. Monad m => m a -> m b -> m b
>> Element r o v a -> Value (Ptr o) -> v -> CodeGenFunction r ()
forall r o v x.
Element r o v x -> Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement Element r o v a
x Value (Ptr o)
ptr v
y,
         extractElement :: Value o -> CodeGenFunction r b
extractElement = \Value o
o -> Element r o v (a -> b) -> Value o -> CodeGenFunction r (a -> b)
forall r o v x. Element r o v x -> Value o -> CodeGenFunction r x
extractElement Element r o v (a -> b)
f Value o
o CodeGenFunction r (a -> b)
-> CodeGenFunction r a -> CodeGenFunction r b
forall (m :: * -> *) a b. Monad m => m (a -> b) -> m a -> m b
`ap` Element r o v a -> Value o -> CodeGenFunction r a
forall r o v x. Element r o v x -> Value o -> CodeGenFunction r x
extractElement Element r o v a
x Value o
o,
         insertElement :: v -> Value o -> CodeGenFunction r (Value o)
insertElement = \v
y Value o
o -> Element r o v (a -> b)
-> v -> Value o -> CodeGenFunction r (Value o)
forall r o v x.
Element r o v x -> v -> Value o -> CodeGenFunction r (Value o)
insertElement Element r o v (a -> b)
f v
y Value o
o CodeGenFunction r (Value o)
-> (Value o -> CodeGenFunction r (Value o))
-> CodeGenFunction r (Value o)
forall a b.
CodeGenFunction r a
-> (a -> CodeGenFunction r b) -> CodeGenFunction r b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Element r o v a -> v -> Value o -> CodeGenFunction r (Value o)
forall r o v x.
Element r o v x -> v -> Value o -> CodeGenFunction r (Value o)
insertElement Element r o v a
x v
y
      }


loadRecord ::
   Record r o llvmValue ->
   Value (LLVM.Ptr o) -> CodeGenFunction r llvmValue
loadRecord :: forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord = Element r o llvmValue llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
forall r o v x.
Element r o v x -> Value (Ptr o) -> CodeGenFunction r x
loadElement

storeRecord ::
   Record r o llvmValue ->
   llvmValue -> Value (LLVM.Ptr o) -> CodeGenFunction r ()
storeRecord :: forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r o llvmValue
m llvmValue
y Value (Ptr o)
ptr = Record r o llvmValue
-> Value (Ptr o) -> llvmValue -> CodeGenFunction r ()
forall r o v x.
Element r o v x -> Value (Ptr o) -> v -> CodeGenFunction r ()
storeElement Record r o llvmValue
m Value (Ptr o)
ptr llvmValue
y

decomposeRecord ::
   Record r o llvmValue ->
   Value o -> CodeGenFunction r llvmValue
decomposeRecord :: forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r o llvmValue
m =
   Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
forall r o v x. Element r o v x -> Value o -> CodeGenFunction r x
extractElement Record r o llvmValue
m

composeRecord ::
   (IsType o) =>
   Record r o llvmValue ->
   llvmValue -> CodeGenFunction r (Value o)
composeRecord :: forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r o llvmValue
m llvmValue
v =
   Record r o llvmValue
-> llvmValue -> Value o -> CodeGenFunction r (Value o)
forall r o v x.
Element r o v x -> v -> Value o -> CodeGenFunction r (Value o)
insertElement Record r o llvmValue
m llvmValue
v (ConstValue o -> Value o
forall a. ConstValue a -> Value a
LLVM.value ConstValue o
forall a. IsType a => ConstValue a
LLVM.undef)



pair ::
   (C a, C b) =>
   Record r (LLVM.Struct (Struct a, (Struct b, ()))) (a, b)
pair :: forall a b r.
(C a, C b) =>
Record r (Struct (Struct a, (Struct b, ()))) (a, b)
pair =
   (a -> b -> (a, b))
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) a
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) b
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) (a, b)
forall a b c.
(a -> b -> c)
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) a
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) b
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) c
forall (f :: * -> *) a b c.
Applicative f =>
(a -> b -> c) -> f a -> f b -> f c
liftA2 (,)
      (((a, b) -> a)
-> Proxy D0
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (a, b) -> a
forall a b. (a, b) -> a
fst Proxy D0
d0)
      (((a, b) -> b)
-> Proxy D1
-> Element r (Struct (Struct a, (Struct b, ()))) (a, b) b
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (a, b) -> b
forall a b. (a, b) -> b
snd Proxy D1
d1)

instance (C a, C b) => C (a, b) where
   type Struct (a, b) = LLVM.Struct (Struct a, (Struct b, ()))
   load :: forall r. Value (Ptr (Struct (a, b))) -> CodeGenFunction r (a, b)
load = Record r (Struct (Struct a, (Struct b, ()))) (a, b)
-> Value (Ptr (Struct (Struct a, (Struct b, ()))))
-> CodeGenFunction r (a, b)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record r (Struct (Struct a, (Struct b, ()))) (a, b)
forall a b r.
(C a, C b) =>
Record r (Struct (Struct a, (Struct b, ()))) (a, b)
pair
   store :: forall r.
(a, b) -> Value (Ptr (Struct (a, b))) -> CodeGenFunction r ()
store = Record r (Struct (Struct a, (Struct b, ()))) (a, b)
-> (a, b)
-> Value (Ptr (Struct (Struct a, (Struct b, ()))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r (Struct (Struct a, (Struct b, ()))) (a, b)
forall a b r.
(C a, C b) =>
Record r (Struct (Struct a, (Struct b, ()))) (a, b)
pair
   decompose :: forall r. Value (Struct (a, b)) -> CodeGenFunction r (a, b)
decompose = Record r (Struct (Struct a, (Struct b, ()))) (a, b)
-> Value (Struct (Struct a, (Struct b, ())))
-> CodeGenFunction r (a, b)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r (Struct (Struct a, (Struct b, ()))) (a, b)
forall a b r.
(C a, C b) =>
Record r (Struct (Struct a, (Struct b, ()))) (a, b)
pair
   compose :: forall r. (a, b) -> CodeGenFunction r (Value (Struct (a, b)))
compose = Record r (Struct (Struct a, (Struct b, ()))) (a, b)
-> (a, b)
-> CodeGenFunction r (Value (Struct (Struct a, (Struct b, ()))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r (Struct (Struct a, (Struct b, ()))) (a, b)
forall a b r.
(C a, C b) =>
Record r (Struct (Struct a, (Struct b, ()))) (a, b)
pair


triple ::
   (C a, C b, C c) =>
   Record r (LLVM.Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple :: forall a b c r.
(C a, C b, C c) =>
Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple =
   (a -> b -> c -> (a, b, c))
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) a
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) b
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) c
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, ()))))
     (a, b, c)
     (a, b, c)
forall (f :: * -> *) a b c d.
Applicative f =>
(a -> b -> c -> d) -> f a -> f b -> f c -> f d
liftA3 (,,)
      (((a, b, c) -> a)
-> Proxy D0
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (a, b, c) -> a
forall a b c. (a, b, c) -> a
fst3 Proxy D0
d0)
      (((a, b, c) -> b)
-> Proxy D1
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) b
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (a, b, c) -> b
forall a b c. (a, b, c) -> b
snd3 Proxy D1
d1)
      (((a, b, c) -> c)
-> Proxy D2
-> Element
     r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c) c
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (a, b, c) -> c
forall a b c. (a, b, c) -> c
thd3 Proxy D2
d2)

instance (C a, C b, C c) => C (a, b, c) where
   type Struct (a, b, c) =
           LLVM.Struct (Struct a, (Struct b, (Struct c, ())))
   load :: forall r.
Value (Ptr (Struct (a, b, c))) -> CodeGenFunction r (a, b, c)
load = Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
-> Value (Ptr (Struct (Struct a, (Struct b, (Struct c, ())))))
-> CodeGenFunction r (a, b, c)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
forall a b c r.
(C a, C b, C c) =>
Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple
   store :: forall r.
(a, b, c) -> Value (Ptr (Struct (a, b, c))) -> CodeGenFunction r ()
store = Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
-> (a, b, c)
-> Value (Ptr (Struct (Struct a, (Struct b, (Struct c, ())))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
forall a b c r.
(C a, C b, C c) =>
Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple
   decompose :: forall r. Value (Struct (a, b, c)) -> CodeGenFunction r (a, b, c)
decompose = Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
-> Value (Struct (Struct a, (Struct b, (Struct c, ()))))
-> CodeGenFunction r (a, b, c)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
forall a b c r.
(C a, C b, C c) =>
Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple
   compose :: forall r. (a, b, c) -> CodeGenFunction r (Value (Struct (a, b, c)))
compose = Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
-> (a, b, c)
-> CodeGenFunction
     r (Value (Struct (Struct a, (Struct b, (Struct c, ())))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
forall a b c r.
(C a, C b, C c) =>
Record r (Struct (Struct a, (Struct b, (Struct c, ())))) (a, b, c)
triple


quadruple ::
   (C a, C b, C c, C d) =>
   Record r
      (LLVM.Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
      (a, b, c, d)
quadruple :: forall a b c d r.
(C a, C b, C c, C d) =>
Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
quadruple =
   (a -> b -> c -> d -> (a, b, c, d))
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     a
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     b
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     c
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     d
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     (a, b, c, d)
forall (m :: * -> *) a b c d r.
Applicative m =>
(a -> b -> c -> d -> r) -> m a -> m b -> m c -> m d -> m r
App.lift4 (,,,)
      (((a, b, c, d) -> a)
-> Proxy D0
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (\(a
x,b
_,c
_,d
_) -> a
x) Proxy D0
d0)
      (((a, b, c, d) -> b)
-> Proxy D1
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     b
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (\(a
_,b
x,c
_,d
_) -> b
x) Proxy D1
d1)
      (((a, b, c, d) -> c)
-> Proxy D2
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     c
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (\(a
_,b
_,c
x,d
_) -> c
x) Proxy D2
d2)
      (((a, b, c, d) -> d)
-> Proxy D3
-> Element
     r
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
     (a, b, c, d)
     d
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element (\(a
_,b
_,c
_,d
x) -> d
x) Proxy D3
d3)

instance (C a, C b, C c, C d) => C (a, b, c, d) where
   type Struct (a, b, c, d) =
           LLVM.Struct (Struct a, (Struct b, (Struct c, (Struct d, ()))))
   load :: forall r.
Value (Ptr (Struct (a, b, c, d))) -> CodeGenFunction r (a, b, c, d)
load = Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
-> Value
     (Ptr (Struct (Struct a, (Struct b, (Struct c, (Struct d, ()))))))
-> CodeGenFunction r (a, b, c, d)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
forall a b c d r.
(C a, C b, C c, C d) =>
Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
quadruple
   store :: forall r.
(a, b, c, d)
-> Value (Ptr (Struct (a, b, c, d))) -> CodeGenFunction r ()
store = Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
-> (a, b, c, d)
-> Value
     (Ptr (Struct (Struct a, (Struct b, (Struct c, (Struct d, ()))))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
forall a b c d r.
(C a, C b, C c, C d) =>
Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
quadruple
   decompose :: forall r.
Value (Struct (a, b, c, d)) -> CodeGenFunction r (a, b, c, d)
decompose = Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
-> Value
     (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
-> CodeGenFunction r (a, b, c, d)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
forall a b c d r.
(C a, C b, C c, C d) =>
Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
quadruple
   compose :: forall r.
(a, b, c, d) -> CodeGenFunction r (Value (Struct (a, b, c, d)))
compose = Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
-> (a, b, c, d)
-> CodeGenFunction
     r
     (Value (Struct (Struct a, (Struct b, (Struct c, (Struct d, ()))))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
forall a b c d r.
(C a, C b, C c, C d) =>
Record
  r
  (Struct (Struct a, (Struct b, (Struct c, (Struct d, ())))))
  (a, b, c, d)
quadruple


complex ::
   (C a) =>
   Record r (LLVM.Struct (Struct a, (Struct a, ()))) (Complex a)
complex :: forall a r.
C a =>
Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
complex =
   (a -> a -> Complex a)
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) a
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) a
-> Element
     r (Struct (Struct a, (Struct a, ()))) (Complex a) (Complex a)
forall a b c.
(a -> b -> c)
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) a
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) b
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) c
forall (f :: * -> *) a b c.
Applicative f =>
(a -> b -> c) -> f a -> f b -> f c
liftA2 a -> a -> Complex a
forall a. a -> a -> Complex a
(:+)
      ((Complex a -> a)
-> Proxy D0
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element Complex a -> a
forall a. Complex a -> a
Complex.realPart Proxy D0
d0)
      ((Complex a -> a)
-> Proxy D1
-> Element r (Struct (Struct a, (Struct a, ()))) (Complex a) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element Complex a -> a
forall a. Complex a -> a
Complex.imagPart Proxy D1
d1)

instance (C a) => C (Complex a) where
   type Struct (Complex a) = LLVM.Struct (Struct a, (Struct a, ()))
   load :: forall r.
Value (Ptr (Struct (Complex a))) -> CodeGenFunction r (Complex a)
load = Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
-> Value (Ptr (Struct (Struct a, (Struct a, ()))))
-> CodeGenFunction r (Complex a)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
forall a r.
C a =>
Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
complex
   store :: forall r.
Complex a
-> Value (Ptr (Struct (Complex a))) -> CodeGenFunction r ()
store = Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
-> Complex a
-> Value (Ptr (Struct (Struct a, (Struct a, ()))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
forall a r.
C a =>
Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
complex
   decompose :: forall r.
Value (Struct (Complex a)) -> CodeGenFunction r (Complex a)
decompose = Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
-> Value (Struct (Struct a, (Struct a, ())))
-> CodeGenFunction r (Complex a)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
forall a r.
C a =>
Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
complex
   compose :: forall r.
Complex a -> CodeGenFunction r (Value (Struct (Complex a)))
compose = Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
-> Complex a
-> CodeGenFunction r (Value (Struct (Struct a, (Struct a, ()))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
forall a r.
C a =>
Record r (Struct (Struct a, (Struct a, ()))) (Complex a)
complex


instance
   (Unary.Natural n, C a,
    TypeNum.Natural (TypeNum.FromUnary n),
    TypeNum.Natural (TypeNum.FromUnary n TypeNum.:*: LLVM.SizeOf (Struct a)),
    LLVM.IsFirstClass (Struct a)) =>
      C (FixedLength.T n a) where
   type Struct (FixedLength.T n a) =
            LLVM.Array (TypeNum.FromUnary n) (Struct a)
   compose :: forall r. T n a -> CodeGenFunction r (Value (Struct (T n a)))
compose T n a
xs =
      (Value (Struct (T n a))
 -> (a, Word) -> CodeGenFunction r (Value (Struct (T n a))))
-> Value (Struct (T n a))
-> T n (a, Word)
-> CodeGenFunction r (Value (Struct (T n a)))
forall (t :: * -> *) (m :: * -> *) b a.
(Foldable t, Monad m) =>
(b -> a -> m b) -> b -> t a -> m b
Fold.foldlM
         (\Value (Struct (T n a))
arr (a
x,Word
i) -> a -> CodeGenFunction r (Value (Struct a))
forall r. a -> CodeGenFunction r (Value (Struct a))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose a
x CodeGenFunction r (Value (Struct a))
-> (Value (Struct a)
    -> CodeGenFunction r (Value (Array (FromUnary n) (Struct a))))
-> CodeGenFunction r (Value (Array (FromUnary n) (Struct a)))
forall a b.
CodeGenFunction r a
-> (a -> CodeGenFunction r b) -> CodeGenFunction r b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \Value (Struct a)
xc -> Value (Array (FromUnary n) (Struct a))
-> Value (ValueType (Array (FromUnary n) (Struct a)) Word)
-> Word
-> CodeGenFunction r (Value (Array (FromUnary n) (Struct a)))
forall r agg i.
GetValue agg i =>
Value agg
-> Value (ValueType agg i) -> i -> CodeGenFunction r (Value agg)
LLVM.insertvalue Value (Array (FromUnary n) (Struct a))
Value (Struct (T n a))
arr Value (ValueType (Array (FromUnary n) (Struct a)) Word)
Value (Struct a)
xc Word
i)
         (ConstValue (Array (FromUnary n) (Struct a))
-> Value (Array (FromUnary n) (Struct a))
forall a. ConstValue a -> Value a
LLVM.value ConstValue (Array (FromUnary n) (Struct a))
forall a. IsType a => ConstValue a
LLVM.undef) (T n (a, Word) -> CodeGenFunction r (Value (Struct (T n a))))
-> T n (a, Word) -> CodeGenFunction r (Value (Struct (T n a)))
forall a b. (a -> b) -> a -> b
$
      (a -> Word -> (a, Word)) -> T n a -> T n Word -> T n (a, Word)
forall n a b c.
Natural n =>
(a -> b -> c) -> T n a -> T n b -> T n c
FixedLength.zipWith (,) T n a
xs (T n Word -> T n (a, Word)) -> T n Word -> T n (a, Word)
forall a b. (a -> b) -> a -> b
$ (Word -> Word) -> Word -> T n Word
forall (t :: * -> *) a.
(Applicative t, Traversable t) =>
(a -> a) -> a -> t a
iterateTrav (Word
1Word -> Word -> Word
forall a. Num a => a -> a -> a
+) (Word
0::Word)
   decompose :: forall r. Value (Struct (T n a)) -> CodeGenFunction r (T n a)
decompose Value (Struct (T n a))
arr =
      (Word -> CodeGenFunction r a)
-> T n Word -> CodeGenFunction r (T n a)
forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
(a -> m b) -> t a -> m (t b)
forall (m :: * -> *) a b.
Monad m =>
(a -> m b) -> T n a -> m (T n b)
Trav.mapM (Value (Struct a) -> CodeGenFunction r a
forall r. Value (Struct a) -> CodeGenFunction r a
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose (Value (Struct a) -> CodeGenFunction r a)
-> (Word -> CodeGenFunction r (Value (Struct a)))
-> Word
-> CodeGenFunction r a
forall (m :: * -> *) b c a.
Monad m =>
(b -> m c) -> (a -> m b) -> a -> m c
<=< Value (Array (FromUnary n) (Struct a))
-> Word
-> CodeGenFunction
     r (Value (ValueType (Array (FromUnary n) (Struct a)) Word))
forall r agg i.
GetValue agg i =>
Value agg -> i -> CodeGenFunction r (Value (ValueType agg i))
LLVM.extractvalue Value (Array (FromUnary n) (Struct a))
Value (Struct (T n a))
arr) (T n Word -> CodeGenFunction r (T n a))
-> T n Word -> CodeGenFunction r (T n a)
forall a b. (a -> b) -> a -> b
$
      (Word -> Word) -> Word -> T n Word
forall (t :: * -> *) a.
(Applicative t, Traversable t) =>
(a -> a) -> a -> t a
iterateTrav (Word
1Word -> Word -> Word
forall a. Num a => a -> a -> a
+) (Word
0::Word)

iterateTrav :: (Applicative t, Trav.Traversable t) => (a -> a) -> a -> t a
iterateTrav :: forall (t :: * -> *) a.
(Applicative t, Traversable t) =>
(a -> a) -> a -> t a
iterateTrav a -> a
f a
a0 = (a, t a) -> t a
forall a b. (a, b) -> b
snd ((a, t a) -> t a) -> (a, t a) -> t a
forall a b. (a -> b) -> a -> b
$ (a -> () -> (a, a)) -> a -> t () -> (a, t a)
forall (t :: * -> *) s a b.
Traversable t =>
(s -> a -> (s, b)) -> s -> t a -> (s, t b)
Trav.mapAccumL (\a
a () -> (a -> a
f a
a, a
a)) a
a0 (t () -> (a, t a)) -> t () -> (a, t a)
forall a b. (a -> b) -> a -> b
$ () -> t ()
forall a. a -> t a
forall (f :: * -> *) a. Applicative f => a -> f a
pure ()


maybe ::
   (C a) =>
   Record r (LLVM.Struct (Bool, (Struct a, ()))) (Maybe.T a)
maybe :: forall a r. C a => Record r (Struct (Bool, (Struct a, ()))) (T a)
maybe =
   (Value Bool -> a -> T a)
-> Element r (Struct (Bool, (Struct a, ()))) (T a) (Value Bool)
-> Element r (Struct (Bool, (Struct a, ()))) (T a) a
-> Element r (Struct (Bool, (Struct a, ()))) (T a) (T a)
forall a b c.
(a -> b -> c)
-> Element r (Struct (Bool, (Struct a, ()))) (T a) a
-> Element r (Struct (Bool, (Struct a, ()))) (T a) b
-> Element r (Struct (Bool, (Struct a, ()))) (T a) c
forall (f :: * -> *) a b c.
Applicative f =>
(a -> b -> c) -> f a -> f b -> f c
liftA2 Value Bool -> a -> T a
forall a. Value Bool -> a -> T a
Maybe.Cons
      ((T a -> Value Bool)
-> Proxy D0
-> Element r (Struct (Bool, (Struct a, ()))) (T a) (Value Bool)
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element T a -> Value Bool
forall a. T a -> Value Bool
Maybe.isJust Proxy D0
d0)
      ((T a -> a)
-> Proxy D1 -> Element r (Struct (Bool, (Struct a, ()))) (T a) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element T a -> a
forall a. T a -> a
Maybe.fromJust Proxy D1
d1)

instance (C a) => C (Maybe.T a) where
   type Struct (Maybe.T a) = LLVM.Struct (Bool, (Struct a, ()))
   load :: forall r. Value (Ptr (Struct (T a))) -> CodeGenFunction r (T a)
load = Record r (Struct (Bool, (Struct a, ()))) (T a)
-> Value (Ptr (Struct (Bool, (Struct a, ()))))
-> CodeGenFunction r (T a)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record r (Struct (Bool, (Struct a, ()))) (T a)
forall a r. C a => Record r (Struct (Bool, (Struct a, ()))) (T a)
maybe
   store :: forall r. T a -> Value (Ptr (Struct (T a))) -> CodeGenFunction r ()
store = Record r (Struct (Bool, (Struct a, ()))) (T a)
-> T a
-> Value (Ptr (Struct (Bool, (Struct a, ()))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r (Struct (Bool, (Struct a, ()))) (T a)
forall a r. C a => Record r (Struct (Bool, (Struct a, ()))) (T a)
maybe
   decompose :: forall r. Value (Struct (T a)) -> CodeGenFunction r (T a)
decompose = Record r (Struct (Bool, (Struct a, ()))) (T a)
-> Value (Struct (Bool, (Struct a, ()))) -> CodeGenFunction r (T a)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r (Struct (Bool, (Struct a, ()))) (T a)
forall a r. C a => Record r (Struct (Bool, (Struct a, ()))) (T a)
maybe
   compose :: forall r. T a -> CodeGenFunction r (Value (Struct (T a)))
compose = Record r (Struct (Bool, (Struct a, ()))) (T a)
-> T a -> CodeGenFunction r (Value (Struct (Bool, (Struct a, ()))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r (Struct (Bool, (Struct a, ()))) (T a)
forall a r. C a => Record r (Struct (Bool, (Struct a, ()))) (T a)
maybe


either ::
   (C a, C b) =>
   Record r (LLVM.Struct (Bool, (Struct a, (Struct b, ())))) (Either.T a b)
either :: forall a b r.
(C a, C b) =>
Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
either =
   (Value Bool -> a -> b -> T a b)
-> Element
     r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) (Value Bool)
-> Element r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) a
-> Element r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) b
-> Element
     r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) (T a b)
forall (f :: * -> *) a b c d.
Applicative f =>
(a -> b -> c -> d) -> f a -> f b -> f c -> f d
liftA3 Value Bool -> a -> b -> T a b
forall a b. Value Bool -> a -> b -> T a b
Either.Cons
      ((T a b -> Value Bool)
-> Proxy D0
-> Element
     r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) (Value Bool)
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element T a b -> Value Bool
forall a b. T a b -> Value Bool
Either.isRight Proxy D0
d0)
      ((T a b -> a)
-> Proxy D1
-> Element r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) a
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element T a b -> a
forall a b. T a b -> a
Either.fromLeft Proxy D1
d1)
      ((T a b -> b)
-> Proxy D2
-> Element r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b) b
forall x o n v r.
(C x, IsType o, GetValue o n, ValueType o n ~ Struct x,
 GetElementPtr o (n, ()), ElementPtrType o (n, ()) ~ Struct x) =>
(v -> x) -> n -> Element r o v x
element T a b -> b
forall a b. T a b -> b
Either.fromRight Proxy D2
d2)

instance (C a, C b) => C (Either.T a b) where
   type Struct (Either.T a b) = LLVM.Struct (Bool, (Struct a, (Struct b, ())))
   load :: forall r. Value (Ptr (Struct (T a b))) -> CodeGenFunction r (T a b)
load = Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
-> Value (Ptr (Struct (Bool, (Struct a, (Struct b, ())))))
-> CodeGenFunction r (T a b)
forall r o llvmValue.
Record r o llvmValue
-> Value (Ptr o) -> CodeGenFunction r llvmValue
loadRecord Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
forall a b r.
(C a, C b) =>
Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
either
   store :: forall r.
T a b -> Value (Ptr (Struct (T a b))) -> CodeGenFunction r ()
store = Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
-> T a b
-> Value (Ptr (Struct (Bool, (Struct a, (Struct b, ())))))
-> CodeGenFunction r ()
forall r o llvmValue.
Record r o llvmValue
-> llvmValue -> Value (Ptr o) -> CodeGenFunction r ()
storeRecord Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
forall a b r.
(C a, C b) =>
Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
either
   decompose :: forall r. Value (Struct (T a b)) -> CodeGenFunction r (T a b)
decompose = Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
-> Value (Struct (Bool, (Struct a, (Struct b, ()))))
-> CodeGenFunction r (T a b)
forall r o llvmValue.
Record r o llvmValue -> Value o -> CodeGenFunction r llvmValue
decomposeRecord Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
forall a b r.
(C a, C b) =>
Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
either
   compose :: forall r. T a b -> CodeGenFunction r (Value (Struct (T a b)))
compose = Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
-> T a b
-> CodeGenFunction
     r (Value (Struct (Bool, (Struct a, (Struct b, ())))))
forall o r llvmValue.
IsType o =>
Record r o llvmValue -> llvmValue -> CodeGenFunction r (Value o)
composeRecord Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
forall a b r.
(C a, C b) =>
Record r (Struct (Bool, (Struct a, (Struct b, ())))) (T a b)
either



instance (C a) => C (Scalar.T a) where
   type Struct (Scalar.T a) = Struct a
   load :: forall r. Value (Ptr (Struct (T a))) -> CodeGenFunction r (T a)
load = (a -> T a) -> Value (Ptr (Struct a)) -> CodeGenFunction r (T a)
forall a llvmValue r.
C a =>
(a -> llvmValue)
-> Value (Ptr (Struct a)) -> CodeGenFunction r llvmValue
loadNewtype a -> T a
forall a. a -> T a
Scalar.Cons
   store :: forall r. T a -> Value (Ptr (Struct (T a))) -> CodeGenFunction r ()
store = (T a -> a) -> T a -> Value (Ptr (Struct a)) -> CodeGenFunction r ()
forall a llvmValue r.
C a =>
(llvmValue -> a)
-> llvmValue -> Value (Ptr (Struct a)) -> CodeGenFunction r ()
storeNewtype T a -> a
forall a. T a -> a
Scalar.decons
   decompose :: forall r. Value (Struct (T a)) -> CodeGenFunction r (T a)
decompose = (a -> T a) -> Value (Struct a) -> CodeGenFunction r (T a)
forall a llvmValue r.
C a =>
(a -> llvmValue) -> Value (Struct a) -> CodeGenFunction r llvmValue
decomposeNewtype a -> T a
forall a. a -> T a
Scalar.Cons
   compose :: forall r. T a -> CodeGenFunction r (Value (Struct (T a)))
compose = (T a -> a) -> T a -> CodeGenFunction r (Value (Struct a))
forall a llvmValue r.
C a =>
(llvmValue -> a)
-> llvmValue -> CodeGenFunction r (Value (Struct a))
composeNewtype T a -> a
forall a. T a -> a
Scalar.decons


instance (IsSized a) => C (Value a) where
   type Struct (Value a) = a
   load :: forall r.
Value (Ptr (Struct (Value a))) -> CodeGenFunction r (Value a)
load = Value (Ptr a) -> CodeGenFunction r (Value a)
Value (Ptr (Struct (Value a))) -> CodeGenFunction r (Value a)
forall a r.
IsType a =>
Value (Ptr a) -> CodeGenFunction r (Value a)
LLVM.load
   store :: forall r.
Value a -> Value (Ptr (Struct (Value a))) -> CodeGenFunction r ()
store = Value a -> Value (Ptr a) -> CodeGenFunction r ()
Value a -> Value (Ptr (Struct (Value a))) -> CodeGenFunction r ()
forall a r.
IsType a =>
Value a -> Value (Ptr a) -> CodeGenFunction r ()
LLVM.store
   decompose :: forall r. Value (Struct (Value a)) -> CodeGenFunction r (Value a)
decompose = Value a -> CodeGenFunction r (Value a)
Value (Struct (Value a)) -> CodeGenFunction r (Value a)
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return
   compose :: forall r. Value a -> CodeGenFunction r (Value (Struct (Value a)))
compose = Value a -> CodeGenFunction r (Value a)
Value a -> CodeGenFunction r (Value (Struct (Value a)))
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return


type family StructStruct s
type instance StructStruct (a,as) = (Struct a, StructStruct as)
type instance StructStruct () = ()

instance
   (Struct.Phi s, Struct.Undefined s,
    LLVM.StructFields (StructStruct s),
    ConvertStruct (StructStruct s) TypeNum.D0 s) =>
      C (Struct.T s) where
   type Struct (Struct.T s) = LLVM.Struct (StructStruct s)
   decompose :: forall r. Value (Struct (T s)) -> CodeGenFunction r (T s)
decompose = (s -> T s) -> CodeGenFunction r s -> CodeGenFunction r (T s)
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap s -> T s
forall struct. struct -> T struct
Struct.Cons (CodeGenFunction r s -> CodeGenFunction r (T s))
-> (Value (Struct (StructStruct s)) -> CodeGenFunction r s)
-> Value (Struct (StructStruct s))
-> CodeGenFunction r (T s)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Proxy D0 -> Value (Struct (StructStruct s)) -> CodeGenFunction r s
forall r.
Proxy D0 -> Value (Struct (StructStruct s)) -> CodeGenFunction r s
forall s i rem r.
ConvertStruct s i rem =>
Proxy i -> Value (Struct s) -> CodeGenFunction r rem
decomposeFields Proxy D0
TypeNum.d0
   compose :: forall r. T s -> CodeGenFunction r (Value (Struct (T s)))
compose (Struct.Cons s
s) = Proxy D0
-> s -> CodeGenFunction r (Value (Struct (StructStruct s)))
forall r.
Proxy D0
-> s -> CodeGenFunction r (Value (Struct (StructStruct s)))
forall s i rem r.
ConvertStruct s i rem =>
Proxy i -> rem -> CodeGenFunction r (Value (Struct s))
composeFields Proxy D0
TypeNum.d0 s
s

class ConvertStruct s i rem where
   decomposeFields ::
      Proxy i -> Value (LLVM.Struct s) -> CodeGenFunction r rem
   composeFields ::
      Proxy i -> rem -> CodeGenFunction r (Value (LLVM.Struct s))

instance
   (TypeNum.Natural i, LLVM.GetField s i, LLVM.FieldType s i ~ Struct a, C a,
    ConvertStruct s (TypeNum.Succ i) rem) =>
      ConvertStruct s i (a,rem) where
   decomposeFields :: forall r. Proxy i -> Value (Struct s) -> CodeGenFunction r (a, rem)
decomposeFields Proxy i
i Value (Struct s)
sm =
      (a -> rem -> (a, rem))
-> CodeGenFunction r a
-> CodeGenFunction r rem
-> CodeGenFunction r (a, rem)
forall a b c.
(a -> b -> c)
-> CodeGenFunction r a
-> CodeGenFunction r b
-> CodeGenFunction r c
forall (f :: * -> *) a b c.
Applicative f =>
(a -> b -> c) -> f a -> f b -> f c
liftA2 (,)
         (Value (Struct a) -> CodeGenFunction r a
forall r. Value (Struct a) -> CodeGenFunction r a
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose (Value (Struct a) -> CodeGenFunction r a)
-> CodeGenFunction r (Value (Struct a)) -> CodeGenFunction r a
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Value (Struct s)
-> Proxy i
-> CodeGenFunction r (Value (ValueType (Struct s) (Proxy i)))
forall r agg i.
GetValue agg i =>
Value agg -> i -> CodeGenFunction r (Value (ValueType agg i))
LLVM.extractvalue Value (Struct s)
sm Proxy i
i)
         (Proxy (Succ i) -> Value (Struct s) -> CodeGenFunction r rem
forall r.
Proxy (Succ i) -> Value (Struct s) -> CodeGenFunction r rem
forall s i rem r.
ConvertStruct s i rem =>
Proxy i -> Value (Struct s) -> CodeGenFunction r rem
decomposeFields (Proxy i -> Proxy (Succ i)
forall n. Proxy n -> Proxy (Succ n)
decSucc Proxy i
i) Value (Struct s)
sm)
   composeFields :: forall r.
Proxy i -> (a, rem) -> CodeGenFunction r (Value (Struct s))
composeFields Proxy i
i (a
a,rem
as) = do
      Value (Struct s)
sm <- Proxy (Succ i) -> rem -> CodeGenFunction r (Value (Struct s))
forall r.
Proxy (Succ i) -> rem -> CodeGenFunction r (Value (Struct s))
forall s i rem r.
ConvertStruct s i rem =>
Proxy i -> rem -> CodeGenFunction r (Value (Struct s))
composeFields (Proxy i -> Proxy (Succ i)
forall n. Proxy n -> Proxy (Succ n)
decSucc Proxy i
i) rem
as
      Value (Struct a)
am <- a -> CodeGenFunction r (Value (Struct a))
forall r. a -> CodeGenFunction r (Value (Struct a))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose a
a
      Value (Struct s)
-> Value (ValueType (Struct s) (Proxy i))
-> Proxy i
-> CodeGenFunction r (Value (Struct s))
forall r agg i.
GetValue agg i =>
Value agg
-> Value (ValueType agg i) -> i -> CodeGenFunction r (Value agg)
LLVM.insertvalue Value (Struct s)
sm Value (ValueType (Struct s) (Proxy i))
Value (Struct a)
am Proxy i
i

decSucc :: Proxy n -> Proxy (TypeNum.Succ n)
decSucc :: forall n. Proxy n -> Proxy (Succ n)
decSucc Proxy n
Proxy = Proxy (Succ n)
forall a. Proxy a
Proxy

instance (LLVM.StructFields s) => ConvertStruct s i () where
   decomposeFields :: forall r. Proxy i -> Value (Struct s) -> CodeGenFunction r ()
decomposeFields Proxy i
_ Value (Struct s)
_ = () -> CodeGenFunction r ()
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
   composeFields :: forall r. Proxy i -> () -> CodeGenFunction r (Value (Struct s))
composeFields Proxy i
_ ()
_ = Value (Struct s) -> CodeGenFunction r (Value (Struct s))
forall a. a -> CodeGenFunction r a
forall (m :: * -> *) a. Monad m => a -> m a
return (ConstValue (Struct s) -> Value (Struct s)
forall a. ConstValue a -> Value a
LLVM.value ConstValue (Struct s)
forall a. IsType a => ConstValue a
LLVM.undef)



-- redundant IsType and IsSized constraints required for loopy instance
instance
   (IsType (Struct (MultiValue.Repr a)),
    IsSized (Struct (MultiValue.Repr a)),
    MultiValue.C a, C (MultiValue.Repr a)) =>
      C (MultiValue.T a) where
   type Struct (MultiValue.T a) = Struct (MultiValue.Repr a)
   load :: forall r. Value (Ptr (Struct (T a))) -> CodeGenFunction r (T a)
load = (Repr a -> T a)
-> CodeGenFunction r (Repr a) -> CodeGenFunction r (T a)
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Repr a -> T a
forall a. Repr a -> T a
MultiValue.Cons (CodeGenFunction r (Repr a) -> CodeGenFunction r (T a))
-> (Value (Ptr (Struct (Repr a))) -> CodeGenFunction r (Repr a))
-> Value (Ptr (Struct (Repr a)))
-> CodeGenFunction r (T a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Value (Ptr (Struct (Repr a))) -> CodeGenFunction r (Repr a)
forall r.
Value (Ptr (Struct (Repr a))) -> CodeGenFunction r (Repr a)
forall llvmValue r.
C llvmValue =>
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
load
   store :: forall r. T a -> Value (Ptr (Struct (T a))) -> CodeGenFunction r ()
store (MultiValue.Cons Repr a
a) = Repr a -> Value (Ptr (Struct (Repr a))) -> CodeGenFunction r ()
forall r.
Repr a -> Value (Ptr (Struct (Repr a))) -> CodeGenFunction r ()
forall llvmValue r.
C llvmValue =>
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
store Repr a
a
   decompose :: forall r. Value (Struct (T a)) -> CodeGenFunction r (T a)
decompose = (Repr a -> T a)
-> CodeGenFunction r (Repr a) -> CodeGenFunction r (T a)
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Repr a -> T a
forall a. Repr a -> T a
MultiValue.Cons (CodeGenFunction r (Repr a) -> CodeGenFunction r (T a))
-> (Value (Struct (Repr a)) -> CodeGenFunction r (Repr a))
-> Value (Struct (Repr a))
-> CodeGenFunction r (T a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Value (Struct (Repr a)) -> CodeGenFunction r (Repr a)
forall r. Value (Struct (Repr a)) -> CodeGenFunction r (Repr a)
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose
   compose :: forall r. T a -> CodeGenFunction r (Value (Struct (T a)))
compose (MultiValue.Cons Repr a
a) = Repr a -> CodeGenFunction r (Value (Struct (Repr a)))
forall r. Repr a -> CodeGenFunction r (Value (Struct (Repr a)))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose Repr a
a

instance
   (IsType (Struct (MultiVector.Repr n a)),
    IsSized (Struct (MultiVector.Repr n a)),
    TypeNum.Positive n, MultiVector.C a, C (MultiVector.Repr n a)) =>
      C (MultiVector.T n a) where
   type Struct (MultiVector.T n a) = Struct (MultiVector.Repr n a)
   load :: forall r. Value (Ptr (Struct (T n a))) -> CodeGenFunction r (T n a)
load = (Repr n a -> T n a)
-> CodeGenFunction r (Repr n a) -> CodeGenFunction r (T n a)
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Repr n a -> T n a
forall n a. Repr n a -> T n a
MultiVector.Cons (CodeGenFunction r (Repr n a) -> CodeGenFunction r (T n a))
-> (Value (Ptr (Struct (Repr n a)))
    -> CodeGenFunction r (Repr n a))
-> Value (Ptr (Struct (Repr n a)))
-> CodeGenFunction r (T n a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Value (Ptr (Struct (Repr n a))) -> CodeGenFunction r (Repr n a)
forall r.
Value (Ptr (Struct (Repr n a))) -> CodeGenFunction r (Repr n a)
forall llvmValue r.
C llvmValue =>
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
load
   store :: forall r.
T n a -> Value (Ptr (Struct (T n a))) -> CodeGenFunction r ()
store (MultiVector.Cons Repr n a
a) = Repr n a -> Value (Ptr (Struct (Repr n a))) -> CodeGenFunction r ()
forall r.
Repr n a -> Value (Ptr (Struct (Repr n a))) -> CodeGenFunction r ()
forall llvmValue r.
C llvmValue =>
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
store Repr n a
a
   decompose :: forall r. Value (Struct (T n a)) -> CodeGenFunction r (T n a)
decompose = (Repr n a -> T n a)
-> CodeGenFunction r (Repr n a) -> CodeGenFunction r (T n a)
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Repr n a -> T n a
forall n a. Repr n a -> T n a
MultiVector.Cons (CodeGenFunction r (Repr n a) -> CodeGenFunction r (T n a))
-> (Value (Struct (Repr n a)) -> CodeGenFunction r (Repr n a))
-> Value (Struct (Repr n a))
-> CodeGenFunction r (T n a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Value (Struct (Repr n a)) -> CodeGenFunction r (Repr n a)
forall r. Value (Struct (Repr n a)) -> CodeGenFunction r (Repr n a)
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose
   compose :: forall r. T n a -> CodeGenFunction r (Value (Struct (T n a)))
compose (MultiVector.Cons Repr n a
a) = Repr n a -> CodeGenFunction r (Value (Struct (Repr n a)))
forall r. Repr n a -> CodeGenFunction r (Value (Struct (Repr n a)))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose Repr n a
a



loadNewtype ::
   (C a) =>
   (a -> llvmValue) ->
   Value (LLVM.Ptr (Struct a)) -> CodeGenFunction r llvmValue
loadNewtype :: forall a llvmValue r.
C a =>
(a -> llvmValue)
-> Value (Ptr (Struct a)) -> CodeGenFunction r llvmValue
loadNewtype a -> llvmValue
wrap Value (Ptr (Struct a))
ptr =
   (a -> llvmValue)
-> CodeGenFunction r a -> CodeGenFunction r llvmValue
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> llvmValue
wrap (CodeGenFunction r a -> CodeGenFunction r llvmValue)
-> CodeGenFunction r a -> CodeGenFunction r llvmValue
forall a b. (a -> b) -> a -> b
$ Value (Ptr (Struct a)) -> CodeGenFunction r a
forall r. Value (Ptr (Struct a)) -> CodeGenFunction r a
forall llvmValue r.
C llvmValue =>
Value (Ptr (Struct llvmValue)) -> CodeGenFunction r llvmValue
load Value (Ptr (Struct a))
ptr

storeNewtype ::
   (C a) =>
   (llvmValue -> a) ->
   llvmValue -> Value (LLVM.Ptr (Struct a)) -> CodeGenFunction r ()
storeNewtype :: forall a llvmValue r.
C a =>
(llvmValue -> a)
-> llvmValue -> Value (Ptr (Struct a)) -> CodeGenFunction r ()
storeNewtype llvmValue -> a
unwrap llvmValue
y Value (Ptr (Struct a))
ptr =
   a -> Value (Ptr (Struct a)) -> CodeGenFunction r ()
forall r. a -> Value (Ptr (Struct a)) -> CodeGenFunction r ()
forall llvmValue r.
C llvmValue =>
llvmValue -> Value (Ptr (Struct llvmValue)) -> CodeGenFunction r ()
store (llvmValue -> a
unwrap llvmValue
y) Value (Ptr (Struct a))
ptr

decomposeNewtype ::
   (C a) =>
   (a -> llvmValue) ->
   Value (Struct a) -> CodeGenFunction r llvmValue
decomposeNewtype :: forall a llvmValue r.
C a =>
(a -> llvmValue) -> Value (Struct a) -> CodeGenFunction r llvmValue
decomposeNewtype a -> llvmValue
wrap Value (Struct a)
y =
   (a -> llvmValue)
-> CodeGenFunction r a -> CodeGenFunction r llvmValue
forall a b. (a -> b) -> CodeGenFunction r a -> CodeGenFunction r b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> llvmValue
wrap (CodeGenFunction r a -> CodeGenFunction r llvmValue)
-> CodeGenFunction r a -> CodeGenFunction r llvmValue
forall a b. (a -> b) -> a -> b
$ Value (Struct a) -> CodeGenFunction r a
forall r. Value (Struct a) -> CodeGenFunction r a
forall llvmValue r.
C llvmValue =>
Value (Struct llvmValue) -> CodeGenFunction r llvmValue
decompose Value (Struct a)
y

composeNewtype ::
   (C a) =>
   (llvmValue -> a) ->
   llvmValue -> CodeGenFunction r (Value (Struct a))
composeNewtype :: forall a llvmValue r.
C a =>
(llvmValue -> a)
-> llvmValue -> CodeGenFunction r (Value (Struct a))
composeNewtype llvmValue -> a
unwrap llvmValue
y =
   a -> CodeGenFunction r (Value (Struct a))
forall r. a -> CodeGenFunction r (Value (Struct a))
forall llvmValue r.
C llvmValue =>
llvmValue -> CodeGenFunction r (Value (Struct llvmValue))
compose (llvmValue -> a
unwrap llvmValue
y)