git ssb

0+

wanderer🌟 / js-primea-hypervisor



Tree: 0df8aae87c8f14c08596394b83b87af8a4d64614

Files: 0df8aae87c8f14c08596394b83b87af8a4d64614 / customTypes.js

3352 bytesRaw
1const Stream = require('buffer-pipe')
2const leb = require('leb128')
3
4const LANGUAGE_TYPES = {
5 'actor': 0x0,
6 'buf': 0x1,
7 'i32': 0x7f,
8 'i64': 0x7e,
9 'f32': 0x7d,
10 'f64': 0x7c,
11 'anyFunc': 0x70,
12 'func': 0x60,
13 'block_type': 0x40,
14
15 0x0: 'actor',
16 0x1: 'buf',
17 0x7f: 'i32',
18 0x7e: 'i64',
19 0x7d: 'f32',
20 0x7c: 'f64',
21 0x70: 'anyFunc',
22 0x60: 'func',
23 0x40: 'block_type'
24}
25
26function encodeJSON (json) {
27 const stream = new Stream()
28 encodeCustomSection('type', json, stream, encodeType)
29 encodeCustomSection('typeMap', json, stream, encodeTypeMap)
30
31 return stream.buffer
32}
33
34function encodeCustomSection (name, json, stream, encodingFunc) {
35 stream.write([0])
36 let payload = new Stream()
37
38 // encode type
39 leb.unsigned.write(name.length, payload)
40 payload.write(name)
41 encodingFunc(json[name], payload)
42 // write the size of the payload
43 leb.unsigned.write(payload.bytesWrote, stream)
44 stream.write(payload.buffer)
45 return stream
46}
47
48function encodeTypeMap (json, stream) {
49 leb.unsigned.write(json.length, stream)
50 for (let entry of json) {
51 leb.unsigned.write(entry.func, stream)
52 leb.unsigned.write(entry.type, stream)
53 }
54 return stream
55}
56
57function decodeTypeMap (buf) {
58 const stream = new Stream(Buffer.from(buf))
59 let numOfEntries = leb.unsigned.read(stream)
60 const json = []
61 while (numOfEntries--) {
62 json.push({
63 func: leb.unsigned.readBn(stream).toNumber(),
64 type: leb.unsigned.readBn(stream).toNumber()
65 })
66 }
67 return json
68}
69
70function encodeType (json, stream = new Stream()) {
71 let binEntries = new Stream()
72
73 leb.unsigned.write(json.length, binEntries)
74 for (let entry of json) {
75 // a single type entry binary encoded
76 binEntries.write([LANGUAGE_TYPES[entry.form]]) // the form
77
78 const len = entry.params.length // number of parameters
79 leb.unsigned.write(len, binEntries)
80 if (len !== 0) {
81 binEntries.write(entry.params.map(type => LANGUAGE_TYPES[type])) // the paramter types
82 }
83
84 binEntries.write([entry.return_type ? 1 : 0]) // number of return types
85
86 if (entry.return_type) {
87 binEntries.write([LANGUAGE_TYPES[entry.return_type]])
88 }
89 }
90
91 stream.write(binEntries.buffer)
92 return stream
93}
94
95function decodeType (buf) {
96 const stream = new Stream(Buffer.from(buf))
97 const numberOfEntries = leb.unsigned.readBn(stream).toNumber()
98 const json = []
99 for (let i = 0; i < numberOfEntries; i++) {
100 let type = stream.read(1)[0]
101 const entry = {
102 form: LANGUAGE_TYPES[type],
103 params: []
104 }
105
106 let paramCount = leb.unsigned.readBn(stream).toNumber()
107
108 // parse the entries
109 while (paramCount--) {
110 const type = stream.read(1)[0]
111 entry.params.push(LANGUAGE_TYPES[type])
112 }
113 const numOfReturns = leb.unsigned.readBn(stream).toNumber()
114 if (numOfReturns) {
115 type = stream.read(1)[0]
116 entry.return_type = LANGUAGE_TYPES[type]
117 }
118
119 json.push(entry)
120 }
121 return json
122}
123
124function injectCustomSection (custom, wasm) {
125 const preramble = wasm.subarray(0, 8)
126 const body = wasm.subarray(8)
127 return Buffer.concat([preramble, custom, body])
128}
129
130function inject (wasm, json) {
131 const buf = encodeJSON(json)
132 return injectCustomSection(buf, wasm)
133}
134
135module.exports = {
136 injectCustomSection,
137 inject,
138 decodeType,
139 decodeTypeMap,
140 encodeType,
141 encodeTypeMap,
142 encodeJSON
143}
144

Built with git-ssb-web