keypair refactor.
This commit is contained in:
parent
9b81126ea4
commit
882b18e188
335
lib/bcoin/hd.js
335
lib/bcoin/hd.js
@ -129,6 +129,12 @@ function Mnemonic(options) {
|
|||||||
this.fromOptions(options);
|
this.fromOptions(options);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from options object.
|
||||||
|
* @private
|
||||||
|
* @param {Object} options
|
||||||
|
*/
|
||||||
|
|
||||||
Mnemonic.prototype.fromOptions = function fromOptions(options) {
|
Mnemonic.prototype.fromOptions = function fromOptions(options) {
|
||||||
if (!options)
|
if (!options)
|
||||||
options = {};
|
options = {};
|
||||||
@ -147,65 +153,16 @@ Mnemonic.prototype.fromOptions = function fromOptions(options) {
|
|||||||
assert(this.bits % 32 === 0);
|
assert(this.bits % 32 === 0);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate mnemonic from options.
|
||||||
|
* @param {Object} options
|
||||||
|
* @returns {Mnemonic}
|
||||||
|
*/
|
||||||
|
|
||||||
Mnemonic.fromOptions = function fromOptions(options) {
|
Mnemonic.fromOptions = function fromOptions(options) {
|
||||||
return new Mnemonic().fromOptions(options);
|
return new Mnemonic().fromOptions(options);
|
||||||
};
|
};
|
||||||
|
|
||||||
Mnemonic.prototype.toJSON = function toJSON() {
|
|
||||||
return {
|
|
||||||
bits: this.bits,
|
|
||||||
entropy: this.entropy ? this.entropy.toString('hex') : null,
|
|
||||||
phrase: this.phrase,
|
|
||||||
passphrase: this.passphrase,
|
|
||||||
language: this.language,
|
|
||||||
seed: this.seed ? this.seed.toString('hex') : null
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
Mnemonic.prototype.fromJSON = function fromJSON(json) {
|
|
||||||
this.bits = json.bits;
|
|
||||||
if (json.entropy)
|
|
||||||
this.entropy = new Buffer(json.entropy, 'hex');
|
|
||||||
this.phrase = json.phrase;
|
|
||||||
this.passphrase = json.passphrase;
|
|
||||||
this.language = json.language;
|
|
||||||
if (json.seed)
|
|
||||||
this.seed = new Buffer(json.seed, 'hex');
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
|
|
||||||
Mnemonic.fromJSON = function fromJSON(json) {
|
|
||||||
return new Mnemonic().fromJSON(json);
|
|
||||||
};
|
|
||||||
|
|
||||||
Mnemonic.prototype.toRaw = function toRaw(writer) {
|
|
||||||
var p = new BufferWriter(writer);
|
|
||||||
p.writeU16(this.bits);
|
|
||||||
p.writeBytes(this.entropy);
|
|
||||||
p.writeVarString(this.phrase, 'utf8');
|
|
||||||
p.writeVarString(this.passphrase, 'utf8');
|
|
||||||
p.writeVarString(this.language, 'utf8');
|
|
||||||
p.writeBytes(this.seed);
|
|
||||||
if (!writer)
|
|
||||||
p = p.render();
|
|
||||||
return p;
|
|
||||||
};
|
|
||||||
|
|
||||||
Mnemonic.prototype.fromRaw = function fromRaw(data) {
|
|
||||||
var p = new BufferReader(data);
|
|
||||||
this.bits = p.readU16();
|
|
||||||
this.entropy = p.readBytes(this.bits / 8);
|
|
||||||
this.phrase = p.readVarString('utf8');
|
|
||||||
this.passphrase = p.readVarString('utf8');
|
|
||||||
this.language = p.readVarString('utf8');
|
|
||||||
this.seed = p.readBytes(64);
|
|
||||||
return this;
|
|
||||||
};
|
|
||||||
|
|
||||||
Mnemonic.fromRaw = function fromRaw(data) {
|
|
||||||
return new Mnemonic().fromRaw(data);
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate the seed.
|
* Generate the seed.
|
||||||
* @returns {Buffer} pbkdf2 seed.
|
* @returns {Buffer} pbkdf2 seed.
|
||||||
@ -300,6 +257,96 @@ Mnemonic.getWordlist = function getWordlist(language) {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert mnemonic to a json-friendly object.
|
||||||
|
* @returns {Object}
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.prototype.toJSON = function toJSON() {
|
||||||
|
return {
|
||||||
|
bits: this.bits,
|
||||||
|
entropy: this.entropy ? this.entropy.toString('hex') : null,
|
||||||
|
phrase: this.phrase,
|
||||||
|
passphrase: this.passphrase,
|
||||||
|
language: this.language,
|
||||||
|
seed: this.seed ? this.seed.toString('hex') : null
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from json object.
|
||||||
|
* @private
|
||||||
|
* @param {Object} json
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.prototype.fromJSON = function fromJSON(json) {
|
||||||
|
this.bits = json.bits;
|
||||||
|
this.entropy = new Buffer(json.entropy, 'hex');
|
||||||
|
this.phrase = json.phrase;
|
||||||
|
this.passphrase = json.passphrase;
|
||||||
|
this.language = json.language;
|
||||||
|
this.seed = new Buffer(json.seed, 'hex');
|
||||||
|
return this;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate mnemonic from json object.
|
||||||
|
* @param {Object} json
|
||||||
|
* @returns {Mnemonic}
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.fromJSON = function fromJSON(json) {
|
||||||
|
return new Mnemonic().fromJSON(json);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Serialize mnemonic.
|
||||||
|
* @returns {Buffer}
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.prototype.toRaw = function toRaw(writer) {
|
||||||
|
var p = new BufferWriter(writer);
|
||||||
|
|
||||||
|
p.writeU16(this.bits);
|
||||||
|
p.writeBytes(this.entropy);
|
||||||
|
p.writeVarString(this.phrase, 'utf8');
|
||||||
|
p.writeVarString(this.passphrase, 'utf8');
|
||||||
|
p.writeVarString(this.language, 'utf8');
|
||||||
|
p.writeBytes(this.seed);
|
||||||
|
|
||||||
|
if (!writer)
|
||||||
|
p = p.render();
|
||||||
|
|
||||||
|
return p;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from serialized data.
|
||||||
|
* @private
|
||||||
|
* @param {Buffer} data
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.prototype.fromRaw = function fromRaw(data) {
|
||||||
|
var p = new BufferReader(data);
|
||||||
|
this.bits = p.readU16();
|
||||||
|
this.entropy = p.readBytes(this.bits / 8);
|
||||||
|
this.phrase = p.readVarString('utf8');
|
||||||
|
this.passphrase = p.readVarString('utf8');
|
||||||
|
this.language = p.readVarString('utf8');
|
||||||
|
this.seed = p.readBytes(64);
|
||||||
|
return this;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate mnemonic from serialized data.
|
||||||
|
* @param {Buffer} data
|
||||||
|
* @returns {Mnemonic}
|
||||||
|
*/
|
||||||
|
|
||||||
|
Mnemonic.fromRaw = function fromRaw(data) {
|
||||||
|
return new Mnemonic().fromRaw(data);
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test whether an object is a Mnemonic.
|
* Test whether an object is a Mnemonic.
|
||||||
* @param {Object} obj
|
* @param {Object} obj
|
||||||
@ -401,6 +448,18 @@ HD.fromRaw = function fromRaw(data) {
|
|||||||
return HDPublicKey.fromRaw(data);
|
return HDPublicKey.fromRaw(data);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate HD key from extended serialized data.
|
||||||
|
* @param {Buffer} data
|
||||||
|
* @returns {HDPrivateKey|HDPublicKey}
|
||||||
|
*/
|
||||||
|
|
||||||
|
HD.fromExtended = function fromExtended(data) {
|
||||||
|
if (HDPrivateKey.hasPrefix(data))
|
||||||
|
return HDPrivateKey.fromExtended(data);
|
||||||
|
return HDPublicKey.fromRaw(data);
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate an hdkey from any number of options.
|
* Generate an hdkey from any number of options.
|
||||||
* @param {Object|Mnemonic|Buffer} options - mnemonic, mnemonic
|
* @param {Object|Mnemonic|Buffer} options - mnemonic, mnemonic
|
||||||
@ -571,6 +630,12 @@ function HDPrivateKey(options) {
|
|||||||
|
|
||||||
utils.inherits(HDPrivateKey, HD);
|
utils.inherits(HDPrivateKey, HD);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from options object.
|
||||||
|
* @private
|
||||||
|
* @param {Object} options
|
||||||
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromOptions = function fromOptions(options) {
|
HDPrivateKey.prototype.fromOptions = function fromOptions(options) {
|
||||||
assert(options, 'No options for HD private key.');
|
assert(options, 'No options for HD private key.');
|
||||||
assert(options.depth <= 0xff, 'Depth is too high.');
|
assert(options.depth <= 0xff, 'Depth is too high.');
|
||||||
@ -590,6 +655,12 @@ HDPrivateKey.prototype.fromOptions = function fromOptions(options) {
|
|||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate HD private key from options object.
|
||||||
|
* @param {Object} options
|
||||||
|
* @returns {HDPrivateKey}
|
||||||
|
*/
|
||||||
|
|
||||||
HDPrivateKey.fromOptions = function fromOptions(options) {
|
HDPrivateKey.fromOptions = function fromOptions(options) {
|
||||||
return new HDPrivateKey().fromOptions(options);
|
return new HDPrivateKey().fromOptions(options);
|
||||||
};
|
};
|
||||||
@ -846,13 +917,10 @@ HDPrivateKey.prototype.equal = function equal(obj) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create an hd private key from a seed.
|
* Inject properties from seed.
|
||||||
* @param {Buffer|Mnemonic|Object} options - A seed,
|
* @private
|
||||||
* mnemonic, or mnemonic options.
|
* @param {Buffer} seed
|
||||||
* @param {String?} network
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {Object} A "naked" key (a
|
|
||||||
* plain javascript object which is suitable
|
|
||||||
* for passing to the HDPrivateKey constructor).
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromSeed = function fromSeed(seed, network) {
|
HDPrivateKey.prototype.fromSeed = function fromSeed(seed, network) {
|
||||||
@ -885,10 +953,9 @@ HDPrivateKey.prototype.fromSeed = function fromSeed(seed, network) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate an hd private key from a seed.
|
* Instantiate an hd private key from a 512 bit seed.
|
||||||
* @param {Buffer|Mnemonic|Object} seed - A
|
* @param {Buffer} seed
|
||||||
* seed, mnemonic, or mnemonic options.
|
* @param {(Network|NetworkType)?} network
|
||||||
* @param {String?} network
|
|
||||||
* @returns {HDPrivateKey}
|
* @returns {HDPrivateKey}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -897,10 +964,10 @@ HDPrivateKey.fromSeed = function fromSeed(seed, network) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate an hd private key from a mnemonic.
|
* Inject properties from a mnemonic.
|
||||||
|
* @private
|
||||||
* @param {Mnemonic|Object} mnemonic
|
* @param {Mnemonic|Object} mnemonic
|
||||||
* @param {String?} network
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {HDPrivateKey}
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromMnemonic = function fromMnemonic(mnemonic, network) {
|
HDPrivateKey.prototype.fromMnemonic = function fromMnemonic(mnemonic, network) {
|
||||||
@ -936,19 +1003,22 @@ HDPrivateKey.prototype.fromMnemonic = function fromMnemonic(mnemonic, network) {
|
|||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate an hd private key from a mnemonic.
|
||||||
|
* @param {Mnemonic|Object} mnemonic
|
||||||
|
* @param {(Network|NetworkType)?} network
|
||||||
|
* @returns {HDPrivateKey}
|
||||||
|
*/
|
||||||
|
|
||||||
HDPrivateKey.fromMnemonic = function fromMnemonic(mnemonic, network) {
|
HDPrivateKey.fromMnemonic = function fromMnemonic(mnemonic, network) {
|
||||||
return new HDPrivateKey().fromMnemonic(mnemonic, network);
|
return new HDPrivateKey().fromMnemonic(mnemonic, network);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate an hd private key from a key and/or entropy bytes.
|
* Inject properties from privateKey and entropy.
|
||||||
* @param {Object?} options
|
* @private
|
||||||
* @param {Buffer?} options.privateKey
|
* @param {Object} options
|
||||||
* @param {Buffer?} options.entropy
|
* @param {(Network|NetworkType)?} network
|
||||||
* @param {String?} network
|
|
||||||
* @returns {Object} A "naked" key (a
|
|
||||||
* plain javascript object which is suitable
|
|
||||||
* for passing to the HDPrivateKey constructor).
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.generate = function _generate(options, network) {
|
HDPrivateKey.prototype.generate = function _generate(options, network) {
|
||||||
@ -985,7 +1055,7 @@ HDPrivateKey.prototype.generate = function _generate(options, network) {
|
|||||||
* @param {Object?} options
|
* @param {Object?} options
|
||||||
* @param {Buffer?} options.privateKey
|
* @param {Buffer?} options.privateKey
|
||||||
* @param {Buffer?} options.entropy
|
* @param {Buffer?} options.entropy
|
||||||
* @param {String?} network
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {HDPrivateKey}
|
* @returns {HDPrivateKey}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -994,9 +1064,9 @@ HDPrivateKey.generate = function generate(options, network) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a base58 extended private key.
|
* Inject properties from base58 key.
|
||||||
|
* @private
|
||||||
* @param {Base58String} xkey
|
* @param {Base58String} xkey
|
||||||
* @returns {Object}
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromBase58 = function fromBase58(xkey) {
|
HDPrivateKey.prototype.fromBase58 = function fromBase58(xkey) {
|
||||||
@ -1006,9 +1076,9 @@ HDPrivateKey.prototype.fromBase58 = function fromBase58(xkey) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a raw serialized key.
|
* Inject properties from serialized data.
|
||||||
|
* @private
|
||||||
* @param {Buffer} raw
|
* @param {Buffer} raw
|
||||||
* @returns {Object}
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromRaw = function fromRaw(raw) {
|
HDPrivateKey.prototype.fromRaw = function fromRaw(raw) {
|
||||||
@ -1041,7 +1111,7 @@ HDPrivateKey.prototype.fromRaw = function fromRaw(raw) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Serialize key to a base58 string.
|
* Serialize key to a base58 string.
|
||||||
* @param {Network|String} network
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {Base58String}
|
* @returns {Base58String}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -1051,7 +1121,7 @@ HDPrivateKey.prototype.toBase58 = function toBase58(network) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Serialize the key.
|
* Serialize the key.
|
||||||
* @param {Network|NetworkType} network
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {Buffer}
|
* @returns {Buffer}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -1079,7 +1149,56 @@ HDPrivateKey.prototype.toRaw = function toRaw(network, writer) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate a transaction from a base58 string.
|
* Serialize the key in "extended"
|
||||||
|
* format (includes the mnemonic).
|
||||||
|
* @param {(Network|NetworkType)?} network
|
||||||
|
* @returns {Buffer}
|
||||||
|
*/
|
||||||
|
|
||||||
|
HDPrivateKey.prototype.toExtended = function toExtended(network, writer) {
|
||||||
|
var p = new BufferWriter(writer);
|
||||||
|
|
||||||
|
this.toRaw(network, p);
|
||||||
|
|
||||||
|
if (this.mnemonic) {
|
||||||
|
p.writeU8(1);
|
||||||
|
this.mnemonic.toRaw(p);
|
||||||
|
} else {
|
||||||
|
p.writeU8(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!writer)
|
||||||
|
p = p.render();
|
||||||
|
|
||||||
|
return p;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from extended serialized data.
|
||||||
|
* @private
|
||||||
|
* @param {Buffer} data
|
||||||
|
*/
|
||||||
|
|
||||||
|
HDPrivateKey.prototype.fromExtended = function fromExtended(data) {
|
||||||
|
var p = new BufferReader(data);
|
||||||
|
this.fromRaw(p);
|
||||||
|
if (p.readU8() === 1)
|
||||||
|
this.mnemonic = Mnemonic.fromRaw(p);
|
||||||
|
return this;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate key from "extended" serialized data.
|
||||||
|
* @param {Buffer} data
|
||||||
|
* @returns {HDPrivateKey}
|
||||||
|
*/
|
||||||
|
|
||||||
|
HDPrivateKey.fromExtended = function fromExtended(data) {
|
||||||
|
return new HDPrivateKey().fromExtended(data);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate an HD private key from a base58 string.
|
||||||
* @param {Base58String} xkey
|
* @param {Base58String} xkey
|
||||||
* @returns {HDPrivateKey}
|
* @returns {HDPrivateKey}
|
||||||
*/
|
*/
|
||||||
@ -1111,9 +1230,9 @@ HDPrivateKey.prototype.toJSON = function toJSON() {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handle a deserialized JSON HDPrivateKey object.
|
* Inject properties from json object.
|
||||||
|
* @private
|
||||||
* @param {Object} json
|
* @param {Object} json
|
||||||
* @returns {Object} A "naked" HDPrivateKey.
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPrivateKey.prototype.fromJSON = function fromJSON(json) {
|
HDPrivateKey.prototype.fromJSON = function fromJSON(json) {
|
||||||
@ -1129,7 +1248,7 @@ HDPrivateKey.prototype.fromJSON = function fromJSON(json) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate an HDPrivateKey from a jsonified key object.
|
* Instantiate an HDPrivateKey from a jsonified key object.
|
||||||
* @param {Object} json - The jsonified transaction object.
|
* @param {Object} json - The jsonified key object.
|
||||||
* @returns {HDPrivateKey}
|
* @returns {HDPrivateKey}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -1145,9 +1264,9 @@ HDPrivateKey.fromJSON = function fromJSON(json) {
|
|||||||
|
|
||||||
HDPrivateKey.isHDPrivateKey = function isHDPrivateKey(obj) {
|
HDPrivateKey.isHDPrivateKey = function isHDPrivateKey(obj) {
|
||||||
return obj
|
return obj
|
||||||
&& obj.privateKey
|
&& typeof obj.derive === 'function'
|
||||||
&& Buffer.isBuffer(obj.chainCode)
|
&& typeof obj.toExtended === 'function'
|
||||||
&& typeof obj.derive === 'function';
|
&& obj.chainCode !== undefined;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -1195,6 +1314,12 @@ function HDPublicKey(options) {
|
|||||||
|
|
||||||
utils.inherits(HDPublicKey, HD);
|
utils.inherits(HDPublicKey, HD);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from options object.
|
||||||
|
* @private
|
||||||
|
* @param {Object} options
|
||||||
|
*/
|
||||||
|
|
||||||
HDPublicKey.prototype.fromOptions = function fromOptions(options) {
|
HDPublicKey.prototype.fromOptions = function fromOptions(options) {
|
||||||
assert(options, 'No options for HDPublicKey');
|
assert(options, 'No options for HDPublicKey');
|
||||||
assert(options.depth <= 0xff, 'Depth is too high.');
|
assert(options.depth <= 0xff, 'Depth is too high.');
|
||||||
@ -1211,6 +1336,12 @@ HDPublicKey.prototype.fromOptions = function fromOptions(options) {
|
|||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate HD public key from options object.
|
||||||
|
* @param {Object} options
|
||||||
|
* @returns {HDPublicKey}
|
||||||
|
*/
|
||||||
|
|
||||||
HDPublicKey.fromOptions = function fromOptions(options) {
|
HDPublicKey.fromOptions = function fromOptions(options) {
|
||||||
return new HDPublicKey().fromOptions(options);
|
return new HDPublicKey().fromOptions(options);
|
||||||
};
|
};
|
||||||
@ -1388,7 +1519,6 @@ HDPublicKey.prototype.equal = function equal(obj) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Convert key to a more json-friendly object.
|
* Convert key to a more json-friendly object.
|
||||||
* @method
|
|
||||||
* @returns {Object}
|
* @returns {Object}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -1399,9 +1529,9 @@ HDPublicKey.prototype.toJSON = function toJSON() {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handle a deserialized JSON HDPublicKey object.
|
* Inject properties from json object.
|
||||||
|
* @private
|
||||||
* @param {Object} json
|
* @param {Object} json
|
||||||
* @returns {Object} A "naked" HDPublicKey.
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPublicKey.prototype.fromJSON = function fromJSON(json) {
|
HDPublicKey.prototype.fromJSON = function fromJSON(json) {
|
||||||
@ -1412,7 +1542,6 @@ HDPublicKey.prototype.fromJSON = function fromJSON(json) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate an HDPrivateKey from a jsonified key object.
|
* Instantiate an HDPrivateKey from a jsonified key object.
|
||||||
* @method
|
|
||||||
* @param {Object} json - The jsonified transaction object.
|
* @param {Object} json - The jsonified transaction object.
|
||||||
* @returns {HDPrivateKey}
|
* @returns {HDPrivateKey}
|
||||||
*/
|
*/
|
||||||
@ -1468,9 +1597,9 @@ HDPublicKey.hasPrefix = function hasPrefix(data) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a base58 extended public key.
|
* Inject properties from a base58 key.
|
||||||
|
* @private
|
||||||
* @param {Base58String} xkey
|
* @param {Base58String} xkey
|
||||||
* @returns {Object}
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPublicKey.prototype.fromBase58 = function fromBase58(xkey) {
|
HDPublicKey.prototype.fromBase58 = function fromBase58(xkey) {
|
||||||
@ -1480,9 +1609,9 @@ HDPublicKey.prototype.fromBase58 = function fromBase58(xkey) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a raw serialized key.
|
* Inject properties from serialized data.
|
||||||
|
* @private
|
||||||
* @param {Buffer} raw
|
* @param {Buffer} raw
|
||||||
* @returns {Object}
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
HDPublicKey.prototype.fromRaw = function fromRaw(raw) {
|
HDPublicKey.prototype.fromRaw = function fromRaw(raw) {
|
||||||
@ -1550,7 +1679,7 @@ HDPublicKey.prototype.toRaw = function toRaw(network, writer) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate a transaction from a base58 string.
|
* Instantiate an HD public key from a base58 string.
|
||||||
* @param {Base58String} xkey
|
* @param {Base58String} xkey
|
||||||
* @returns {HDPublicKey}
|
* @returns {HDPublicKey}
|
||||||
*/
|
*/
|
||||||
@ -1577,9 +1706,9 @@ HDPublicKey.fromRaw = function fromRaw(data) {
|
|||||||
|
|
||||||
HDPublicKey.isHDPublicKey = function isHDPublicKey(obj) {
|
HDPublicKey.isHDPublicKey = function isHDPublicKey(obj) {
|
||||||
return obj
|
return obj
|
||||||
&& !obj.privateKey
|
&& typeof obj.derive === 'function'
|
||||||
&& Buffer.isBuffer(obj.chainCode)
|
&& typeof obj.toExtended !== 'function'
|
||||||
&& typeof obj.derive === 'function';
|
&& obj.chainCode !== undefined;
|
||||||
};
|
};
|
||||||
|
|
||||||
[HDPrivateKey, HDPublicKey].forEach(function(HD) {
|
[HDPrivateKey, HDPublicKey].forEach(function(HD) {
|
||||||
|
|||||||
@ -29,11 +29,25 @@ function KeyPair(options) {
|
|||||||
if (!(this instanceof KeyPair))
|
if (!(this instanceof KeyPair))
|
||||||
return new KeyPair(options);
|
return new KeyPair(options);
|
||||||
|
|
||||||
|
this.network = null;
|
||||||
|
this.compressed = true;
|
||||||
|
this.privateKey = null;
|
||||||
|
this._publicKey = null;
|
||||||
|
|
||||||
|
if (options)
|
||||||
|
this.fromOptions(options);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from options object.
|
||||||
|
* @private
|
||||||
|
* @param {Object} options
|
||||||
|
*/
|
||||||
|
|
||||||
|
KeyPair.prototype.fromOptions = function fromOptions(options) {
|
||||||
if (!options)
|
if (!options)
|
||||||
options = {};
|
options = {};
|
||||||
|
|
||||||
this.options = options;
|
|
||||||
this.key = null;
|
|
||||||
this.compressed = options.compressed !== false;
|
this.compressed = options.compressed !== false;
|
||||||
this.network = bcoin.network.get(options.network);
|
this.network = bcoin.network.get(options.network);
|
||||||
|
|
||||||
@ -45,15 +59,31 @@ function KeyPair(options) {
|
|||||||
|
|
||||||
this.privateKey = options.privateKey;
|
this.privateKey = options.privateKey;
|
||||||
this._publicKey = options.publicKey;
|
this._publicKey = options.publicKey;
|
||||||
}
|
|
||||||
|
return this;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generate a keypair.
|
* Instantiate key pair from options object.
|
||||||
|
* @param {Object} options
|
||||||
* @returns {KeyPair}
|
* @returns {KeyPair}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.generate = function() {
|
KeyPair.fromOptions = function fromOptions(options) {
|
||||||
return new KeyPair({ privateKey: bcoin.ec.generatePrivateKey() });
|
return new KeyPair().fromOptions(options);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generate a keypair.
|
||||||
|
* @param {(Network|NetworkType)?} network
|
||||||
|
* @returns {KeyPair}
|
||||||
|
*/
|
||||||
|
|
||||||
|
KeyPair.generate = function(network) {
|
||||||
|
var key = new KeyPair();
|
||||||
|
key.network = bcoin.network.get(network);
|
||||||
|
key.privateKey = bcoin.ec.generatePrivateKey();
|
||||||
|
return key;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -127,85 +157,105 @@ KeyPair.prototype.getPublicKey = function getPublicKey(enc) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Convert key to a CBitcoinSecret.
|
* Convert key to a CBitcoinSecret.
|
||||||
* @returns {Base58String}
|
* @param {(Network|NetworkType)?} network
|
||||||
|
* @returns {Buffer}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.prototype.toSecret = function toSecret(network) {
|
KeyPair.prototype.toRaw = function toRaw(network, writer) {
|
||||||
|
var p = new BufferWriter(writer);
|
||||||
|
|
||||||
if (!network)
|
if (!network)
|
||||||
network = this.network;
|
network = this.network;
|
||||||
|
|
||||||
return KeyPair.toSecret(this.getPrivateKey(), this.compressed, network);
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Convert key to a CBitcoinSecret.
|
|
||||||
* @param {Buffer} privateKey
|
|
||||||
* @param {Boolean?} compressed
|
|
||||||
* @returns {Base58String}
|
|
||||||
*/
|
|
||||||
|
|
||||||
KeyPair.toSecret = function toSecret(privateKey, compressed, network) {
|
|
||||||
var p = new BufferWriter();
|
|
||||||
|
|
||||||
network = bcoin.network.get(network);
|
network = bcoin.network.get(network);
|
||||||
p.writeU8(network.prefixes.privkey);
|
|
||||||
p.writeBytes(privateKey);
|
|
||||||
|
|
||||||
if (compressed !== false)
|
p.writeU8(network.prefixes.privkey);
|
||||||
|
p.writeBytes(this.getPrivateKey());
|
||||||
|
|
||||||
|
if (this.compressed)
|
||||||
p.writeU8(1);
|
p.writeU8(1);
|
||||||
|
|
||||||
p.writeChecksum();
|
p.writeChecksum();
|
||||||
|
|
||||||
return utils.toBase58(p.render());
|
if (!writer)
|
||||||
|
p = p.render();
|
||||||
|
|
||||||
|
return p;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a serialized CBitcoinSecret.
|
* Convert key to a CBitcoinSecret.
|
||||||
* @param {Base58String} secret
|
* @param {(Network|NetworkType)?} network
|
||||||
* @returns {Object} A "naked" keypair object.
|
* @returns {Base58String}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.parseSecret = function parseSecret(secret) {
|
KeyPair.prototype.toSecret = function toSecret(network) {
|
||||||
var data = utils.fromBase58(secret);
|
return utils.toBase58(this.toRaw(network));
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Inject properties from serialized CBitcoinSecret.
|
||||||
|
* @private
|
||||||
|
* @param {Buffer} data
|
||||||
|
*/
|
||||||
|
|
||||||
|
KeyPair.prototype.fromRaw = function fromRaw(data) {
|
||||||
var p = new BufferReader(data, true);
|
var p = new BufferReader(data, true);
|
||||||
var compressed = false;
|
var compressed = false;
|
||||||
var i, prefix, type, privateKey;
|
var i, prefix, version, type, privateKey;
|
||||||
|
|
||||||
prefix = p.readU8();
|
version = p.readU8();
|
||||||
|
|
||||||
for (i = 0; i < network.types.length; i++) {
|
for (i = 0; i < network.types.length; i++) {
|
||||||
type = network.types[i];
|
type = network.types[i];
|
||||||
prefix = network[type].prefixes.privkey;
|
prefix = network[type].prefixes.privkey;
|
||||||
if (data.version === prefix)
|
if (version === prefix)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(i < network.types.length, 'Network not found.');
|
assert(i < network.types.length, 'Network not found.');
|
||||||
|
|
||||||
privateKey = p.readBytes(32);
|
this.network = bcoin.network.get(type);
|
||||||
|
this.privateKey = p.readBytes(32);
|
||||||
|
|
||||||
if (p.left() > 4) {
|
if (p.left() > 4) {
|
||||||
assert(p.readU8() === 1, 'Bad compression flag.');
|
assert(p.readU8() === 1, 'Bad compression flag.');
|
||||||
compressed = true;
|
this.compressed = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
p.verifyChecksum();
|
p.verifyChecksum();
|
||||||
|
|
||||||
return {
|
return this;
|
||||||
network: type,
|
|
||||||
privateKey: privateKey,
|
|
||||||
compressed: compressed
|
|
||||||
};
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate a transaction from a serialized CBitcoinSecret.
|
* Inject properties from serialized CBitcoinSecret.
|
||||||
|
* @private
|
||||||
* @param {Base58String} secret
|
* @param {Base58String} secret
|
||||||
* @returns {Keypair}
|
*/
|
||||||
|
|
||||||
|
KeyPair.prototype.fromSecret = function fromSecret(secret) {
|
||||||
|
return this.fromRaw(utils.fromBase58(secret));
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate a key pair from a serialized CBitcoinSecret.
|
||||||
|
* @param {Buffer} data
|
||||||
|
* @returns {KeyPair}
|
||||||
|
*/
|
||||||
|
|
||||||
|
KeyPair.fromRaw = function fromRaw(data) {
|
||||||
|
return new KeyPair().fromRaw(data);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Instantiate a key pair from a serialized CBitcoinSecret.
|
||||||
|
* @param {Base58String} secret
|
||||||
|
* @returns {KeyPair}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.fromSecret = function fromSecret(secret) {
|
KeyPair.fromSecret = function fromSecret(secret) {
|
||||||
return new KeyPair(KeyPair.parseSecret(secret));
|
return new KeyPair().fromSecret(secret);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -214,68 +264,57 @@ KeyPair.fromSecret = function fromSecret(secret) {
|
|||||||
* @returns {Object}
|
* @returns {Object}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.prototype.toJSON = function toJSON(passphrase) {
|
KeyPair.prototype.toJSON = function toJSON() {
|
||||||
var json = {
|
return {
|
||||||
v: 1,
|
network: this.network.type,
|
||||||
name: 'keypair',
|
compressed: this.compressed,
|
||||||
encrypted: passphrase ? true : false
|
privateKey: this.privateKey ? this.toSecret() : null,
|
||||||
|
publicKey: this.getPublicKey('base58')
|
||||||
};
|
};
|
||||||
|
|
||||||
if (this.key.privateKey) {
|
|
||||||
json.privateKey = passphrase
|
|
||||||
? utils.encrypt(this.toSecret(), passphrase).toString('hex')
|
|
||||||
: this.toSecret();
|
|
||||||
return json;
|
|
||||||
}
|
|
||||||
|
|
||||||
json.publicKey = this.getPublicKey('base58');
|
|
||||||
|
|
||||||
return json;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handle a deserialized JSON keypair object.
|
* Inject properties from json object.
|
||||||
|
* @private
|
||||||
* @param {Object} json
|
* @param {Object} json
|
||||||
* @returns {Object} A "naked" keypair (a
|
|
||||||
* plain javascript object which is suitable
|
|
||||||
* for passing to the KeyPair constructor).
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.parseJSON = function parseJSON(json, passphrase) {
|
KeyPair.prototype.fromJSON = function fromJSON(json) {
|
||||||
var privateKey, publicKey;
|
this.network = bcoin.network.get(json.network);
|
||||||
|
this.compressed = json.compressed;
|
||||||
|
|
||||||
assert.equal(json.v, 1);
|
if (json.privateKey)
|
||||||
assert.equal(json.name, 'keypair');
|
return this.fromSecret(json.privateKey);
|
||||||
|
|
||||||
if (json.encrypted && !passphrase)
|
|
||||||
throw new Error('Cannot decrypt key.');
|
|
||||||
|
|
||||||
if (json.privateKey) {
|
|
||||||
privateKey = json.privateKey;
|
|
||||||
if (json.encrypted)
|
|
||||||
privateKey = utils.decrypt(privateKey, passphrase).toString('utf8');
|
|
||||||
return KeyPair.parseSecret(privateKey);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (json.publicKey) {
|
if (json.publicKey) {
|
||||||
publicKey = utils.fromBase58(json.publicKey);
|
this.publicKey = utils.fromBase58(json.publicKey);
|
||||||
return {
|
this.compressed = this.publicKey[0] !== 0x04;
|
||||||
publicKey: publicKey,
|
return this;
|
||||||
compressed: publicKey[0] !== 0x04
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(false, 'Could not parse KeyPair JSON.');
|
assert(false, 'Could not parse KeyPair JSON.');
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Instantiate a transaction from a jsonified keypair object.
|
* Instantiate a key pair from a jsonified object.
|
||||||
* @param {Object} json - The jsonified transaction object.
|
* @param {Object} json - The jsonified key pair object.
|
||||||
* @returns {KeyPair}
|
* @returns {KeyPair}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
KeyPair.fromJSON = function fromJSON(json, passphrase) {
|
KeyPair.fromJSON = function fromJSON(passphrase) {
|
||||||
return new KeyPair(KeyPair.parseJSON(json, passphrase));
|
return new KeyPair().fromJSON(json);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test whether an object is a key pair.
|
||||||
|
* @param {Object?} obj
|
||||||
|
* @returns {Boolean}
|
||||||
|
*/
|
||||||
|
|
||||||
|
KeyPair.isKeyPair = function isKeyPair(obj) {
|
||||||
|
return obj
|
||||||
|
&& obj._privateKey !== undefined
|
||||||
|
&& typeof obj.fromSecret === 'function';
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|||||||
@ -597,6 +597,8 @@ KeyRing.prototype.toJSON = function toJSON() {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
KeyRing.prototype.fromJSON = function fromJSON(json) {
|
KeyRing.prototype.fromJSON = function fromJSON(json) {
|
||||||
|
var i;
|
||||||
|
|
||||||
this.nework = bcoin.network.get(json.network);
|
this.nework = bcoin.network.get(json.network);
|
||||||
this.type = json.type;
|
this.type = json.type;
|
||||||
this.m = json.m;
|
this.m = json.m;
|
||||||
@ -607,7 +609,10 @@ KeyRing.prototype.fromJSON = function fromJSON(json) {
|
|||||||
this.change = json.change;
|
this.change = json.change;
|
||||||
this.index = json.index;
|
this.index = json.index;
|
||||||
this.key = utils.fromBase58(json.key);
|
this.key = utils.fromBase58(json.key);
|
||||||
this.keys = json.keys.map(utils.fromBase58);
|
|
||||||
|
for (i = 0; i < json.keys.length; i++)
|
||||||
|
this.keys.push(utils.fromBase58(json.keys[i]));
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -671,7 +676,6 @@ KeyRing.prototype.fromRaw = function fromRaw(data) {
|
|||||||
this.change = p.readU32();
|
this.change = p.readU32();
|
||||||
this.index = p.readU32();
|
this.index = p.readU32();
|
||||||
this.key = p.readVarBytes();
|
this.key = p.readVarBytes();
|
||||||
this.keys = [];
|
|
||||||
|
|
||||||
count = p.readU8();
|
count = p.readU8();
|
||||||
|
|
||||||
|
|||||||
@ -1402,7 +1402,7 @@ Wallet.prototype.inspect = function inspect() {
|
|||||||
network: this.network.type,
|
network: this.network.type,
|
||||||
initialized: this.initialized,
|
initialized: this.initialized,
|
||||||
accountDepth: this.accountDepth,
|
accountDepth: this.accountDepth,
|
||||||
master: this.master.toJSON(),
|
master: this.master,
|
||||||
account: this.account
|
account: this.account
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
@ -2192,7 +2192,6 @@ Account.prototype.fromJSON = function fromJSON(json) {
|
|||||||
this.receiveDepth = json.receiveDepth;
|
this.receiveDepth = json.receiveDepth;
|
||||||
this.changeDepth = json.changeDepth;
|
this.changeDepth = json.changeDepth;
|
||||||
this.accountKey = bcoin.hd.fromBase58(json.accountKey);
|
this.accountKey = bcoin.hd.fromBase58(json.accountKey);
|
||||||
this.keys = [];
|
|
||||||
|
|
||||||
for (i = 0; i < json.keys.length; i++)
|
for (i = 0; i < json.keys.length; i++)
|
||||||
this.keys.push(bcoin.hd.fromBase58(key));
|
this.keys.push(bcoin.hd.fromBase58(key));
|
||||||
@ -2255,7 +2254,6 @@ Account.prototype.fromRaw = function fromRaw(data) {
|
|||||||
this.receiveDepth = p.readU32();
|
this.receiveDepth = p.readU32();
|
||||||
this.changeDepth = p.readU32();
|
this.changeDepth = p.readU32();
|
||||||
this.accountKey = bcoin.hd.fromRaw(p.readBytes(82));
|
this.accountKey = bcoin.hd.fromRaw(p.readBytes(82));
|
||||||
this.keys = [];
|
|
||||||
|
|
||||||
count = p.readU8();
|
count = p.readU8();
|
||||||
|
|
||||||
@ -2313,12 +2311,10 @@ function MasterKey(options) {
|
|||||||
return new MasterKey(options);
|
return new MasterKey(options);
|
||||||
|
|
||||||
this.encrypted = false;
|
this.encrypted = false;
|
||||||
this.xprivkey = null;
|
|
||||||
this.phrase = null;
|
|
||||||
this.passphrase = null;
|
|
||||||
this.key = null;
|
|
||||||
this.iv = null;
|
this.iv = null;
|
||||||
this.ciphertext = null;
|
this.ciphertext = null;
|
||||||
|
this.key = null;
|
||||||
|
|
||||||
this.timer = null;
|
this.timer = null;
|
||||||
this._destroy = this.destroy.bind(this);
|
this._destroy = this.destroy.bind(this);
|
||||||
this.locker = new bcoin.locker(this);
|
this.locker = new bcoin.locker(this);
|
||||||
@ -2332,9 +2328,6 @@ function MasterKey(options) {
|
|||||||
|
|
||||||
MasterKey.prototype.fromOptions = function fromOptions(options) {
|
MasterKey.prototype.fromOptions = function fromOptions(options) {
|
||||||
this.encrypted = !!options.encrypted;
|
this.encrypted = !!options.encrypted;
|
||||||
this.xprivkey = options.xprivkey;
|
|
||||||
this.phrase = options.phrase;
|
|
||||||
this.passphrase = options.passphrase;
|
|
||||||
this.iv = options.iv;
|
this.iv = options.iv;
|
||||||
this.ciphertext = options.ciphertext;
|
this.ciphertext = options.ciphertext;
|
||||||
this.key = options.key || null;
|
this.key = options.key || null;
|
||||||
@ -2362,7 +2355,7 @@ MasterKey.fromOptions = function fromOptions(options) {
|
|||||||
|
|
||||||
MasterKey.prototype.toKey = function toKey(passphrase, timeout, callback) {
|
MasterKey.prototype.toKey = function toKey(passphrase, timeout, callback) {
|
||||||
var self = this;
|
var self = this;
|
||||||
var unlock, data;
|
var unlock;
|
||||||
|
|
||||||
unlock = this.locker.lock(toKey, [passphrase, timeout, callback]);
|
unlock = this.locker.lock(toKey, [passphrase, timeout, callback]);
|
||||||
|
|
||||||
@ -2384,16 +2377,13 @@ MasterKey.prototype.toKey = function toKey(passphrase, timeout, callback) {
|
|||||||
return callback(err);
|
return callback(err);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
data = MasterKey.fromRaw(data);
|
self.key = bcoin.hd.fromExtended(data);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return callback(e);
|
return callback(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
self.key = data.key;
|
|
||||||
self.start(timeout);
|
self.start(timeout);
|
||||||
|
|
||||||
data.destroy();
|
|
||||||
|
|
||||||
return callback(null, self.key);
|
return callback(null, self.key);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@ -2481,12 +2471,16 @@ MasterKey.prototype.decrypt = function decrypt(passphrase, callback) {
|
|||||||
if (err)
|
if (err)
|
||||||
return callback(err);
|
return callback(err);
|
||||||
|
|
||||||
|
try {
|
||||||
|
self.key = bcoin.hd.fromExtended(data);
|
||||||
|
} catch (e) {
|
||||||
|
return callback(e);
|
||||||
|
}
|
||||||
|
|
||||||
self.encrypted = false;
|
self.encrypted = false;
|
||||||
self.iv = null;
|
self.iv = null;
|
||||||
self.ciphertext = null;
|
self.ciphertext = null;
|
||||||
|
|
||||||
self.fromRaw(data);
|
|
||||||
|
|
||||||
return callback();
|
return callback();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@ -2514,7 +2508,8 @@ MasterKey.prototype.encrypt = function encrypt(passphrase, callback) {
|
|||||||
return callback();
|
return callback();
|
||||||
|
|
||||||
iv = bcoin.ec.random(16);
|
iv = bcoin.ec.random(16);
|
||||||
data = this.toRaw();
|
data = this.key.toExtended();
|
||||||
|
this.stop();
|
||||||
|
|
||||||
utils.encrypt(data, passphrase, iv, function(err, data) {
|
utils.encrypt(data, passphrase, iv, function(err, data) {
|
||||||
if (err)
|
if (err)
|
||||||
@ -2525,23 +2520,13 @@ MasterKey.prototype.encrypt = function encrypt(passphrase, callback) {
|
|||||||
self.iv = iv;
|
self.iv = iv;
|
||||||
self.ciphertext = data;
|
self.ciphertext = data;
|
||||||
|
|
||||||
self.xprivkey.fill(0);
|
|
||||||
self.xprivkey = null;
|
|
||||||
|
|
||||||
if (self.phrase) {
|
|
||||||
self.phrase.fill(0);
|
|
||||||
self.phrase = null;
|
|
||||||
self.passphrase.fill(0);
|
|
||||||
self.passphrase = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return callback();
|
return callback();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Serialize the key in the form of:
|
* Serialize the key in the form of:
|
||||||
* `[enc-flag][iv?][ciphertext?][phrase-marker][phrase?][passphrase?][xprivkey]`
|
* `[enc-flag][iv?][ciphertext?][extended-key?]`
|
||||||
* @returns {Buffer}
|
* @returns {Buffer}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -2560,16 +2545,7 @@ MasterKey.prototype.toRaw = function toRaw(writer) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
p.writeU8(0);
|
p.writeU8(0);
|
||||||
|
p.writeVarBytes(this.key.toExtended());
|
||||||
if (this.phrase) {
|
|
||||||
p.writeU8(1);
|
|
||||||
p.writeVarBytes(this.phrase);
|
|
||||||
p.writeVarBytes(this.passphrase);
|
|
||||||
} else {
|
|
||||||
p.writeU8(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
p.writeBytes(this.xprivkey);
|
|
||||||
|
|
||||||
if (!writer)
|
if (!writer)
|
||||||
p = p.render();
|
p = p.render();
|
||||||
@ -2594,13 +2570,7 @@ MasterKey.prototype.fromRaw = function fromRaw(raw) {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (p.readU8() === 1) {
|
this.key = bcoin.hd.fromExtended(p.readVarBytes());
|
||||||
this.phrase = p.readVarBytes();
|
|
||||||
this.passphrase = p.readVarBytes();
|
|
||||||
}
|
|
||||||
|
|
||||||
this.xprivkey = p.readBytes(82);
|
|
||||||
this.key = bcoin.hd.fromRaw(this.xprivkey);
|
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
@ -2624,15 +2594,7 @@ MasterKey.prototype.fromKey = function fromKey(key) {
|
|||||||
this.encrypted = false;
|
this.encrypted = false;
|
||||||
this.iv = null;
|
this.iv = null;
|
||||||
this.ciphertext = null;
|
this.ciphertext = null;
|
||||||
|
|
||||||
if (key.mnemonic) {
|
|
||||||
this.phrase = new Buffer(key.mnemonic.phrase, 'utf8');
|
|
||||||
this.passphrase = new Buffer(key.mnemonic.passphrase, 'utf8');
|
|
||||||
}
|
|
||||||
|
|
||||||
this.xprivkey = key.toRaw();
|
|
||||||
this.key = key;
|
this.key = key;
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -2652,26 +2614,20 @@ MasterKey.fromKey = function fromKey(key) {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
MasterKey.prototype.toJSON = function toJSON() {
|
MasterKey.prototype.toJSON = function toJSON() {
|
||||||
var phrase, passphrase, xprivkey, iv, ciphertext;
|
var iv, ciphertext, key;
|
||||||
|
|
||||||
if (this.encrypted) {
|
if (this.encrypted) {
|
||||||
iv = this.iv.toString('hex');
|
iv = this.iv.toString('hex');
|
||||||
ciphertext = this.ciphertext.toString('hex');
|
ciphertext = this.ciphertext.toString('hex');
|
||||||
} else {
|
} else {
|
||||||
if (this.phrase) {
|
key = this.key.toJSON();
|
||||||
phrase = this.phrase.toString('utf8');
|
|
||||||
passphrase = this.passphrase.toString('utf8');
|
|
||||||
}
|
|
||||||
xprivkey = utils.toBase58(this.xprivkey);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
encrypted: this.encrypted,
|
encrypted: this.encrypted,
|
||||||
iv: iv,
|
iv: iv,
|
||||||
ciphertext: ciphertext,
|
ciphertext: ciphertext,
|
||||||
phrase: phrase,
|
key: key
|
||||||
passphrase: passphrase,
|
|
||||||
xprivkey: xprivkey
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -2688,12 +2644,7 @@ MasterKey.prototype.fromJSON = function fromJSON(json) {
|
|||||||
this.iv = new Buffer(json.iv, 'hex');
|
this.iv = new Buffer(json.iv, 'hex');
|
||||||
this.ciphertext = new Buffer(json.ciphertext, 'hex');
|
this.ciphertext = new Buffer(json.ciphertext, 'hex');
|
||||||
} else {
|
} else {
|
||||||
if (json.phrase) {
|
this.key = bcoin.hd.fromJSON(json.key);
|
||||||
this.phrase = new Buffer(json.phrase, 'utf8');
|
|
||||||
this.passphrase = new Buffer(json.passphrase, 'utf8');
|
|
||||||
}
|
|
||||||
this.xprivkey = utils.fromBase58(json.xprivkey);
|
|
||||||
this.key = bcoin.hd.fromRaw(this.xprivkey);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
@ -2715,7 +2666,10 @@ MasterKey.fromJSON = function fromJSON(json) {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
MasterKey.prototype.inspect = function inspect() {
|
MasterKey.prototype.inspect = function inspect() {
|
||||||
return this.toJSON();
|
var json = this.toJSON();
|
||||||
|
if (this.key)
|
||||||
|
json.key = this.key.toJSON();
|
||||||
|
return json;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user