@scriptc/cli-darwin-arm64 0.2.3 → 0.2.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.
- package/dist/THIRD_PARTY_NOTICES +1 -1
- package/dist/bin/scriptc +0 -0
- package/dist/bin/scriptc.json +1 -1
- package/dist/lib/declarations/scriptc-node-fallback.d.ts +915 -215
- package/dist/lib/declarations/scriptc-overrides.d.ts +5 -1
- package/dist/lib/declarations/scriptc.d.ts +22 -2
- package/dist/lib/llvm/bin/scriptc-llvm-codegen +0 -0
- package/dist/lib/llvm/package.json +1 -1
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/dynamic-text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/library-thread-release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/default/scr_util_compare.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_array.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_bigint.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_bytes_io.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_copying.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_cycle.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_json.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_lib.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_map.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_number.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_regex.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_string.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic/scr_util_compare.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/dynamic-text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/artifacts/release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
- package/dist/lib/runtime-darwin-arm64/package.json +1 -1
- package/dist/lib/runtime-darwin-arm64/runtime-pack.json +213 -213
- package/dist/lib/runtime-sources/package.json +1 -1
- package/dist/lib/runtime-sources/src/scr_array.c +317 -40
- package/dist/lib/runtime-sources/src/scr_async.test.ts +16 -6
- package/dist/lib/runtime-sources/src/scr_bigint.c +15 -0
- package/dist/lib/runtime-sources/src/scr_bytes.c +437 -216
- package/dist/lib/runtime-sources/src/scr_bytes.test.c +85 -0
- package/dist/lib/runtime-sources/src/scr_bytes_io.c +0 -34
- package/dist/lib/runtime-sources/src/scr_copying.c +12 -2
- package/dist/lib/runtime-sources/src/scr_cycle.c +84 -60
- package/dist/lib/runtime-sources/src/scr_json.c +494 -161
- package/dist/lib/runtime-sources/src/scr_json.test.c +323 -1
- package/dist/lib/runtime-sources/src/scr_json.test.ts +58 -25
- package/dist/lib/runtime-sources/src/scr_key.h +68 -0
- package/dist/lib/runtime-sources/src/scr_lib.c +177 -89
- package/dist/lib/runtime-sources/src/scr_map.c +268 -96
- package/dist/lib/runtime-sources/src/scr_number.c +2 -4
- package/dist/lib/runtime-sources/src/scr_numeric.h +25 -0
- package/dist/lib/runtime-sources/src/scr_numeric.test.c +37 -0
- package/dist/lib/runtime-sources/src/scr_numeric.test.ts +33 -0
- package/dist/lib/runtime-sources/src/scr_regex.c +255 -145
- package/dist/lib/runtime-sources/src/scr_runtime.h +76 -19
- package/dist/lib/runtime-sources/src/scr_string.c +184 -42
- package/package.json +1 -1
|
@@ -147,10 +147,14 @@ static void scr_arr_grow_dense(ScrArr *a, size_t need) {
|
|
|
147
147
|
cap *= 2;
|
|
148
148
|
}
|
|
149
149
|
if (cap > SCR_ARR_DENSE_LIMIT) cap = SCR_ARR_DENSE_LIMIT;
|
|
150
|
-
|
|
150
|
+
/* Values and states share one allocation. Move the old states before
|
|
151
|
+
* publishing the larger capacity: their previous location is now part
|
|
152
|
+
* of the value area. Existing data and state pointers keep their ABI. */
|
|
153
|
+
if (cap > SIZE_MAX / (sizeof(uint64_t) + sizeof(uint8_t))) scr_arr_oom();
|
|
154
|
+
uint64_t *data = realloc(a->data, cap * (sizeof(uint64_t) + sizeof(uint8_t)));
|
|
151
155
|
if (!data) scr_arr_oom();
|
|
152
|
-
uint8_t *present =
|
|
153
|
-
if (
|
|
156
|
+
uint8_t *present = (uint8_t *)(data + cap);
|
|
157
|
+
if (a->cap) memmove(present, (uint8_t *)(data + a->cap), a->cap);
|
|
154
158
|
memset(present + a->cap, 0, cap - a->cap);
|
|
155
159
|
a->data = data;
|
|
156
160
|
a->present = present;
|
|
@@ -397,11 +401,58 @@ static ScrArrStorage scr_arr_take_storage(ScrArr *a) {
|
|
|
397
401
|
|
|
398
402
|
static void scr_arr_free_storage(ScrArrStorage *s) {
|
|
399
403
|
free(s->data);
|
|
400
|
-
free(s->present);
|
|
401
404
|
free(s->sparse);
|
|
402
405
|
memset(s, 0, sizeof(*s));
|
|
403
406
|
}
|
|
404
407
|
|
|
408
|
+
/* Dense storage may still contain holes and explicit undefined. These
|
|
409
|
+
* operations move ownership with the slots and move the states alongside
|
|
410
|
+
* them; they never inspect an uninitialized hole payload. */
|
|
411
|
+
static bool scr_arr_is_dense(const ScrArr *a) {
|
|
412
|
+
return a->len <= a->cap && a->sparse_len == 0;
|
|
413
|
+
}
|
|
414
|
+
|
|
415
|
+
static void scr_arr_move_dense(ScrArr *a, size_t to, size_t from, size_t count) {
|
|
416
|
+
if (count == 0) return;
|
|
417
|
+
memmove(a->data + to, a->data + from, count * sizeof(*a->data));
|
|
418
|
+
memmove(a->present + to, a->present + from, count);
|
|
419
|
+
}
|
|
420
|
+
|
|
421
|
+
static void scr_arr_clear_dense(ScrArr *a, size_t from, size_t count) {
|
|
422
|
+
if (count == 0) return;
|
|
423
|
+
memset(a->present + from, SCR_ARR_HOLE, count);
|
|
424
|
+
memset(a->data + from, 0, count * sizeof(*a->data));
|
|
425
|
+
}
|
|
426
|
+
|
|
427
|
+
/* The destination owns no values in this range. Only retain adapters run
|
|
428
|
+
* while copying references: no release can collect an intermediate copy.
|
|
429
|
+
* Self-appends use disjoint ranges after reserving capacity. */
|
|
430
|
+
static void scr_arr_copy_dense(ScrArr *dst, size_t to, const ScrArr *src,
|
|
431
|
+
size_t from, size_t count, bool reverse,
|
|
432
|
+
bool materialize_holes) {
|
|
433
|
+
if (count == 0) return;
|
|
434
|
+
if (!reverse) {
|
|
435
|
+
memcpy(dst->data + to, src->data + from, count * sizeof(*dst->data));
|
|
436
|
+
memcpy(dst->present + to, src->present + from, count);
|
|
437
|
+
} else {
|
|
438
|
+
for (size_t i = 0; i < count; i++) {
|
|
439
|
+
size_t source = from + count - i - 1;
|
|
440
|
+
memcpy(dst->data + to + i, src->data + source, sizeof(*dst->data));
|
|
441
|
+
dst->present[to + i] = src->present[source];
|
|
442
|
+
}
|
|
443
|
+
}
|
|
444
|
+
bool refs = scr_elem_is_ref(src->elem);
|
|
445
|
+
if (!refs && !materialize_holes) return;
|
|
446
|
+
for (size_t i = to; i < to + count; i++) {
|
|
447
|
+
if (dst->present[i] == SCR_ARR_VALUE) {
|
|
448
|
+
if (refs) dst->data[i] = scr_elem_retain_slot(src, dst->data[i]);
|
|
449
|
+
} else if (materialize_holes && dst->present[i] == SCR_ARR_HOLE) {
|
|
450
|
+
dst->data[i] = 0;
|
|
451
|
+
dst->present[i] = SCR_ARR_UNDEFINED;
|
|
452
|
+
}
|
|
453
|
+
}
|
|
454
|
+
}
|
|
455
|
+
|
|
405
456
|
ScrArr *scr_arr_new(ScrElemKind elem, size_t initial_cap) {
|
|
406
457
|
ScrArr *a = malloc(sizeof(ScrArr));
|
|
407
458
|
if (!a) scr_arr_oom();
|
|
@@ -434,8 +485,10 @@ ScrArr *scr_arr_new(ScrElemKind elem, size_t initial_cap) {
|
|
|
434
485
|
* below releases none — the complement contract in scr_runtime.h. */
|
|
435
486
|
void scr_arr_trace_v(void *a0, ScrTraceVisit visit, void *ctx) {
|
|
436
487
|
ScrArr *a = (ScrArr *)a0;
|
|
437
|
-
visit(a->metadata, ctx);
|
|
438
|
-
|
|
488
|
+
if (a->metadata) visit(a->metadata, ctx);
|
|
489
|
+
/* Growth and truncation leave spare capacity empty. Sparse slots and
|
|
490
|
+
* named properties are separate edges, independent of dense length. */
|
|
491
|
+
for (size_t i = 0, end = a->len < a->cap ? a->len : a->cap; i < end; i++) {
|
|
439
492
|
if (a->present[i] == SCR_ARR_VALUE) visit(scr_slot_to_ptr(a->data[i]), ctx);
|
|
440
493
|
}
|
|
441
494
|
for (size_t i = 0; i < a->sparse_len; i++) {
|
|
@@ -453,7 +506,6 @@ void scr_arr_trace_v(void *a0, ScrTraceVisit visit, void *ctx) {
|
|
|
453
506
|
static void scr_arr_gc_free(void *a0) {
|
|
454
507
|
ScrArr *a = (ScrArr *)a0;
|
|
455
508
|
free(a->data);
|
|
456
|
-
free(a->present);
|
|
457
509
|
free(a->sparse);
|
|
458
510
|
for (size_t i = 0; i < a->prop_len; i++) free(a->props[i].key);
|
|
459
511
|
free(a->props);
|
|
@@ -503,7 +555,7 @@ void scr_arr_release(ScrArr *a) {
|
|
|
503
555
|
scr_dyn_release(a->metadata);
|
|
504
556
|
a->metadata = NULL;
|
|
505
557
|
if (scr_elem_is_ref(a->elem)) {
|
|
506
|
-
for (size_t i = 0
|
|
558
|
+
for (size_t i = 0, end = a->len < a->cap ? a->len : a->cap; i < end; i++) {
|
|
507
559
|
if (a->present[i] != SCR_ARR_HOLE) {
|
|
508
560
|
uint64_t old = a->data[i];
|
|
509
561
|
uint8_t state = a->present[i];
|
|
@@ -532,7 +584,6 @@ void scr_arr_release(ScrArr *a) {
|
|
|
532
584
|
scr_arr_gc_free(a);
|
|
533
585
|
} else {
|
|
534
586
|
free(a->data);
|
|
535
|
-
free(a->present);
|
|
536
587
|
free(a->sparse);
|
|
537
588
|
for (size_t i = 0; i < a->prop_len; i++) free(a->props[i].key);
|
|
538
589
|
free(a->props);
|
|
@@ -647,6 +698,16 @@ void scr_arr_copy_range_ex(ScrArr *dst, size_t dst_start, const ScrArr *src,
|
|
|
647
698
|
size_t src_start, size_t count, bool reverse,
|
|
648
699
|
bool materialize_holes) {
|
|
649
700
|
if (count == 0) return;
|
|
701
|
+
if (src != dst && src_start <= src->cap && count <= src->cap - src_start &&
|
|
702
|
+
dst_start <= dst->cap && count <= dst->cap - dst_start) {
|
|
703
|
+
size_t empty = 0;
|
|
704
|
+
while (empty < count && dst->present[dst_start + empty] == SCR_ARR_HOLE) empty++;
|
|
705
|
+
if (empty == count) {
|
|
706
|
+
scr_arr_copy_dense(dst, dst_start, src, src_start, count, reverse,
|
|
707
|
+
materialize_holes);
|
|
708
|
+
return;
|
|
709
|
+
}
|
|
710
|
+
}
|
|
650
711
|
size_t end = src_start + count;
|
|
651
712
|
size_t dense_start = src_start < src->cap ? src_start : src->cap;
|
|
652
713
|
size_t dense_end = end < src->cap ? end : src->cap;
|
|
@@ -676,6 +737,76 @@ void scr_arr_copy_range_ex(ScrArr *dst, size_t dst_start, const ScrArr *src,
|
|
|
676
737
|
}
|
|
677
738
|
}
|
|
678
739
|
|
|
740
|
+
static size_t scr_arr_relative_index(double value, size_t length) {
|
|
741
|
+
double integer = isnan(value) ? 0 : trunc(value);
|
|
742
|
+
if (integer < 0) integer += (double)length;
|
|
743
|
+
return integer <= 0 ? 0 : integer >= (double)length ? length : (size_t)integer;
|
|
744
|
+
}
|
|
745
|
+
|
|
746
|
+
ScrArr *scr_arr_copy_within(ScrArr *a, double target, double start, double end) {
|
|
747
|
+
size_t to = scr_arr_relative_index(target, a->len);
|
|
748
|
+
size_t from = scr_arr_relative_index(start, a->len);
|
|
749
|
+
size_t last = scr_arr_relative_index(end, a->len);
|
|
750
|
+
size_t count = last > from ? last - from : 0;
|
|
751
|
+
if (count > a->len - to) count = a->len - to;
|
|
752
|
+
if (count == 0 || from == to) return scr_arr_retain(a);
|
|
753
|
+
if (!scr_elem_is_ref(a->elem) && from < a->cap && count <= a->cap - from &&
|
|
754
|
+
to < a->cap && count <= a->cap - to) {
|
|
755
|
+
scr_arr_move_dense(a, to, from, count);
|
|
756
|
+
return scr_arr_retain(a);
|
|
757
|
+
}
|
|
758
|
+
bool backwards = from < to && to - from < count;
|
|
759
|
+
for (size_t i = 0; i < count; i++) {
|
|
760
|
+
size_t offset = backwards ? count - i - 1 : i;
|
|
761
|
+
uint64_t slot = 0;
|
|
762
|
+
uint8_t state = scr_arr_state_at(a, from + offset, &slot);
|
|
763
|
+
if (state == SCR_ARR_HOLE) {
|
|
764
|
+
scr_arr_delete(a, (double)(to + offset));
|
|
765
|
+
} else {
|
|
766
|
+
if (state == SCR_ARR_VALUE) slot = scr_elem_retain_slot(a, slot);
|
|
767
|
+
/* Each replacement publishes its edge before releasing the previous
|
|
768
|
+
* owner; cycle collection can run between successive positions. */
|
|
769
|
+
scr_arr_replace_state_owned(a, to + offset, slot, state);
|
|
770
|
+
}
|
|
771
|
+
}
|
|
772
|
+
return scr_arr_retain(a);
|
|
773
|
+
}
|
|
774
|
+
|
|
775
|
+
static ScrArr *scr_arr_fill_slot(ScrArr *a, uint64_t slot, uint8_t state,
|
|
776
|
+
double start, double end) {
|
|
777
|
+
size_t from = scr_arr_relative_index(start, a->len);
|
|
778
|
+
size_t until = scr_arr_relative_index(end, a->len);
|
|
779
|
+
if (from >= until) return scr_arr_retain(a);
|
|
780
|
+
bool refs = scr_elem_is_ref(a->elem);
|
|
781
|
+
if (!refs && until <= SCR_ARR_DENSE_LIMIT) {
|
|
782
|
+
scr_arr_grow_dense(a, until);
|
|
783
|
+
for (size_t i = from; i < until; i++) a->data[i] = slot;
|
|
784
|
+
memset(a->present + from, state, until - from);
|
|
785
|
+
} else {
|
|
786
|
+
for (size_t i = from; i < until; i++) {
|
|
787
|
+
uint64_t value = refs && state == SCR_ARR_VALUE ? scr_elem_retain_slot(a, slot) : slot;
|
|
788
|
+
scr_arr_replace_state_owned(a, i, value, state);
|
|
789
|
+
}
|
|
790
|
+
}
|
|
791
|
+
return scr_arr_retain(a);
|
|
792
|
+
}
|
|
793
|
+
|
|
794
|
+
ScrArr *scr_arr_fill_f64(ScrArr *a, double value, double start, double end) {
|
|
795
|
+
return scr_arr_fill_slot(a, scr_slot_from_f64(value), SCR_ARR_VALUE, start, end);
|
|
796
|
+
}
|
|
797
|
+
|
|
798
|
+
ScrArr *scr_arr_fill_bool(ScrArr *a, bool value, double start, double end) {
|
|
799
|
+
return scr_arr_fill_slot(a, value ? 1 : 0, SCR_ARR_VALUE, start, end);
|
|
800
|
+
}
|
|
801
|
+
|
|
802
|
+
ScrArr *scr_arr_fill_ref(ScrArr *a, void *value, double start, double end) {
|
|
803
|
+
return scr_arr_fill_slot(a, scr_slot_from_ptr(value), SCR_ARR_VALUE, start, end);
|
|
804
|
+
}
|
|
805
|
+
|
|
806
|
+
ScrArr *scr_arr_fill_undefined(ScrArr *a, double start, double end) {
|
|
807
|
+
return scr_arr_fill_slot(a, 0, SCR_ARR_UNDEFINED, start, end);
|
|
808
|
+
}
|
|
809
|
+
|
|
679
810
|
/* ── Math.max/min over one spread number[] ─────────────────────────────
|
|
680
811
|
* The JS fold exactly (ECMA Math.max/min applied to the elements): any
|
|
681
812
|
* NaN poisons the result, +0 beats -0 for max (the reverse for min), and
|
|
@@ -922,10 +1053,33 @@ double scr_arr_push_ref(ScrArr *a, void *v) {
|
|
|
922
1053
|
return scr_arr_push_slot(a, scr_slot_from_ptr(v));
|
|
923
1054
|
}
|
|
924
1055
|
|
|
1056
|
+
double scr_arr_push_many(ScrArr *a, size_t count, const uint64_t *slots) {
|
|
1057
|
+
if (count > SCR_ARR_MAX_LENGTH - a->len) scr_arr_oom();
|
|
1058
|
+
size_t from = a->len, next = from + count;
|
|
1059
|
+
if (next <= SCR_ARR_DENSE_LIMIT) {
|
|
1060
|
+
scr_arr_grow_dense(a, next);
|
|
1061
|
+
if (count) {
|
|
1062
|
+
memcpy(a->data + from, slots, count * sizeof(*slots));
|
|
1063
|
+
memset(a->present + from, SCR_ARR_VALUE, count);
|
|
1064
|
+
}
|
|
1065
|
+
} else {
|
|
1066
|
+
for (size_t i = 0; i < count; i++) scr_arr_store_owned(a, from + i, slots[i]);
|
|
1067
|
+
}
|
|
1068
|
+
a->len = next;
|
|
1069
|
+
return (double)next;
|
|
1070
|
+
}
|
|
1071
|
+
|
|
925
1072
|
double scr_arr_push_spread(ScrArr *a, const ScrArr *src) {
|
|
926
1073
|
size_t old_len = a->len;
|
|
927
1074
|
size_t add = src->len;
|
|
928
1075
|
if (add > SCR_ARR_MAX_LENGTH - old_len) scr_arr_oom();
|
|
1076
|
+
if (scr_arr_is_dense(a) && scr_arr_is_dense(src) &&
|
|
1077
|
+
old_len + add <= SCR_ARR_DENSE_LIMIT) {
|
|
1078
|
+
scr_arr_grow_dense(a, old_len + add);
|
|
1079
|
+
scr_arr_copy_dense(a, old_len, src, 0, add, false, true);
|
|
1080
|
+
a->len += add;
|
|
1081
|
+
return (double)a->len;
|
|
1082
|
+
}
|
|
929
1083
|
if (src == a) {
|
|
930
1084
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
931
1085
|
a->len = 0;
|
|
@@ -960,6 +1114,13 @@ double scr_arr_concat_copy(ScrArr *a, const ScrArr *src) {
|
|
|
960
1114
|
size_t old_len = a->len;
|
|
961
1115
|
size_t add = src->len;
|
|
962
1116
|
if (add > SCR_ARR_MAX_LENGTH - old_len) scr_arr_oom();
|
|
1117
|
+
if (scr_arr_is_dense(a) && scr_arr_is_dense(src) &&
|
|
1118
|
+
old_len + add <= SCR_ARR_DENSE_LIMIT) {
|
|
1119
|
+
scr_arr_grow_dense(a, old_len + add);
|
|
1120
|
+
scr_arr_copy_dense(a, old_len, src, 0, add, false, false);
|
|
1121
|
+
a->len += add;
|
|
1122
|
+
return (double)a->len;
|
|
1123
|
+
}
|
|
963
1124
|
if (src == a) {
|
|
964
1125
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
965
1126
|
a->len = 0;
|
|
@@ -1001,6 +1162,14 @@ static double scr_arr_unshift_slot(ScrArr *a, uint64_t slot) {
|
|
|
1001
1162
|
scr_arr_trap_oob((double)a->len, a->len);
|
|
1002
1163
|
}
|
|
1003
1164
|
size_t old_len = a->len;
|
|
1165
|
+
if (scr_arr_is_dense(a) && old_len < SCR_ARR_DENSE_LIMIT) {
|
|
1166
|
+
scr_arr_grow_dense(a, old_len + 1);
|
|
1167
|
+
scr_arr_move_dense(a, 1, 0, old_len);
|
|
1168
|
+
a->data[0] = slot;
|
|
1169
|
+
a->present[0] = SCR_ARR_VALUE;
|
|
1170
|
+
a->len++;
|
|
1171
|
+
return (double)a->len;
|
|
1172
|
+
}
|
|
1004
1173
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1005
1174
|
a->len = 0;
|
|
1006
1175
|
scr_arr_store_owned(a, 0, slot);
|
|
@@ -1028,11 +1197,46 @@ double scr_arr_unshift_ref(ScrArr *a, void *v) {
|
|
|
1028
1197
|
return scr_arr_unshift_slot(a, scr_slot_from_ptr(v));
|
|
1029
1198
|
}
|
|
1030
1199
|
|
|
1200
|
+
double scr_arr_unshift_many(ScrArr *a, size_t count, const uint64_t *slots) {
|
|
1201
|
+
size_t old_len = a->len;
|
|
1202
|
+
if (count == 0) return (double)old_len;
|
|
1203
|
+
if (count > SCR_ARR_MAX_LENGTH - old_len) scr_arr_oom();
|
|
1204
|
+
if (scr_arr_is_dense(a) && old_len + count <= SCR_ARR_DENSE_LIMIT) {
|
|
1205
|
+
scr_arr_grow_dense(a, old_len + count);
|
|
1206
|
+
scr_arr_move_dense(a, count, 0, old_len);
|
|
1207
|
+
memcpy(a->data, slots, count * sizeof(*slots));
|
|
1208
|
+
memset(a->present, SCR_ARR_VALUE, count);
|
|
1209
|
+
} else {
|
|
1210
|
+
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1211
|
+
for (size_t i = 0; i < count; i++) scr_arr_store_owned(a, i, slots[i]);
|
|
1212
|
+
for (size_t i = 0; i < old.cap; i++) {
|
|
1213
|
+
if (old.present[i] != SCR_ARR_HOLE)
|
|
1214
|
+
scr_arr_store_state_owned(a, i + count, old.data[i], old.present[i]);
|
|
1215
|
+
}
|
|
1216
|
+
for (size_t i = 0; i < old.sparse_len; i++) {
|
|
1217
|
+
scr_arr_store_state_owned(a, old.sparse[i].index + count,
|
|
1218
|
+
old.sparse[i].slot, old.sparse[i].state);
|
|
1219
|
+
}
|
|
1220
|
+
scr_arr_free_storage(&old);
|
|
1221
|
+
}
|
|
1222
|
+
a->len = old_len + count;
|
|
1223
|
+
return (double)a->len;
|
|
1224
|
+
}
|
|
1225
|
+
|
|
1031
1226
|
double scr_arr_unshift_spread(ScrArr *a, const ScrArr *src) {
|
|
1032
1227
|
size_t old_len = a->len;
|
|
1033
1228
|
size_t add = src->len;
|
|
1034
1229
|
if (add == 0) return (double)old_len;
|
|
1035
1230
|
if (add > SCR_ARR_MAX_LENGTH - old_len) scr_arr_oom();
|
|
1231
|
+
if (scr_arr_is_dense(a) && scr_arr_is_dense(src) &&
|
|
1232
|
+
old_len + add <= SCR_ARR_DENSE_LIMIT) {
|
|
1233
|
+
scr_arr_grow_dense(a, old_len + add);
|
|
1234
|
+
scr_arr_move_dense(a, add, 0, old_len);
|
|
1235
|
+
/* A self-spread reads the original values at their moved location. */
|
|
1236
|
+
scr_arr_copy_dense(a, 0, src, src == a ? add : 0, add, false, true);
|
|
1237
|
+
a->len += add;
|
|
1238
|
+
return (double)a->len;
|
|
1239
|
+
}
|
|
1036
1240
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1037
1241
|
a->len = 0;
|
|
1038
1242
|
for (size_t i = 0; i < add; i++) {
|
|
@@ -1062,6 +1266,19 @@ double scr_arr_unshift_spread(ScrArr *a, const ScrArr *src) {
|
|
|
1062
1266
|
|
|
1063
1267
|
ScrArr *scr_arr_reverse(ScrArr *a) {
|
|
1064
1268
|
size_t len = a->len;
|
|
1269
|
+
if (scr_arr_is_dense(a)) {
|
|
1270
|
+
for (size_t i = 0; i < len / 2; i++) {
|
|
1271
|
+
size_t j = len - i - 1;
|
|
1272
|
+
uint64_t slot;
|
|
1273
|
+
memcpy(&slot, a->data + i, sizeof slot);
|
|
1274
|
+
memcpy(a->data + i, a->data + j, sizeof slot);
|
|
1275
|
+
memcpy(a->data + j, &slot, sizeof slot);
|
|
1276
|
+
uint8_t state = a->present[i];
|
|
1277
|
+
a->present[i] = a->present[j];
|
|
1278
|
+
a->present[j] = state;
|
|
1279
|
+
}
|
|
1280
|
+
return scr_arr_retain(a);
|
|
1281
|
+
}
|
|
1065
1282
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1066
1283
|
a->len = len;
|
|
1067
1284
|
for (size_t i = 0; i < old.cap; i++) {
|
|
@@ -1111,6 +1328,14 @@ uint8_t scr_arr_shift_state(ScrArr *a, uint64_t *slot_out) {
|
|
|
1111
1328
|
if (slot_out) *slot_out = 0;
|
|
1112
1329
|
if (a->len == 0) return SCR_ARR_HOLE;
|
|
1113
1330
|
size_t old_len = a->len;
|
|
1331
|
+
if (scr_arr_is_dense(a)) {
|
|
1332
|
+
uint8_t state = a->present[0];
|
|
1333
|
+
if (slot_out && state == SCR_ARR_VALUE) *slot_out = a->data[0];
|
|
1334
|
+
scr_arr_move_dense(a, 0, 1, old_len - 1);
|
|
1335
|
+
scr_arr_clear_dense(a, old_len - 1, 1);
|
|
1336
|
+
a->len--;
|
|
1337
|
+
return state;
|
|
1338
|
+
}
|
|
1114
1339
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1115
1340
|
uint64_t s = 0;
|
|
1116
1341
|
uint8_t state = scr_arr_state_at_storage(&old, 0, &s);
|
|
@@ -1167,6 +1392,16 @@ ScrArr *scr_arr_splice(ScrArr *a, double start, double deleteCount) {
|
|
|
1167
1392
|
: scr_arr_new(a->elem, n ? n : 1);
|
|
1168
1393
|
out->len = n;
|
|
1169
1394
|
size_t old_len = a->len;
|
|
1395
|
+
if (scr_arr_is_dense(a)) {
|
|
1396
|
+
if (n) {
|
|
1397
|
+
memcpy(out->data, a->data + from, n * sizeof(*a->data));
|
|
1398
|
+
memcpy(out->present, a->present + from, n);
|
|
1399
|
+
}
|
|
1400
|
+
scr_arr_move_dense(a, from, from + n, old_len - from - n);
|
|
1401
|
+
scr_arr_clear_dense(a, old_len - n, n);
|
|
1402
|
+
a->len -= n;
|
|
1403
|
+
return out;
|
|
1404
|
+
}
|
|
1170
1405
|
ScrArrStorage old = scr_arr_take_storage(a);
|
|
1171
1406
|
a->len = 0;
|
|
1172
1407
|
for (size_t i = 0; i < old.cap; i++) {
|
|
@@ -1213,6 +1448,30 @@ ScrArr *scr_arr_splice_insert(ScrArr *a, double start, double deleteCount,
|
|
|
1213
1448
|
double d0 = isnan(deleteCount) ? 0 : trunc(deleteCount);
|
|
1214
1449
|
size_t n = d0 <= 0 ? 0 : d0 >= avail ? (size_t)avail : (size_t)d0;
|
|
1215
1450
|
if (items->len > SCR_ARR_MAX_LENGTH - (a->len - n)) scr_arr_oom();
|
|
1451
|
+
size_t add = items->len, next_len = a->len - n + add;
|
|
1452
|
+
if (scr_arr_is_dense(a) && scr_arr_is_dense(items) &&
|
|
1453
|
+
next_len <= SCR_ARR_DENSE_LIMIT) {
|
|
1454
|
+
/* Snapshot an aliased argument before changing the receiver. Ordinary
|
|
1455
|
+
* callers have already materialized variadic arguments, so this copy
|
|
1456
|
+
* is needed only by direct self-spread runtime callers. */
|
|
1457
|
+
ScrArr *snapshot = items == a ? scr_arr_slice(a, 0, INFINITY) : NULL;
|
|
1458
|
+
if (snapshot) items = snapshot;
|
|
1459
|
+
ScrArr *removed = a->elem == SCR_ELEM_REF
|
|
1460
|
+
? scr_arr_new_ref(a->elem_retain, a->elem_release, a->elem_trace, n)
|
|
1461
|
+
: scr_arr_new(a->elem, n);
|
|
1462
|
+
if (n) {
|
|
1463
|
+
memcpy(removed->data, a->data + from, n * sizeof(*a->data));
|
|
1464
|
+
memcpy(removed->present, a->present + from, n);
|
|
1465
|
+
}
|
|
1466
|
+
removed->len = n;
|
|
1467
|
+
scr_arr_grow_dense(a, next_len);
|
|
1468
|
+
scr_arr_move_dense(a, from + add, from + n, a->len - from - n);
|
|
1469
|
+
scr_arr_copy_dense(a, from, items, 0, add, false, true);
|
|
1470
|
+
if (next_len < a->len) scr_arr_clear_dense(a, next_len, a->len - next_len);
|
|
1471
|
+
a->len = next_len;
|
|
1472
|
+
scr_arr_release(snapshot);
|
|
1473
|
+
return removed;
|
|
1474
|
+
}
|
|
1216
1475
|
ScrArr *removed = scr_arr_splice(a, start, deleteCount);
|
|
1217
1476
|
ScrArr *tail = scr_arr_splice(a, (double)from, INFINITY);
|
|
1218
1477
|
scr_arr_push_spread(a, items);
|
|
@@ -1333,21 +1592,26 @@ bool scr_arr_includes_ref(ScrArr *a, void *v) {
|
|
|
1333
1592
|
|
|
1334
1593
|
/* ── join ──────────────────────────────────────────────────────────────── */
|
|
1335
1594
|
|
|
1336
|
-
static
|
|
1337
|
-
|
|
1338
|
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1595
|
+
static size_t scr_join_size(size_t len, size_t extra) {
|
|
1596
|
+
if (extra > SIZE_MAX - sizeof(ScrStr) - 1 - len) scr_arr_oom();
|
|
1597
|
+
return len + extra;
|
|
1598
|
+
}
|
|
1599
|
+
|
|
1600
|
+
/* The builder owns the final string allocation throughout construction.
|
|
1601
|
+
* It has no aliases or index-cache entries, and no user callbacks run while
|
|
1602
|
+
* appending primitive array values. Finish by publishing the terminator. */
|
|
1603
|
+
static void scr_join_append(ScrStr **out, const char *bytes, size_t n) {
|
|
1604
|
+
ScrStr *s = *out;
|
|
1605
|
+
size_t need = scr_join_size(s->len, n);
|
|
1606
|
+
if (need > s->cap) {
|
|
1607
|
+
const size_t limit = SIZE_MAX - sizeof(ScrStr) - 1;
|
|
1608
|
+
size_t cap = s->cap;
|
|
1609
|
+
while (cap < need) cap = cap > limit / 2 ? need : cap * 2;
|
|
1610
|
+
s = scr_str_regrow(s, cap);
|
|
1611
|
+
*out = s;
|
|
1348
1612
|
}
|
|
1349
|
-
memcpy(
|
|
1350
|
-
|
|
1613
|
+
memcpy(s->data + s->len, bytes, n);
|
|
1614
|
+
s->len = need;
|
|
1351
1615
|
}
|
|
1352
1616
|
|
|
1353
1617
|
/* `a.slice(start?, end?)` — a fresh shallow copy of the index range,
|
|
@@ -1370,6 +1634,10 @@ ScrArr *scr_arr_slice(ScrArr *a, double start, double end) {
|
|
|
1370
1634
|
? scr_arr_new_ref(a->elem_retain, a->elem_release, a->elem_trace, n ? n : 1)
|
|
1371
1635
|
: scr_arr_new(a->elem, n ? n : 1);
|
|
1372
1636
|
out->len = n;
|
|
1637
|
+
if (to <= a->cap) {
|
|
1638
|
+
scr_arr_copy_dense(out, 0, a, from, n, false, false);
|
|
1639
|
+
return out;
|
|
1640
|
+
}
|
|
1373
1641
|
for (size_t i = 0; i < a->cap && i < to; i++) {
|
|
1374
1642
|
if (i < from || a->present[i] == SCR_ARR_HOLE) continue;
|
|
1375
1643
|
uint8_t state = a->present[i];
|
|
@@ -1390,11 +1658,24 @@ ScrArr *scr_arr_slice(ScrArr *a, double start, double end) {
|
|
|
1390
1658
|
}
|
|
1391
1659
|
|
|
1392
1660
|
ScrStr *scr_arr_join(ScrArr *a, ScrStr *sep) {
|
|
1393
|
-
size_t cap = 64
|
|
1394
|
-
|
|
1395
|
-
|
|
1661
|
+
size_t cap = 64;
|
|
1662
|
+
/* String widths are already known. Size once to avoid growth and copying
|
|
1663
|
+
* even when the array holds holes, explicit undefined or sparse slots.
|
|
1664
|
+
* Numeric formatting stays single-pass rather than formatting twice. */
|
|
1665
|
+
if (a->elem == SCR_ELEM_STR) {
|
|
1666
|
+
const size_t limit = SIZE_MAX - sizeof(ScrStr) - 1;
|
|
1667
|
+
if (a->len > 1 && sep->len > limit / (a->len - 1)) scr_arr_oom();
|
|
1668
|
+
cap = a->len > 1 ? (a->len - 1) * sep->len : 0;
|
|
1669
|
+
for (size_t i = 0; i < a->len; i++) {
|
|
1670
|
+
uint64_t slot;
|
|
1671
|
+
if (scr_arr_state_at(a, i, &slot) != SCR_ARR_VALUE) continue;
|
|
1672
|
+
const ScrStr *s = (const ScrStr *)scr_slot_to_ptr(slot);
|
|
1673
|
+
if (s) cap = scr_join_size(cap, s->len);
|
|
1674
|
+
}
|
|
1675
|
+
}
|
|
1676
|
+
ScrStr *out = scr_str_alloc_raw(0, cap);
|
|
1396
1677
|
for (size_t i = 0; i < a->len; i++) {
|
|
1397
|
-
if (i > 0) scr_join_append(&
|
|
1678
|
+
if (i > 0) scr_join_append(&out, sep->data, sep->len);
|
|
1398
1679
|
uint64_t slot;
|
|
1399
1680
|
uint8_t state = scr_arr_state_at(a, i, &slot);
|
|
1400
1681
|
if (state != SCR_ARR_VALUE) continue;
|
|
@@ -1402,16 +1683,16 @@ ScrStr *scr_arr_join(ScrArr *a, ScrStr *sep) {
|
|
|
1402
1683
|
case SCR_ELEM_F64: {
|
|
1403
1684
|
char nb[32];
|
|
1404
1685
|
size_t n = scr_f64_to_str(scr_slot_to_f64(slot), nb);
|
|
1405
|
-
scr_join_append(&
|
|
1686
|
+
scr_join_append(&out, nb, n);
|
|
1406
1687
|
break;
|
|
1407
1688
|
}
|
|
1408
1689
|
case SCR_ELEM_BOOL:
|
|
1409
|
-
if (slot != 0) scr_join_append(&
|
|
1410
|
-
else scr_join_append(&
|
|
1690
|
+
if (slot != 0) scr_join_append(&out, "true", 4);
|
|
1691
|
+
else scr_join_append(&out, "false", 5);
|
|
1411
1692
|
break;
|
|
1412
1693
|
case SCR_ELEM_STR: {
|
|
1413
1694
|
const ScrStr *s = (const ScrStr *)scr_slot_to_ptr(slot);
|
|
1414
|
-
if (s) scr_join_append(&
|
|
1695
|
+
if (s) scr_join_append(&out, s->data, s->len);
|
|
1415
1696
|
break;
|
|
1416
1697
|
}
|
|
1417
1698
|
case SCR_ELEM_ARR:
|
|
@@ -1421,8 +1702,7 @@ ScrStr *scr_arr_join(ScrArr *a, ScrStr *sep) {
|
|
|
1421
1702
|
scr_trap("scriptc: internal error: join on a ref-element array\n");
|
|
1422
1703
|
}
|
|
1423
1704
|
}
|
|
1424
|
-
|
|
1425
|
-
free(buf);
|
|
1705
|
+
out->data[out->len] = '\0';
|
|
1426
1706
|
return out;
|
|
1427
1707
|
}
|
|
1428
1708
|
|
|
@@ -1432,25 +1712,22 @@ ScrStr *scr_arr_join(ScrArr *a, ScrStr *sep) {
|
|
|
1432
1712
|
* missing ones skip, exactly the spec's loop. Both arrays are
|
|
1433
1713
|
* SCR_ELEM_STR; borrows both; +1 result. Never throws. */
|
|
1434
1714
|
ScrStr *scr_str_raw(ScrArr *raw, ScrArr *subs) {
|
|
1435
|
-
|
|
1436
|
-
char *buf = malloc(cap);
|
|
1437
|
-
if (!buf) scr_arr_oom();
|
|
1715
|
+
ScrStr *out = scr_str_alloc_raw(0, 64);
|
|
1438
1716
|
for (size_t i = 0; i < raw->len; i++) {
|
|
1439
1717
|
uint64_t raw_slot;
|
|
1440
1718
|
if (scr_arr_slot_at(raw, i, &raw_slot)) {
|
|
1441
1719
|
const ScrStr *s = (const ScrStr *)scr_slot_to_ptr(raw_slot);
|
|
1442
|
-
if (s) scr_join_append(&
|
|
1720
|
+
if (s) scr_join_append(&out, s->data, s->len);
|
|
1443
1721
|
}
|
|
1444
1722
|
if (i + 1 < raw->len && i < subs->len) {
|
|
1445
1723
|
uint64_t sub_slot;
|
|
1446
1724
|
if (scr_arr_slot_at(subs, i, &sub_slot)) {
|
|
1447
1725
|
const ScrStr *v = (const ScrStr *)scr_slot_to_ptr(sub_slot);
|
|
1448
|
-
if (v) scr_join_append(&
|
|
1726
|
+
if (v) scr_join_append(&out, v->data, v->len);
|
|
1449
1727
|
}
|
|
1450
1728
|
}
|
|
1451
1729
|
}
|
|
1452
|
-
|
|
1453
|
-
free(buf);
|
|
1730
|
+
out->data[out->len] = '\0';
|
|
1454
1731
|
return out;
|
|
1455
1732
|
}
|
|
1456
1733
|
|
|
@@ -14,20 +14,30 @@ test("fiber stacks commit on demand and preserve large frames across suspension"
|
|
|
14
14
|
try {
|
|
15
15
|
const bin = join(dir, "fiber-stacks");
|
|
16
16
|
await execFileAsync("clang", [
|
|
17
|
-
"-std=c11",
|
|
17
|
+
"-std=c11",
|
|
18
|
+
"-O1",
|
|
19
|
+
"-Wall",
|
|
20
|
+
"-Wextra",
|
|
21
|
+
"-Wno-deprecated-declarations",
|
|
18
22
|
"-pthread",
|
|
19
23
|
...(sanitize ? ["-fsanitize=address,undefined", "-DSCR_RC_AUDIT"] : []),
|
|
20
24
|
...(process.platform === "linux" ? ["-D_GNU_SOURCE"] : []),
|
|
21
25
|
join(import.meta.dirname, "scr_async.test.c"),
|
|
22
|
-
...EXECUTABLE_RUNTIME_SOURCES
|
|
23
|
-
.
|
|
24
|
-
|
|
26
|
+
...EXECUTABLE_RUNTIME_SOURCES.filter((name) => name !== "scr_async.c").map((name) =>
|
|
27
|
+
join(import.meta.dirname, name),
|
|
28
|
+
),
|
|
25
29
|
...(process.platform === "linux" ? ["-lm"] : []),
|
|
26
|
-
"-o",
|
|
30
|
+
"-o",
|
|
31
|
+
bin,
|
|
27
32
|
]);
|
|
28
33
|
const result = await execFileAsync(bin);
|
|
29
34
|
expect(result.stdout).toBe("fiber stacks stay lazy and preserve large suspended frames\n");
|
|
30
|
-
expect(
|
|
35
|
+
expect(
|
|
36
|
+
result.stderr.replace(
|
|
37
|
+
/^==\d+==WARNING: ASan doesn't fully support makecontext\/swapcontext.*\n/gm,
|
|
38
|
+
"",
|
|
39
|
+
),
|
|
40
|
+
).toBe("");
|
|
31
41
|
} finally {
|
|
32
42
|
await rm(dir, { recursive: true, force: true });
|
|
33
43
|
}
|
|
@@ -132,6 +132,21 @@ static int bi_cmp(const ScrBigInt *a, const ScrBigInt *b) {
|
|
|
132
132
|
}
|
|
133
133
|
|
|
134
134
|
bool scr_bigint_eq(ScrBigInt *a, ScrBigInt *b) { return bi_cmp(a, b) == 0; }
|
|
135
|
+
|
|
136
|
+
uint64_t scr_bigint_hash(const ScrBigInt *value) {
|
|
137
|
+
/* BigInts are immutable and normalized. Ignore capacity and ownership;
|
|
138
|
+
* equal values made by parsing, arithmetic or conversion hash alike. */
|
|
139
|
+
uint64_t hash = UINT64_C(0xcbf29ce484222325) ^ (uint64_t)(value->sign + 1);
|
|
140
|
+
for (size_t i = 0; i < value->len; i++) {
|
|
141
|
+
hash ^= value->limb[i];
|
|
142
|
+
hash *= UINT64_C(0x100000001b3);
|
|
143
|
+
}
|
|
144
|
+
hash ^= hash >> 30;
|
|
145
|
+
hash *= UINT64_C(0xbf58476d1ce4e5b9);
|
|
146
|
+
hash ^= hash >> 27;
|
|
147
|
+
hash *= UINT64_C(0x94d049bb133111eb);
|
|
148
|
+
return hash ^ (hash >> 31);
|
|
149
|
+
}
|
|
135
150
|
double scr_bigint_cmp_f64(ScrBigInt *a, ScrBigInt *b) { return (double)bi_cmp(a, b); }
|
|
136
151
|
bool scr_bigint_truthy(ScrBigInt *v) { return v->sign != 0; }
|
|
137
152
|
|