improve int functions and usage in parser and framer.
This commit is contained in:
parent
c94457cf1f
commit
de455fa3e9
@ -8,6 +8,7 @@ var inherits = require('inherits');
|
|||||||
var EventEmitter = require('events').EventEmitter;
|
var EventEmitter = require('events').EventEmitter;
|
||||||
|
|
||||||
var bcoin = require('../bcoin');
|
var bcoin = require('../bcoin');
|
||||||
|
var bn = require('bn.js');
|
||||||
var utils = bcoin.utils;
|
var utils = bcoin.utils;
|
||||||
var assert = utils.assert;
|
var assert = utils.assert;
|
||||||
var constants = bcoin.protocol.constants;
|
var constants = bcoin.protocol.constants;
|
||||||
@ -46,6 +47,9 @@ function Peer(pool, createSocket, options) {
|
|||||||
this.host = null;
|
this.host = null;
|
||||||
this.port = 0;
|
this.port = 0;
|
||||||
|
|
||||||
|
this.challenge = null;
|
||||||
|
this.lastPong = 0;
|
||||||
|
|
||||||
if (this.options.backoff) {
|
if (this.options.backoff) {
|
||||||
setTimeout(function() {
|
setTimeout(function() {
|
||||||
self.socket = createSocket(self, pool);
|
self.socket = createSocket(self, pool);
|
||||||
@ -135,10 +139,10 @@ Peer.prototype._init = function init() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
this._ping.timer = setInterval(function() {
|
this._ping.timer = setInterval(function() {
|
||||||
self._write(self.framer.ping([
|
self.challenge = self._nonce();
|
||||||
0xde, 0xad, 0xbe, 0xef,
|
self._write(self.framer.ping({
|
||||||
0xde, 0xad, 0xbe, 0xef
|
nonce: self.challenge
|
||||||
]));
|
}));
|
||||||
}, this._ping.interval);
|
}, this._ping.interval);
|
||||||
|
|
||||||
// Send hello
|
// Send hello
|
||||||
@ -441,12 +445,20 @@ Peer.prototype._handleAddr = function handleAddr(addrs) {
|
|||||||
}, this);
|
}, this);
|
||||||
};
|
};
|
||||||
|
|
||||||
Peer.prototype._handlePing = function handlePing() {
|
Peer.prototype._handlePing = function handlePing(data) {
|
||||||
// No-op for now
|
this._write(this.framer.pong({
|
||||||
|
nonce: data.nonce
|
||||||
|
}));
|
||||||
|
this.emit('ping', data);
|
||||||
};
|
};
|
||||||
|
|
||||||
Peer.prototype._handlePong = function handlePong() {
|
Peer.prototype._handlePong = function handlePong(data) {
|
||||||
// No-op for now
|
if (!this.challenge || this.challenge.cmp(data.nonce) !== 0)
|
||||||
|
return this.emit('pong', false);
|
||||||
|
|
||||||
|
this.lastPong = utils.now();
|
||||||
|
|
||||||
|
return this.emit('pong', true);
|
||||||
};
|
};
|
||||||
|
|
||||||
Peer.prototype._handleGetAddr = function handleGetAddr() {
|
Peer.prototype._handleGetAddr = function handleGetAddr() {
|
||||||
@ -586,6 +598,14 @@ Peer.prototype.reject = function reject(details) {
|
|||||||
this._write(this.framer.reject(details));
|
this._write(this.framer.reject(details));
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Peer.nonce = new bn(0xffffffff).ushln(32).uor(new bn(0xffffffff));
|
||||||
|
|
||||||
|
Peer.prototype._nonce = function _nonce() {
|
||||||
|
var nonce = Peer.nonce.clone();
|
||||||
|
nonce.imuln(Math.random());
|
||||||
|
return nonce;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Expose
|
* Expose
|
||||||
*/
|
*/
|
||||||
|
|||||||
@ -667,10 +667,15 @@ Pool.prototype._createPeer = function _createPeer(backoff) {
|
|||||||
});
|
});
|
||||||
|
|
||||||
peer.on('reject', function(payload) {
|
peer.on('reject', function(payload) {
|
||||||
|
payload.data = utils.toHex(payload.data);
|
||||||
|
|
||||||
self.emit('debug',
|
self.emit('debug',
|
||||||
'Reject: msg=%s ccode=%s reason=%s data=%s',
|
'Reject: msg=%s ccode=%s reason=%s data=%s',
|
||||||
payload.message, payload.ccode, payload.reason,
|
payload.message,
|
||||||
utils.toHex(payload.data));
|
payload.ccode,
|
||||||
|
payload.reason,
|
||||||
|
payload.data);
|
||||||
|
|
||||||
self.emit('reject', payload, peer);
|
self.emit('reject', payload, peer);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@ -158,12 +158,16 @@ Framer.prototype.notFound = function notFound(items) {
|
|||||||
return this._inv('notfound', items);
|
return this._inv('notfound', items);
|
||||||
};
|
};
|
||||||
|
|
||||||
Framer.prototype.ping = function ping(nonce) {
|
Framer.prototype.ping = function ping(data) {
|
||||||
return this.packet('ping', nonce);
|
var p = [];
|
||||||
|
utils.writeU64(p, data.nonce, 0);
|
||||||
|
return this.packet('ping', p);
|
||||||
};
|
};
|
||||||
|
|
||||||
Framer.prototype.pong = function pong(nonce) {
|
Framer.prototype.pong = function pong(data) {
|
||||||
return this.packet('pong', nonce.slice(0, 8));
|
var p = [];
|
||||||
|
utils.writeU64(p, data.nonce, 0);
|
||||||
|
return this.packet('pong', p);
|
||||||
};
|
};
|
||||||
|
|
||||||
Framer.prototype.filterLoad = function filterLoad(bloom, update) {
|
Framer.prototype.filterLoad = function filterLoad(bloom, update) {
|
||||||
|
|||||||
@ -139,9 +139,33 @@ Parser.prototype.parsePayload = function parsePayload(cmd, p) {
|
|||||||
if (cmd === 'addr')
|
if (cmd === 'addr')
|
||||||
return this.parseAddr(p);
|
return this.parseAddr(p);
|
||||||
|
|
||||||
|
if (cmd === 'ping')
|
||||||
|
return this.parsePing(p);
|
||||||
|
|
||||||
|
if (cmd === 'pong')
|
||||||
|
return this.parsePong(p);
|
||||||
|
|
||||||
return p;
|
return p;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Parser.prototype.parsePing = function parsePing(p) {
|
||||||
|
if (p.length < 8)
|
||||||
|
return this._error('pong packet is too small');
|
||||||
|
|
||||||
|
return {
|
||||||
|
nonce: readU64(p, 0)
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
Parser.prototype.parsePong = function parsePong(p) {
|
||||||
|
if (p.length < 8)
|
||||||
|
return this._error('ping packet is too small');
|
||||||
|
|
||||||
|
return {
|
||||||
|
nonce: readU64(p, 0)
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
Parser.prototype.parseVersion = function parseVersion(p) {
|
Parser.prototype.parseVersion = function parseVersion(p) {
|
||||||
var v, services, ts, nonce, result, off, agent, height, relay;
|
var v, services, ts, nonce, result, off, agent, height, relay;
|
||||||
|
|
||||||
@ -152,10 +176,10 @@ Parser.prototype.parseVersion = function parseVersion(p) {
|
|||||||
services = readU64(p, 4);
|
services = readU64(p, 4);
|
||||||
|
|
||||||
// Timestamp
|
// Timestamp
|
||||||
ts = readU64(p, 12);
|
ts = utils.read64(p, 12);
|
||||||
|
|
||||||
// Nonce, very dramatic
|
// Nonce, very dramatic
|
||||||
nonce = { lo: readU32(p, 72), hi: readU32(p, 76) };
|
nonce = readU64(p, 72);
|
||||||
|
|
||||||
// User agent length
|
// User agent length
|
||||||
result = utils.readIntv(p, 80);
|
result = utils.readIntv(p, 80);
|
||||||
@ -356,7 +380,7 @@ Parser.prototype.parseTXOut = function parseTXOut(p) {
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
size: off + scriptLen,
|
size: off + scriptLen,
|
||||||
value: new bn(utils.toArray(p.slice(0, 8)).reverse()),
|
value: utils.read64(p, 0),
|
||||||
script: bcoin.script.decode(utils.toArray(p.slice(off, off + scriptLen)))
|
script: bcoin.script.decode(utils.toArray(p.slice(off, off + scriptLen)))
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1288,7 +1288,7 @@ TX.prototype.toRaw = function toRaw(enc) {
|
|||||||
TX.fromRaw = function fromRaw(raw, enc) {
|
TX.fromRaw = function fromRaw(raw, enc) {
|
||||||
if (enc === 'hex')
|
if (enc === 'hex')
|
||||||
raw = utils.toArray(raw, 'hex');
|
raw = utils.toArray(raw, 'hex');
|
||||||
return new bcoin.protocol.parser().parseTX(raw);
|
return new bcoin.tx(new bcoin.protocol.parser().parseTX(raw));
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -188,134 +188,6 @@ utils.dsha256 = function dsha256(data, enc) {
|
|||||||
return utils.sha256(utils.sha256(data, enc));
|
return utils.sha256(utils.sha256(data, enc));
|
||||||
};
|
};
|
||||||
|
|
||||||
utils.readU16 = function readU16(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
return arr[off] | (arr[off + 1] << 8);
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.readU32 = function readU32(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
var r = arr[off]
|
|
||||||
| (arr[off + 1] << 8)
|
|
||||||
| (arr[off + 2] << 16)
|
|
||||||
| (arr[off + 3] << 24);
|
|
||||||
|
|
||||||
if (r < 0)
|
|
||||||
r += 0x100000000;
|
|
||||||
|
|
||||||
return r;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.readU64 = function readU64(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
return utils.readU32(arr, off) + utils.readU32(arr, off + 4) * 0x100000000;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU16 = function writeU16(dst, num, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
dst[off] = num & 0xff;
|
|
||||||
dst[off + 1] = (num >>> 8) & 0xff;
|
|
||||||
return 2;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU32 = function writeU32(dst, num, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
dst[off] = num & 0xff;
|
|
||||||
dst[off + 1] = (num >>> 8) & 0xff;
|
|
||||||
dst[off + 2] = (num >>> 16) & 0xff;
|
|
||||||
dst[off + 3] = (num >>> 24) & 0xff;
|
|
||||||
return 4;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU64 = function writeU64(dst, num, off) {
|
|
||||||
var i = 0;
|
|
||||||
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
num = new bn(num).maskn(64).toArray();
|
|
||||||
while (num.length < 8)
|
|
||||||
num.unshift(0);
|
|
||||||
|
|
||||||
num.reverse().forEach(function(ch) {
|
|
||||||
dst[off++] = ch;
|
|
||||||
});
|
|
||||||
|
|
||||||
i = num.length;
|
|
||||||
|
|
||||||
while (i--)
|
|
||||||
dst[off++] = num[i];
|
|
||||||
|
|
||||||
return 8;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU16BE = function writeU16BE(dst, num, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
dst[off] = (num >>> 8) & 0xff;
|
|
||||||
dst[off + 1] = num & 0xff;
|
|
||||||
return 2;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU32BE = function writeU32BE(dst, num, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
dst[off] = (num >>> 24) & 0xff;
|
|
||||||
dst[off + 1] = (num >>> 16) & 0xff;
|
|
||||||
dst[off + 2] = (num >>> 8) & 0xff;
|
|
||||||
dst[off + 3] = num & 0xff;
|
|
||||||
return 4;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeU64BE = function writeU64BE(dst, num, off) {
|
|
||||||
var i = 0;
|
|
||||||
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
num = new bn(num).maskn(64).toArray();
|
|
||||||
while (num.length < 8)
|
|
||||||
num.unshift(0);
|
|
||||||
|
|
||||||
for (; i < num.length; i++)
|
|
||||||
dst[off++] = num[i];
|
|
||||||
|
|
||||||
return 8;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.readU16BE = function readU16BE(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
return (arr[off] << 8) | arr[off + 1];
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.readU32BE = function readU32BE(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
var r = (arr[off] << 24)
|
|
||||||
| (arr[off + 1] << 16)
|
|
||||||
| (arr[off + 2] << 8)
|
|
||||||
| arr[off + 3];
|
|
||||||
|
|
||||||
if (r < 0)
|
|
||||||
r += 0x100000000;
|
|
||||||
|
|
||||||
return r;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.readU64BE = function readU64BE(arr, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
return utils.readU32BE(arr, off) * 0x100000000 + utils.readU32BE(arr, off + 4);
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeAscii = function writeAscii(dst, str, off) {
|
utils.writeAscii = function writeAscii(dst, str, off) {
|
||||||
var i = 0;
|
var i = 0;
|
||||||
var c;
|
var c;
|
||||||
@ -660,10 +532,10 @@ utils.isIP = function isIP(ip) {
|
|||||||
if (typeof ip !== 'string')
|
if (typeof ip !== 'string')
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (~ip.indexOf('.'))
|
if (ip.indexOf('.') !== -1)
|
||||||
return 4;
|
return 4;
|
||||||
|
|
||||||
if (~ip.indexOf(':'))
|
if (ip.indexOf(':') !== -1)
|
||||||
return 6;
|
return 6;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
@ -759,65 +631,12 @@ utils.sortKeys = function sortKeys(keys) {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
utils.readIntv = function readIntv(p, off) {
|
|
||||||
var r, bytes;
|
|
||||||
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
if (p[off] < 0xfd) {
|
|
||||||
r = p[off];
|
|
||||||
bytes = 1;
|
|
||||||
} else if (p[off] === 0xfd) {
|
|
||||||
r = p[off + 1] | (p[off + 2] << 8);
|
|
||||||
bytes = 3;
|
|
||||||
} else if (p[off] === 0xfe) {
|
|
||||||
r = utils.readU32(p, off + 1);
|
|
||||||
bytes = 5;
|
|
||||||
} else {
|
|
||||||
r = 0;
|
|
||||||
bytes = 9;
|
|
||||||
}
|
|
||||||
|
|
||||||
return { off: off + bytes, r: r };
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.writeIntv = function writeIntv(arr, value, off) {
|
|
||||||
if (!off)
|
|
||||||
off = 0;
|
|
||||||
|
|
||||||
if (value < 0xfd) {
|
|
||||||
arr[off] = value;
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (value <= 0xffff) {
|
|
||||||
arr[off] = 0xfd;
|
|
||||||
arr[off + 1] = value & 0xff;
|
|
||||||
arr[off + 2] = value >>> 8;
|
|
||||||
return 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (value <= 0xffffffff) {
|
|
||||||
arr[off] = 0xfe;
|
|
||||||
arr[off + 1] = value & 0xff;
|
|
||||||
arr[off + 2] = (value >>> 8) & 0xff;
|
|
||||||
arr[off + 3] = (value >>> 16) & 0xff;
|
|
||||||
arr[off + 4] = value >>> 24;
|
|
||||||
return 5;
|
|
||||||
}
|
|
||||||
|
|
||||||
arr[off] = 0xff;
|
|
||||||
utils.writeU64(arr, value, off + 1);
|
|
||||||
return 9;
|
|
||||||
};
|
|
||||||
|
|
||||||
utils.uniq = function(obj) {
|
utils.uniq = function(obj) {
|
||||||
var out = [];
|
var out = [];
|
||||||
var i = 0;
|
var i = 0;
|
||||||
|
|
||||||
for (; i < obj.length; i++) {
|
for (; i < obj.length; i++) {
|
||||||
if (!~out.indexOf(obj[i]))
|
if (out.indexOf(obj[i]) === -1)
|
||||||
out.push(obj[i]);
|
out.push(obj[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -917,3 +736,406 @@ utils.hash = function hash(obj, enc) {
|
|||||||
|
|
||||||
throw new Error('Cannot get hash of object');
|
throw new Error('Cannot get hash of object');
|
||||||
};
|
};
|
||||||
|
|
||||||
|
//
|
||||||
|
// Integer Functions
|
||||||
|
//
|
||||||
|
// Non-64-bit functions originally taken from the node.js tree:
|
||||||
|
//
|
||||||
|
// Copyright Joyent, Inc. and other Node contributors. All rights reserved.
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to
|
||||||
|
// deal in the Software without restriction, including without limitation the
|
||||||
|
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||||
|
// sell copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||||
|
// IN THE SOFTWARE.
|
||||||
|
//
|
||||||
|
|
||||||
|
utils.readU8 = function readU8(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
return arr[off];
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU16 = function readU16(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
return arr[off] | (arr[off + 1] << 8);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU16BE = function readU16BE(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
return (arr[off] << 8) | arr[off + 1];
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU32 = function readU32(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
return ((arr[off])
|
||||||
|
| (arr[off + 1] << 8)
|
||||||
|
| (arr[off + 2] << 16))
|
||||||
|
+ (arr[off + 3] * 0x1000000);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU32BE = function readU32BE(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
return (arr[off] * 0x1000000)
|
||||||
|
+ ((arr[off + 1] << 16)
|
||||||
|
| (arr[off + 2] << 8)
|
||||||
|
| arr[off + 3]);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU64 = function readU64(arr, off) {
|
||||||
|
var num;
|
||||||
|
off = off >>> 0;
|
||||||
|
num = utils.toArray(arr.slice(off, off + 8)).reverse();
|
||||||
|
return new bn(num);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readU64BE = function readU64BE(arr, off) {
|
||||||
|
var num;
|
||||||
|
off = off >>> 0;
|
||||||
|
num = utils.toArray(arr.slice(off, off + 8));
|
||||||
|
return new bn(num);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read8 = function read8(arr, off) {
|
||||||
|
var num;
|
||||||
|
off = off >>> 0;
|
||||||
|
num = arr[off];
|
||||||
|
return !(num & 0x80) ? num : (0xff - num + 1) * -1;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read16 = function read16(arr, off) {
|
||||||
|
var num;
|
||||||
|
off = off >>> 0;
|
||||||
|
num = arr[off] | (arr[off + 1] << 8);
|
||||||
|
return (num & 0x8000) ? num | 0xffff0000 : num;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read16BE = function read16BE(arr, off) {
|
||||||
|
var num;
|
||||||
|
off = off >>> 0;
|
||||||
|
num = arr[off + 1] | (arr[off] << 8);
|
||||||
|
return (num & 0x8000) ? num | 0xffff0000 : num;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read32 = function read32(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
return (arr[off])
|
||||||
|
| (arr[off + 1] << 8)
|
||||||
|
| (arr[off + 2] << 16)
|
||||||
|
| (arr[off + 3] << 24);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read32BE = function read32BE(arr, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
return (arr[off] << 24)
|
||||||
|
| (arr[off + 1] << 16)
|
||||||
|
| (arr[off + 2] << 8)
|
||||||
|
| (arr[off + 3]);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read64 = function read64(arr, off) {
|
||||||
|
var num;
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = utils.toArray(arr.slice(off, off + 8)).reverse();
|
||||||
|
|
||||||
|
if (num[0] & 0x80) {
|
||||||
|
num[0] &= ~0x80;
|
||||||
|
num = new bn(num);
|
||||||
|
num = num.neg();
|
||||||
|
return num;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new bn(num);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.read64BE = function read64BE(arr, off) {
|
||||||
|
var num;
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = utils.toArray(arr.slice(off, off + 8));
|
||||||
|
|
||||||
|
if (num[0] & 0x80) {
|
||||||
|
num[0] &= ~0x80;
|
||||||
|
num = new bn(num);
|
||||||
|
num = num.neg();
|
||||||
|
return num;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new bn(num);
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU8 = function readU8(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
return 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU16 = function readU16(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 8) & 0xff;
|
||||||
|
return 2;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU16BE = function read16BE(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 1] = num & 0xff;
|
||||||
|
return 2;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU32 = function writeU32(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off + 3] = (num >>> 24) & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 16) & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 8) & 0xff;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
return 4;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU32BE = function writeU32BE(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = (num >>> 24) & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 16) & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 3] = num & 0xff;
|
||||||
|
return 4;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU64 = function writeU64(dst, num, off) {
|
||||||
|
var i;
|
||||||
|
|
||||||
|
if (!(num instanceof bn)) {
|
||||||
|
num = +num;
|
||||||
|
num = new bn(num);
|
||||||
|
}
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = num.maskn(64).toArray();
|
||||||
|
|
||||||
|
while (num.length < 8)
|
||||||
|
num.unshift(0);
|
||||||
|
|
||||||
|
for (i = num.length - 1; i >= 0; i--)
|
||||||
|
dst[off++] = num[i] & 0xff;
|
||||||
|
|
||||||
|
return 8;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeU64BE = function writeU64BE(dst, num, off) {
|
||||||
|
var i;
|
||||||
|
|
||||||
|
if (!(num instanceof bn)) {
|
||||||
|
num = +num;
|
||||||
|
bn = new bn(num);
|
||||||
|
}
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = num.maskn(64).toArray();
|
||||||
|
|
||||||
|
while (num.length < 8)
|
||||||
|
num.unshift(0);
|
||||||
|
|
||||||
|
for (i = 0; i < num.length; i++)
|
||||||
|
dst[off++] = num[i] & 0xff;
|
||||||
|
|
||||||
|
return 8;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write8 = function write8(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
return 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write16 = function write16(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 8) & 0xff;
|
||||||
|
return 2;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write16BE = function write16BE(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 1] = num & 0xff;
|
||||||
|
return 2;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write32 = function write32(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 16) & 0xff;
|
||||||
|
dst[off + 3] = (num >>> 24) & 0xff;
|
||||||
|
return 4;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write32BE = function write32BE(dst, num, off) {
|
||||||
|
num = +num;
|
||||||
|
off = off >>> 0;
|
||||||
|
dst[off] = (num >>> 24) & 0xff;
|
||||||
|
dst[off + 1] = (num >>> 16) & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 3] = num & 0xff;
|
||||||
|
return 4;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write64 = function write64(dst, num, off) {
|
||||||
|
var i;
|
||||||
|
|
||||||
|
if (!(num instanceof bn)) {
|
||||||
|
num = +num;
|
||||||
|
if (num < 0) {
|
||||||
|
num &= ~0x80000000;
|
||||||
|
num = new bn(num);
|
||||||
|
num = num.neg();
|
||||||
|
} else {
|
||||||
|
num = new bn(num);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = num.maskn(64).toArray();
|
||||||
|
|
||||||
|
while (num.length < 8)
|
||||||
|
num.unshift(0);
|
||||||
|
|
||||||
|
if (num.isNeg())
|
||||||
|
num[0] |= 0x80;
|
||||||
|
|
||||||
|
for (i = num.length - 1; i >= 0; i--)
|
||||||
|
dst[off++] = num[i] & 0xff;
|
||||||
|
|
||||||
|
return 8;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.write64BE = function write64BE(dst, num, off) {
|
||||||
|
var i;
|
||||||
|
|
||||||
|
if (!(num instanceof bn)) {
|
||||||
|
num = +num;
|
||||||
|
if (num < 0) {
|
||||||
|
num &= ~0x80000000;
|
||||||
|
num = new bn(num);
|
||||||
|
num = num.neg();
|
||||||
|
} else {
|
||||||
|
num = new bn(num);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
num = num.maskn(64).toArray();
|
||||||
|
|
||||||
|
while (num.length < 8)
|
||||||
|
num.unshift(0);
|
||||||
|
|
||||||
|
if (num.isNeg())
|
||||||
|
num[0] |= 0x80;
|
||||||
|
|
||||||
|
for (i = 0; i < num.length; i++)
|
||||||
|
dst[off++] = num[i] & 0xff;
|
||||||
|
|
||||||
|
return 8;
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.readIntv = function readIntv(arr, off) {
|
||||||
|
var r, bytes;
|
||||||
|
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
if (arr[off] < 0xfd) {
|
||||||
|
r = arr[off];
|
||||||
|
bytes = 1;
|
||||||
|
} else if (arr[off] === 0xfd) {
|
||||||
|
r = arr[off + 1] | (arr[off + 2] << 8);
|
||||||
|
bytes = 3;
|
||||||
|
} else if (arr[off] === 0xfe) {
|
||||||
|
r = utils.readU32(arr, off + 1);
|
||||||
|
bytes = 5;
|
||||||
|
} else if (arr[off] === 0xff) {
|
||||||
|
try {
|
||||||
|
r = utils.readU64(arr, off + 1).toNumber();
|
||||||
|
} catch (e) {
|
||||||
|
r = 0;
|
||||||
|
}
|
||||||
|
bytes = 9;
|
||||||
|
} else {
|
||||||
|
// Malformed
|
||||||
|
r = arr[off];
|
||||||
|
bytes = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return { off: off + bytes, r: r };
|
||||||
|
};
|
||||||
|
|
||||||
|
utils.writeIntv = function writeIntv(dst, num, off) {
|
||||||
|
off = off >>> 0;
|
||||||
|
|
||||||
|
if (num instanceof bn) {
|
||||||
|
if (num.cmpn(0xffffffff) > 0) {
|
||||||
|
dst[off] = 0xff;
|
||||||
|
utils.writeU64(dst, num, off + 1);
|
||||||
|
return 9;
|
||||||
|
}
|
||||||
|
num = num.toNumber();
|
||||||
|
}
|
||||||
|
|
||||||
|
num = +num;
|
||||||
|
|
||||||
|
if (num < 0xfd) {
|
||||||
|
dst[off] = num & 0xff;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (num <= 0xffff) {
|
||||||
|
dst[off] = 0xfd;
|
||||||
|
dst[off + 1] = num & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 8) & 0xff;
|
||||||
|
return 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (num <= 0xffffffff) {
|
||||||
|
dst[off] = 0xfe;
|
||||||
|
dst[off + 1] = num & 0xff;
|
||||||
|
dst[off + 2] = (num >>> 8) & 0xff;
|
||||||
|
dst[off + 3] = (num >>> 16) & 0xff;
|
||||||
|
dst[off + 4] = (num >>> 24) & 0xff;
|
||||||
|
return 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
dst[off] = 0xff;
|
||||||
|
utils.writeU64(dst, num, off + 1);
|
||||||
|
return 9;
|
||||||
|
};
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user