refactor signing.

This commit is contained in:
Christopher Jeffrey 2016-02-11 01:29:35 -08:00
parent b963809318
commit 4a6c73fc8e
4 changed files with 48 additions and 30 deletions

View File

@ -331,12 +331,18 @@ Address.prototype.ownInput = function ownInput(tx, index) {
return inputs;
};
Address.prototype.scriptInputs = function scriptInputs(tx) {
Address.prototype.scriptInputs = function scriptInputs(tx, index) {
var self = this;
var publicKey = this.getPublicKey();
var redeem = this.getScript();
if (index && typeof index === 'object')
index = tx.inputs.indexOf(index);
return tx.inputs.reduce(function(total, input, i) {
if (index != null && index !== i)
return total;
if (!input.output)
return total;
@ -350,15 +356,21 @@ Address.prototype.scriptInputs = function scriptInputs(tx) {
}, 0);
};
Address.prototype.signInputs = function signInputs(tx, type) {
Address.prototype.signInputs = function signInputs(tx, type, index) {
var self = this;
var key = this.key;
var total = 0;
if (index && typeof index === 'object')
index = tx.inputs.indexOf(index);
if (!key.privateKey)
return 0;
return tx.inputs.reduce(function(total, input, i) {
if (index != null && index !== i)
return total;
if (!input.output)
return total;
@ -372,17 +384,22 @@ Address.prototype.signInputs = function signInputs(tx, type) {
}, 0);
};
Address.prototype.sign = function sign(tx, type) {
Address.prototype.sign = function sign(tx, type, index) {
var self = this;
var publicKey = this.getPublicKey();
var redeem = this.getScript();
var key = this.key;
if (index && typeof index === 'object')
index = tx.inputs.indexOf(index);
if (!key.privateKey)
return 0;
// Add signature script to each input
return tx.inputs.reduce(function(total, input, i) {
if (index != null && index !== i)
return total;
// Filter inputs that this wallet own
if (!input.output)
return total;
@ -390,7 +407,7 @@ Address.prototype.sign = function sign(tx, type) {
if (!self.ownOutput(input.output))
return total;
if (tx.scriptSig(i, key, publicKey, redeem, type))
if (tx.sign(i, key, redeem, type))
total++;
return total;

View File

@ -218,7 +218,7 @@ TX.prototype._inputIndex = function _inputIndex(hash, index) {
return -1;
};
TX.prototype.scriptInput = function scriptInput(index, pub, redeem) {
TX.prototype.scriptInput = function scriptInput(index, publicKey, redeem) {
var input, s, n, i;
if (typeof index !== 'number')
@ -249,7 +249,7 @@ TX.prototype.scriptInput = function scriptInput(index, pub, redeem) {
if (bcoin.script.isPubkey(s)) {
// P2PK
if (!utils.isEqual(s[0], pub))
if (!utils.isEqual(s[0], publicKey))
return false;
// Already has a script template (at least)
if (input.script.length)
@ -257,16 +257,16 @@ TX.prototype.scriptInput = function scriptInput(index, pub, redeem) {
input.script = [[]];
} else if (bcoin.script.isPubkeyhash(s)) {
// P2PKH
if (!utils.isEqual(s[2], bcoin.address.hash160(pub)))
if (!utils.isEqual(s[2], bcoin.address.hash160(publicKey)))
return false;
// Already has a script template (at least)
if (input.script.length)
return true;
input.script = [[], pub];
input.script = [[], publicKey];
} else if (bcoin.script.isMultisig(s)) {
// Multisig
for (i = 0; i < s.length; i++) {
if (utils.isEqual(s[i], pub))
if (utils.isEqual(s[i], publicKey))
break;
}
@ -290,7 +290,7 @@ TX.prototype.scriptInput = function scriptInput(index, pub, redeem) {
input.script[i + 1] = [];
} else {
for (i = 0; i < s.length; i++) {
if (utils.isEqual(s[i], pub))
if (utils.isEqual(s[i], publicKey))
break;
}
@ -371,8 +371,8 @@ TX.prototype.signature = TX.prototype.createSignature;
// Sign the now-built scriptSigs
TX.prototype.signInput = function signInput(index, key, type) {
var input, s, hash, signature;
var len, m, n, keys, pub, pkh, ki, signatures, i;
var input, s, signature, ki, signatures, i;
var len, m, n, keys, publicKey, keyHash;
if (typeof index !== 'number')
index = this.inputs.indexOf(index);
@ -401,9 +401,8 @@ TX.prototype.signInput = function signInput(index, key, type) {
len--;
}
// Get pubkey and pubkey hash.
pub = key.getPublic(true, 'array');
pkh = bcoin.address.hash160(pub);
// Get pubkey.
publicKey = key.getPublic(true, 'array');
// Add signatures.
if (bcoin.script.isPubkey(s)) {
@ -418,7 +417,7 @@ TX.prototype.signInput = function signInput(index, key, type) {
return true;
// Make sure the pubkey is ours.
if (!utils.isEqual(pub, s[0]))
if (!utils.isEqual(publicKey, s[0]))
return false;
input.script[0] = signature;
@ -438,7 +437,8 @@ TX.prototype.signInput = function signInput(index, key, type) {
return true;
// Make sure the pubkey hash is ours.
if (!utils.isEqual(pkh, s[2]))
keyHash = bcoin.address.hash160(publicKey);
if (!utils.isEqual(keyHash, s[2]))
return false;
input.script[0] = signature;
@ -502,7 +502,7 @@ TX.prototype.signInput = function signInput(index, key, type) {
// Find the key index so we can place
// the signature in the same index.
for (ki = 0; ki < keys.length; ki++) {
if (utils.isEqual(pub, keys[ki]))
if (utils.isEqual(publicKey, keys[ki]))
break;
}
@ -555,7 +555,8 @@ TX.prototype.signInput = function signInput(index, key, type) {
return signatures === m;
};
TX.prototype.scriptSig = function scriptSig(index, key, pub, redeem, type) {
TX.prototype.sign = function sign(index, key, redeem, type) {
var publicKey = key.getPublic(true, 'array');
var input;
if (index && typeof index === 'object')
@ -565,14 +566,14 @@ TX.prototype.scriptSig = function scriptSig(index, key, pub, redeem, type) {
assert(input);
// Build script for input
if (!this.scriptInput(index, pub, redeem))
if (!this.scriptInput(index, publicKey, redeem))
return false;
// Sign input
if (!this.signInput(index, key, type))
return false;
return input.script;
return true;
};
TX.prototype.isSigned = function isSigned(index, required) {

View File

@ -683,27 +683,27 @@ Wallet.prototype.syncOutputDepth = function syncOutputDepth(tx) {
this.setReceiveDepth(depth.receive);
};
Wallet.prototype.scriptInputs = function scriptInputs(tx) {
Wallet.prototype.scriptInputs = function scriptInputs(tx, index) {
this.fillPrevout(tx);
var addresses = this.deriveInputs(tx);
return addresses.reduce(function(total, address) {
return total + address.scriptInputs(tx);
return total + address.scriptInputs(tx, index);
}, 0);
};
Wallet.prototype.signInputs = function signInputs(tx, type) {
Wallet.prototype.signInputs = function signInputs(tx, type, index) {
this.fillPrevout(tx);
var addresses = this.deriveInputs(tx);
return addresses.reduce(function(total, address) {
return total + address.signInputs(tx, type);
return total + address.signInputs(tx, type, index);
}, 0);
};
Wallet.prototype.sign = function sign(tx, type) {
Wallet.prototype.sign = function sign(tx, type, index) {
this.fillPrevout(tx);
var addresses = this.deriveInputs(tx);
return addresses.reduce(function(total, address) {
return total + address.sign(tx, type);
return total + address.sign(tx, type, index);
}, 0);
};

View File

@ -256,8 +256,8 @@ describe('Wallet', function() {
tx.input(unspent1[1]);
tx.input(unspent1[2]);
tx.input(unspent2[1]);
assert.equal(w1.sign(tx, 'all', tx.inputs.slice()), 2);
assert.equal(w2.sign(tx, 'all', tx.inputs.slice(2)), 1);
assert.equal(w1.sign(tx, 'all'), 2);
assert.equal(w2.sign(tx, 'all'), 1);
// Verify
assert.equal(tx.verify(), true);