git ssb

0+

wanderer🌟 / js-primea-hypervisor



Tree: 93764459c5a9d26427a8995f181e763cee8ace32

Files: 93764459c5a9d26427a8995f181e763cee8ace32 / portManager.js

2561 bytesRaw
1const Port = require('./port.js')
2const PARENT = Symbol('parent')
3
4// decides which message to go firts
5function messageArbiter (pairA, pairB) {
6 const a = pairA[1].peek()
7 const b = pairB[1].peek()
8
9 if (!a) {
10 return pairB
11 } else if (!b) {
12 return pairA
13 }
14
15 const aGasPrice = a.resources.gasPrice
16 const bGasPrice = b.resources.gasPrice
17 if (a.ticks !== b.ticks) {
18 return a.ticks < b.ticks ? pairA : pairB
19 } else if (aGasPrice === bGasPrice) {
20 return a.hash() > b.hash() ? pairA : pairB
21 } else {
22 return aGasPrice > bGasPrice ? pairA : pairB
23 }
24}
25
26module.exports = class PortManager {
27 constructor (kernel) {
28 this.kernel = kernel
29 this.hypervisor = kernel._opts.hypervisor
30 this.ports = kernel.state.ports
31 this.parentPort = kernel._opts.parentPort
32 this.parentId = {
33 id: this.parentPort.id['/'].parent
34 }
35 this._portMap = new Map()
36 }
37
38 async start () {
39 // map ports to thier id's
40 let ports = Object.keys(this.ports).map(name => {
41 const port = this.ports[name]
42 this._mapPort(name, port)
43 })
44
45 // create the parent port
46 await Promise.all(ports)
47 const parentID = await this.hypervisor.generateID(this.parentPort)
48 this._portMap.set(parentID, new Port(PARENT))
49 }
50
51 async _mapPort (name, port) {
52 const id = await this.hypervisor.generateID(port)
53 port = new Port(name)
54 this._portMap.set(id, port)
55 }
56
57 queue (message) {
58 this._portMap.get(message.fromPort).queue(message)
59 }
60
61 set (name, port) {
62 this.ports[name] = port
63 return this._mapPort(name, port)
64 }
65
66 async get (port) {
67 const id = await this.hypervisor.generateID(port)
68 return this._portMap.get(id)
69 }
70
71 getRef (key) {
72 return this.ports[key]
73 }
74
75 // waits till all ports have reached a threshold tick count
76 async wait (threshold) {
77 // find the ports that have a smaller tick count then the threshold tick count
78 const unkownPorts = [...this._portMap].filter(([id, port]) => {
79 return (port.hasSent || port.name === PARENT) && port.ticks < threshold
80 })
81
82 const promises = unkownPorts.map(async ([id, port]) => {
83 const portObj = port.name === PARENT ? this.parentPort : this.ports[port.name]
84 // update the port's tick count
85 port.ticks = await this.hypervisor.wait(portObj, threshold)
86 })
87 return Promise.all(promises)
88 }
89
90 async getNextMessage () {
91 await this.wait(this.kernel.ticks)
92 const portMap = [...this._portMap].reduce(messageArbiter)
93 if (portMap) {
94 return portMap[1].shift()
95 }
96 }
97}
98

Built with git-ssb-web