@grain/stdlib 0.4.1 → 0.4.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/CHANGELOG.md +63 -0
  2. package/LICENSE +21 -0
  3. package/README.md +34 -0
  4. package/array.gr +200 -89
  5. package/array.md +81 -5
  6. package/buffer.gr +93 -36
  7. package/bytes.gr +512 -407
  8. package/bytes.md +621 -0
  9. package/char.gr +119 -55
  10. package/char.md +200 -0
  11. package/hash.gr +42 -15
  12. package/hash.md +44 -0
  13. package/list.gr +121 -50
  14. package/map.gr +106 -110
  15. package/number.gr +37 -1
  16. package/number.md +66 -0
  17. package/option.gr +260 -53
  18. package/option.md +579 -0
  19. package/package.json +33 -29
  20. package/pervasives.gr +32 -20
  21. package/queue.gr +102 -30
  22. package/queue.md +191 -0
  23. package/range.gr +26 -26
  24. package/range.md +1 -1
  25. package/regex.gr +3055 -0
  26. package/regex.md +449 -0
  27. package/result.gr +216 -70
  28. package/result.md +446 -0
  29. package/runtime/dataStructures.gr +28 -29
  30. package/runtime/debug.gr +0 -1
  31. package/runtime/equal.gr +37 -16
  32. package/runtime/exception.gr +28 -15
  33. package/runtime/gc.gr +33 -20
  34. package/runtime/malloc.gr +19 -11
  35. package/runtime/numberUtils.gr +208 -105
  36. package/runtime/numbers.gr +217 -118
  37. package/runtime/string.gr +150 -59
  38. package/runtime/stringUtils.gr +176 -0
  39. package/runtime/unsafe/conv.gr +51 -8
  40. package/runtime/unsafe/memory.gr +14 -3
  41. package/runtime/unsafe/printWasm.gr +4 -4
  42. package/runtime/unsafe/tags.gr +2 -2
  43. package/runtime/unsafe/wasmf32.gr +9 -2
  44. package/runtime/unsafe/wasmf64.gr +9 -2
  45. package/runtime/unsafe/wasmi32.gr +65 -47
  46. package/runtime/unsafe/wasmi64.gr +78 -50
  47. package/runtime/wasi.gr +199 -45
  48. package/set.gr +281 -119
  49. package/set.md +502 -0
  50. package/stack.gr +26 -26
  51. package/stack.md +143 -0
  52. package/string.gr +697 -329
  53. package/string.md +815 -0
  54. package/sys/file.gr +356 -177
  55. package/sys/process.gr +10 -6
  56. package/sys/random.gr +3 -6
  57. package/sys/time.gr +3 -3
package/buffer.gr CHANGED
@@ -23,17 +23,17 @@ record Buffer {
23
23
  }
24
24
 
25
25
  @disableGC
26
- let mut _SIZE_OFFSET = 1n;
26
+ let mut _SIZE_OFFSET = 1n
27
27
 
28
28
  @disableGC
29
- let mut _VALUE_OFFSET = 1n;
29
+ let mut _VALUE_OFFSET = 1n
30
30
 
31
31
  @disableGC
32
32
  let initOffsets = () => {
33
- _SIZE_OFFSET = 4n;
34
- _VALUE_OFFSET = 8n;
33
+ _SIZE_OFFSET = 4n
34
+ _VALUE_OFFSET = 8n
35
35
  }
36
- initOffsets();
36
+ initOffsets()
37
37
 
38
38
  let _8BIT_LEN = 1
39
39
 
@@ -45,27 +45,28 @@ let _64BIT_LEN = 8
45
45
 
46
46
  /* Gets the size of a Bytes via its ptr */
47
47
  @disableGC
48
- let getSize = (ptr) => WasmI32.load(ptr, _SIZE_OFFSET)
48
+ let getSize = ptr => WasmI32.load(ptr, _SIZE_OFFSET)
49
49
 
50
50
  /* Doubles the size of buffer's underlying byte sequence, if the given size is larger than the size of a buffer's underlying byte sequence */
