URI: 
       tledger: don't throw exception if user cancels signing - electrum - Electrum Bitcoin wallet
  HTML git clone https://git.parazyd.org/electrum
   DIR Log
   DIR Files
   DIR Refs
   DIR Submodules
       ---
   DIR commit 8589c1b0bb79c3c6a8506d5ef875bd1e2bb055e6
   DIR parent 5e5134b76ffec8ed9702f5661a1d16e9e52a24c8
  HTML Author: SomberNight <somber.night@protonmail.com>
       Date:   Wed, 14 Mar 2018 15:18:26 +0100
       
       ledger: don't throw exception if user cancels signing
       
       Used to show "Exception : Invalid status 6985", which is not really user-friendly. This now mimics the behaviour with Trezor where we silently ignore cancellation (not showing any popup).
       
       Diffstat:
         M plugins/ledger/ledger.py            |      30 ++++++++++++++++++++++--------
       
       1 file changed, 22 insertions(+), 8 deletions(-)
       ---
   DIR diff --git a/plugins/ledger/ledger.py b/plugins/ledger/ledger.py
       t@@ -229,6 +229,16 @@ class Ledger_KeyStore(Hardware_KeyStore):
                    self.client = None
                raise Exception(message)
        
       +    def set_and_unset_signing(func):
       +        """Function decorator to set and unset self.signing."""
       +        def wrapper(self, *args, **kwargs):
       +            try:
       +                self.signing = True
       +                return func(self, *args, **kwargs)
       +            finally:
       +                self.signing = False
       +        return wrapper
       +
            def address_id_stripped(self, address):
                # Strip the leading "m/"
                change, index = self.get_address_index(address)
       t@@ -239,8 +249,8 @@ class Ledger_KeyStore(Hardware_KeyStore):
            def decrypt_message(self, pubkey, message, password):
                raise RuntimeError(_('Encryption and decryption are currently not supported for {}').format(self.device))
        
       +    @set_and_unset_signing
            def sign_message(self, sequence, message, password):
       -        self.signing = True
                message = message.encode('utf8')
                message_hash = hashlib.sha256(message).hexdigest().upper()
                # prompt for the PIN before displaying the dialog if necessary
       t@@ -259,16 +269,17 @@ class Ledger_KeyStore(Hardware_KeyStore):
                except BTChipException as e:
                    if e.sw == 0x6a80:
                        self.give_error("Unfortunately, this message cannot be signed by the Ledger wallet. Only alphanumerical messages shorter than 140 characters are supported. Please remove any extra characters (tab, carriage return) and retry.")
       +            elif e.sw == 0x6985:  # cancelled by user
       +                return b''
                    else:
                        self.give_error(e, True)
                except UserWarning:
                    self.handler.show_error(_('Cancelled by user'))
       -            return ''
       +            return b''
                except Exception as e:
                    self.give_error(e, True)
                finally:
                    self.handler.finished()
       -        self.signing = False
                # Parse the ASN.1 signature
                rLength = signature[3]
                r = signature[4 : 4 + rLength]
       t@@ -281,12 +292,11 @@ class Ledger_KeyStore(Hardware_KeyStore):
                # And convert it
                return bytes([27 + 4 + (signature[0] & 0x01)]) + r + s
        
       -
       +    @set_and_unset_signing
            def sign_transaction(self, tx, password):
                if tx.is_complete():
                    return
                client = self.get_client()
       -        self.signing = True
                inputs = []
                inputsPaths = []
                pubKeys = []
       t@@ -446,6 +456,12 @@ class Ledger_KeyStore(Hardware_KeyStore):
                except UserWarning:
                    self.handler.show_error(_('Cancelled by user'))
                    return
       +        except BTChipException as e:
       +            if e.sw == 0x6985:  # cancelled by user
       +                return
       +            else:
       +                traceback.print_exc(file=sys.stderr)
       +                self.give_error(e, True)
                except BaseException as e:
                    traceback.print_exc(file=sys.stdout)
                    self.give_error(e, True)
       t@@ -456,10 +472,9 @@ class Ledger_KeyStore(Hardware_KeyStore):
                    signingPos = inputs[i][4]
                    txin['signatures'][signingPos] = bh2u(signatures[i])
                tx.raw = tx.serialize()
       -        self.signing = False
        
       +    @set_and_unset_signing
            def show_address(self, sequence, txin_type):
       -        self.signing = True
                client = self.get_client()
                address_path = self.get_derivation()[2:] + "/%d/%d"%sequence
                self.handler.show_message(_("Showing address ..."))
       t@@ -478,7 +493,6 @@ class Ledger_KeyStore(Hardware_KeyStore):
                    self.handler.show_error(e)
                finally:
                    self.handler.finished()
       -        self.signing = False
        
        class LedgerPlugin(HW_PluginBase):
            libraries_available = BTCHIP