2 | import Control.Monad.Resource
3 | import Data.C.Integer
5 | import Data.Linear.ELift1
8 | import public Data.Fin
9 | import public Data.Linear.Token
10 | import public Data.Array.Index
16 | export %foreign "scheme,chez:(lambda (x y z) (foreign-set! 'unsigned-8 x y z))"
17 | prim__setbits8 : AnyPtr -> Integer -> Bits8 -> PrimIO ()
19 | export %foreign "scheme,chez:(lambda (x y) (foreign-ref 'unsigned-8 x y))"
20 | prim__getbits8 : AnyPtr -> Integer -> Bits8
27 | record CIArray8 (n : Nat) where
32 | at : CIArray8 n -> Fin n -> Bits8
33 | at r x = prim__getbits8 r.ptr (cast $
finToNat x)
36 | ix : CIArray8 n -> (0 m : Nat) -> (x : Ix (S m) n) => Bits8
37 | ix r m = at r (ixToFin x)
40 | atNat : CIArray8 n -> (m : Nat) -> (0 lt : LT m n) => Bits8
41 | atNat r m = at r (natToFinLT m)
43 | foldrI : (m : Nat) -> (0 _ : LTE m n) => (Bits8 -> b -> b) -> b -> CIArray8 n -> b
45 | foldrI (S k) f x r = foldrI k f (f (atNat r k) x) r
49 | -> {auto 0 prf : LTE m n}
50 | -> (Fin n -> Bits8 -> b -> b)
54 | foldrKV_ 0 _ x r = x
55 | foldrKV_ (S k) f x r =
56 | let fin := natToFinLT k @{prf} in foldrKV_ k f (f fin (at r fin) x) r
58 | foldlI : (m : Nat) -> (x : Ix m n) => (b -> Bits8 -> b) -> b -> CIArray8 n -> b
60 | foldlI (S k) f v r = foldlI k f (f v (ix r k)) r
64 | -> {auto x : Ix m n}
65 | -> (Fin n -> b -> Bits8 -> b)
69 | foldlKV_ 0 _ v r = v
70 | foldlKV_ (S k) f v r =
71 | let fin := ixToFin x in foldlKV_ k f (f fin v (at r fin)) r
77 | -> {auto 0 lt : LTE k n}
79 | ontoVect r vs 0 = rewrite plusCommutative m 0 in vs
80 | ontoVect r vs (S x) =
81 | let v := atNat r x {lt}
82 | in rewrite sym (plusSuccRightSucc m x) in ontoVect r (v::vs) x
86 | toVect : {n : _} -> (r : CIArray8 n) -> Vect n Bits8
87 | toVect r = ontoVect r [] n
91 | foldrKV : {n : _} -> (Fin n -> Bits8 -> b -> b) -> b -> CIArray8 n -> b
92 | foldrKV = foldrKV_ n
96 | foldr : {n : _} -> (Bits8 -> b -> b) -> b -> CIArray8 n -> b
101 | foldlKV : {n : _} -> (Fin n -> b -> Bits8 -> b) -> b -> CIArray8 n -> b
102 | foldlKV = foldlKV_ n
106 | foldl : {n : _} -> (b -> Bits8 -> b) -> b -> CIArray8 n -> b
114 | record CArray8 (s : Type) (n : Nat) where
120 | 0 CArray8IO : Nat -> Type
121 | CArray8IO = CArray8 World
124 | unsafeUnwrap : CArray8 s n -> AnyPtr
128 | unsafeWrap : AnyPtr -> CArray8 s n
137 | malloc1 : (n : Nat) -> F1 s (CArray8 s n)
139 | let p := prim__malloc (cast n)
144 | calloc1 : (n : Nat) -> F1 s (CArray8 s n)
146 | let p := prim__calloc (cast n) 1
152 | free1 : (r : CArray8 s n) -> F1' s
153 | free1 r = ffi (prim__free r.ptr)
155 | parameters {0 n : Nat}
160 | get : Fin n -> F1 s Bits8
161 | get x t = prim__getbits8 r.ptr (cast $
finToNat x) # t
165 | getIx : (0 m : Nat) -> (x : Ix (S m) n) => F1 s Bits8
166 | getIx m = get (ixToFin x)
170 | getNat : (m : Nat) -> (0 lt : LT m n) => F1 s Bits8
171 | getNat m = get (natToFinLT m)
175 | set : Fin n -> Bits8 -> F1' s
176 | set x v = ffi $
prim__setbits8 r.ptr (cast $
finToNat x) v
180 | setIx : (0 m : Nat) -> (x : Ix (S m) n) => Bits8 -> F1' s
181 | setIx m = set (ixToFin x)
185 | setNat : (m : Nat) -> (0 lt : LT m n) => Bits8 -> F1' s
186 | setNat m = set (natToFinLT m)
188 | writeVect1 : Vect k Bits8 -> Ix k n => F1' s
189 | writeVect1 [] t = () # t
190 | writeVect1 {k = S m} (x :: xs) t =
191 | let _ # t := Array8.setIx m x t
196 | writeVect : Vect n Bits8 -> F1' s
197 | writeVect as = writeVect1 as
206 | withIArray : (CIArray8 n -> b) -> F1 s b
207 | withIArray f t = f (IA r.ptr) # t
211 | writeList : (as : List Bits8) -> CArray8 s (length as) -> F1' s
212 | writeList as r = writeVect r (fromList as)
215 | withCArray : (n : Nat) -> (f : forall s . CArray8 s n -> F1 s b) -> b
218 | let r # t := Array8.malloc1 n t
220 | _ # t := Array8.free1 r t
227 | parameters {auto has : Lift1 s f}
231 | malloc : (n : Nat) -> f (CArray8 s n)
232 | malloc n = lift1 (malloc1 n)
236 | calloc : (n : Nat) -> f (CArray8 s n)
237 | calloc n = lift1 (calloc1 n)
240 | free : CArray8 s n -> f ()
241 | free arr = lift1 (free1 arr)
244 | fromList : (as : List Bits8) -> f (CArray8 s (length as))
245 | fromList as = Prelude.do
246 | arr <- Array8.malloc (length as)
247 | lift1 $
writeList as arr
255 | ELift1 s f => Resource f (CArray8 s n) where
256 | cleanup arr = lift1 (free1 arr)