porffor 0.0.0-44bc2d8 → 0.0.0-48403fd

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/compiler/parse.js CHANGED
@@ -1,3 +1,4 @@
1
+ // import { parse } from 'acorn';
1
2
  const { parse } = (await import(globalThis.document ? 'https://esm.sh/acorn' : 'acorn'));
2
3
 
3
4
  export default (input, flags) => {
@@ -15,17 +15,20 @@ const TYPES = {
15
15
  bigint: 0xffffffffffff7,
16
16
 
17
17
  // these are not "typeof" types but tracked internally
18
- _array: 0xffffffffffff8
18
+ _array: 0xfffffffffff0f,
19
+ _regexp: 0xfffffffffff1f
19
20
  };
20
21
 
21
22
  // todo: turn these into built-ins once arrays and these become less hacky
22
23
 
23
24
  export const PrototypeFuncs = function() {
24
25
  const noUnlikelyChecks = process.argv.includes('-funsafe-no-unlikely-proto-checks');
26
+ let zeroChecks = process.argv.find(x => x.startsWith('-funsafe-zero-proto-checks='));
27
+ if (zeroChecks) zeroChecks = zeroChecks.split('=')[1].split(',').reduce((acc, x) => { acc[x.toLowerCase()] = true; return acc; }, {});
28
+ else zeroChecks = {};
25
29
 
26
30
  this[TYPES._array] = {
27
31
  // lX = local accessor of X ({ get, set }), iX = local index of X, wX = wasm ops of X
28
- // todo: out of bounds (>) properly
29
32
  at: (pointer, length, wIndex, iTmp) => [
30
33
  ...wIndex,
31
34
  Opcodes.i32_to,
@@ -36,7 +39,7 @@ export const PrototypeFuncs = function() {
36
39
  [ Opcodes.i32_lt_s ],
37
40
  [ Opcodes.if, Blocktype.void ],
38
41
  [ Opcodes.local_get, iTmp ],
39
- ...length.cachedI32,
42
+ ...length.getCachedI32(),
40
43
  [ Opcodes.i32_add ],
41
44
  [ Opcodes.local_set, iTmp ],
42
45
  [ Opcodes.end ],
@@ -47,7 +50,7 @@ export const PrototypeFuncs = function() {
47
50
  [ Opcodes.i32_lt_s ],
48
51
 
49
52
  [ Opcodes.local_get, iTmp ],
50
- ...length.cachedI32,
53
+ ...length.getCachedI32(),
51
54
  [ Opcodes.i32_ge_s ],
52
55
  [ Opcodes.i32_or ],
53
56
 
@@ -67,7 +70,7 @@ export const PrototypeFuncs = function() {
67
70
  // todo: only for 1 argument
68
71
  push: (pointer, length, wNewMember) => [
69
72
  // get memory offset of array at last index (length)
70
- ...length.cachedI32,
73
+ ...length.getCachedI32(),
71
74
  ...number(ValtypeSize[valtype], Valtype.i32),
72
75
  [ Opcodes.i32_mul ],
73
76
 
@@ -79,17 +82,17 @@ export const PrototypeFuncs = function() {
79
82
 
80
83
  // bump array length by 1 and return it
81
84
  ...length.setI32([
82
- ...length.cachedI32,
85
+ ...length.getCachedI32(),
83
86
  ...number(1, Valtype.i32),
84
87
  [ Opcodes.i32_add ]
85
88
  ]),
86
89
 
87
- ...length.get
90
+ ...length.get()
88
91
  ],
89
92
 
90
93
  pop: (pointer, length) => [
91
94
  // if length == 0, noop
92
- ...length.cachedI32,
95
+ ...length.getCachedI32(),
93
96
  [ Opcodes.i32_eqz ],
94
97
  [ Opcodes.if, Blocktype.void ],
95
98
  ...number(UNDEFINED),
@@ -100,13 +103,13 @@ export const PrototypeFuncs = function() {
100
103
 
101
104
  // decrement length by 1
102
105
  ...length.setI32([
103
- ...length.cachedI32,
106
+ ...length.getCachedI32(),
104
107
  ...number(1, Valtype.i32),
105
108
  [ Opcodes.i32_sub ]
106
109
  ]),
107
110
 
108
111
  // load last element
109
- ...length.cachedI32,
112
+ ...length.getCachedI32(),
110
113
  ...number(ValtypeSize[valtype], Valtype.i32),
111
114
  [ Opcodes.i32_mul ],
112
115
 
@@ -115,7 +118,7 @@ export const PrototypeFuncs = function() {
115
118
 
116
119
  shift: (pointer, length) => [
117
120
  // if length == 0, noop
118
- ...length.cachedI32,
121
+ ...length.getCachedI32(),
119
122
  Opcodes.i32_eqz,
120
123
  [ Opcodes.if, Blocktype.void ],
121
124
  ...number(UNDEFINED),
@@ -126,7 +129,7 @@ export const PrototypeFuncs = function() {
126
129
 
127
130
  // decrement length by 1
128
131
  ...length.setI32([
129
- ...length.cachedI32,
132
+ ...length.getCachedI32(),
130
133
  ...number(1, Valtype.i32),
131
134
  [ Opcodes.i32_sub ]
132
135
  ]),
@@ -140,15 +143,69 @@ export const PrototypeFuncs = function() {
140
143
  ...number(pointer + ValtypeSize.i32 + ValtypeSize[valtype], Valtype.i32), // src = base array index + length size + an index
141
144
  ...number(pageSize - ValtypeSize.i32 - ValtypeSize[valtype], Valtype.i32), // size = PageSize - length size - an index
142
145
  [ ...Opcodes.memory_copy, 0x00, 0x00 ]
146
+ ],
147
+
148
+ fill: (pointer, length, wElement, iTmp) => [
149
+ ...wElement,
150
+ [ Opcodes.local_set, iTmp ],
151
+
152
+ // use cached length i32 as pointer
153
+ ...length.getCachedI32(),
154
+
155
+ // length - 1 for indexes
156
+ ...number(1, Valtype.i32),
157
+ [ Opcodes.i32_sub ],
158
+
159
+ // * sizeof value
160
+ ...number(ValtypeSize[valtype], Valtype.i32),
161
+ [ Opcodes.i32_mul ],
162
+
163
+ ...length.setCachedI32(),
164
+
165
+ ...(noUnlikelyChecks ? [] : [
166
+ ...length.getCachedI32(),
167
+ ...number(0, Valtype.i32),
168
+ [ Opcodes.i32_lt_s ],
169
+ [ Opcodes.if, Blocktype.void ],
170
+ ...number(pointer),
171
+ [ Opcodes.br, 1 ],
172
+ [ Opcodes.end ]
173
+ ]),
174
+
175
+ [ Opcodes.loop, Blocktype.void ],
176
+
177
+ // set element using pointer
178
+ ...length.getCachedI32(),
179
+ [ Opcodes.local_get, iTmp ],
180
+ [ Opcodes.store, Math.log2(ValtypeSize[valtype]) - 1, ...unsignedLEB128(pointer + ValtypeSize.i32) ],
181
+
182
+ // pointer - sizeof value
183
+ ...length.getCachedI32(),
184
+ ...number(ValtypeSize[valtype], Valtype.i32),
185
+ [ Opcodes.i32_sub ],
186
+
187
+ ...length.setCachedI32(),
188
+
189
+ // if pointer >= 0, loop
190
+ ...length.getCachedI32(),
191
+ ...number(0, Valtype.i32),
192
+ [ Opcodes.i32_ge_s ],
193
+ [ Opcodes.br_if, 0 ],
194
+
195
+ [ Opcodes.end ],
196
+
197
+ // return this array
198
+ ...number(pointer)
143
199
  ]
144
200
  };
145
201
 
146
202
  this[TYPES._array].at.local = Valtype.i32;
147
203
  this[TYPES._array].push.noArgRetLength = true;
204
+ this[TYPES._array].fill.local = valtypeBinary;
205
+ this[TYPES._array].fill.returnType = TYPES._array;
148
206
 
149
207
  this[TYPES.string] = {
150
- // todo: out of bounds properly
151
- at: (pointer, length, wIndex, iTmp, arrayShell) => {
208
+ at: (pointer, length, wIndex, iTmp, _, arrayShell) => {
152
209
  const [ newOut, newPointer ] = arrayShell(1, 'i16');
153
210
 
154
211
  return [
@@ -157,9 +214,9 @@ export const PrototypeFuncs = function() {
157
214
  [ Opcodes.drop ],
158
215
 
159
216
  ...number(0, Valtype.i32), // base 0 for store later
160
- Opcodes.i32_to_u,
161
217
 
162
218
  ...wIndex,
219
+ Opcodes.i32_to_u,
163
220
  [ Opcodes.local_tee, iTmp ],
164
221
 
165
222
  // if index < 0: access index + array length
@@ -167,7 +224,7 @@ export const PrototypeFuncs = function() {
167
224
  [ Opcodes.i32_lt_s ],
168
225
  [ Opcodes.if, Blocktype.void ],
169
226
  [ Opcodes.local_get, iTmp ],
170
- ...length.cachedI32,
227
+ ...length.getCachedI32(),
171
228
  [ Opcodes.i32_add ],
172
229
  [ Opcodes.local_set, iTmp ],
173
230
  [ Opcodes.end ],
@@ -178,7 +235,7 @@ export const PrototypeFuncs = function() {
178
235
  [ Opcodes.i32_lt_s ],
179
236
 
180
237
  [ Opcodes.local_get, iTmp ],
181
- ...length.cachedI32,
238
+ ...length.getCachedI32(),
182
239
  [ Opcodes.i32_ge_s ],
183
240
  [ Opcodes.i32_or ],
184
241
 
@@ -203,7 +260,7 @@ export const PrototypeFuncs = function() {
203
260
  },
204
261
 
205
262
  // todo: out of bounds properly
206
- charAt: (pointer, length, wIndex, _, arrayShell) => {
263
+ charAt: (pointer, length, wIndex, _1, _2, arrayShell) => {
207
264
  const [ newOut, newPointer ] = arrayShell(1, 'i16');
208
265
 
209
266
  return [
@@ -234,39 +291,120 @@ export const PrototypeFuncs = function() {
234
291
  return [
235
292
  ...wIndex,
236
293
  Opcodes.i32_to,
237
- [ Opcodes.local_set, iTmp ],
238
294
 
239
- // index < 0
240
- ...(noUnlikelyChecks ? [] : [
295
+ ...(zeroChecks.charcodeat ? [] : [
296
+ [ Opcodes.local_set, iTmp ],
297
+
298
+ // index < 0
299
+ ...(noUnlikelyChecks ? [] : [
300
+ [ Opcodes.local_get, iTmp ],
301
+ ...number(0, Valtype.i32),
302
+ [ Opcodes.i32_lt_s ],
303
+ ]),
304
+
305
+ // index >= length
306
+ [ Opcodes.local_get, iTmp ],
307
+ ...length.getCachedI32(),
308
+ [ Opcodes.i32_ge_s ],
309
+
310
+ ...(noUnlikelyChecks ? [] : [ [ Opcodes.i32_or ] ]),
311
+ [ Opcodes.if, Blocktype.void ],
312
+ ...number(NaN),
313
+ [ Opcodes.br, 1 ],
314
+ [ Opcodes.end ],
315
+
241
316
  [ Opcodes.local_get, iTmp ],
242
- ...number(0, Valtype.i32),
243
- [ Opcodes.i32_lt_s ],
244
317
  ]),
245
318
 
246
- // index >= length
319
+ ...number(ValtypeSize.i16, Valtype.i32),
320
+ [ Opcodes.i32_mul ],
321
+
322
+ // load current string ind {arg}
323
+ [ Opcodes.i32_load16_u, Math.log2(ValtypeSize.i16) - 1, ...unsignedLEB128(pointer + ValtypeSize.i32) ],
324
+ Opcodes.i32_from_u
325
+ ];
326
+ },
327
+
328
+ isWellFormed: (pointer, length, wIndex, iTmp, iTmp2, arrayShell, { wellFormed } = {}) => {
329
+ // aot approx metadata
330
+ if (wellFormed != null) return number(wellFormed ? 1 : 0);
331
+
332
+ return [
333
+ // note: we cannot presume it begins as 0 in case it was used previously
334
+ ...number(0, Valtype.i32),
335
+ [ Opcodes.local_set, iTmp ],
336
+
337
+ [ Opcodes.loop, Blocktype.void ],
338
+
339
+ [ Opcodes.block, Blocktype.void ],
340
+
247
341
  [ Opcodes.local_get, iTmp ],
248
- ...length.cachedI32,
342
+ [ Opcodes.i32_load16_u, Math.log2(ValtypeSize.i16) - 1, ...unsignedLEB128(pointer + ValtypeSize.i32) ],
343
+ [ Opcodes.local_set, iTmp2 ],
344
+
345
+ // if not surrogate, continue
346
+ [ Opcodes.local_get, iTmp2 ],
347
+ ...number(0xF800, Valtype.i32),
348
+ [ Opcodes.i32_and ],
349
+ ...number(0xD800, Valtype.i32),
350
+ [ Opcodes.i32_ne ],
351
+ [ Opcodes.br_if, 0 ],
352
+
353
+ // if not leading surrogate, return false
354
+ [ Opcodes.local_get, iTmp2 ],
355
+ ...number(0xDC00, Valtype.i32),
249
356
  [ Opcodes.i32_ge_s ],
357
+ [ Opcodes.if, Blocktype.void ],
358
+ ...number(0),
359
+ [ Opcodes.br, 3 ],
360
+ [ Opcodes.end ],
250
361
 
251
- ...(noUnlikelyChecks ? [] : [ [ Opcodes.i32_or ] ]),
362
+ // if not followed by trailing surrogate, return false
363
+ [ Opcodes.local_get, iTmp ],
364
+ [ Opcodes.i32_load16_u, Math.log2(ValtypeSize.i16) - 1, ...unsignedLEB128(pointer + ValtypeSize.i32 + ValtypeSize.i16) ],
365
+ ...number(0xFC00, Valtype.i32),
366
+ [ Opcodes.i32_and ],
367
+ ...number(0xDC00, Valtype.i32),
368
+ [ Opcodes.i32_ne ],
252
369
  [ Opcodes.if, Blocktype.void ],
253
- ...number(NaN),
254
- [ Opcodes.br, 1 ],
370
+ ...number(0),
371
+ [ Opcodes.br, 3 ],
255
372
  [ Opcodes.end ],
256
373
 
374
+ // bump index again since gone through two valid chars
257
375
  [ Opcodes.local_get, iTmp ],
258
376
  ...number(ValtypeSize.i16, Valtype.i32),
377
+ [ Opcodes.i32_add ],
378
+ [ Opcodes.local_set, iTmp ],
379
+
380
+ [ Opcodes.end ],
381
+
382
+ // bump pointer and loop if not at the end
383
+ [ Opcodes.local_get, iTmp ],
384
+ ...number(ValtypeSize.i16, Valtype.i32),
385
+ [ Opcodes.i32_add ],
386
+ [ Opcodes.local_tee, iTmp ],
387
+
388
+ ...length.getCachedI32(),
389
+ ...number(ValtypeSize.i16, Valtype.i32),
259
390
  [ Opcodes.i32_mul ],
391
+ [ Opcodes.i32_ne ],
392
+ [ Opcodes.br_if, 0 ],
260
393
 
261
- // load current string ind {arg}
262
- [ Opcodes.i32_load16_u, Math.log2(ValtypeSize.i16) - 1, ...unsignedLEB128(pointer + ValtypeSize.i32) ],
263
- Opcodes.i32_from_u
264
- ];
265
- },
394
+ [ Opcodes.end ],
395
+
396
+ // return true
397
+ ...number(1)
398
+ ]
399
+ }
266
400
  };
267
401
 
268
- this[TYPES.string].at.local = valtypeBinary;
402
+ this[TYPES.string].at.local = Valtype.i32;
269
403
  this[TYPES.string].at.returnType = TYPES.string;
270
404
  this[TYPES.string].charAt.returnType = TYPES.string;
271
405
  this[TYPES.string].charCodeAt.local = Valtype.i32;
406
+
407
+ this[TYPES.string].isWellFormed.local = Valtype.i32;
408
+ this[TYPES.string].isWellFormed.local2 = Valtype.i32;
409
+ this[TYPES.string].isWellFormed.returnType = TYPES.boolean;
272
410
  };
@@ -1,5 +1,5 @@
1
1
  import { Valtype, FuncType, Empty, ExportDesc, Section, Magic, ModuleVersion, Opcodes, PageSize } from './wasmSpec.js';
2
- import { encodeVector, encodeString, encodeLocal } from './encoding.js';
2
+ import { encodeVector, encodeString, encodeLocal, unsignedLEB128, signedLEB128 } from './encoding.js';
3
3
  import { number } from './embedding.js';
4
4
  import { importedFuncs } from './builtins.js';
5
5
 
@@ -8,11 +8,26 @@ const createSection = (type, data) => [
8
8
  ...encodeVector(data)
9
9
  ];
10
10
 
11
- export default (funcs, globals, tags, pages, flags) => {
11
+ const customSection = (name, data) => [
12
+ Section.custom,
13
+ ...encodeVector([...encodeString(name), ...data])
14
+ ];
15
+
16
+ const chHint = (topTier, baselineTier, strategy) => {
17
+ // 1 byte of 4 2 bit components: spare, top tier, baseline tier, compilation strategy
18
+ // tiers: 0x00 = default, 0x01 = baseline (liftoff), 0x02 = optimized (turbofan)
19
+ // strategy: 0x00 = default, 0x01 = lazy, 0x02 = eager, 0x03 = lazy baseline, eager top tier
20
+ return (strategy | (baselineTier << 2) | (topTier << 4));
21
+ };
22
+
23
+ export default (funcs, globals, tags, pages, data, flags) => {
12
24
  const types = [], typeCache = {};
13
25
 
14
26
  const optLevel = parseInt(process.argv.find(x => x.startsWith('-O'))?.[2] ?? 1);
15
27
 
28
+ const compileHints = process.argv.includes('-compile-hints');
29
+ if (compileHints) log('sections', 'warning: compile hints is V8 only w/ experimental arg! (you used -compile-hints)');
30
+
16
31
  const getType = (params, returns) => {
17
32
  const hash = `${params.join(',')}_${returns.join(',')}`;
18
33
  if (optLog) log('sections', `getType(${JSON.stringify(params)}, ${JSON.stringify(returns)}) -> ${hash} | cache: ${typeCache[hash]}`);
@@ -61,6 +76,7 @@ export default (funcs, globals, tags, pages, flags) => {
61
76
  }
62
77
  }
63
78
  }
79
+ globalThis.importFuncs = importFuncs;
64
80
 
65
81
  if (optLog) log('sections', `treeshake: using ${importFuncs.length}/${importedFuncs.length} imports`);
66
82
 
@@ -74,6 +90,14 @@ export default (funcs, globals, tags, pages, flags) => {
74
90
  encodeVector(funcs.map(x => getType(x.params, x.returns))) // type indexes
75
91
  );
76
92
 
93
+ // compilation hints section - unspecd, v8 only
94
+ // https://github.com/WebAssembly/design/issues/1473#issuecomment-1431274746
95
+ const chSection = !compileHints ? [] : customSection(
96
+ 'compilationHints',
97
+ // for now just do everything as optimise eager
98
+ encodeVector(funcs.map(_ => chHint(0x02, 0x02, 0x02)))
99
+ );
100
+
77
101
  const globalSection = Object.keys(globals).length === 0 ? [] : createSection(
78
102
  Section.global,
79
103
  encodeVector(Object.keys(globals).map(x => [ globals[x].type, 0x01, ...number(globals[x].init ?? 0, globals[x].type).flat(), Opcodes.end ]))
@@ -81,6 +105,9 @@ export default (funcs, globals, tags, pages, flags) => {
81
105
 
82
106
  const exports = funcs.filter(x => x.export).map((x, i) => [ ...encodeString(x.name === 'main' ? 'm' : x.name), ExportDesc.func, x.index ]);
83
107
 
108
+ if (process.argv.includes('-always-memory') && pages.size === 0) pages.set('-always-memory', 0);
109
+ if (optLevel === 0) pages.set('O0 precaution', 0);
110
+
84
111
  const usesMemory = pages.size > 0;
85
112
  const memorySection = !usesMemory ? [] : createSection(
86
113
  Section.memory,
@@ -122,7 +149,7 @@ export default (funcs, globals, tags, pages, flags) => {
122
149
 
123
150
  if (typeCount !== 0) localDecl.push(encodeLocal(typeCount, lastType));
124
151
 
125
- return encodeVector([ ...encodeVector(localDecl), ...x.wasm.flat().filter(x => x !== null), Opcodes.end ]);
152
+ return encodeVector([ ...encodeVector(localDecl), ...x.wasm.flat().filter(x => x < 0xff), Opcodes.end ]);
126
153
  }))
127
154
  );
128
155
 
@@ -131,13 +158,24 @@ export default (funcs, globals, tags, pages, flags) => {
131
158
  encodeVector(types)
132
159
  );
133
160
 
161
+ const dataSection = data.length === 0 ? [] : createSection(
162
+ Section.data,
163
+ encodeVector(data.map(x => [ 0x00, Opcodes.i32_const, ...signedLEB128(x.offset), Opcodes.end, ...encodeVector(x.bytes) ]))
164
+ );
165
+
166
+ const dataCountSection = data.length === 0 ? [] : createSection(
167
+ Section.data_count,
168
+ unsignedLEB128(data.length)
169
+ );
170
+
134
171
  if (process.argv.includes('-sections')) console.log({
135
172
  typeSection: typeSection.map(x => x.toString(16)),
136
173
  importSection: importSection.map(x => x.toString(16)),
137
174
  funcSection: funcSection.map(x => x.toString(16)),
138
175
  globalSection: globalSection.map(x => x.toString(16)),
139
176
  exportSection: exportSection.map(x => x.toString(16)),
140
- codeSection: codeSection.map(x => x.toString(16))
177
+ codeSection: codeSection.map(x => x.toString(16)),
178
+ dataSection: dataSection.map(x => x.toString(16)),
141
179
  });
142
180
 
143
181
  return Uint8Array.from([
@@ -146,10 +184,13 @@ export default (funcs, globals, tags, pages, flags) => {
146
184
  ...typeSection,
147
185
  ...importSection,
148
186
  ...funcSection,
187
+ ...chSection,
149
188
  ...memorySection,
150
189
  ...tagSection,
151
190
  ...globalSection,
152
191
  ...exportSection,
153
- ...codeSection
192
+ ...dataCountSection,
193
+ ...codeSection,
194
+ ...dataSection
154
195
  ]);
155
196
  };
@@ -118,6 +118,7 @@ export const Opcodes = {
118
118
  i64_shl: 0x86,
119
119
  i64_shr_s: 0x87,
120
120
  i64_shr_u: 0x88,
121
+ i64_rotl: 0x89,
121
122
 
122
123
  f64_eq: 0x61,
123
124
  f64_ne: 0x62,
@@ -156,6 +157,8 @@ export const Opcodes = {
156
157
  f64_convert_i64_s: 0xb9,
157
158
  f64_convert_i64_u: 0xba,
158
159
 
160
+ f64_reinterpret_i64: 0xbf,
161
+
159
162
  i32_trunc_sat_f64_s: [ 0xfc, 0x02 ],
160
163
  i32_trunc_sat_f64_u: [ 0xfc, 0x03 ],
161
164
 
package/compiler/wrap.js CHANGED
@@ -4,7 +4,8 @@ import fs from 'node:fs';
4
4
 
5
5
  const bold = x => `\u001b[1m${x}\u001b[0m`;
6
6
 
7
- const typeBase = 0xffffffffffff0;
7
+ const typeBase = 0x00;
8
+ const internalTypeBase = 0x10;
8
9
  const TYPES = {
9
10
  [typeBase]: 'number',
10
11
  [typeBase + 1]: 'boolean',
@@ -16,7 +17,8 @@ const TYPES = {
16
17
  [typeBase + 7]: 'bigint',
17
18
 
18
19
  // internal
19
- [typeBase + 8]: '_array'
20
+ [internalTypeBase]: '_array',
21
+ [internalTypeBase + 1]: '_regexp'
20
22
  };
21
23
 
22
24
  export default async (source, flags = [ 'module' ], customImports = {}, print = str => process.stdout.write(str)) => {
@@ -64,11 +66,15 @@ export default async (source, flags = [ 'module' ], customImports = {}, print =
64
66
 
65
67
  exports[func.name] = function() {
66
68
  try {
67
- const ret = exp.apply(this, arguments);
69
+ const _ret = exp.apply(this, arguments);
68
70
 
69
- if (ret >= typeBase && ret <= typeBase + 8) return ret > (typeBase + 7) ? 'object' : TYPES[ret];
71
+ if (_ret == null) return undefined;
70
72
 
71
- switch (TYPES[func.returnType]) {
73
+ const [ ret, type ] = _ret;
74
+
75
+ // if (ret >= typeBase && ret <= typeBase + 8) return ret > (typeBase + 7) ? 'object' : TYPES[ret];
76
+
77
+ switch (TYPES[type]) {
72
78
  case 'boolean': return Boolean(ret);
73
79
  case 'undefined': return undefined;
74
80
  case 'object': return ret === 0 ? null : {};
package/cool.exe ADDED
Binary file
package/fib.js ADDED
@@ -0,0 +1,10 @@
1
+ function fibonacci(num) {
2
+ if(num < 2) {
3
+ return num;
4
+ }
5
+ else {
6
+ return fibonacci(num-1) + fibonacci(num - 2);
7
+ }
8
+ }
9
+
10
+ console.log(fibonacci(42));
package/g ADDED
Binary file
package/g.exe ADDED
Binary file
package/hi.c ADDED
@@ -0,0 +1,37 @@
1
+ #include <stdio.h>
2
+
3
+ double inline f64_f(double x, double y) {
4
+ return x - (int)(x / y) * y;
5
+ }
6
+
7
+ double isPrime(double number) {
8
+ double i;
9
+
10
+ if (number < 2e+0) {
11
+ return 0e+0;
12
+ }
13
+ i = 2e+0;
14
+ while (i < number) {
15
+ if (f64_f(number, i) == 0e+0) {
16
+ return 0e+0;
17
+ }
18
+ i = i + 1e+0;
19
+ }
20
+ return 1e+0;
21
+ }
22
+
23
+ int main() {
24
+ double sum;
25
+ double counter;
26
+
27
+ sum = 0e+0;
28
+ counter = 0e+0;
29
+ while (counter <= 1e+5) {
30
+ if (isPrime(counter) == 1e+0) {
31
+ sum = sum + counter;
32
+ }
33
+ counter = counter + 1e+0;
34
+ }
35
+ printf("%f\n", sum);
36
+ }
37
+
package/out ADDED
Binary file
package/out.exe ADDED
Binary file
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "porffor",
3
3
  "description": "a basic experimental wip aot optimizing js -> wasm engine/compiler/runtime in js",
4
- "version": "0.0.0-44bc2d8",
4
+ "version": "0.0.0-48403fd",
5
5
  "author": "CanadaHonk",
6
6
  "license": "MIT",
7
7
  "dependencies": {
package/r.js ADDED
@@ -0,0 +1,39 @@
1
+ compareArray.isSameValue = function(a, b) {
2
+ if (a === 0 && b === 0) return 1 / a === 1 / b;
3
+ if (a !== a && b !== b) return true;
4
+
5
+ return a === b;
6
+ };
7
+
8
+ function compareArray(a, b) {
9
+ // if either are nullish
10
+ if (a == null || b == null) return false;
11
+
12
+ // megahack: all arrays from now on will be >0 pointer
13
+ const _hack = '';
14
+
15
+ // hack: enforce type inference of being arrays
16
+ a ??= [];
17
+ b ??= [];
18
+
19
+ if (b.length !== a.length) {
20
+ return false;
21
+ }
22
+
23
+ for (var i = 0; i < a.length; i++) {
24
+ if (!compareArray.isSameValue(b[i], a[i])) {
25
+ return false;
26
+ }
27
+ }
28
+
29
+ return true;
30
+ }
31
+
32
+ console.log(compareArray(null, []));
33
+ console.log(compareArray(undefined, []));
34
+
35
+ console.log(compareArray([], []));
36
+ console.log(compareArray([ 1 ], []));
37
+ console.log(compareArray([ 1 ], [ 1 ]));
38
+ console.log(compareArray([ 1, 2 ], [ 1 ]));
39
+ console.log(compareArray([ 1, 2 ], [ 1, 2 ]));
@@ -0,0 +1,37 @@
1
+ # rhemyn
2
+ a basic experimental wip regex engine/aot wasm compiler in js. regex engine for porffor. uses own regex parser, no dependencies (excluding porffor internals). <br>
3
+ age: ~1 day
4
+
5
+ made for use with porffor but could possibly be adapted, implementation/library notes:
6
+ - exposes functions for each regex "operation" (eg test, match)
7
+ - given a regex pattern string (eg `a+`), it returns a "function" object
8
+ - wasm function returned expects an i32 pointer to a utf-16 string (can add utf-8 option later if someone else actually wants to use this)
9
+
10
+ ## syntax
11
+ 🟢 supported 🟡 partial 🟠 parsed only 🔴 unsupported
12
+
13
+ - 🟢 literal characters (eg `a`)
14
+ - 🟢 escaping (eg `\.\n\cJ\x0a\u000a`)
15
+ - 🟢 character itself (eg `\.`)
16
+ - 🟢 escape sequences (eg `\n`)
17
+ - 🟢 control character (eg `\cJ`)
18
+ - 🟢 unicode code points (eg `\x00`, `\u0000`)
19
+ - 🟢 sets (eg `[ab]`)
20
+ - 🟢 ranges (eg `[a-z]`)
21
+ - 🟢 negated sets (eg `[^ab]`)
22
+ - 🟢 metacharacters
23
+ - 🟢 dot (eg `a.b`)
24
+ - 🟢 digit, not digit (eg `\d\D`)
25
+ - 🟢 word, not word (eg `\w\W`)
26
+ - 🟢 whitespace, not whitespace (eg `\s\S`)
27
+ - 🟠 quantifiers
28
+ - 🟠 star (eg `a*`)
29
+ - 🟠 plus (eg `a+`)
30
+ - 🟠 optional (eg `a?`)
31
+ - 🟠 lazy modifier (eg `a*?`)
32
+ - 🔴 n repetitions (eg `a{4}`)
33
+ - 🔴 n-m repetitions (eg `a{2,4}`)
34
+ - 🔴 assertions
35
+ - 🔴 beginning (eg `^a`)
36
+ - 🔴 end (eg `a$`)
37
+ - 🔴 word boundary assertion (eg `\b\B`)