@scriptc/compiler 0.1.4 → 0.1.6

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 (158) hide show
  1. package/ambient/scriptc-node-fallback.d.ts +75 -11
  2. package/dist/backend/c/c-emitter.d.ts +5 -1
  3. package/dist/backend/c/c-emitter.js +22 -9
  4. package/dist/backend/c/c-emitter.js.map +1 -1
  5. package/dist/backend/c/exprs.d.ts +2 -2
  6. package/dist/backend/c/exprs.js +298 -27
  7. package/dist/backend/c/exprs.js.map +1 -1
  8. package/dist/backend/c/stmts.js +5 -3
  9. package/dist/backend/c/stmts.js.map +1 -1
  10. package/dist/backend/c/types.d.ts +2 -3
  11. package/dist/backend/c/types.js +8 -1
  12. package/dist/backend/c/types.js.map +1 -1
  13. package/dist/backend/c/walkers.js +1 -1
  14. package/dist/backend/c/walkers.js.map +1 -1
  15. package/dist/backend/link-plan.d.ts +1 -0
  16. package/dist/backend/link-plan.js +2 -1
  17. package/dist/backend/link-plan.js.map +1 -1
  18. package/dist/backend/llvm/dyn.js +1 -1
  19. package/dist/backend/llvm/dyn.js.map +1 -1
  20. package/dist/backend/llvm/emitter.js +25 -9
  21. package/dist/backend/llvm/emitter.js.map +1 -1
  22. package/dist/backend/llvm/expr-bytes.d.ts +1 -2
  23. package/dist/backend/llvm/expr-bytes.js +22 -17
  24. package/dist/backend/llvm/expr-bytes.js.map +1 -1
  25. package/dist/backend/llvm/expr-containers.d.ts +1 -0
  26. package/dist/backend/llvm/expr-containers.js +58 -4
  27. package/dist/backend/llvm/expr-containers.js.map +1 -1
  28. package/dist/backend/llvm/expr-context.d.ts +6 -2
  29. package/dist/backend/llvm/expr-primitives.js +22 -7
  30. package/dist/backend/llvm/expr-primitives.js.map +1 -1
  31. package/dist/backend/llvm/lib-filesystem.js +20 -0
  32. package/dist/backend/llvm/lib-filesystem.js.map +1 -1
  33. package/dist/backend/llvm/lib-network.js +53 -10
  34. package/dist/backend/llvm/lib-network.js.map +1 -1
  35. package/dist/backend/llvm/lib-process.js +4 -3
  36. package/dist/backend/llvm/lib-process.js.map +1 -1
  37. package/dist/backend/llvm/lib-shared.js +65 -0
  38. package/dist/backend/llvm/lib-shared.js.map +1 -1
  39. package/dist/backend/native-toolchain.d.ts +2 -0
  40. package/dist/backend/native-toolchain.js +2 -1
  41. package/dist/backend/native-toolchain.js.map +1 -1
  42. package/dist/backend/targets.d.ts +3 -0
  43. package/dist/backend/targets.js +13 -0
  44. package/dist/backend/targets.js.map +1 -1
  45. package/dist/coverage/surface-manifest.js +12 -5
  46. package/dist/coverage/surface-manifest.js.map +1 -1
  47. package/dist/executable/executable-cache.d.ts +2 -0
  48. package/dist/executable/executable-cache.js +3 -1
  49. package/dist/executable/executable-cache.js.map +1 -1
  50. package/dist/executable/executable-cache.test.js +3 -3
  51. package/dist/executable/executable-cache.test.js.map +1 -1
  52. package/dist/frontend/lowering/array-indexed-mutation.d.ts +8 -0
  53. package/dist/frontend/lowering/array-indexed-mutation.js +176 -0
  54. package/dist/frontend/lowering/array-indexed-mutation.js.map +1 -0
  55. package/dist/frontend/lowering/containers/bytes.d.ts +1 -1
  56. package/dist/frontend/lowering/containers/bytes.js +6 -5
  57. package/dist/frontend/lowering/containers/bytes.js.map +1 -1
  58. package/dist/frontend/lowering/containers/string-and-regexp.d.ts +14 -6
  59. package/dist/frontend/lowering/containers/string-and-regexp.js +420 -34
  60. package/dist/frontend/lowering/containers/string-and-regexp.js.map +1 -1
  61. package/dist/frontend/lowering/expressions/object-literals.js +8 -0
  62. package/dist/frontend/lowering/expressions/object-literals.js.map +1 -1
  63. package/dist/frontend/lowering/indexed-comparison.d.ts +6 -0
  64. package/dist/frontend/lowering/indexed-comparison.js +30 -0
  65. package/dist/frontend/lowering/indexed-comparison.js.map +1 -0
  66. package/dist/frontend/lowering/lower-builtins.d.ts +5 -6
  67. package/dist/frontend/lowering/lower-builtins.js +24 -16
  68. package/dist/frontend/lowering/lower-builtins.js.map +1 -1
  69. package/dist/frontend/lowering/lower-calls.d.ts +3 -2
  70. package/dist/frontend/lowering/lower-calls.js +522 -89
  71. package/dist/frontend/lowering/lower-calls.js.map +1 -1
  72. package/dist/frontend/lowering/lower-classes.js +5 -29
  73. package/dist/frontend/lowering/lower-classes.js.map +1 -1
  74. package/dist/frontend/lowering/lower-containers.d.ts +15 -11
  75. package/dist/frontend/lowering/lower-containers.js +588 -146
  76. package/dist/frontend/lowering/lower-containers.js.map +1 -1
  77. package/dist/frontend/lowering/lower-exprs.d.ts +12 -0
  78. package/dist/frontend/lowering/lower-exprs.js +145 -11
  79. package/dist/frontend/lowering/lower-exprs.js.map +1 -1
  80. package/dist/frontend/lowering/lower-island.js +17 -6
  81. package/dist/frontend/lowering/lower-island.js.map +1 -1
  82. package/dist/frontend/lowering/lower-server.d.ts +2 -4
  83. package/dist/frontend/lowering/lower-server.js +288 -32
  84. package/dist/frontend/lowering/lower-server.js.map +1 -1
  85. package/dist/frontend/lowering/lower-stmts.js +4 -4
  86. package/dist/frontend/lowering/lower-stmts.js.map +1 -1
  87. package/dist/frontend/lowering/lowerer.js +37 -2
  88. package/dist/frontend/lowering/lowerer.js.map +1 -1
  89. package/dist/frontend/lowering/optional-arguments.d.ts +9 -1
  90. package/dist/frontend/lowering/optional-arguments.js +67 -1
  91. package/dist/frontend/lowering/optional-arguments.js.map +1 -1
  92. package/dist/frontend/lowering/pairs-snapshot.d.ts +3 -1
  93. package/dist/frontend/lowering/pairs-snapshot.js +12 -4
  94. package/dist/frontend/lowering/pairs-snapshot.js.map +1 -1
  95. package/dist/frontend/lowering/surfaces.d.ts +10 -14
  96. package/dist/frontend/lowering/surfaces.js +50 -28
  97. package/dist/frontend/lowering/surfaces.js.map +1 -1
  98. package/dist/frontend/npm-static-prune.d.ts +6 -0
  99. package/dist/frontend/npm-static-prune.js +203 -0
  100. package/dist/frontend/npm-static-prune.js.map +1 -0
  101. package/dist/frontend/npm-static-prune.test.d.ts +1 -0
  102. package/dist/frontend/npm-static-prune.test.js +48 -0
  103. package/dist/frontend/npm-static-prune.test.js.map +1 -0
  104. package/dist/frontend/npm.js +7 -6
  105. package/dist/frontend/npm.js.map +1 -1
  106. package/dist/frontend/program.js +15 -4
  107. package/dist/frontend/program.js.map +1 -1
  108. package/dist/frontend/provenance.js +8 -3
  109. package/dist/frontend/provenance.js.map +1 -1
  110. package/dist/frontend/type-mapper.js +16 -5
  111. package/dist/frontend/type-mapper.js.map +1 -1
  112. package/dist/index.d.ts +3 -3
  113. package/dist/index.js +13 -41
  114. package/dist/index.js.map +1 -1
  115. package/dist/ir/analysis.d.ts +5 -3
  116. package/dist/ir/analysis.js +25 -11
  117. package/dist/ir/analysis.js.map +1 -1
  118. package/dist/ir/analysis.test.js +50 -2
  119. package/dist/ir/analysis.test.js.map +1 -1
  120. package/dist/ir/constant-tables.d.ts +17 -0
  121. package/dist/ir/constant-tables.js +99 -0
  122. package/dist/ir/constant-tables.js.map +1 -0
  123. package/dist/ir/constant-tables.test.d.ts +1 -0
  124. package/dist/ir/constant-tables.test.js +78 -0
  125. package/dist/ir/constant-tables.test.js.map +1 -0
  126. package/dist/ir/integer-ranges.d.ts +13 -0
  127. package/dist/ir/integer-ranges.js +122 -0
  128. package/dist/ir/integer-ranges.js.map +1 -0
  129. package/dist/ir/integer-ranges.test.d.ts +1 -0
  130. package/dist/ir/integer-ranges.test.js +63 -0
  131. package/dist/ir/integer-ranges.test.js.map +1 -0
  132. package/dist/ir/ir.d.ts +56 -35
  133. package/dist/ir/ir.js +9 -1
  134. package/dist/ir/ir.js.map +1 -1
  135. package/dist/ir/ir.test.js +6 -0
  136. package/dist/ir/ir.test.js.map +1 -1
  137. package/dist/ir/scalar-records.d.ts +8 -0
  138. package/dist/ir/scalar-records.js +216 -0
  139. package/dist/ir/scalar-records.js.map +1 -0
  140. package/dist/ir/scalar-records.test.d.ts +1 -0
  141. package/dist/ir/scalar-records.test.js +142 -0
  142. package/dist/ir/scalar-records.test.js.map +1 -0
  143. package/dist/ir/validate.js +135 -34
  144. package/dist/ir/validate.js.map +1 -1
  145. package/dist/ir/validate.test.d.ts +1 -0
  146. package/dist/ir/validate.test.js +48 -0
  147. package/dist/ir/validate.test.js.map +1 -0
  148. package/dist/library/cache-primitives.d.ts +1 -1
  149. package/dist/library/cache-primitives.js +3 -3
  150. package/dist/library/cache-primitives.js.map +1 -1
  151. package/dist/library/fence-eval.js +11 -4
  152. package/dist/library/fence-eval.js.map +1 -1
  153. package/dist/library/library-cache.js +0 -1
  154. package/dist/library/library-cache.js.map +1 -1
  155. package/dist/library/library-cache.test.js +3 -3
  156. package/dist/library/library-cache.test.js.map +1 -1
  157. package/package.json +17 -17
  158. package/surface-manifest.json +90 -45