51
51
  let autogrow = (len, buf) => {
52
52
  while (buf.len + len > Bytes.length(buf.data)) {
53
53
  let mut n = Bytes.length(buf.data)
54
- if (n == 0) n = 4 // Make sure bytes of 0 length grow too
54
+ if (n == 0) n = 4
55
+ // Make sure bytes of 0 length grow too
55
56
  buf.data = Bytes.resize(0, n, buf.data)
56
57
  }
57
58
  }
58
59
 
59
60
  /* Gets the pointer for a char's bytes following the char's tag */
60
61
  @disableGC
61
- let rec getCharAsWasmI32 = (char) => {
62
+ let rec getCharAsWasmI32 = char => {
62
63
  let c = WasmI32.fromGrain(char)
63
64
  WasmI32.load(c, 4n)
64
65
  }
65
66
 
66
67
  /* Gets the UTF-8 byte length of a char */
67
68
  @disableGC
68
- let rec getCharByteLength = (byte) => {
69
+ let rec getCharByteLength = byte => {
69
70
  let (+) = WasmI32.add
70
71
  let (&) = WasmI32.and
71
72
  let (==) = WasmI32.eq
@@ -132,13 +133,10 @@ let addInt32help = (value, buffer) => {
132
133
  *
133
134
  * @since v0.4.0
134
135
  */
135
- export let make = (initialSize) => {
136
- if (initialSize < 0) throw Exception.InvalidArgument("Buffers size must be >= 0")
137
- {
138
- len: 0,
139
- initialSize,
140
- data: Bytes.make(initialSize),
141
- }
136
+ export let make = initialSize => {
137
+ if (initialSize < 0)
138
+ throw Exception.InvalidArgument("Buffers size must be >= 0")
139
+ { len: 0, initialSize, data: Bytes.make(initialSize) }
142
140
  }
143
141
 
144
142
  /**
@@ -149,7 +147,7 @@ export let make = (initialSize) => {
149
147
  *
150
148
  * @since v0.4.0
151
149
  */
152
- export let length = (buffer) => buffer.len
150
+ export let length = buffer => buffer.len
153
151
 
154
152
  /**
155
153
  * Clears data in the buffer and sets its length to zero.
@@ -160,7 +158,7 @@ export let length = (buffer) => buffer.len
160
158
  *
161
159
  * @since v0.4.0
162
160
  */
163
- export let clear = (buffer) => {
161
+ export let clear = buffer => {
164
162
  Bytes.fill(0x0l, buffer.data)
165
163
  buffer.len = 0
166
164
  }
@@ -174,7 +172,7 @@ export let clear = (buffer) => {
174
172
  *
175
173
  * @since v0.4.0
176
174
  */
177
- export let reset = (buffer) => {
175
+ export let reset = buffer => {
178
176
  buffer.data = Bytes.make(buffer.initialSize)
179
177
  buffer.len = 0
180
178
  }
@@ -192,7 +190,6 @@ export let reset = (buffer) => {
192
190
  @disableGC
193
191
  export let rec truncate = (length, buffer) => {
194
192
  Memory.incRef(WasmI32.fromGrain((<)))
195
- Memory.incRef(WasmI32.fromGrain((||)))
196
193
  Memory.incRef(WasmI32.fromGrain((>)))
197
194
  if (length < 0 || length > buffer.len) throw Exception.IndexOutOfBounds
198
195
 
@@ -217,7 +214,7 @@ export let rec truncate = (length, buffer) => {
217
214
  *
218
215
  * @since v0.4.0
219
216
  */
220
- export let toBytes = (buffer) => {
217
+ export let toBytes = buffer => {
221
218
  let len = Bytes.length(buffer.data)
222
219
  if (buffer.len == len) {
223
220
  buffer.data
@@ -249,7 +246,7 @@ export let toBytesSlice = (start, length, buffer) => {
249
246
  *
250
247
  * @since v0.4.0
251
248
  */
252
- export let toString = (buffer) => {
249
+ export let toString = buffer => {
253
250
  Bytes.toString(toBytes(buffer))
254
251
  }
255
252
 
@@ -286,6 +283,8 @@ export let rec addChar = (char: Char, buffer: Buffer) => {
286
283
  Memory.incRef(WasmI32.fromGrain(c))
287
284
  Memory.incRef(WasmI32.fromGrain(buffer))
288
285
  addInt8help(c, buffer)
286
+ Memory.decRef(WasmI32.fromGrain(c))
287
+ void
289
288
  },
290
289
  2n => {
291
290
  let c = Conv.toInt32(n)
@@ -293,6 +292,8 @@ export let rec addChar = (char: Char, buffer: Buffer) => {
293
292
  Memory.incRef(WasmI32.fromGrain(c))
294
293
  Memory.incRef(WasmI32.fromGrain(buffer))
295
294
  addInt16help(c, buffer)
295
+ Memory.decRef(WasmI32.fromGrain(c))
296
+ void
296
297
  },
297
298
  3n => {
298
299
  let (<) = WasmI32.ltU
@@ -300,12 +301,14 @@ export let rec addChar = (char: Char, buffer: Buffer) => {
300
301
  let (*) = WasmI32.mul
301
302
  let (&) = WasmI32.and
302
303
  let (>>) = WasmI32.shrU
303
- for (let mut i = 0n; i < 3n; i = i + 1n) {
304
- let c = Conv.toInt32(n >> (i * 8n) & 0xffn)
304
+ for (let mut i = 0n; i < 3n; i += 1n) {
305
+ let c = Conv.toInt32(n >> i * 8n & 0xffn)
305
306
  Memory.incRef(WasmI32.fromGrain(addInt8help))
306
307
  Memory.incRef(WasmI32.fromGrain(c))
307
308
  Memory.incRef(WasmI32.fromGrain(buffer))
308
309
  addInt8help(c, buffer)
310
+ Memory.decRef(WasmI32.fromGrain(c))
311
+ void
309
312
  }
310
313
  },
311
314
  _ => {
@@ -314,6 +317,8 @@ export let rec addChar = (char: Char, buffer: Buffer) => {
314
317
  Memory.incRef(WasmI32.fromGrain(c))
315
318
  Memory.incRef(WasmI32.fromGrain(buffer))
316
319
  addInt32help(c, buffer)
320
+ Memory.decRef(WasmI32.fromGrain(c))
321
+ void
317
322
  },
318
323
  }
319
324
 
@@ -406,28 +411,58 @@ export let rec addString = (string, buffer) => {
406
411
  * @since v0.4.0
407
412
  */
408
413
  @disableGC
409
- export let rec addStringSlice = (start, length, string, buffer) => {
410
- Memory.incRef(WasmI32.fromGrain(String.byteLength))
411
- Memory.incRef(WasmI32.fromGrain(start))
412
- Memory.incRef(WasmI32.fromGrain(length))
414
+ export let rec addStringSlice = (start: Number, length, string, buffer) => {
415
+ // Handle negative start index (needed before #1071 is fixed)
416
+ let start = {
417
+ // this is a block to avoid making all of these operators
418
+ // overriden in the whole function
419
+ let (<<) = WasmI32.shl
420
+ let (>>) = WasmI32.shrS
421
+ let (+) = WasmI32.add
422
+ let (!=) = WasmI32.ne
423
+ let (&) = WasmI32.and
424
+ Memory.incRef(WasmI32.fromGrain(String.length))
425
+ Memory.incRef(WasmI32.fromGrain(string))
426
+ let strlen = WasmI32.fromGrain(String.length(string)) >> 1n
427
+ let mut startW = WasmI32.fromGrain(start)
428
+ if ((startW & 1n) != 1n) {
429
+ throw InvalidArgument("Invalid start index")
430
+ }
431
+ startW = startW >> 1n
432
+ if (WasmI32.ltS(startW, 0n)) {
433
+ WasmI32.toGrain(WasmI32.shl(startW + strlen, 1n) + 1n)
434
+ } else {
435
+ start
436
+ }
437
+ }
438
+ let end = start + length
439
+ Memory.incRef(WasmI32.fromGrain(String.slice))
440
+ // no incref for start since we know it's a simple num. Add back for good measure after #1071 is fixed!
441
+ Memory.incRef(WasmI32.fromGrain(end))
413
442
  Memory.incRef(WasmI32.fromGrain(string))
414
- let bytelen = String.byteLength(String.slice(start, length, string))
443
+ let slice = String.slice(start, end, string)
444
+
445
+ Memory.incRef(WasmI32.fromGrain(String.byteLength))
446
+ Memory.incRef(WasmI32.fromGrain(slice))
447
+ let bytelen = String.byteLength(slice)
415
448
 
416
449
  Memory.incRef(WasmI32.fromGrain(autogrow))
417
450
  Memory.incRef(WasmI32.fromGrain(bytelen))
418
451
  Memory.incRef(WasmI32.fromGrain(buffer))
419
452
  autogrow(bytelen, buffer)
420
453
 
421
- let srcOff = coerceNumberToWasmI32(start)
454
+ let srcOff = 0n
422
455
  let dstOff = coerceNumberToWasmI32(buffer.len)
423
- let src = WasmI32.fromGrain(string)
456
+ let src = WasmI32.fromGrain(slice)
424
457
  let dst = WasmI32.fromGrain(buffer.data)
425
458
  appendBytes(srcOff, dstOff, coerceNumberToWasmI32(bytelen), src, dst)
459
+ Memory.decRef(WasmI32.fromGrain(slice))
426
460
 
427
461
  Memory.incRef(WasmI32.fromGrain((+)))
428
462
  Memory.incRef(WasmI32.fromGrain(buffer.len))
429
463
  Memory.incRef(WasmI32.fromGrain(bytelen))
430
464
  buffer.len = buffer.len + bytelen
465
+ Memory.decRef(WasmI32.fromGrain(bytelen))
431
466
 
432
467
  Memory.decRef(WasmI32.fromGrain(start))
433
468
  Memory.decRef(WasmI32.fromGrain(length))
@@ -448,17 +483,40 @@ export let rec addStringSlice = (start, length, string, buffer) => {
448
483
  * @since v0.4.0
449
484
  */
450
485
  @disableGC
451
- export let rec addBytesSlice = (start: Number, length: Number, bytes: Bytes, buffer: Buffer) => {
486
+ export let rec addBytesSlice =
487
+ (
488
+ start: Number,
489
+ length: Number,
490
+ bytes: Bytes,
491
+ buffer: Buffer,
492
+ ) => {
493
+ let (-) = WasmI32.sub
494
+ let (<) = WasmI32.ltS
495
+ let (>) = WasmI32.gtS
496
+ let (>=) = WasmI32.geS
497
+
498
+ // bounds check start
499
+ let bytelen = WasmI32.load(WasmI32.fromGrain(bytes), 4n)
500
+ let srcOff = coerceNumberToWasmI32(start)
501
+ if (srcOff < 0n || srcOff >= bytelen) {
502
+ throw Exception.IndexOutOfBounds
503
+ }
504
+
505
+ // bounds check length
506
+ let len = coerceNumberToWasmI32(length)
507
+ if (len < 0n || len > bytelen - srcOff) {
508
+ throw Exception.IndexOutOfBounds
509
+ }
510
+
452
511
  Memory.incRef(WasmI32.fromGrain(autogrow))
453
512
  Memory.incRef(WasmI32.fromGrain(length))
454
513
  Memory.incRef(WasmI32.fromGrain(buffer))
455
514
  autogrow(length, buffer)
456
515
 
457
- let srcOff = coerceNumberToWasmI32(start)
458
516
  let dstOff = coerceNumberToWasmI32(buffer.len)
459
517
  let src = WasmI32.fromGrain(bytes)
460
518
  let dst = WasmI32.fromGrain(buffer.data)
461
- appendBytes(srcOff, dstOff, coerceNumberToWasmI32(length), src, dst)
519
+ appendBytes(srcOff, dstOff, len, src, dst)
462
520
 
463
521
  Memory.incRef(WasmI32.fromGrain((+)))
464
522
  Memory.incRef(WasmI32.fromGrain(buffer.len))
@@ -507,7 +565,6 @@ export let addBufferSlice = (start, length, srcBuffer, dstBuffer) => {
507
565
  * @section Binary operations on integers: Functions for encoding and decoding integers stored in a buffer.
508
566
  */
509
567
 
510
-
511
568
  /**
512
569
  * Gets a signed 8-bit integer starting at the given byte index.
513
570
  *
@@ -783,4 +840,4 @@ export let addFloat64 = (value, buffer) => {
783
840
  let index = buffer.len
784
841
  buffer.len = buffer.len + _64BIT_LEN
785
842
  setFloat64(index, value, buffer)
786
- }
843
+ }