tx: clean up address handling.

This commit is contained in:
Christopher Jeffrey 2016-10-20 07:22:03 -07:00
parent de178092f1
commit 690c8840e0
No known key found for this signature in database
GPG Key ID: 8962AB9DE6666BBD
3 changed files with 102 additions and 108 deletions

View File

@ -1597,7 +1597,7 @@ Chain.prototype._getLocator = co(function* getLocator(start) {
* Will also calculate "orphan soil" -- the block needed * Will also calculate "orphan soil" -- the block needed
* in * order to resolve the orphan root. * in * order to resolve the orphan root.
* @param {Hash} hash * @param {Hash} hash
* @returns {Object?} root - { root: {@link Hash}, soil: {@link Hash} }. * @returns {Hash}
*/ */
Chain.prototype.getOrphanRoot = function getOrphanRoot(hash) { Chain.prototype.getOrphanRoot = function getOrphanRoot(hash) {

View File

@ -340,54 +340,6 @@ Coin.fromCompressed = function fromCompressed(data, enc) {
return new Coin().fromCompressed(data); return new Coin().fromCompressed(data);
}; };
/**
* Serialize the coin to an "extended" format,
* including both the hash and the index.
* @param {String?} enc - Encoding, can be `'hex'` or null.
* @returns {Buffer|String}
*/
Coin.prototype.toExtended = function toExtended(writer) {
var p = BufferWriter(writer);
this.toRaw(p);
p.writeHash(this.hash);
p.writeU32(this.index);
if (!writer)
p = p.render();
return p;
};
/**
* Inject properties from extended serialized data.
* @private
* @param {Buffer} data
*/
Coin.prototype.fromExtended = function fromExtended(data) {
var p = BufferReader(data);
this.fromRaw(p);
this.hash = p.readHash('hex');
this.index = p.readU32();
return this;
};
/**
* Instantiate a coin from a Buffer
* in "extended" serialization format.
* @param {Buffer} data
* @param {String?} enc - Encoding, can be `'hex'` or null.
* @returns {Coin}
*/
Coin.fromExtended = function fromExtended(data, enc) {
if (typeof data === 'string')
data = new Buffer(data, enc);
return new Coin().fromExtended(data);
};
/** /**
* Inject properties from TX. * Inject properties from TX.
* @param {TX} tx * @param {TX} tx

View File

@ -795,25 +795,22 @@ TX.prototype.isCoinbase = function isCoinbase() {
}; };
/** /**
* Test whether the transaction is a replacement. * Test whether the transaction is replaceable.
* @returns {Boolean} * @returns {Boolean}
*/ */
TX.prototype.isRBF = function isRBF() { TX.prototype.isRBF = function isRBF() {
var i, input; var i, input;
// Core doesn't do this, but it should:
if (this.version === 2)
return false;
for (i = 0; i < this.inputs.length; i++) { for (i = 0; i < this.inputs.length; i++) {
input = this.inputs[i]; input = this.inputs[i];
if (!input.isRBF()) if (input.isRBF())
continue; return true;
if (this.version === 2) {
if (!(input.sequence & constants.sequence.DISABLE_FLAG))
continue;
}
return true;
} }
return false; return false;
@ -878,75 +875,114 @@ TX.prototype.getOutputValue = function getOutputValue() {
/** /**
* Get all input addresses. * Get all input addresses.
* @returns {Base58Address[]} addresses * @private
* @returns {Array}
*/ */
TX.prototype.getInputAddresses = function getInputAddresses() { TX.prototype._getInputAddresses = function getInputAddresses() {
var table = {}; var table = {};
var addresses = []; var addrs = [];
var i, address, hash; var i, address, hash;
if (this.isCoinbase())
return [addrs, table];
for (i = 0; i < this.inputs.length; i++) { for (i = 0; i < this.inputs.length; i++) {
address = this.inputs[i].getAddress(); address = this.inputs[i].getAddress();
if (address) {
hash = address.getHash('hex'); if (!address)
if (!table[hash]) { continue;
table[hash] = true;
addresses.push(address); hash = address.getHash('hex');
}
if (!table[hash]) {
table[hash] = true;
addrs.push(address);
} }
} }
addresses.table = table; return [addrs, table];
return addresses;
}; };
/** /**
* Get all output addresses. * Get all output addresses.
* @returns {Base58Address[]} addresses * @private
* @returns {Array}
*/ */
TX.prototype.getOutputAddresses = function getOutputAddresses() { TX.prototype._getOutputAddresses = function getOutputAddresses() {
var table = {}; var table = {};
var addresses = []; var addrs = [];
var i, address, hash; var i, address, hash;
for (i = 0; i < this.outputs.length; i++) { for (i = 0; i < this.outputs.length; i++) {
address = this.outputs[i].getAddress(); address = this.outputs[i].getAddress();
if (address) {
hash = address.getHash('hex'); if (!address)
if (!table[hash]) { continue;
table[hash] = true;
addresses.push(address); hash = address.getHash('hex');
}
if (!table[hash]) {
table[hash] = true;
addrs.push(address);
} }
} }
addresses.table = table; return [addrs, table];
return addresses;
}; };
/** /**
* Get all addresses. * Get all addresses.
* @returns {Base58Address[]} addresses * @private
* @returns {Array}
*/ */
TX.prototype.getAddresses = function getAddresses() { TX.prototype._getAddresses = function getAddresses() {
var input = this.getInputAddresses(); var inputs = this._getInputAddresses();
var output = this.getOutputAddresses(); var output = this.getOutputAddresses();
var addrs = inputs[0];
var table = inputs[1];
var i, hash; var i, hash;
for (i = 0; i < output.length; i++) { for (i = 0; i < output.length; i++) {
hash = output[i].getHash('hex'); hash = output[i].getHash('hex');
if (!input.table[hash]) {
input.table[hash] = true; if (!table[hash]) {
input.push(output[i]); table[hash] = true;
addrs.push(output[i]);
} }
} }
return input; return [addrs, table];
};
/**
* Get all input addresses.
* @private
* @returns {Address[]} addresses
*/
TX.prototype.getInputAddresses = function getInputAddresses() {
return this._getInputAddresses()[0];
};
/**
* Get all output addresses.
* @returns {Address[]} addresses
*/
TX.prototype.getOutputAddresses = function getOutputAddresses() {
return this._getOutputAddresses()[0];
};
/**
* Get all addresses.
* @returns {Address[]} addresses
*/
TX.prototype.getAddresses = function getAddresses() {
return this._getAddresses()[0];
}; };
/** /**
@ -955,11 +991,14 @@ TX.prototype.getAddresses = function getAddresses() {
*/ */
TX.prototype.getInputHashes = function getInputHashes(enc) { TX.prototype.getInputHashes = function getInputHashes(enc) {
var input = this.getInputAddresses(); var i, input, table;
var i;
if (enc === 'hex') if (enc === 'hex') {
return Object.keys(input.table); table = this._getInputAddresses()[1];
return Object.keys(table);
}
input = this.getInputAddresses();
for (i = 0; i < input.length; i++) for (i = 0; i < input.length; i++)
input[i] = input[i].getHash(); input[i] = input[i].getHash();
@ -973,11 +1012,14 @@ TX.prototype.getInputHashes = function getInputHashes(enc) {
*/ */
TX.prototype.getOutputHashes = function getOutputHashes(enc) { TX.prototype.getOutputHashes = function getOutputHashes(enc) {
var output = this.getOutputAddresses(); var i, output, table;
var i;
if (enc === 'hex') if (enc === 'hex') {
return Object.keys(output.table); table = this._getOutputAddresses()[1];
return Object.keys(table);
}
output = this.getOutputAddresses();
for (i = 0; i < output.length; i++) for (i = 0; i < output.length; i++)
output[i] = output[i].getHash(); output[i] = output[i].getHash();
@ -991,11 +1033,14 @@ TX.prototype.getOutputHashes = function getOutputHashes(enc) {
*/ */
TX.prototype.getHashes = function getHashes(enc) { TX.prototype.getHashes = function getHashes(enc) {
var hashes = this.getAddresses(); var i, hashes, table;
var i;
if (enc === 'hex') if (enc === 'hex') {
return Object.keys(hashes.table); table = this._getAddresses()[1];
return Object.keys(table);
}
hashes = this.getAddresses();
for (i = 0; i < hashes.length; i++) for (i = 0; i < hashes.length; i++)
hashes[i] = hashes[i].getHash(); hashes[i] = hashes[i].getHash();
@ -1042,15 +1087,12 @@ TX.prototype.fillCoins = function fillCoins(coins) {
map = {}; map = {};
for (i = 0; i < coins.length; i++) { for (i = 0; i < coins.length; i++) {
coin = coins[i]; coin = coins[i];
if (coin instanceof TX) { if (coin instanceof TX)
map[coin.hash('hex')] = coin; map[coin.hash('hex')] = coin;
} else if (coin instanceof Coin) { else if (coin instanceof Coin)
assert(typeof coin.hash === 'string');
assert(typeof coin.index === 'number');
map[coin.hash + coin.index] = coin; map[coin.hash + coin.index] = coin;
} else { else
assert(false, 'Non-coin object passed to fillCoins.'); assert(false, 'Non-coin object passed to fillCoins.');
}
} }
coins = map; coins = map;
} }