From 0f23304a6872d088a3d7f0c3821aee2953f54385 Mon Sep 17 00:00:00 2001 From: Christopher Jeffrey Date: Thu, 18 Aug 2016 20:29:30 -0700 Subject: [PATCH] mtx: maxSize. --- lib/bcoin/mtx.js | 61 ++++++++++++++++++++------------------------- lib/bcoin/wallet.js | 5 ++-- 2 files changed, 30 insertions(+), 36 deletions(-) diff --git a/lib/bcoin/mtx.js b/lib/bcoin/mtx.js index 03746e7e..04e7d128 100644 --- a/lib/bcoin/mtx.js +++ b/lib/bcoin/mtx.js @@ -925,49 +925,20 @@ MTX.prototype.isScripted = function isScripted() { * @param {(Wallet|Object)?} options - Wallet or options object. * @param {Number} options.m - Multisig `m` value. * @param {Number} options.n - Multisig `n` value. - * @param {Boolean} force - `maxSize` will just calculate - * the virtual size instead of _estimating_ it if the - * templates are already built. If true, this will force - * estimation of the size. * @returns {Number} */ -MTX.prototype.maxSize = function maxSize(options, force) { +MTX.prototype.maxSize = function maxSize(options) { var scale = constants.WITNESS_SCALE_FACTOR; var i, j, input, total, size, prev, m, n, sz; var witness, hadWitness, redeem, wallet; - if (!force && this.isScripted()) + if (!options && this.isScripted()) return this.getVirtualSize(); if (!options) options = {}; - if (options instanceof bcoin.wallet) - options = { wallet: options }; - - if (options.wallet) - wallet = options.wallet; - - function getRedeem(vector, hash) { - var redeem = vector.getRedeem(); - var address; - - if (redeem) - return redeem; - - if (!wallet) - return; - - // Hack - address = wallet.receiveAddress; - - if (address.program && hash.length === 20) - return address.program; - - return address.script; - } - // Calculate the size, minus the input scripts. total = this.getBaseSize(); @@ -1001,7 +972,7 @@ MTX.prototype.maxSize = function maxSize(options, force) { // here since it will be ignored by // the isMultisig clause. // OP_PUSHDATA2 [redeem] - redeem = getRedeem(input.script, prev.get(1)); + redeem = this._guessRedeem(prev.get(1), options); if (redeem) { prev = redeem; sz = prev.getSize(); @@ -1032,7 +1003,7 @@ MTX.prototype.maxSize = function maxSize(options, force) { hadWitness = true; if (prev.isWitnessScripthash()) { - redeem = getRedeem(input.witness, prev.get(1)); + redeem = this._guessRedeem(prev.get(1), options); if (redeem) { prev = redeem; sz = prev.getSize(); @@ -1114,6 +1085,28 @@ MTX.prototype.maxSize = function maxSize(options, force) { return total; }; +/** + * "Guess" a redeem script based on some options. + * @private + * @param {Object} options + * @param {Buffer} hash + * @returns {Script|null} + */ + +MTX.prototype._guessRedeem = function guessRedeem(options, hash) { + switch (hash.length) { + case 20: + if (options.witness) { + if (options.n > 1) + return bcoin.script.fromProgram(0, constants.ZERO_HASH); + return bcoin.script.fromProgram(0, constants.ZERO_HASH160); + } + return options.script; + case 32: + return options.script; + } +}; + /** * Select necessary coins based on total output value. * @param {Coin[]} coins @@ -1232,7 +1225,7 @@ MTX.prototype.selectCoins = function selectCoins(coins, options) { // bytes (10000 satoshi for every 1024 bytes). do { // Calculate max possible size after signing. - size = tx.maxSize(options, true); + size = tx.maxSize(options.key, options.script); if (tryFree && options.height >= 0) { // Note that this will only work diff --git a/lib/bcoin/wallet.js b/lib/bcoin/wallet.js index dc3f2225..8c96d9ac 100644 --- a/lib/bcoin/wallet.js +++ b/lib/bcoin/wallet.js @@ -878,9 +878,10 @@ Wallet.prototype.fund = function fund(tx, options, callback, force) { changeAddress: account.changeAddress.getAddress(), height: self.db.height, rate: rate, - wallet: self, m: account.m, - n: account.n + n: account.n, + witness: account.witness, + script: account.receiveAddress.script }); } catch (e) { return callback(e);