@@ -66,6 +66,9 @@ import { endsWithJump, matchStringSelfConcat, streamTypedRefEligible } from "../
66
66
  import { emitLibraryIdentityLines } from "../library-identity-markers.js";
67
67
  import { CAUGHT, ffiCallbackType, isDynTypedRefType, isFfiContextParam, isRefCounted, isUnitType, moduleEmbedsBuiltin, moduleEmbedsCompressedNpm, moduleUsesChildProcess, moduleUsesDynInvoke, moduleUsesFetch, moduleUsesFsWatch, moduleUsesHttpServer, moduleUsesNet, moduleUsesNodeTest, moduleUsesProcessEvents, moduleUsesStream, moduleUsesTls, moduleUsesTlsCa, NPM_COMPRESS_MIN, POINTER_KINDS, RUNTIME_EMITTER_CLASS, RUNTIME_ERROR_CLASSES, RUNTIME_STREAM_CLASSES, typeKey, VOID } from "../../ir/ir.js";
68
68
  import { matchIntegerBytesForLoop } from "../../ir/integer-loops.js";
69
+ import { scalarizeNumericRecords } from "../../ir/scalar-records.js";
70
+ import { analyzeIntegerRanges } from "../../ir/integer-ranges.js";
71
+ import { findConstantNumericTables } from "../../ir/constant-tables.js";
69
72
  import { allocateFfiCallbackAdapters, hasForeignFfiCallback, hasRetainedFfiCallback } from "../ffi-callbacks.js";
