Browse Source

trezor: support outdated firmware notifications

Outdated firmware error messages were originally raised from
create_client, which would mean that a client for an outdated device
would not be created.

This had a number of undesirable outcomes due to "client does not exist"
being conflated with "no device is connected".

Instead, we raise in setup_client (which prevents creating new wallets
with outdated devices, BUT shows them in device list), and python-trezor
also raises on most calls (which gives us an error message when opening
wallet and/or trying to do basically anything with it).

This is still suboptimal - i.e., there's currently no way for Electrum to
claim higher version requirement than the underlying python-trezor, and
so minimum_firmware property is pretty much useless ATM.
3.3.3.1
matejcik 6 years ago
parent
commit
43acd09df8
  1. 16
      electrum/plugins/trezor/clientbase.py
  2. 22
      electrum/plugins/trezor/trezor.py

16
electrum/plugins/trezor/clientbase.py

@ -2,12 +2,12 @@ import time
from struct import pack
from electrum.i18n import _
from electrum.util import PrintError, UserCancelled
from electrum.util import PrintError, UserCancelled, UserFacingException
from electrum.keystore import bip39_normalize_passphrase
from electrum.bip32 import serialize_xpub, convert_bip32_path_to_list_of_uint32 as parse_path
from trezorlib.client import TrezorClient
from trezorlib.exceptions import TrezorFailure, Cancelled
from trezorlib.exceptions import TrezorFailure, Cancelled, OutdatedFirmwareError
from trezorlib.messages import WordRequestType, FailureType, RecoveryDeviceType
import trezorlib.btc
import trezorlib.device
@ -66,6 +66,8 @@ class TrezorClientBase(PrintError):
raise UserCancelled from exc_value
elif issubclass(exc_type, TrezorFailure):
raise RuntimeError(exc_value.message) from exc_value
elif issubclass(exc_type, OutdatedFirmwareError):
raise UserFacingException(exc_value) from exc_value
else:
return False
return True
@ -163,12 +165,10 @@ class TrezorClientBase(PrintError):
self.print_error("closing client")
self.clear_session()
def firmware_version(self):
f = self.features
return (f.major_version, f.minor_version, f.patch_version)
def atleast_version(self, major, minor=0, patch=0):
return self.firmware_version() >= (major, minor, patch)
def is_uptodate(self):
if self.client.is_outdated():
return False
return self.client.version >= self.plugin.minimum_firmware
def get_trezor_model(self):
"""Returns '1' for Trezor One, 'T' for Trezor T."""

22
electrum/plugins/trezor/trezor.py

@ -141,20 +141,7 @@ class TrezorPlugin(HW_PluginBase):
self.print_error("connected to device at", device.path)
# note that this call can still raise!
client = TrezorClientBase(transport, handler, self)
if not client.atleast_version(*self.minimum_firmware):
msg = (_('Outdated {} firmware for device labelled {}. Please '
'download the updated firmware from {}')
.format(self.device, client.label(), self.firmware_URL))
self.print_error(msg)
if handler:
handler.show_error(msg)
else:
raise UserFacingException(msg)
return None
return client
return TrezorClientBase(transport, handler, self)
def get_client(self, keystore, force_pair=True):
devmgr = self.device_manager()
@ -265,6 +252,13 @@ class TrezorPlugin(HW_PluginBase):
if client is None:
raise UserFacingException(_('Failed to create a client for this device.') + '\n' +
_('Make sure it is in the correct state.'))
if not client.is_uptodate():
msg = (_('Outdated {} firmware for device labelled {}. Please '
'download the updated firmware from {}')
.format(self.device, client.label(), self.firmware_URL))
raise UserFacingException(msg)
# fixme: we should use: client.handler = wizard
client.handler = self.create_handler(wizard)
if not device_info.initialized:

Loading…
Cancel
Save