porffor 0.58.17 → 0.58.19

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.
@@ -2,7 +2,6 @@ import { Blocktype, Opcodes, Valtype, ValtypeSize } from './wasmSpec.js';
2
2
  import { number, ieee754_binary64, signedLEB128, unsignedLEB128, encodeVector, read_signedLEB128 } from './encoding.js';
3
3
  import { operatorOpcode } from './expression.js';
4
4
  import { BuiltinFuncs, BuiltinVars, importedFuncs, NULL, UNDEFINED } from './builtins.js';
5
- import { PrototypeFuncs } from './prototype.js';
6
5
  import { TYPES, TYPE_FLAGS, TYPE_NAMES } from './types.js';
7
6
  import parse from './parse.js';
8
7
  import { log } from './log.js';
@@ -556,7 +555,7 @@ const lookup = (scope, name, failEarly = false) => {
556
555
  includeBuiltin(scope, name);
557
556
  }
558
557
 
559
- if (isExistingProtoFunc(name) || Object.hasOwn(internalConstrs, name)) {
558
+ if (Object.hasOwn(internalConstrs, name)) {
560
559
  // todo: return an actual something
561
560
  return [ number(1) ];
562
561
  }
@@ -1520,16 +1519,9 @@ const includeBuiltin = (scope, builtin) => {
1520
1519
  const generateLogicExp = (scope, decl) =>
1521
1520
  performLogicOp(scope, decl.operator, generate(scope, decl.left), generate(scope, decl.right), getNodeType(scope, decl.left), getNodeType(scope, decl.right));
1522
1521
 
1523
- const isExistingProtoFunc = name => {
1524
- if (name.startsWith('__Array_prototype')) return Object.hasOwn(prototypeFuncs[TYPES.array], name.slice(18));
1525
- if (name.startsWith('__String_prototype_')) return Object.hasOwn(prototypeFuncs[TYPES.string], name.slice(19));
1526
-
1527
- return false;
1528
- };
1529
-
1530
1522
  const getInferred = (scope, name, global = false) => {
1531
1523
  if (global) {
1532
- if (globalInfer.has(name)) return globalInfer.get(name);
1524
+ if (globalInfer.has(name) && inferLoopPrev.length === 0) return globalInfer.get(name);
1533
1525
  } else if (scope.inferTree) {
1534
1526
  for (let i = scope.inferTree.length - 1; i >= 0; i--) {
1535
1527
  const x = scope.inferTree[i];
@@ -1595,7 +1587,7 @@ const getType = (scope, name, failEarly = false) => {
1595
1587
  [ global ? Opcodes.global_get : Opcodes.local_get, typeLocal.idx ]
1596
1588
  ];
1597
1589
 
1598
- if (hasFuncWithName(name) || isExistingProtoFunc(name)) {
1590
+ if (hasFuncWithName(name)) {
1599
1591
  return [ number(TYPES.function, Valtype.i32) ];
1600
1592
  }
1601
1593
 
@@ -2294,9 +2286,7 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
2294
2286
  });
2295
2287
  }
2296
2288
 
2297
- const protoBC = {};
2298
2289
  const builtinProtoCands = Object.keys(builtinFuncs).filter(x => x.startsWith('__') && x.endsWith('_prototype_' + protoName));
2299
-
2300
2290
  if (!decl._protoInternalCall && builtinProtoCands.length > 0) {
2301
2291
  out.push(
2302
2292
  ...generate(scope, target),
@@ -2315,6 +2305,7 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
2315
2305
  );
2316
2306
  }
2317
2307
 
2308
+ const protoBC = {};
2318
2309
  for (const x of builtinProtoCands) {
2319
2310
  const name = x.split('_prototype_')[0].toLowerCase();
2320
2311
  const type = TYPES[name.slice(2)] ?? TYPES[name];
@@ -2338,88 +2329,7 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
2338
2329
  _protoInternalCall: true
2339
2330
  });
2340
2331
  }
2341
- }
2342
-
2343
- const protoCands = Object.keys(prototypeFuncs).reduce((acc, x) => {
2344
- if (Object.hasOwn(prototypeFuncs[x], protoName)) acc[x] = prototypeFuncs[x][protoName];
2345
- return acc;
2346
- }, {});
2347
-
2348
- if (Object.keys(protoCands).length > 0) {
2349
- // use local for cached i32 length as commonly used
2350
- const lengthLocal = localTmp(scope, '__proto_length_cache', Valtype.i32);
2351
- const pointerLocal = localTmp(scope, '__proto_pointer_cache', Valtype.i32);
2352
-
2353
- if (out.length === 0) {
2354
- out.push(
2355
- ...generate(scope, target),
2356
- Opcodes.i32_to_u,
2357
- [ Opcodes.local_set, pointerLocal ]
2358
- );
2359
- } else {
2360
- out.push(
2361
- [ Opcodes.local_get, localTmp(scope, '#proto_target') ],
2362
- Opcodes.i32_to_u,
2363
- [ Opcodes.local_set, pointerLocal ]
2364
- );
2365
- }
2366
-
2367
- for (const x in protoCands) {
2368
- const protoFunc = protoCands[x];
2369
- const getPointer = [ [ Opcodes.local_get, pointerLocal ] ];
2370
-
2371
- if (protoFunc.noArgRetLength && decl.arguments.length === 0) {
2372
- protoBC[x] = [
2373
- ...ArrayUtil.getLength(getPointer),
2374
- ...setLastType(scope, TYPES.number)
2375
- ];
2376
- continue;
2377
- }
2378
-
2379
- protoBC[x] = () => {
2380
- const protoLocal = protoFunc.local ? localTmp(scope, `__${protoName}_tmp`, protoFunc.local) : -1;
2381
- const protoLocal2 = protoFunc.local2 ? localTmp(scope, `__${protoName}_tmp2`, protoFunc.local2) : -1;
2382
-
2383
- let optUnused = false;
2384
- const protoOut = protoFunc({
2385
- pointer: getPointer,
2386
- length: {
2387
- getCachedI32: () => [ [ Opcodes.local_get, lengthLocal ] ],
2388
- setCachedI32: () => [ [ Opcodes.local_set, lengthLocal ] ],
2389
- get: () => ArrayUtil.getLength(getPointer),
2390
- getI32: () => ArrayUtil.getLengthI32(getPointer),
2391
- set: value => ArrayUtil.setLength(getPointer, value),
2392
- setI32: value => ArrayUtil.setLengthI32(getPointer, value)
2393
- },
2394
- arg: generate(scope, decl.arguments[0] ?? DEFAULT_VALUE()),
2395
- argType: getNodeType(scope, decl.arguments[0] ?? DEFAULT_VALUE()),
2396
- iTmp: protoLocal,
2397
- iTmp2: protoLocal2,
2398
- alloc: bytes => [
2399
- number(bytes, Valtype.i32),
2400
- [ Opcodes.call, includeBuiltin(scope, '__Porffor_allocateBytes').index ]
2401
- ],
2402
- unusedValue: () => {
2403
- optUnused = true;
2404
- return unusedValue;
2405
- },
2406
- setType: type => setLastType(scope, type)
2407
- });
2408
-
2409
- return [
2410
- ...ArrayUtil.getLengthI32(getPointer),
2411
- [ Opcodes.local_set, lengthLocal ],
2412
-
2413
- [ Opcodes.block, unusedValue && optUnused ? Blocktype.void : valtypeBinary ],
2414
- ...protoOut,
2415
- [ Opcodes.end ],
2416
- ...(unusedValue && optUnused ? [ number(UNDEFINED) ] : [])
2417
- ];
2418
- };
2419
- }
2420
- }
2421
2332
 