70
73
  import { RUNTIME_ABI_MARKER } from "../runtime-abi.js";
71
74
  import { computeMayThrow } from "../c/may-throw.js";
@@ -81,8 +84,8 @@ import { emitJsInteropExpr, emitExpr } from "./expr-dispatch.js";
81
84
  import { emitJsMarshal, emitJsOp, emitJsExit, islandAdapter, islandTypedAdapter } from "./expr-island.js";
82
85
  import { dynKind, raceAdapterFor, genResultThunkFor, childExitThunkFor, childExitSignalThunkFor, childDataThunkFor, execFileThunkFor, ipcMessageThunkFor, ipcSendThunkFor, emitterFixedAdapter, wrapEmitterListener, unwrapNullableClosure, closeBindThunkFor, closeOverrideWrapFor } from "./expr-callbacks.js";
83
86
  import { streamDataAdapter, streamDoneFnFor, cryptoBytesThunkFor, fsRenameThunkFor, streamCbThunkFor, zlibBytesThunkFor } from "./expr-stream-callbacks.js";
84
- import { resolveThunkFor, tagInSet, arrPush, emitArrayCopyLoop, emitStrIntrinsic, emitArrIntrinsic, wrapNullable, emitMapNew, mapSet, emitMapLikeIntrinsic, emitSetNew } from "./expr-containers.js";
85
- import { emitBytesReceiver, emitIntegerLoopIndex, emitBytesIndex, emitBytesData, emitBytesLength, emitBytesGet, emitToUint32, emitBytesSet, emitBytesIntrinsic } from "./expr-bytes.js";
87
+ import { emitStableReceiver, resolveThunkFor, tagInSet, arrPush, emitArrayCopyLoop, emitStrIntrinsic, emitArrIntrinsic, wrapNullable, emitMapNew, mapSet, emitMapLikeIntrinsic, emitSetNew } from "./expr-containers.js";
88
+ import { emitIntegerLoopIndex, emitBytesIndex, emitBytesData, emitBytesLength, emitBytesGet, emitToUint32, emitBytesSet, emitBytesIntrinsic } from "./expr-bytes.js";
86
89
  import { emitRegexIntrinsic, emitRecordKeyGet, keyedRecordReadInto } from "./expr-records.js";
