source: trip-planner-front/node_modules/@assemblyscript/loader/index.js@ b738035

Last change on this file since b738035 was 6a3a178, checked in by Ema <ema_spirova@…>, 3 years ago

initial commit

  • Property mode set to 100644
File size: 15.2 KB
RevLine 
[6a3a178]1"use strict";
2
3// Runtime header offsets
4const ID_OFFSET = -8;
5const SIZE_OFFSET = -4;
6
7// Runtime ids
8const ARRAYBUFFER_ID = 0;
9const STRING_ID = 1;
10// const ARRAYBUFFERVIEW_ID = 2;
11
12// Runtime type information
13const ARRAYBUFFERVIEW = 1 << 0;
14const ARRAY = 1 << 1;
15const STATICARRAY = 1 << 2;
16// const SET = 1 << 3;
17// const MAP = 1 << 4;
18const VAL_ALIGN_OFFSET = 6;
19// const VAL_ALIGN = 1 << VAL_ALIGN_OFFSET;
20const VAL_SIGNED = 1 << 11;
21const VAL_FLOAT = 1 << 12;
22// const VAL_NULLABLE = 1 << 13;
23const VAL_MANAGED = 1 << 14;
24// const KEY_ALIGN_OFFSET = 15;
25// const KEY_ALIGN = 1 << KEY_ALIGN_OFFSET;
26// const KEY_SIGNED = 1 << 20;
27// const KEY_FLOAT = 1 << 21;
28// const KEY_NULLABLE = 1 << 22;
29// const KEY_MANAGED = 1 << 23;
30
31// Array(BufferView) layout
32const ARRAYBUFFERVIEW_BUFFER_OFFSET = 0;
33const ARRAYBUFFERVIEW_DATASTART_OFFSET = 4;
34const ARRAYBUFFERVIEW_DATALENGTH_OFFSET = 8;
35const ARRAYBUFFERVIEW_SIZE = 12;
36const ARRAY_LENGTH_OFFSET = 12;
37const ARRAY_SIZE = 16;
38
39const BIGINT = typeof BigUint64Array !== "undefined";
40const THIS = Symbol();
41const CHUNKSIZE = 1024;
42
43/** Gets a string from an U32 and an U16 view on a memory. */
44function getStringImpl(buffer, ptr) {
45 const U32 = new Uint32Array(buffer);
46 const U16 = new Uint16Array(buffer);
47 let length = U32[(ptr + SIZE_OFFSET) >>> 2] >>> 1;
48 let offset = ptr >>> 1;
49 if (length <= CHUNKSIZE) return String.fromCharCode.apply(String, U16.subarray(offset, offset + length));
50 const parts = [];
51 do {
52 const last = U16[offset + CHUNKSIZE - 1];
53 const size = last >= 0xD800 && last < 0xDC00 ? CHUNKSIZE - 1 : CHUNKSIZE;
54 parts.push(String.fromCharCode.apply(String, U16.subarray(offset, offset += size)));
55 length -= size;
56 } while (length > CHUNKSIZE);
57 return parts.join("") + String.fromCharCode.apply(String, U16.subarray(offset, offset + length));
58}
59
60/** Prepares the base module prior to instantiation. */
61function preInstantiate(imports) {
62 const extendedExports = {};
63
64 function getString(memory, ptr) {
65 if (!memory) return "<yet unknown>";
66 return getStringImpl(memory.buffer, ptr);
67 }
68
69 // add common imports used by stdlib for convenience
70 const env = (imports.env = imports.env || {});
71 env.abort = env.abort || function abort(msg, file, line, colm) {
72 const memory = extendedExports.memory || env.memory; // prefer exported, otherwise try imported
73 throw Error("abort: " + getString(memory, msg) + " at " + getString(memory, file) + ":" + line + ":" + colm);
74 };
75 env.trace = env.trace || function trace(msg, n) {
76 const memory = extendedExports.memory || env.memory;
77 console.log("trace: " + getString(memory, msg) + (n ? " " : "") + Array.prototype.slice.call(arguments, 2, 2 + n).join(", "));
78 };
79 env.seed = env.seed || function seed() {
80 return Date.now();
81 };
82 imports.Math = imports.Math || Math;
83 imports.Date = imports.Date || Date;
84
85 return extendedExports;
86}
87
88/** Prepares the final module once instantiation is complete. */
89function postInstantiate(extendedExports, instance) {
90 const exports = instance.exports;
91 const memory = exports.memory;
92 const table = exports.table;
93 const alloc = exports["__alloc"];
94 const retain = exports["__retain"];
95 const rttiBase = exports["__rtti_base"] || ~0; // oob if not present
96
97 /** Gets the runtime type info for the given id. */
98 function getInfo(id) {
99 const U32 = new Uint32Array(memory.buffer);
100 const count = U32[rttiBase >>> 2];
101 if ((id >>>= 0) >= count) throw Error("invalid id: " + id);
102 return U32[(rttiBase + 4 >>> 2) + id * 2];
103 }
104
105 /** Gets the runtime base id for the given id. */
106 function getBase(id) {
107 const U32 = new Uint32Array(memory.buffer);
108 const count = U32[rttiBase >>> 2];
109 if ((id >>>= 0) >= count) throw Error("invalid id: " + id);
110 return U32[(rttiBase + 4 >>> 2) + id * 2 + 1];
111 }
112
113 /** Gets the runtime alignment of a collection's values. */
114 function getValueAlign(info) {
115 return 31 - Math.clz32((info >>> VAL_ALIGN_OFFSET) & 31); // -1 if none
116 }
117
118 /** Gets the runtime alignment of a collection's keys. */
119 // function getKeyAlign(info) {
120 // return 31 - Math.clz32((info >>> KEY_ALIGN_OFFSET) & 31); // -1 if none
121 // }
122
123 /** Allocates a new string in the module's memory and returns its retained pointer. */
124 function __allocString(str) {
125 const length = str.length;
126 const ptr = alloc(length << 1, STRING_ID);
127 const U16 = new Uint16Array(memory.buffer);
128 for (var i = 0, p = ptr >>> 1; i < length; ++i) U16[p + i] = str.charCodeAt(i);
129 return ptr;
130 }
131
132 extendedExports.__allocString = __allocString;
133
134 /** Reads a string from the module's memory by its pointer. */
135 function __getString(ptr) {
136 const buffer = memory.buffer;
137 const id = new Uint32Array(buffer)[ptr + ID_OFFSET >>> 2];
138 if (id !== STRING_ID) throw Error("not a string: " + ptr);
139 return getStringImpl(buffer, ptr);
140 }
141
142 extendedExports.__getString = __getString;
143
144 /** Gets the view matching the specified alignment, signedness and floatness. */
145 function getView(alignLog2, signed, float) {
146 const buffer = memory.buffer;
147 if (float) {
148 switch (alignLog2) {
149 case 2: return new Float32Array(buffer);
150 case 3: return new Float64Array(buffer);
151 }
152 } else {
153 switch (alignLog2) {
154 case 0: return new (signed ? Int8Array : Uint8Array)(buffer);
155 case 1: return new (signed ? Int16Array : Uint16Array)(buffer);
156 case 2: return new (signed ? Int32Array : Uint32Array)(buffer);
157 case 3: return new (signed ? BigInt64Array : BigUint64Array)(buffer);
158 }
159 }
160 throw Error("unsupported align: " + alignLog2);
161 }
162
163 /** Allocates a new array in the module's memory and returns its retained pointer. */
164 function __allocArray(id, values) {
165 const info = getInfo(id);
166 if (!(info & (ARRAYBUFFERVIEW | ARRAY | STATICARRAY))) throw Error("not an array: " + id + ", flags= " + info);
167 const align = getValueAlign(info);
168 const length = values.length;
169 const buf = alloc(length << align, info & STATICARRAY ? id : ARRAYBUFFER_ID);
170 let result;
171 if (info & STATICARRAY) {
172 result = buf;
173 } else {
174 const arr = alloc(info & ARRAY ? ARRAY_SIZE : ARRAYBUFFERVIEW_SIZE, id);
175 const U32 = new Uint32Array(memory.buffer);
176 U32[arr + ARRAYBUFFERVIEW_BUFFER_OFFSET >>> 2] = retain(buf);
177 U32[arr + ARRAYBUFFERVIEW_DATASTART_OFFSET >>> 2] = buf;
178 U32[arr + ARRAYBUFFERVIEW_DATALENGTH_OFFSET >>> 2] = length << align;
179 if (info & ARRAY) U32[arr + ARRAY_LENGTH_OFFSET >>> 2] = length;
180 result = arr;
181 }
182 const view = getView(align, info & VAL_SIGNED, info & VAL_FLOAT);
183 if (info & VAL_MANAGED) {
184 for (let i = 0; i < length; ++i) view[(buf >>> align) + i] = retain(values[i]);
185 } else {
186 view.set(values, buf >>> align);
187 }
188 return result;
189 }
190
191 extendedExports.__allocArray = __allocArray;
192
193 /** Gets a live view on an array's values in the module's memory. Infers the array type from RTTI. */
194 function __getArrayView(arr) {
195 const U32 = new Uint32Array(memory.buffer);
196 const id = U32[arr + ID_OFFSET >>> 2];
197 const info = getInfo(id);
198 if (!(info & (ARRAYBUFFERVIEW | ARRAY | STATICARRAY))) throw Error("not an array: " + id + ", flags=" + info);
199 const align = getValueAlign(info);
200 let buf = info & STATICARRAY
201 ? arr
202 : U32[arr + ARRAYBUFFERVIEW_DATASTART_OFFSET >>> 2];
203 const length = info & ARRAY
204 ? U32[arr + ARRAY_LENGTH_OFFSET >>> 2]
205 : U32[buf + SIZE_OFFSET >>> 2] >>> align;
206 return getView(align, info & VAL_SIGNED, info & VAL_FLOAT).subarray(buf >>>= align, buf + length);
207 }
208
209 extendedExports.__getArrayView = __getArrayView;
210
211 /** Copies an array's values from the module's memory. Infers the array type from RTTI. */
212 function __getArray(arr) {
213 const input = __getArrayView(arr);
214 const len = input.length;
215 const out = new Array(len);
216 for (let i = 0; i < len; i++) out[i] = input[i];
217 return out;
218 }
219
220 extendedExports.__getArray = __getArray;
221
222 /** Copies an ArrayBuffer's value from the module's memory. */
223 function __getArrayBuffer(ptr) {
224 const buffer = memory.buffer;
225 const length = new Uint32Array(buffer)[ptr + SIZE_OFFSET >>> 2];
226 return buffer.slice(ptr, ptr + length);
227 }
228
229 extendedExports.__getArrayBuffer = __getArrayBuffer;
230
231 /** Copies a typed array's values from the module's memory. */
232 function getTypedArray(Type, alignLog2, ptr) {
233 return new Type(getTypedArrayView(Type, alignLog2, ptr));
234 }
235
236 /** Gets a live view on a typed array's values in the module's memory. */
237 function getTypedArrayView(Type, alignLog2, ptr) {
238 const buffer = memory.buffer;
239 const U32 = new Uint32Array(buffer);
240 const bufPtr = U32[ptr + ARRAYBUFFERVIEW_DATASTART_OFFSET >>> 2];
241 return new Type(buffer, bufPtr, U32[bufPtr + SIZE_OFFSET >>> 2] >>> alignLog2);
242 }
243
244 /** Attach a set of get TypedArray and View functions to the exports. */
245 function attachTypedArrayFunctions(ctor, name, align) {
246 extendedExports["__get" + name] = getTypedArray.bind(null, ctor, align);
247 extendedExports["__get" + name + "View"] = getTypedArrayView.bind(null, ctor, align);
248 }
249
250 [
251 Int8Array,
252 Uint8Array,
253 Uint8ClampedArray,
254 Int16Array,
255 Uint16Array,
256 Int32Array,
257 Uint32Array,
258 Float32Array,
259 Float64Array
260 ].forEach(ctor => {
261 attachTypedArrayFunctions(ctor, ctor.name, 31 - Math.clz32(ctor.BYTES_PER_ELEMENT));
262 });
263
264 if (BIGINT) {
265 [BigUint64Array, BigInt64Array].forEach(ctor => {
266 attachTypedArrayFunctions(ctor, ctor.name.slice(3), 3);
267 });
268 }
269
270 /** Tests whether an object is an instance of the class represented by the specified base id. */
271 function __instanceof(ptr, baseId) {
272 const U32 = new Uint32Array(memory.buffer);
273 let id = U32[(ptr + ID_OFFSET) >>> 2];
274 if (id <= U32[rttiBase >>> 2]) {
275 do {
276 if (id == baseId) return true;
277 id = getBase(id);
278 } while (id);
279 }
280 return false;
281 }
282
283 extendedExports.__instanceof = __instanceof;
284
285 // Pull basic exports to extendedExports so code in preInstantiate can use them
286 extendedExports.memory = extendedExports.memory || memory;
287 extendedExports.table = extendedExports.table || table;
288
289 // Demangle exports and provide the usual utility on the prototype
290 return demangle(exports, extendedExports);
291}
292
293function isResponse(src) {
294 return typeof Response !== "undefined" && src instanceof Response;
295}
296
297function isModule(src) {
298 return src instanceof WebAssembly.Module;
299}
300
301/** Asynchronously instantiates an AssemblyScript module from anything that can be instantiated. */
302async function instantiate(source, imports = {}) {
303 if (isResponse(source = await source)) return instantiateStreaming(source, imports);
304 const module = isModule(source) ? source : await WebAssembly.compile(source);
305 const extended = preInstantiate(imports);
306 const instance = await WebAssembly.instantiate(module, imports);
307 const exports = postInstantiate(extended, instance);
308 return { module, instance, exports };
309}
310
311exports.instantiate = instantiate;
312
313/** Synchronously instantiates an AssemblyScript module from a WebAssembly.Module or binary buffer. */
314function instantiateSync(source, imports = {}) {
315 const module = isModule(source) ? source : new WebAssembly.Module(source);
316 const extended = preInstantiate(imports);
317 const instance = new WebAssembly.Instance(module, imports);
318 const exports = postInstantiate(extended, instance);
319 return { module, instance, exports };
320}
321
322exports.instantiateSync = instantiateSync;
323
324/** Asynchronously instantiates an AssemblyScript module from a response, i.e. as obtained by `fetch`. */
325async function instantiateStreaming(source, imports = {}) {
326 if (!WebAssembly.instantiateStreaming) {
327 return instantiate(
328 isResponse(source = await source)
329 ? source.arrayBuffer()
330 : source,
331 imports
332 );
333 }
334 const extended = preInstantiate(imports);
335 const result = await WebAssembly.instantiateStreaming(source, imports);
336 const exports = postInstantiate(extended, result.instance);
337 return { ...result, exports };
338}
339
340exports.instantiateStreaming = instantiateStreaming;
341
342/** Demangles an AssemblyScript module's exports to a friendly object structure. */
343function demangle(exports, extendedExports = {}) {
344 extendedExports = Object.create(extendedExports);
345 const setArgumentsLength = exports["__argumentsLength"]
346 ? length => { exports["__argumentsLength"].value = length; }
347 : exports["__setArgumentsLength"] || exports["__setargc"] || (() => { /* nop */ });
348 for (let internalName in exports) {
349 if (!Object.prototype.hasOwnProperty.call(exports, internalName)) continue;
350 const elem = exports[internalName];
351 let parts = internalName.split(".");
352 let curr = extendedExports;
353 while (parts.length > 1) {
354 let part = parts.shift();
355 if (!Object.prototype.hasOwnProperty.call(curr, part)) curr[part] = {};
356 curr = curr[part];
357 }
358 let name = parts[0];
359 let hash = name.indexOf("#");
360 if (hash >= 0) {
361 const className = name.substring(0, hash);
362 const classElem = curr[className];
363 if (typeof classElem === "undefined" || !classElem.prototype) {
364 const ctor = function(...args) {
365 return ctor.wrap(ctor.prototype.constructor(0, ...args));
366 };
367 ctor.prototype = {
368 valueOf: function valueOf() {
369 return this[THIS];
370 }
371 };
372 ctor.wrap = function(thisValue) {
373 return Object.create(ctor.prototype, { [THIS]: { value: thisValue, writable: false } });
374 };
375 if (classElem) Object.getOwnPropertyNames(classElem).forEach(name =>
376 Object.defineProperty(ctor, name, Object.getOwnPropertyDescriptor(classElem, name))
377 );
378 curr[className] = ctor;
379 }
380 name = name.substring(hash + 1);
381 curr = curr[className].prototype;
382 if (/^(get|set):/.test(name)) {
383 if (!Object.prototype.hasOwnProperty.call(curr, name = name.substring(4))) {
384 let getter = exports[internalName.replace("set:", "get:")];
385 let setter = exports[internalName.replace("get:", "set:")];
386 Object.defineProperty(curr, name, {
387 get: function() { return getter(this[THIS]); },
388 set: function(value) { setter(this[THIS], value); },
389 enumerable: true
390 });
391 }
392 } else {
393 if (name === 'constructor') {
394 (curr[name] = (...args) => {
395 setArgumentsLength(args.length);
396 return elem(...args);
397 }).original = elem;
398 } else { // instance method
399 (curr[name] = function(...args) { // !
400 setArgumentsLength(args.length);
401 return elem(this[THIS], ...args);
402 }).original = elem;
403 }
404 }
405 } else {
406 if (/^(get|set):/.test(name)) {
407 if (!Object.prototype.hasOwnProperty.call(curr, name = name.substring(4))) {
408 Object.defineProperty(curr, name, {
409 get: exports[internalName.replace("set:", "get:")],
410 set: exports[internalName.replace("get:", "set:")],
411 enumerable: true
412 });
413 }
414 } else if (typeof elem === "function" && elem !== setArgumentsLength) {
415 (curr[name] = (...args) => {
416 setArgumentsLength(args.length);
417 return elem(...args);
418 }).original = elem;
419 } else {
420 curr[name] = elem;
421 }
422 }
423 }
424 return extendedExports;
425}
426
427exports.demangle = demangle;
Note: See TracBrowser for help on using the repository browser.