2422
- if (Object.keys(protoBC).length > 0) {
2423
2333
  protoBC.default = decl.optional ?
2424
2334
  withType(scope, [ number(UNDEFINED) ], TYPES.undefined) :
2425
2335
  internalThrow(scope, 'TypeError', `'${protoName}' proto func tried to be called on a type without an impl`, true);
@@ -6717,7 +6627,7 @@ const objectHack = node => {
6717
6627
  if (objectName !== 'Object_prototype' && (node.property.name === 'propertyIsEnumerable' || node.property.name === 'hasOwnProperty' || node.property.name === 'isPrototypeOf')) return abortOut;
6718
6628
 
6719
6629
  const name = '__' + objectName + '_' + node.property.name;
6720
- if ((!hasFuncWithName(name) && !Object.hasOwn(builtinVars, name) && !isExistingProtoFunc(name) && !hasFuncWithName(name + '$get')) && (hasFuncWithName(objectName) || Object.hasOwn(builtinVars, objectName) || hasFuncWithName('__' + objectName) || Object.hasOwn(builtinVars, '__' + objectName))) return abortOut;
6630
+ if ((!hasFuncWithName(name) && !Object.hasOwn(builtinVars, name) && !hasFuncWithName(name + '$get')) && (hasFuncWithName(objectName) || Object.hasOwn(builtinVars, objectName) || hasFuncWithName('__' + objectName) || Object.hasOwn(builtinVars, '__' + objectName))) return abortOut;
6721
6631
 
6722
6632
  if (Prefs.codeLog) log('codegen', `object hack! ${node.object.name}.${node.property.name} -> ${name}`);
6723
6633
 
@@ -7294,7 +7204,7 @@ const internalConstrs = {
7294
7204
  }
7295
7205
  };
7296
7206
 
7297
- let globals, tags, exceptions, funcs, indirectFuncs, funcIndex, currentFuncIndex, depth, pages, data, typeswitchDepth, usedTypes, coctc, globalInfer, builtinFuncs, builtinVars, prototypeFuncs, lastValtype;
7207
+ let globals, tags, exceptions, funcs, indirectFuncs, funcIndex, currentFuncIndex, depth, pages, data, typeswitchDepth, usedTypes, coctc, globalInfer, builtinFuncs, builtinVars, lastValtype;
7298
7208
  export default program => {
7299
7209
  globals = { ['#ind']: 0 };
7300
7210
  tags = [];
@@ -7333,7 +7243,6 @@ export default program => {
7333
7243
  lastValtype = valtypeBinary;
7334
7244
  builtinFuncs = new BuiltinFuncs();
7335
7245
  builtinVars = new BuiltinVars({ builtinFuncs });
7336
- prototypeFuncs = new PrototypeFuncs();
7337
7246
 
7338
7247
  const getObjectName = x => x.startsWith('__') && x.slice(2, x.indexOf('_', 2));
7339
7248
  objectHackers = ['assert', 'compareArray', 'Test262Error', ...new Set(Object.keys(builtinFuncs).map(getObjectName).concat(Object.keys(builtinVars).map(getObjectName)).filter(x => x))];
@@ -57,7 +57,7 @@ const compile = async (file, _funcs) => {
57
57
  first = source.slice(0, source.indexOf('\n'));
58
58
  }
59
59
 
60
- let args = ['--module', '--todo-time=compile', '--truthy=no_nan_negative', '--no-rm-unused-types', '--scoped-page-names', '--funsafe-no-unlikely-proto-checks', '--zero-checks=charCodeAt', '--fast-length', '--parse-types', '--opt-types', '--no-passive-data', '--active-data', '--no-treeshake-wasm-imports', '--no-coctc'];
60
+ let args = ['--module', '--todo-time=compile', '--truthy=no_nan_negative', '--no-rm-unused-types', '--scoped-page-names', '--fast-length', '--parse-types', '--opt-types', '--no-passive-data', '--active-data', '--no-treeshake-wasm-imports', '--no-coctc'];
61
61
  if (first.startsWith('// @porf')) {
62
62
  args = first.slice('// @porf '.length).split(' ').concat(args);
63
63
  }
@@ -119,18 +119,18 @@ const compile = async (file, _funcs) => {
119
119
  const f = funcs.find(x => x.index === idx);
120
120
  if (!f) {
121
121
  if (idx < importedFuncs.length) {
122
- y.splice(1, 10, importedFuncs[idx].name);
122
+ wasm[i] = [ Opcodes.call, importedFuncs[idx].name ];
123
123
  }
124
124
 
125
125
  continue;
126
126
  }
127
127
 
128
- y.splice(1, 10, f.name);
128
+ wasm[i] = [ Opcodes.call, f.name ];
129
129
  }
130
130
 
131
131
  if (y[0] === Opcodes.global_get || y[0] === Opcodes.global_set) {
132
132
  const global = invGlobals[y[1]];
133
- y.splice(0, 10, 'global', y[0], global.name, global.type);
133
+ wasm[i] = [ 'global', y[0], global.name, global.type ];
134
134
 
135
135
  if (!x.globalInits) {
136
136
  if (!main.rewrittenGlobalInits) {
@@ -147,7 +147,7 @@ const compile = async (file, _funcs) => {
147
147
 
148
148
  if (rewriteLocals && typeof y[1] === 'number' && (y[0] === Opcodes.local_get || y[0] === Opcodes.local_set || y[0] === Opcodes.local_tee)) {
149
149
  const local = locals[y[1]];
150
- y.splice(1, 10, 'local', local.name, local.type);
150
+ wasm[i] = [ y[0], 'local', local.name, local.type ];
151
151
  }
152
152
 
153
153
  if (!n) continue;
@@ -161,7 +161,7 @@ const compile = async (file, _funcs) => {
161
161
  if (!pageName || allocated.has(pageName)) return;
162
162
  allocated.add(pageName);
163
163
 
164
- y.splice(0, 10, 'alloc', pageName, valtypeBinary);
164
+ wasm[i] = [ 'alloc', pageName, valtypeBinary ];
165
165
  };
166
166
 
167
167
  if (y[0] === Opcodes.const &&(n[0] === Opcodes.local_set || n[0] === Opcodes.local_tee)) {
@@ -177,7 +177,7 @@ const compile = async (file, _funcs) => {
177
177
  let id;
178
178
  if (y[0] === Opcodes.i32_const && n[1] === 0) {
179
179
  id = read_signedLEB128(y.slice(1));
180
- y.splice(0, 10, 'throw', exceptions[id].constructor, exceptions[id].message);
180
+ wasm[i] = [ 'throw', exceptions[id].constructor, exceptions[id].message ];
181
181
 
182
182
  // remove throw inst
183
183
  wasm.splice(i + 1, 1);
@@ -249,7 +249,7 @@ ${funcs.map(x => {
249
249
  .replace(/\"local","(.*?)",(.*?)\]/g, (_, name, valtype) => `loc('${name}',${valtype})]`)
250
250
  .replace(/\[16,"(.*?)"]/g, (_, name) => `[16,builtin('${name}')]`)
251
251
  .replace(/\["funcref",(.*?),"(.*?)"]/g, (_1, op, name) => op === '65' ? `...i32ify(funcRef('${name}'))` : `...funcRef('${name}')`)
252
- .replace(/\["str",(.*?),"(.*?)",(.*?)]/g, (_1, op, str, bytestring) => op === '65' ? `...i32ify(makeString(_,"${str}",${bytestring}))` : `...makeString(_,"${str}",${bytestring === 'true' ? 1 : 0})`)
252
+ .replace(/\["str",(.*?),"(.*?)",(.*?)]/g, (_1, op, str, bytestring) => op === '65' ? `...i32ify(makeString(_,"${str}",${bytestring === 'true' ? 1 : 0}))` : `...makeString(_,"${str}",${bytestring === 'true' ? 1 : 0})`)
253
253
  .replace(/\["throw","(.*?)","(.*?)"\]/g, (_, constructor, message) => `...internalThrow(_,'${constructor}',\`${message}\`)`)
254
254
  .replace(/\["get object","(.*?)"\]/g, (_, objName) => `...generateIdent(_,{name:'${objName}'})`)
255
255
  .replace(/\[null,"typeswitch case start",\[(.*?)\]\],/g, (_, types) => `...t([${types}],()=>[`)
package/fuzz/generator.js CHANGED
@@ -8,9 +8,17 @@ const generators = {
8
8
  return `(${num})`;
9
9
  },
10
10
  string: () => {
11
- const chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
12
- const len = Math.floor(Math.random() * 8) + 1;
13
- return `'${Array.from({length: len}, () => chars[Math.floor(Math.random() * chars.length)]).join('')}'`;
11
+ if (Math.random() < 0.1) {
12
+ return `''`;
13
+ }
14
+
15
+ const len = Math.floor(Math.random() * 32) + 1;
16
+ if (Math.random() < 0.8) { // bytestring
17
+ const chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
18
+ return `'${Array.from({length: len}, () => chars[Math.floor(Math.random() * chars.length)]).join('')}'`;
19
+ } else { // unicode string
20
+ return `'${Array.from({length: len}, () => `\\u${Math.floor(Math.random() * 0x10000).toString(16).padStart(4, '0')}`).join('')}'`;
21
+ }
14
22
  },
15
23
  boolean: () => Math.random() < 0.5 ? 'true' : 'false',
16
24
  null: () => 'null',
@@ -21,7 +29,7 @@ const generators = {
21
29
  if (depth > 2) return '[]';
22
30
  const len = Math.floor(Math.random() * 3);
23
31
  if (len === 0) return '[]';
24
- const items = Array.from({length: len}, () => generateSimple());
32
+ const items = Array.from({ length: len }, () => generateExpression(depth + 1));
25
33
  return `[${items.join(', ')}]`;
26
34
  },
27
35
 
@@ -31,9 +39,12 @@ const generators = {
31
39
  const len = Math.floor(Math.random() * 3);
32
40
  if (len === 0) return '{}';
33
41
  const props = Array.from({length: len}, () => {
34
- const key = String.fromCharCode(97 + Math.floor(Math.random() * 26));
35
- // Ensure valid property syntax
36
- return `'${key}': ${generateSimple()}`;
42
+ if (Math.random() < 0.5) {
43
+ const key = String.fromCharCode(97 + Math.floor(Math.random() * 26));
44
+ return `'${key}': ${generateExpression(depth + 1)}`;
45
+ } else {
46
+ return `[${generateExpression(depth + 1)}]: ${generateExpression(depth + 1)}`;
47
+ }
37
48
  });
38
49
  return `({${props.join(', ')}})`;
39
50
  },
@@ -63,27 +74,27 @@ function generateExpression(depth = 0) {
63
74
 
64
75
  const roll = Math.random();
65
76
 
66
- if (roll < 0.4) {
77
+ if (roll < 0.3) {
67
78
  // Simple value
68
79
  return generateSimple();
69
- } else if (roll < 0.6) {
80
+ } else if (roll < 0.4) {
70
81
  // Binary operation
71
82
  const ops = ['+', '-', '*', '/', '%', '===', '!==', '>', '<', '>=', '<=', '&&', '||'];
72
83
  const op = ops[Math.floor(Math.random() * ops.length)];
73
84
  return `(${generateExpression(depth + 1)} ${op} ${generateExpression(depth + 1)})`;
74
- } else if (roll < 0.75) {
85
+ } else if (roll < 0.65) {
75
86
  // Unary operation
76
87
  const ops = ['!', '-', '+', 'typeof'];
77
88
  const op = ops[Math.floor(Math.random() * ops.length)];
78
89
  return `(${op} ${generateExpression(depth + 1)})`;
79
- } else if (roll < 0.85) {
90
+ } else if (roll < 0.75) {
80
91
  // Function call
81
92
  const builtins = ['Math.abs', 'Math.floor', 'Math.ceil', 'String', 'Number', 'Boolean'];
82
93
  const func = builtins[Math.floor(Math.random() * builtins.length)];
83
94
  const argCount = Math.floor(Math.random() * 2);
84
95
  const args = Array.from({length: argCount}, () => generateExpression(depth + 1));
85
96
  return `${func}(${args.join(', ')})`;
86
- } else if (roll < 0.95) {
97
+ } else if (roll < 0.85) {
87
98
  // Conditional
88
99
  return `(${generateExpression(depth + 1)} ? ${generateExpression(depth + 1)} : ${generateExpression(depth + 1)})`;
89
100
  } else {
@@ -105,10 +116,10 @@ function generateStatement(depth = 0, inFunction = false) {
105
116
  } else if (roll < 0.5 && declaredVars.length > 0) {
106
117
  // Variable assignment
107
118
  const varName = declaredVars[Math.floor(Math.random() * declaredVars.length)];
108
- const ops = ['=', '+=', '-=', '*='];
119
+ const ops = ['=', '+=', '-=', '*=', '/=', '%=', '&=', '|=', '^=', '>>=', '>>>=', '<<='];
109
120
  const op = ops[Math.floor(Math.random() * ops.length)];
110
121
  return `${varName} ${op} ${generateExpression()};`;
111
- } else if (roll < 0.65) {
122
+ } else if (roll < 0.6) {
112
123
  // If statement
113
124
  if (Math.random() < 0.5) {
114
125
  return `if (${generateExpression()}) { ${generateStatement(depth + 1, inFunction)} }`;
@@ -150,8 +161,7 @@ function generateFunction() {
150
161
  statements.push(' ' + generateStatement(0, true));
151
162
  }
152
163
 
153
- // Always add a simple return to avoid syntax issues
154
- statements.push(' return ' + generateSimple() + ';');
164
+ statements.push(' return ' + generateExpression() + ';');
155
165
 
156
166
  // Restore variables
157
167
  declaredVars = savedVars;
@@ -193,7 +203,7 @@ function generateProgram(options = {}) {
193
203
  }
194
204
 
195
205
  // Always end with a result
196
- code += `var result = ${generateExpression()};\n`;
206
+ code += `var result = ${generateExpression()};`;
197
207
 
198
208
  return code;
199
209
  }
package/fuzz/index.js CHANGED
@@ -17,8 +17,8 @@ if (cluster.isPrimary) {
17
17
  }
18
18
 
19
19
  const duration = parseFloat(process.argv.find(x => x.startsWith('--duration='))?.split('=')?.[1]) || 60; // seconds
20
- const maxStatements = parseInt(process.argv.find(x => x.startsWith('--max-statements='))?.split('=')?.[1]) || 8;
21
- const maxFunctions = parseInt(process.argv.find(x => x.startsWith('--max-functions='))?.split('=')?.[1]) || 2;
20
+ const maxStatements = parseInt(process.argv.find(x => x.startsWith('--max-statements='))?.split('=')?.[1]) || 20;
21
+ const maxFunctions = parseInt(process.argv.find(x => x.startsWith('--max-functions='))?.split('=')?.[1]) || 4;
22
22
  const verbose = process.argv.includes('--verbose');
23
23
  const saveFailures = process.argv.includes('--save-failures');
24
24
  const plainResults = process.argv.includes('--plain-results');
@@ -141,7 +141,17 @@ if (cluster.isPrimary) {
141
141
  const error = `${msg.error.name}: ${msg.error.message}`
142
142
  .replace(/\([0-9]+:[0-9]+\)/, '')
143
143
  .replace(/@\+[0-9]+/, '');
144
- errorCounts.set(error, (errorCounts.get(error) || 0) + 1);
144
+
145
+ const count = errorCounts.get(error) || 0;
146
+ errorCounts.set(error, count + 1);
147
+
148
+ if (count === 0) {
149
+ const resultNames = ['PASS', 'TODO', 'WASM_ERROR', 'COMPILE_ERROR', 'FAIL', 'TIMEOUT', 'RUNTIME_ERROR'];
150
+ console.log('\n---');
151
+ console.log(`\x1b[4mNEW ${resultNames[result]}: ${error}\x1b[0m`);
152
+ console.log(msg.code);
153
+ console.log('---\n');
154
+ }
145
155
  }
146
156
 
147
157
  if (result === 0) {
@@ -262,7 +272,8 @@ if (cluster.isPrimary) {
262
272
  process.send({
263
273
  result,
264
274
  error: error ? { name: error.name, message: error.message } : null,
265
- code: verbose || saveFailures ? code : null
275
+ // code: verbose || saveFailures ? code : null
276
+ code
266
277
  });
267
278
  });
268
279
 
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "porffor",
3
3
  "description": "An ahead-of-time JavaScript compiler",
4
- "version": "0.58.17",
4
+ "version": "0.58.19",
5
5
  "author": "Oliver Medhurst <honk@goose.icu>",
6
6
  "license": "MIT",
7
7
  "scripts": {},
package/runtime/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  #!/usr/bin/env node
2
2
  import fs from 'node:fs';
3
- globalThis.version = '0.58.17';
3
+ globalThis.version = '0.58.19';
4
4
 
5
5
  // deno compat
6
6
  if (typeof process === 'undefined' && typeof Deno !== 'undefined') {
package/wow.js ADDED
@@ -0,0 +1 @@
1
+ (false ? 42 : 42) + (false ? null : 'G9vBsCA4GzkqlZN')