87
90
  import { dynPromiseAdapter, streamTypedRefCommitAdapter, liveDynUnionRefAdapter, streamTypedRefBoxValue, streamTypedRefMaterializeAdapter, streamFromArrayAdapter } from "./expr-stream-bridges.js";
88
91
  import { emitWebLibCall, emitDynamicLibCall, emitFilesystemLibCall, emitPathUrlLibCall, emitPrimitiveLibCall } from "./lib-filesystem.js";
@@ -111,7 +114,7 @@ function ffiCallbackDummyLl(callback) {
111
114
  }
112
115
  }
113
116
  export function emitLlvmModule(mod, options = {}) {
114
- return new LlEmitter(mod, options).emit();
117
+ return new LlEmitter(scalarizeNumericRecords(mod), options).emit();
115
118
  }
116
119
  /** LLVM c"..." payload for a UTF-8 literal, NUL-terminated like the C
117
120
  * emitter's flexible-array-member initializer. */
@@ -185,6 +188,7 @@ class LlEmitter {
185
188
  ffiHasRetainedCallback;
186
189
  ffiHasForeignCallback;
187
190
  globalTypes = new Map();
191
+ constantNumericTables;
188
192
  /** May-throw analysis (the C emitter's computeMayThrow, shared): pending
189
193
  * checks are emitted only after calls that can actually raise. */
190
194
  mayThrow;
@@ -249,6 +253,7 @@ class LlEmitter {
249
253
  captureIds = new Set();
250
254
  /** Active canonical byte-loop induction bindings: local id → size_t slot. */
251
255
  integerLoopBindings = new Map();
256
+ integerRanges = new Map();
252
257
  /** Enclosing try-with-FINALLY regions, innermost last: a `return`
253
258
  * inside one runs every crossed finally (innermost first) before the
254
259
  * actual ret — the C emitter's pending-return path, with the finally
@@ -280,6 +285,7 @@ class LlEmitter {
280
285
  logArgSlots = 0;
281
286
  constructor(mod, options) {
282
287
  this.mod = mod;
288
+ this.constantNumericTables = findConstantNumericTables(mod);
283
289
  this.sizeType = options.pointerBits === 32 ? "i32" : "i64";
284
290
  this.wasi = options.wasi === true;
285
291
  this.emitLibraryIdentity = options.emitLibraryIdentity !== false;
@@ -890,6 +896,8 @@ class LlEmitter {
890
896
  // Helpers assemble BEFORE the declaration table flushes (they add
891
897
  // write/abort declarations).
892
898
  const helpers = this.helperDefs();
899
+ if (this.constantNumericTables.size > 0)
900
+ this.declare(`declare double @scr_arr_get_number(ptr, double)`);
893
901
  const out = [
894
902
  `; Generated by scriptc (LLVM backend) from ${this.mod.sourceFile}. Do not edit.`,
895
903
  ``,
@@ -959,6 +967,13 @@ class LlEmitter {
959
967
  for (const d of this.decls)
960
968
  out.push(d);
961
969
  out.push(``);
970
+ for (const table of this.constantNumericTables.values()) {
971
+ const n = table.values.length;
972
+ out.push(`@${table.symbol} = private constant [${n} x double] [${table.values.map((v) => `double ${f64Lit(v)}`).join(", ")}]`, `define internal double @${table.symbol}_get(ptr %a, double %i) alwaysinline #0 {`, `entry:`, ` %initialized = icmp ne ptr %a, null`, ` %nonnegative = fcmp oge double %i, ${f64Lit(0)}`, ` %below = fcmp olt double %i, ${f64Lit(n)}`, ` %range = and i1 %nonnegative, %below`, ` %safe = and i1 %initialized, %range`, ` br i1 %safe, label %convert, label %fallback`, `convert:`,
973
+ // The branch must dominate fptoui: NaN/out-of-range conversion
974
+ // would produce poison. Fractional indices also need a fallback.
975
+ ` %index = fptoui double %i to ${this.sizeType}`, ` %roundtrip = uitofp ${this.sizeType} %index to double`, ` %integer = fcmp oeq double %roundtrip, %i`, ` br i1 %integer, label %read, label %fallback`, `read:`, ` %slot = getelementptr inbounds [${n} x double], ptr @${table.symbol}, ${this.sizeType} 0, ${this.sizeType} %index`, ` %value = load double, ptr %slot`, ` ret double %value`, `fallback:`, ` %generic = call double @scr_arr_get_number(ptr %a, double %i)`, ` ret double %generic`, `}`, ``);
976
+ }
962
977
  for (const [text, lit] of this.literals) {
963
978
  // Immortal interned ScrStr: { rc = SIZE_MAX, len, cap = len, bytes\0 } —
964
979
  // the C emitter's static table, retain/release skip rc == SIZE_MAX.
@@ -2532,6 +2547,7 @@ class LlEmitter {
2532
2547
  this.currentLocals = new Map(fn.locals.map((l) => [l.id, l]));
2533
2548
  this.captureIds = new Set((fn.captures ?? []).map((c) => c.localId));
2534
2549
  this.integerLoopBindings.clear();
2550
+ this.integerRanges = analyzeIntegerRanges(fn);
2535
2551
  this.chainSlots.clear();
2536
2552
  this.finallyStack = [];
2537
2553
  this.tryStack = [];
@@ -2841,7 +2857,7 @@ class LlEmitter {
2841
2857
  // JS-exactly), so no ownership moves. Any invalid index traps — no
2842
2858
  // append. IrBytesElem is static, so never rediscover it through the
2843
2859
  // generic runtime switch in a hot loop.
2844
- const arr = this.emitBytesReceiver(s.arr, [s.index, s.value]);
2860
+ const arr = this.emitStableReceiver(s.arr, [s.index, s.value]);
2845
2861
  const integerIndex = this.emitIntegerLoopIndex(s.index);
2846
2862
  const idx = integerIndex ?? this.emitExpr(s.index).name;
2847
2863
  const v = this.emitExpr(s.value);
@@ -3133,7 +3149,7 @@ class LlEmitter {
3133
3149
  B.br(lc);
3134
3150
  B.startBlock(lc);
3135
3151
  if (integerLoop && integerSlot) {
3136
- const receiver = this.emitBytesReceiver(integerLoop.limitReceiver, []);
3152
+ const receiver = this.emitStableReceiver(integerLoop.limitReceiver, []);
3137
3153
  const lenPtr = B.tmp();
3138
3154
  const len = B.tmp();
3139
3155
  const index = B.tmp();
@@ -3875,8 +3891,8 @@ class LlEmitter {
3875
3891
  emitSetNew(e) {
3876
3892
  return emitSetNew(this.expressionContext(), e);
3877
3893
  }
3878
- emitBytesReceiver(receiver, following) {
3879
- return emitBytesReceiver(this.expressionContext(), receiver, following);
3894
+ emitStableReceiver(receiver, following) {
3895
+ return emitStableReceiver(this.expressionContext(), receiver, following);
3880
3896
  }
3881
3897
  emitIntegerLoopIndex(expr) {
3882
3898
  return emitIntegerLoopIndex(this.expressionContext(), expr);
@@ -3893,8 +3909,8 @@ class LlEmitter {
3893
3909
  emitBytesGet(elem, receiver, index, integerIndex = false) {
3894
3910
  return emitBytesGet(this.expressionContext(), elem, receiver, index, integerIndex);
3895
3911
  }
3896
- emitToUint32(value) {
3897
- return emitToUint32(this.expressionContext(), value);
3912
+ emitToUint32(value, expr) {
3913
+ return emitToUint32(this.expressionContext(), value, expr);
3898
3914
  }
3899
3915
  emitBytesSet(elem, receiver, index, value, integerIndex = false) {
3900
3916
  return emitBytesSet(this.expressionContext(), elem, receiver, index, value, integerIndex);