mirror of
https://github.com/LBRYFoundation/LBRY-Vault.git
synced 2025-08-23 17:47:31 +00:00
transaction: always sort i/o deterministically
this was previously the caller's responsibility; now it's done implicitly when creating a txn
This commit is contained in:
parent
5e4a4ae16b
commit
53fd6a2df5
2 changed files with 8 additions and 9 deletions
|
@ -747,6 +747,7 @@ class Transaction:
|
||||||
self._inputs = inputs
|
self._inputs = inputs
|
||||||
self._outputs = outputs
|
self._outputs = outputs
|
||||||
self.locktime = locktime
|
self.locktime = locktime
|
||||||
|
self.BIP69_sort()
|
||||||
return self
|
return self
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
|
@ -981,9 +982,10 @@ class Transaction:
|
||||||
for txin in self.inputs():
|
for txin in self.inputs():
|
||||||
txin['sequence'] = nSequence
|
txin['sequence'] = nSequence
|
||||||
|
|
||||||
def BIP_LI01_sort(self):
|
def BIP69_sort(self, inputs=True, outputs=True):
|
||||||
# See https://github.com/kristovatlas/rfc/blob/master/bips/bip-li01.mediawiki
|
if inputs:
|
||||||
self._inputs.sort(key = lambda i: (i['prevout_hash'], i['prevout_n']))
|
self._inputs.sort(key = lambda i: (i['prevout_hash'], i['prevout_n']))
|
||||||
|
if outputs:
|
||||||
self._outputs.sort(key = lambda o: (o[2], self.pay_script(o[0], o[1])))
|
self._outputs.sort(key = lambda o: (o[2], self.pay_script(o[0], o[1])))
|
||||||
|
|
||||||
def serialize_output(self, output):
|
def serialize_output(self, output):
|
||||||
|
@ -1070,10 +1072,12 @@ class Transaction:
|
||||||
def add_inputs(self, inputs):
|
def add_inputs(self, inputs):
|
||||||
self._inputs.extend(inputs)
|
self._inputs.extend(inputs)
|
||||||
self.raw = None
|
self.raw = None
|
||||||
|
self.BIP69_sort(outputs=False)
|
||||||
|
|
||||||
def add_outputs(self, outputs):
|
def add_outputs(self, outputs):
|
||||||
self._outputs.extend(outputs)
|
self._outputs.extend(outputs)
|
||||||
self.raw = None
|
self.raw = None
|
||||||
|
self.BIP69_sort(inputs=False)
|
||||||
|
|
||||||
def input_value(self):
|
def input_value(self):
|
||||||
return sum(x['value'] for x in self.inputs())
|
return sum(x['value'] for x in self.inputs())
|
||||||
|
|
|
@ -143,7 +143,6 @@ def sweep(privkeys, network, config, recipient, fee=None, imax=100):
|
||||||
locktime = network.get_local_height()
|
locktime = network.get_local_height()
|
||||||
|
|
||||||
tx = Transaction.from_io(inputs, outputs, locktime=locktime)
|
tx = Transaction.from_io(inputs, outputs, locktime=locktime)
|
||||||
tx.BIP_LI01_sort()
|
|
||||||
tx.set_rbf(True)
|
tx.set_rbf(True)
|
||||||
tx.sign(keypairs)
|
tx.sign(keypairs)
|
||||||
return tx
|
return tx
|
||||||
|
@ -608,8 +607,6 @@ class Abstract_Wallet(AddressSynchronizer):
|
||||||
outputs[i_max] = outputs[i_max]._replace(value=amount)
|
outputs[i_max] = outputs[i_max]._replace(value=amount)
|
||||||
tx = Transaction.from_io(inputs, outputs[:])
|
tx = Transaction.from_io(inputs, outputs[:])
|
||||||
|
|
||||||
# Sort the inputs and outputs deterministically
|
|
||||||
tx.BIP_LI01_sort()
|
|
||||||
# Timelock tx to current height.
|
# Timelock tx to current height.
|
||||||
tx.locktime = self.get_local_height()
|
tx.locktime = self.get_local_height()
|
||||||
run_hook('make_unsigned_transaction', self, tx)
|
run_hook('make_unsigned_transaction', self, tx)
|
||||||
|
@ -714,7 +711,6 @@ class Abstract_Wallet(AddressSynchronizer):
|
||||||
raise CannotBumpFee(_('Cannot bump fee') + ': ' + _('could not find suitable outputs'))
|
raise CannotBumpFee(_('Cannot bump fee') + ': ' + _('could not find suitable outputs'))
|
||||||
locktime = self.get_local_height()
|
locktime = self.get_local_height()
|
||||||
tx_new = Transaction.from_io(inputs, outputs, locktime=locktime)
|
tx_new = Transaction.from_io(inputs, outputs, locktime=locktime)
|
||||||
tx_new.BIP_LI01_sort()
|
|
||||||
return tx_new
|
return tx_new
|
||||||
|
|
||||||
def cpfp(self, tx, fee):
|
def cpfp(self, tx, fee):
|
||||||
|
@ -733,7 +729,6 @@ class Abstract_Wallet(AddressSynchronizer):
|
||||||
inputs = [item]
|
inputs = [item]
|
||||||
outputs = [TxOutput(TYPE_ADDRESS, address, value - fee)]
|
outputs = [TxOutput(TYPE_ADDRESS, address, value - fee)]
|
||||||
locktime = self.get_local_height()
|
locktime = self.get_local_height()
|
||||||
# note: no need to call tx.BIP_LI01_sort() here - single input/output
|
|
||||||
return Transaction.from_io(inputs, outputs, locktime=locktime)
|
return Transaction.from_io(inputs, outputs, locktime=locktime)
|
||||||
|
|
||||||
def add_input_sig_info(self, txin, address):
|
def add_input_sig_info(self, txin, address):
|
||||||
|
|
Loading…
Add table
Reference in a new issue