|
1 | 1 | -- | Mutable buffers and associated operations. |
2 | 2 | module Node.Buffer |
3 | | - ( class MutableBuffer |
4 | | - , create |
5 | | - , freeze |
6 | | - , unsafeFreeze |
7 | | - , thaw |
8 | | - , unsafeThaw |
9 | | - , fromArray |
10 | | - , fromString |
11 | | - , fromArrayBuffer |
12 | | - , toArrayBuffer |
13 | | - , read |
14 | | - , readString |
15 | | - , toString |
16 | | - , write |
17 | | - , writeString |
18 | | - , toArray |
19 | | - , getAtOffset |
20 | | - , setAtOffset |
21 | | - , slice |
22 | | - , size |
23 | | - , concat |
24 | | - , concat' |
25 | | - , copy |
26 | | - , fill |
27 | | - , Buffer |
28 | | - , STBuffer |
29 | | - , runST |
| 3 | + ( Buffer |
30 | 4 | , module TypesExports |
| 5 | + , module Class |
31 | 6 | ) where |
32 | 7 |
|
33 | | -import Prelude |
34 | | - |
35 | | -import Control.Monad.ST (ST, kind Region) |
36 | | -import Control.Monad.ST as ST |
37 | | -import Data.ArrayBuffer.Types (ArrayBuffer) |
38 | | -import Data.Maybe (Maybe) |
39 | 8 | import Effect (Effect) |
40 | | -import Node.Buffer.Immutable (ImmutableBuffer) |
41 | | -import Node.Buffer.Immutable as Immutable |
42 | | -import Node.Buffer.Types (BufferValueType, Octet, Offset) |
| 9 | +import Node.Buffer.Class (class MutableBuffer) |
| 10 | +import Node.Buffer.Class (class MutableBuffer, concat, concat', copy, create, fill, freeze, fromArray, fromArrayBuffer, fromString, getAtOffset, read, readString, setAtOffset, size, slice, thaw, toArray, toArrayBuffer, toString, unsafeFreeze, unsafeThaw, write, writeString) as Class |
| 11 | +import Node.Buffer.Internal as Internal |
43 | 12 | import Node.Buffer.Types (BufferValueType(..), Octet, Offset) as TypesExports |
44 | | -import Node.Encoding (Encoding, encodingToNode) |
45 | | -import Unsafe.Coerce (unsafeCoerce) |
46 | | - |
47 | | --- | A type class for mutable buffers `buf` where operations on those buffers are |
48 | | --- | represented by a particular monadic effect type `m`. |
49 | | -class Monad m <= MutableBuffer buf m | m -> buf, buf -> m where |
50 | | - |
51 | | - -- | Creates a new buffer of the specified size. |
52 | | - create :: Int -> m buf |
53 | | - |
54 | | - -- | Creates an immutable copy of a mutable buffer. |
55 | | - freeze :: buf -> m ImmutableBuffer |
56 | | - |
57 | | - -- | O(1). Convert a mutable buffer to an immutable buffer, without copying. The |
58 | | - -- | mutable buffer must not be mutated afterwards. |
59 | | - unsafeFreeze :: buf -> m ImmutableBuffer |
60 | | - |
61 | | - -- | Creates a mutable copy of an immutable buffer. |
62 | | - thaw :: ImmutableBuffer -> m buf |
63 | | - |
64 | | - -- | O(1) Convert an immutable buffer to a mutable buffer, without copying. The |
65 | | - -- | input buffer must not be used afterward. |
66 | | - unsafeThaw :: ImmutableBuffer -> m buf |
67 | | - |
68 | | - -- | Creates a new buffer from an array of octets, sized to match the array. |
69 | | - fromArray :: Array Octet -> m buf |
70 | | - |
71 | | - -- | Creates a new buffer from a string with the specified encoding, sized to |
72 | | - -- | match the string. |
73 | | - fromString :: String -> Encoding -> m buf |
74 | | - |
75 | | - -- | Creates a buffer view from a JS ArrayByffer without copying data. |
76 | | - fromArrayBuffer :: ArrayBuffer -> m buf |
77 | | - |
78 | | - -- | Copies the data in the buffer to a new JS ArrayBuffer |
79 | | - toArrayBuffer :: buf -> m ArrayBuffer |
80 | | - |
81 | | - -- | Reads a numeric value from a buffer at the specified offset. |
82 | | - read :: BufferValueType -> Offset -> buf -> m Int |
83 | | - |
84 | | - -- | Reads a section of a buffer as a string with the specified encoding. |
85 | | - readString :: Encoding -> Offset -> Offset -> buf -> m String |
86 | | - |
87 | | - -- | Reads the buffer as a string with the specified encoding. |
88 | | - toString :: Encoding -> buf -> m String |
89 | | - |
90 | | - -- | Writes a numeric value to a buffer at the specified offset. |
91 | | - write :: BufferValueType -> Int -> Offset -> buf -> m Unit |
92 | | - |
93 | | - -- | Writes octets from a string to a buffer at the specified offset. Multi-byte |
94 | | - -- | characters will not be written to the buffer if there is not enough capacity |
95 | | - -- | to write them fully. The number of bytes written is returned. |
96 | | - writeString :: Encoding -> Offset -> Int -> String -> buf -> m Int |
97 | | - |
98 | | - -- | Creates an array of octets from a buffer's contents. |
99 | | - toArray :: buf -> m (Array Octet) |
100 | | - |
101 | | - -- | Reads an octet from a buffer at the specified offset. |
102 | | - getAtOffset :: Offset -> buf -> m (Maybe Octet) |
103 | | - |
104 | | - -- | Writes an octet in the buffer at the specified offset. |
105 | | - setAtOffset :: Octet -> Offset -> buf -> m Unit |
106 | | - |
107 | | - -- | Creates a new buffer slice that acts like a window on the original buffer. |
108 | | - -- | Writing to the slice buffer updates the original buffer and vice-versa. |
109 | | - slice :: Offset -> Offset -> buf -> buf |
110 | | - |
111 | | - -- | Returns the size of a buffer. |
112 | | - size :: buf -> m Int |
113 | | - |
114 | | - -- | Concatenates a list of buffers. |
115 | | - concat :: Array buf -> m buf |
116 | | - |
117 | | - -- | Concatenates a list of buffers, combining them into a new buffer of the |
118 | | - -- | specified length. |
119 | | - concat' :: Array buf -> Int -> m buf |
120 | | - |
121 | | - -- | Copies a section of a source buffer into a target buffer at the specified |
122 | | - -- | offset, and returns the number of octets copied. |
123 | | - copy :: Offset -> Offset -> buf -> Offset -> buf -> m Int |
124 | | - |
125 | | - -- | Fills a range in a buffer with the specified octet. |
126 | | - fill :: Octet -> Offset -> Offset -> buf -> m Unit |
127 | 13 |
|
128 | 14 | -- | A reference to a mutable buffer for use with `Effect` |
129 | 15 | foreign import data Buffer :: Type |
130 | 16 |
|
131 | | --- | A reference to a mutable buffer for use with `ST` |
132 | | --- | |
133 | | --- | The type parameter represents the memory region which the buffer belongs to. |
134 | | -foreign import data STBuffer :: Region -> Type |
135 | | - |
136 | | --- | Runs an effect creating an `STBuffer` then freezes the buffer and returns |
137 | | --- | it, without unneccessary copying. |
138 | | -runST :: (forall h. ST h (STBuffer h)) -> ImmutableBuffer |
139 | | -runST st = ST.run (st >>= unsafeFreeze) |
140 | | - |
141 | 17 | instance mutableBufferEffect :: MutableBuffer Buffer Effect where |
142 | | - create = createImpl |
143 | | - freeze = copyAllImpl |
144 | | - unsafeFreeze = unsafeFreezeImpl |
145 | | - thaw = copyAllImpl |
146 | | - unsafeThaw = unsafeThawImpl |
147 | | - fromArray = fromArrayImpl |
148 | | - fromString = fromStringImpl |
149 | | - fromArrayBuffer = fromArrayBufferImpl |
150 | | - toArrayBuffer = toArrayBufferImpl |
151 | | - read = readImpl |
152 | | - readString = readStringImpl |
153 | | - toString = toStringImpl |
154 | | - write = writeImpl |
155 | | - writeString = writeStringImpl |
156 | | - toArray = toArrayImpl |
157 | | - getAtOffset = getAtOffsetImpl |
158 | | - setAtOffset = setAtOffsetImpl |
159 | | - slice = sliceImpl |
160 | | - size = sizeImpl |
161 | | - concat = concatImpl |
162 | | - concat' = concatImpl' |
163 | | - copy = copyImpl |
164 | | - fill = fillImpl |
165 | | - |
166 | | -instance mutableBufferST :: MutableBuffer (STBuffer h) (ST h) where |
167 | | - create = createImpl |
168 | | - freeze = copyAllImpl |
169 | | - unsafeFreeze = unsafeFreezeImpl |
170 | | - thaw = copyAllImpl |
171 | | - unsafeThaw = unsafeThawImpl |
172 | | - fromArray = fromArrayImpl |
173 | | - fromString = fromStringImpl |
174 | | - fromArrayBuffer = fromArrayBufferImpl |
175 | | - toArrayBuffer = toArrayBufferImpl |
176 | | - read = readImpl |
177 | | - readString = readStringImpl |
178 | | - toString = toStringImpl |
179 | | - write = writeImpl |
180 | | - writeString = writeStringImpl |
181 | | - toArray = toArrayImpl |
182 | | - getAtOffset = getAtOffsetImpl |
183 | | - setAtOffset = setAtOffsetImpl |
184 | | - slice = sliceImpl |
185 | | - size = sizeImpl |
186 | | - concat = concatImpl |
187 | | - concat' = concatImpl' |
188 | | - copy = copyImpl |
189 | | - fill = fillImpl |
190 | | - |
191 | | -unsafeFreezeImpl :: forall buf m. Monad m => buf -> m ImmutableBuffer |
192 | | -unsafeFreezeImpl = pure <<< unsafeCoerce |
193 | | - |
194 | | -unsafeThawImpl :: forall buf m. Monad m => ImmutableBuffer -> m buf |
195 | | -unsafeThawImpl = pure <<< unsafeCoerce |
196 | | - |
197 | | -usingFromImmutable :: forall buf m a. Monad m => (ImmutableBuffer -> a) -> buf -> m a |
198 | | -usingFromImmutable f buf = f <$> unsafeFreezeImpl buf |
199 | | - |
200 | | -usingToImmutable :: forall buf m a. Monad m => (a -> ImmutableBuffer) -> a -> m buf |
201 | | -usingToImmutable f x = unsafeThawImpl $ f x |
202 | | - |
203 | | -createImpl :: forall buf m. Monad m => Int -> m buf |
204 | | -createImpl = usingToImmutable Immutable.create |
205 | | - |
206 | | -foreign import copyAllImpl :: forall a buf m. a -> m buf |
207 | | - |
208 | | -fromArrayImpl :: forall buf m. Monad m => Array Octet -> m buf |
209 | | -fromArrayImpl = usingToImmutable Immutable.fromArray |
210 | | - |
211 | | -fromStringImpl :: forall buf m. Monad m => String -> Encoding -> m buf |
212 | | -fromStringImpl s = usingToImmutable $ Immutable.fromString s |
213 | | - |
214 | | -fromArrayBufferImpl :: forall buf m. Monad m => ArrayBuffer -> m buf |
215 | | -fromArrayBufferImpl = usingToImmutable Immutable.fromArrayBuffer |
216 | | - |
217 | | -toArrayBufferImpl :: forall buf m. Monad m => buf -> m ArrayBuffer |
218 | | -toArrayBufferImpl = usingFromImmutable Immutable.toArrayBuffer |
219 | | - |
220 | | -readImpl :: forall buf m. Monad m => BufferValueType -> Offset -> buf -> m Int |
221 | | -readImpl t o = usingFromImmutable $ Immutable.read t o |
222 | | - |
223 | | -readStringImpl :: forall buf m. Monad m => Encoding -> Offset -> Offset -> buf -> m String |
224 | | -readStringImpl m o o' = usingFromImmutable $ Immutable.readString m o o' |
225 | | - |
226 | | -toStringImpl :: forall buf m. Monad m => Encoding -> buf -> m String |
227 | | -toStringImpl m = usingFromImmutable $ Immutable.toString m |
228 | | - |
229 | | -writeImpl :: forall buf m. Monad m => BufferValueType -> Int -> Offset -> buf -> m Unit |
230 | | -writeImpl = writeInternal <<< show |
231 | | - |
232 | | -foreign import writeInternal :: forall buf m. String -> Int -> Offset -> buf -> m Unit |
233 | | - |
234 | | -writeStringImpl :: forall buf m. Monad m => Encoding -> Offset -> Int -> String -> buf -> m Int |
235 | | -writeStringImpl = writeStringInternal <<< encodingToNode |
236 | | - |
237 | | -foreign import writeStringInternal :: |
238 | | - forall buf m. String -> Offset -> Int -> String -> buf -> m Int |
239 | | - |
240 | | -toArrayImpl :: forall buf m. Monad m => buf -> m (Array Octet) |
241 | | -toArrayImpl = usingFromImmutable Immutable.toArray |
242 | | - |
243 | | -getAtOffsetImpl :: forall buf m. Monad m => Offset -> buf -> m (Maybe Octet) |
244 | | -getAtOffsetImpl o = usingFromImmutable $ Immutable.getAtOffset o |
245 | | - |
246 | | -foreign import setAtOffsetImpl :: forall buf m. Octet -> Offset -> buf -> m Unit |
247 | | - |
248 | | -sliceImpl :: forall buf. Offset -> Offset -> buf -> buf |
249 | | -sliceImpl = unsafeCoerce Immutable.slice |
250 | | - |
251 | | -sizeImpl :: forall buf m. Monad m => buf -> m Int |
252 | | -sizeImpl = usingFromImmutable Immutable.size |
253 | | - |
254 | | -concatImpl :: forall buf m. Array buf -> m buf |
255 | | -concatImpl arrs = unsafeCoerce \_ -> Immutable.concat (unsafeCoerce arrs) |
256 | | - |
257 | | -concatImpl' :: forall buf m. Monad m => Array buf -> Int -> m buf |
258 | | -concatImpl' arrs n = unsafeCoerce \_ -> Immutable.concat' (unsafeCoerce arrs) n |
259 | | - |
260 | | -foreign import copyImpl :: forall buf m. Offset -> Offset -> buf -> Offset -> buf -> m Int |
261 | | - |
262 | | -foreign import fillImpl :: forall buf m. Octet -> Offset -> Offset -> buf -> m Unit |
| 18 | + create = Internal.create |
| 19 | + freeze = Internal.copyAll |
| 20 | + unsafeFreeze = Internal.unsafeFreeze |
| 21 | + thaw = Internal.copyAll |
| 22 | + unsafeThaw = Internal.unsafeThaw |
| 23 | + fromArray = Internal.fromArray |
| 24 | + fromString = Internal.fromString |
| 25 | + fromArrayBuffer = Internal.fromArrayBuffer |
| 26 | + toArrayBuffer = Internal.toArrayBuffer |
| 27 | + read = Internal.read |
| 28 | + readString = Internal.readString |
| 29 | + toString = Internal.toString |
| 30 | + write = Internal.write |
| 31 | + writeString = Internal.writeString |
| 32 | + toArray = Internal.toArray |
| 33 | + getAtOffset = Internal.getAtOffset |
| 34 | + setAtOffset = Internal.setAtOffset |
| 35 | + slice = Internal.slice |
| 36 | + size = Internal.size |
| 37 | + concat = Internal.concat |
| 38 | + concat' = Internal.concat' |
| 39 | + copy = Internal.copy |
| 40 | + fill = Internal.fill |
0 commit comments