1
0
mirror of https://github.com/trezor/trezor-firmware.git synced 2024-12-16 03:18:09 +00:00

stellar: style and text api changes

This commit is contained in:
Jan Pochyla 2018-07-10 16:39:17 +02:00 committed by Tomas Susanka
parent b722fddc58
commit b46ce034d6
11 changed files with 259 additions and 267 deletions

View File

@ -1,21 +1,26 @@
from trezor.wire import register, protobuf_workflow
from trezor.messages.wire_types import StellarGetAddress
from trezor.messages.wire_types import StellarGetPublicKey
from trezor.messages.wire_types import StellarSignTx
from trezor.messages.MessageType import (
StellarGetAddress,
StellarGetPublicKey,
StellarSignTx,
)
from trezor.wire import protobuf_workflow, register
def dispatch_StellarGetAddress(*args, **kwargs):
from .get_address import get_address
return get_address(*args, **kwargs)
def dispatch_StellarGetPublicKey(*args, **kwargs):
from .get_public_key import get_public_key
return get_public_key(*args, **kwargs)
def dispatch_StellarSignTx(*args, **kwargs):
from .sign_tx import sign_tx
return sign_tx(*args, **kwargs)

View File

@ -1,37 +1,38 @@
from trezor.messages import wire_types
from micropython import const
STELLAR_CURVE = 'ed25519'
TX_TYPE = bytearray('\x00\x00\x00\x02')
from trezor.messages import MessageType
STELLAR_CURVE = "ed25519"
TX_TYPE = bytearray("\x00\x00\x00\x02")
# source: https://github.com/stellar/go/blob/3d2c1defe73dbfed00146ebe0e8d7e07ce4bb1b6/xdr/Stellar-transaction.x#L16
# Inflation not supported see https://github.com/trezor/trezor-core/issues/202#issuecomment-393342089
op_codes = {
'StellarAccountMergeOp': const(8),
'StellarAllowTrustOp': const(7),
'StellarBumpSequenceOp': const(11),
'StellarChangeTrustOp': const(6),
'StellarCreateAccountOp': const(0),
'StellarCreatePassiveOfferOp': const(4),
'StellarManageDataOp': const(10),
'StellarManageOfferOp': const(3),
'StellarPathPaymentOp': const(2),
'StellarPaymentOp': const(1),
'StellarSetOptionsOp': const(5),
"StellarAccountMergeOp": const(8),
"StellarAllowTrustOp": const(7),
"StellarBumpSequenceOp": const(11),
"StellarChangeTrustOp": const(6),
"StellarCreateAccountOp": const(0),
"StellarCreatePassiveOfferOp": const(4),
"StellarManageDataOp": const(10),
"StellarManageOfferOp": const(3),
"StellarPathPaymentOp": const(2),
"StellarPaymentOp": const(1),
"StellarSetOptionsOp": const(5),
}
op_wire_types = [
wire_types.StellarAccountMergeOp,
wire_types.StellarAllowTrustOp,
wire_types.StellarBumpSequenceOp,
wire_types.StellarChangeTrustOp,
wire_types.StellarCreateAccountOp,
wire_types.StellarCreatePassiveOfferOp,
wire_types.StellarManageDataOp,
wire_types.StellarManageOfferOp,
wire_types.StellarPathPaymentOp,
wire_types.StellarPaymentOp,
wire_types.StellarSetOptionsOp,
MessageType.StellarAccountMergeOp,
MessageType.StellarAllowTrustOp,
MessageType.StellarBumpSequenceOp,
MessageType.StellarChangeTrustOp,
MessageType.StellarCreateAccountOp,
MessageType.StellarCreatePassiveOfferOp,
MessageType.StellarManageDataOp,
MessageType.StellarManageOfferOp,
MessageType.StellarPathPaymentOp,
MessageType.StellarPaymentOp,
MessageType.StellarSetOptionsOp,
]
# https://github.com/stellar/go/blob/e0ffe19f58879d3c31e2976b97a5bf10e13a337b/xdr/xdr_generated.go#L584
@ -44,8 +45,8 @@ ASSET_TYPE_ALPHANUM12 = const(2)
AMOUNT_DIVISIBILITY = const(7)
# https://github.com/stellar/go/blob/master/network/main.go
NETWORK_PASSPHRASE_PUBLIC = 'Public Global Stellar Network ; September 2015'
NETWORK_PASSPHRASE_TESTNET = 'Test SDF Network ; September 2015'
NETWORK_PASSPHRASE_PUBLIC = "Public Global Stellar Network ; September 2015"
NETWORK_PASSPHRASE_TESTNET = "Test SDF Network ; September 2015"
# https://www.stellar.org/developers/guides/concepts/accounts.html#flags
FLAG_AUTH_REQUIRED = const(1)
@ -68,5 +69,5 @@ SIGN_TYPE_HASH = const(2)
def get_op_code(msg) -> int:
if msg.__qualname__ not in op_codes:
raise ValueError('Stellar: op code unknown')
raise ValueError("Stellar: op code unknown")
return op_codes[msg.__qualname__]

View File

@ -1,8 +1,9 @@
from trezor.messages.StellarAddress import StellarAddress
from trezor.messages.StellarGetAddress import StellarGetAddress
from apps.common import seed
from apps.common.display_address import show_address, show_qr
from apps.stellar import helpers
from trezor.messages.StellarAddress import StellarAddress
from trezor.messages.StellarGetAddress import StellarGetAddress
async def get_address(ctx, msg: StellarGetAddress):

View File

@ -1,13 +1,15 @@
from ubinascii import hexlify
from trezor import ui
from trezor.messages import ButtonRequestType
from trezor.messages.StellarGetPublicKey import StellarGetPublicKey
from trezor.messages.StellarPublicKey import StellarPublicKey
from trezor.ui.text import Text
from apps.common import seed
from apps.common.confirm import confirm
from apps.common.display_address import split_address
from apps.stellar import helpers
from trezor import ui
from trezor.messages.StellarPublicKey import StellarPublicKey
from trezor.messages.StellarGetPublicKey import StellarGetPublicKey
from trezor.messages import ButtonRequestType
from trezor.ui.text import Text
from ubinascii import hexlify
async def get_public_key(ctx, msg: StellarGetPublicKey):
@ -24,13 +26,16 @@ async def get_public_key(ctx, msg: StellarGetPublicKey):
async def _show(ctx, pubkey: bytes):
lines = split_address(hexlify(pubkey))
content = Text('Export Stellar ID', ui.ICON_RECEIVE,
ui.NORMAL, 'Share public account ID?', # todo only two lines are displayed
ui.MONO, *lines,
icon_color=ui.GREEN)
content = Text(
"Export Stellar ID",
ui.ICON_RECEIVE,
ui.NORMAL,
"Share public account ID?", # todo only two lines are displayed
ui.MONO,
*lines,
icon_color=ui.GREEN
)
return await confirm(
ctx,
content,
code=ButtonRequestType.Address,
cancel_style=ui.BTN_KEY)
ctx, content, code=ButtonRequestType.Address, cancel_style=ui.BTN_KEY
)

View File

@ -1,8 +1,9 @@
from trezor.crypto import base32
from trezor.wire import ProcessError
import ustruct
STELLAR_CURVE = 'ed25519'
from trezor.crypto import base32
from trezor.wire import ProcessError
STELLAR_CURVE = "ed25519"
def public_key_from_address(address: str) -> bytes:
@ -27,7 +28,7 @@ def address_from_public_key(pubkey: bytes):
def _crc16_checksum_verify(data: bytes, checksum: bytes):
if _crc16_checksum(data) != checksum:
raise ProcessError('Invalid address checksum')
raise ProcessError("Invalid address checksum")
def _crc16_checksum(data: bytes) -> bytes:
@ -42,8 +43,8 @@ def _crc16_checksum(data: bytes) -> bytes:
for byte in data:
for i in range(8):
bit = ((byte >> (7 - i) & 1) == 1)
c15 = ((crc >> 15 & 1) == 1)
bit = (byte >> (7 - i) & 1) == 1
c15 = (crc >> 15 & 1) == 1
crc <<= 1
if c15 ^ bit:
crc ^= polynomial

View File

@ -1,63 +1,59 @@
from apps.common.confirm import require_confirm, require_hold_to_confirm
from apps.stellar import consts
from trezor import ui
from trezor import ui, utils
from trezor.messages import ButtonRequestType
from trezor.ui.text import Text
from trezor import utils
from apps.common.confirm import require_confirm, require_hold_to_confirm
from apps.stellar import consts
async def require_confirm_init(ctx, address: str, network_passphrase: str):
content = Text('Confirm Stellar', ui.ICON_SEND,
ui.NORMAL, 'Initialize singing with',
ui.MONO, *split(address),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm Stellar", ui.ICON_SEND, icon_color=ui.GREEN)
text.normal("Initialize singing with")
text.mono(*split(address))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
network = get_network_warning(network_passphrase)
if network:
content = Text('Confirm network', ui.ICON_CONFIRM,
ui.NORMAL, 'Transaction is on',
ui.BOLD, network,
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm network", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.normal("Transaction is on")
text.bold(network)
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def require_confirm_memo(ctx, memo_type: int, memo_text: str):
if memo_type == consts.MEMO_TYPE_TEXT:
title = 'Memo (TEXT)'
title = "Memo (TEXT)"
elif memo_type == consts.MEMO_TYPE_ID:
title = 'Memo (ID)'
title = "Memo (ID)"
elif memo_type == consts.MEMO_TYPE_HASH:
title = 'Memo (HASH)'
title = "Memo (HASH)"
elif memo_type == consts.MEMO_TYPE_RETURN:
title = 'Memo (RETURN)'
title = "Memo (RETURN)"
else: # MEMO_TYPE_NONE
title = 'No memo set!' # todo format this as ui.NORMAL not MONO
memo_text = 'Important: Many exchanges require a memo when depositing'
content = Text('Confirm memo', ui.ICON_CONFIRM,
ui.BOLD, title,
ui.MONO, *split(memo_text),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
title = "No memo set!" # todo format this as ui.NORMAL not MONO
memo_text = "Important: Many exchanges require a memo when depositing"
text = Text("Confirm memo", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(title)
text.mono(*split(memo_text))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def require_confirm_final(ctx, fee: int, num_operations: int):
op_str = str(num_operations) + ' operation'
op_str = str(num_operations) + " operation"
if num_operations > 1:
op_str += 's'
content = Text('Final confirm', ui.ICON_SEND,
ui.NORMAL, 'Sign this transaction',
ui.NORMAL, 'made up of ' + op_str,
ui.BOLD, 'and pay ' + format_amount(fee),
ui.NORMAL, 'for fee?',
icon_color=ui.GREEN)
op_str += "s"
text = Text("Final confirm", ui.ICON_SEND, icon_color=ui.GREEN)
text.normal("Sign this transaction")
text.normal("made up of " + op_str)
text.bold("and pay " + format_amount(fee))
text.normal("for fee?")
# we use SignTx, not ConfirmOutput, for compatibility with T1
await require_hold_to_confirm(ctx, content, ButtonRequestType.SignTx)
await require_hold_to_confirm(ctx, text, ButtonRequestType.SignTx)
def format_amount(amount: int, ticker=True) -> str:
t = ''
t = ""
if ticker:
t = ' XLM'
t = " XLM"
return utils.format_amount(amount, consts.AMOUNT_DIVISIBILITY) + t
@ -70,13 +66,13 @@ def split(text):
def trim(payload: str, length: int, dots=True) -> str:
if len(payload) > length:
if dots:
return payload[:length - 2] + '..'
return payload[:length - 2]
return payload[: length - 2] + ".."
return payload[: length - 2]
return payload
# todo merge with nem
def trim_to_rows(payload: str, rows: int=1) -> str:
def trim_to_rows(payload: str, rows: int = 1) -> str:
return trim(payload, rows * 17)
@ -84,5 +80,5 @@ def get_network_warning(network_passphrase: str):
if network_passphrase == consts.NETWORK_PASSPHRASE_PUBLIC:
return None
if network_passphrase == consts.NETWORK_PASSPHRASE_TESTNET:
return 'testnet network'
return 'private network'
return "testnet network"
return "private network"

View File

@ -1,7 +1,5 @@
from apps.stellar.operations import serialize
from apps.stellar.operations import layout
from apps.stellar import consts
from apps.stellar import writers
from apps.stellar import consts, writers
from apps.stellar.operations import layout, serialize
async def operation(ctx, w, op):
@ -43,4 +41,4 @@ async def operation(ctx, w, op):
await layout.confirm_set_options_op(ctx, op)
serialize.serialize_set_options_op(w, op)
else:
raise ValueError('serialize.Stellar: unknown operation')
raise ValueError("serialize.Stellar: unknown operation")

View File

@ -1,10 +1,9 @@
from apps.stellar.layout import split, format_amount, ui, trim_to_rows, require_confirm
from apps.stellar import consts
from ubinascii import hexlify
from trezor.messages import ButtonRequestType
from trezor.ui.text import Text
from trezor.messages.StellarAccountMergeOp import StellarAccountMergeOp
from trezor.messages.StellarAssetType import StellarAssetType
from trezor.messages.StellarAllowTrustOp import StellarAllowTrustOp
from trezor.messages.StellarAssetType import StellarAssetType
from trezor.messages.StellarBumpSequenceOp import StellarBumpSequenceOp
from trezor.messages.StellarChangeTrustOp import StellarChangeTrustOp
from trezor.messages.StellarCreateAccountOp import StellarCreateAccountOp
@ -14,252 +13,238 @@ from trezor.messages.StellarManageOfferOp import StellarManageOfferOp
from trezor.messages.StellarPathPaymentOp import StellarPathPaymentOp
from trezor.messages.StellarPaymentOp import StellarPaymentOp
from trezor.messages.StellarSetOptionsOp import StellarSetOptionsOp
from trezor.ui.text import Text
from trezor.wire import ProcessError
from ubinascii import hexlify
from apps.stellar import consts
from apps.stellar.layout import format_amount, require_confirm, split, trim_to_rows, ui
async def confirm_source_account(ctx, source_account: bytes):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Source account:',
ui.MONO, *split(source_account),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Source account:")
text.mono(*split(source_account))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_allow_trust_op(ctx, op: StellarAllowTrustOp):
if op.is_authorized:
text = 'Allow Trust'
text = "Allow Trust"
else:
text = 'Revoke Trust'
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, text,
ui.NORMAL, 'of %s by:' % op.asset_code,
ui.MONO, *split(trim_to_rows(op.trusted_account, 3)),
icon_color=ui.GREEN)
text = "Revoke Trust"
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(text)
text.normal("of %s by:" % op.asset_code)
text.mono(*split(trim_to_rows(op.trusted_account, 3)))
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_account_merge_op(ctx, op: StellarAccountMergeOp):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Account Merge',
ui.NORMAL, 'All XLM will be sent to:',
ui.MONO, *split(trim_to_rows(op.destination_account, 3)),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Account Merge")
text.normal("All XLM will be sent to:")
text.mono(*split(trim_to_rows(op.destination_account, 3)))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_bump_sequence_op(ctx, op: StellarBumpSequenceOp):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Bump Sequence',
ui.NORMAL, 'Set sequence to',
ui.MONO, str(op.bump_to),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Bump Sequence")
text.normal("Set sequence to")
text.mono(str(op.bump_to))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_change_trust_op(ctx, op: StellarChangeTrustOp):
if op.limit == 0:
text = 'Delete Trust'
text = "Delete Trust"
else:
text = 'Add Trust'
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, text,
ui.NORMAL, 'Asset: %s' % op.asset.code,
ui.NORMAL, 'Amount: %s' % format_amount(op.limit, ticker=False),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = "Add Trust"
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(text)
text.normal("Asset: %s" % op.asset.code)
text.normal("Amount: %s" % format_amount(op.limit, ticker=False))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
await confirm_asset_issuer(ctx, op.asset)
async def confirm_create_account_op(ctx, op: StellarCreateAccountOp):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Create Account',
ui.NORMAL, 'with %s' % format_amount(op.starting_balance),
ui.MONO, *split(trim_to_rows(op.new_account, 3)),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Create Account")
text.normal("with %s" % format_amount(op.starting_balance))
text.mono(*split(trim_to_rows(op.new_account, 3)))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_create_passive_offer_op(ctx, op: StellarCreatePassiveOfferOp):
if op.amount == 0:
text = 'Delete Passive Offer'
text = "Delete Passive Offer"
else:
text = 'New Passive Offer'
text = "New Passive Offer"
await _confirm_offer(ctx, text, op)
async def confirm_manage_offer_op(ctx, op: StellarManageOfferOp):
if op.offer_id == 0:
text = 'New Offer'
text = "New Offer"
else:
if op.amount == 0:
text = 'Delete'
text = "Delete"
else:
text = 'Update'
text += ' #%d' % op.offer_id
text = "Update"
text += " #%d" % op.offer_id
await _confirm_offer(ctx, text, op)
async def _confirm_offer(ctx, text, op):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, text,
ui.NORMAL, 'Sell %s %s' % (format_amount(op.amount, ticker=False), op.selling_asset.code),
ui.NORMAL, 'For %f' % (op.price_n / op.price_d),
ui.NORMAL, 'Per %s' % format_asset_code(op.buying_asset),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(text)
text.normal(
"Sell %s %s" % (format_amount(op.amount, ticker=False), op.selling_asset.code)
)
text.normal("For %f" % (op.price_n / op.price_d))
text.normal("Per %s" % format_asset_code(op.buying_asset))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
await confirm_asset_issuer(ctx, op.selling_asset)
await confirm_asset_issuer(ctx, op.buying_asset)
async def confirm_manage_data_op(ctx, op: StellarManageDataOp):
from trezor.crypto.hashlib import sha256
if op.value:
title = 'Set'
title = "Set"
else:
title = 'Clear'
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, '%s data value key' % title,
ui.MONO, *split(op.key),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
title = "Clear"
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("%s data value key" % title)
text.mono(*split(op.key))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
if op.value:
digest = sha256(op.value).digest()
digest_str = hexlify(digest).decode()
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Value (SHA-256):',
ui.MONO, *split(digest_str),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Value (SHA-256):")
text.mono(*split(digest_str))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
async def confirm_path_payment_op(ctx, op: StellarPathPaymentOp):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Path Pay %s' % format_amount(op.destination_amount, ticker=False),
ui.BOLD, '%s to:' % format_asset_code(op.destination_asset),
ui.MONO, *split(trim_to_rows(op.destination_account, 3)),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Path Pay %s" % format_amount(op.destination_amount, ticker=False))
text.bold("%s to:" % format_asset_code(op.destination_asset))
text.mono(*split(trim_to_rows(op.destination_account, 3)))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
await confirm_asset_issuer(ctx, op.destination_asset)
# confirm what the sender is using to pay
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.NORMAL, 'Pay using',
ui.BOLD, format_amount(op.send_max, ticker=False),
ui.BOLD, format_asset_code(op.send_asset),
ui.NORMAL, 'This amount is debited',
ui.NORMAL, 'from your account.',
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.normal("Pay using")
text.bold(format_amount(op.send_max, ticker=False))
text.bold(format_asset_code(op.send_asset))
text.normal("This amount is debited")
text.normal("from your account.")
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
await confirm_asset_issuer(ctx, op.send_asset)
async def confirm_payment_op(ctx, op: StellarPaymentOp):
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Pay %s' % format_amount(op.amount, ticker=False),
ui.BOLD, '%s to:' % format_asset_code(op.asset),
ui.MONO, *split(trim_to_rows(op.destination_account, 3)),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Pay %s" % format_amount(op.amount, ticker=False))
text.bold("%s to:" % format_asset_code(op.asset))
text.mono(*split(trim_to_rows(op.destination_account, 3)))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
await confirm_asset_issuer(ctx, op.asset)
async def confirm_set_options_op(ctx, op: StellarSetOptionsOp):
if op.inflation_destination_account:
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Set Inflation Destination',
ui.MONO, *split(op.inflation_destination_account),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Set Inflation Destination")
text.mono(*split(op.inflation_destination_account))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
if op.clear_flags:
text = _format_flags(op.clear_flags)
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Clear Flags',
ui.MONO, *text,
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Clear Flags")
text.mono(*text)
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
if op.set_flags:
text = _format_flags(op.set_flags)
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Set Flags',
ui.MONO, *text,
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Set Flags")
text.mono(*text)
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
thresholds = _format_thresholds(op)
if thresholds:
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Account Thresholds',
ui.MONO, *thresholds,
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Account Thresholds")
text.mono(*thresholds)
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
if op.home_domain:
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, 'Home Domain',
ui.MONO, *split(op.home_domain),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("Home Domain")
text.mono(*split(op.home_domain))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
if op.signer_type is not None:
if op.signer_weight > 0:
text = 'Add Signer (%s)'
text = "Add Signer (%s)"
else:
text = 'Remove Signer (%s)'
text = "Remove Signer (%s)"
if op.signer_type == consts.SIGN_TYPE_ACCOUNT:
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, text % 'acc',
ui.MONO, *split(op.signer_key),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(text % "acc")
text.mono(*split(op.signer_key))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
elif op.signer_type in (consts.SIGN_TYPE_PRE_AUTH, consts.SIGN_TYPE_HASH):
if op.signer_type == consts.SIGN_TYPE_PRE_AUTH:
signer_type = 'auth'
signer_type = "auth"
else:
signer_type = 'hash'
content = Text('Confirm operation', ui.ICON_CONFIRM,
ui.BOLD, text % signer_type,
ui.MONO, *split(hexlify(op.signer_key).decode()),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
signer_type = "hash"
text = Text("Confirm operation", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold(text % signer_type)
text.mono(*split(hexlify(op.signer_key).decode()))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)
else:
raise ProcessError('Stellar: invalid signer type')
raise ProcessError("Stellar: invalid signer type")
def _format_thresholds(op: StellarSetOptionsOp) -> tuple:
text = ()
if op.master_weight is not None:
text += ('Master Weight: %d' % op.master_weight, )
text += ("Master Weight: %d" % op.master_weight,)
if op.low_threshold is not None:
text += ('Low: %d' % op.low_threshold, )
text += ("Low: %d" % op.low_threshold,)
if op.medium_threshold is not None:
text += ('Medium: %d' % op.medium_threshold, )
text += ("Medium: %d" % op.medium_threshold,)
if op.high_threshold is not None:
text += ('High: %d' % op.high_threshold, )
text += ("High: %d" % op.high_threshold,)
return text
def _format_flags(flags: int) -> tuple:
if flags > consts.FLAGS_MAX_SIZE:
raise ProcessError('Stellar: invalid flags')
raise ProcessError("Stellar: invalid flags")
text = ()
if flags & consts.FLAG_AUTH_REQUIRED:
text += ('AUTH_REQUIRED', )
text += ("AUTH_REQUIRED",)
if flags & consts.FLAG_AUTH_REVOCABLE:
text += ('AUTH_REVOCABLE', )
text += ("AUTH_REVOCABLE",)
if flags & consts.FLAG_AUTH_IMMUTABLE:
text += ('AUTH_IMMUTABLE', )
text += ("AUTH_IMMUTABLE",)
return text
def format_asset_code(asset: StellarAssetType) -> str:
if asset is None or asset.type == consts.ASSET_TYPE_NATIVE:
return 'XLM (native)'
return "XLM (native)"
return asset.code
async def confirm_asset_issuer(ctx, asset: StellarAssetType):
if asset is None or asset.type == consts.ASSET_TYPE_NATIVE:
return
content = Text('Confirm issuer', ui.ICON_CONFIRM,
ui.BOLD, '%s issuer:' % asset.code,
ui.MONO, *split(asset.issuer),
icon_color=ui.GREEN)
await require_confirm(ctx, content, ButtonRequestType.ConfirmOutput)
text = Text("Confirm issuer", ui.ICON_CONFIRM, icon_color=ui.GREEN)
text.bold("%s issuer:" % asset.code)
text.mono(*split(asset.issuer))
await require_confirm(ctx, text, ButtonRequestType.ConfirmOutput)

View File

@ -1,8 +1,6 @@
from apps.stellar import writers
from apps.stellar import consts
from trezor.messages.StellarAccountMergeOp import StellarAccountMergeOp
from trezor.messages.StellarAssetType import StellarAssetType
from trezor.messages.StellarAllowTrustOp import StellarAllowTrustOp
from trezor.messages.StellarAssetType import StellarAssetType
from trezor.messages.StellarBumpSequenceOp import StellarBumpSequenceOp
from trezor.messages.StellarChangeTrustOp import StellarChangeTrustOp
from trezor.messages.StellarCreateAccountOp import StellarCreateAccountOp
@ -14,6 +12,8 @@ from trezor.messages.StellarPaymentOp import StellarPaymentOp
from trezor.messages.StellarSetOptionsOp import StellarSetOptionsOp
from trezor.wire import ProcessError
from apps.stellar import consts, writers
def serialize_account_merge_op(w, msg: StellarAccountMergeOp):
writers.write_pubkey(w, msg.destination_account)
@ -52,7 +52,7 @@ def serialize_create_passive_offer_op(w, msg: StellarCreatePassiveOfferOp):
def serialize_manage_data_op(w, msg: StellarManageDataOp):
if len(msg.key) > 64:
raise ProcessError('Stellar: max length of a key is 64 bytes')
raise ProcessError("Stellar: max length of a key is 64 bytes")
writers.write_string(w, msg.key)
writers.write_bool(w, bool(msg.value))
if msg.value:
@ -124,7 +124,7 @@ def serialize_set_options_op(w, msg: StellarSetOptionsOp):
writers.write_bool(w, bool(msg.home_domain))
if msg.home_domain:
if len(msg.home_domain) > 32:
raise ProcessError('Stellar: max length of a home domain is 32 bytes')
raise ProcessError("Stellar: max length of a home domain is 32 bytes")
writers.write_string(w, msg.home_domain)
# signer
@ -154,7 +154,7 @@ def _serialize_asset_code(w, asset_type: int, asset_code: str):
# pad with zeros to 12 chars
writers.write_bytes(w, code + bytearray([0] * (12 - len(code))))
else:
raise ProcessError('Stellar: invalid asset type')
raise ProcessError("Stellar: invalid asset type")
def _serialize_asset(w, asset: StellarAssetType):

View File

@ -1,21 +1,20 @@
from apps.common import seed
from apps.stellar import writers
from apps.stellar.operations import operation
from apps.stellar import helpers
from apps.stellar import layout
from apps.stellar import consts
from trezor.wire import ProcessError
from trezor.messages.StellarSignTx import StellarSignTx
from trezor.messages.StellarTxOpRequest import StellarTxOpRequest
from trezor.messages.StellarSignedTx import StellarSignedTx
from ubinascii import hexlify
from trezor.crypto.curve import ed25519
from trezor.crypto.hashlib import sha256
from ubinascii import hexlify
from trezor.messages.StellarSignedTx import StellarSignedTx
from trezor.messages.StellarSignTx import StellarSignTx
from trezor.messages.StellarTxOpRequest import StellarTxOpRequest
from trezor.wire import ProcessError
from apps.common import seed
from apps.stellar import consts, helpers, layout, writers
from apps.stellar.operations import operation
async def sign_tx(ctx, msg: StellarSignTx):
if msg.num_operations == 0:
raise ProcessError('Stellar: At least one operation is required')
raise ProcessError("Stellar: At least one operation is required")
node = await seed.derive_node(ctx, msg.address_n, consts.STELLAR_CURVE)
pubkey = seed.remove_ed25519_prefix(node.public_key())
@ -50,7 +49,7 @@ async def _init(ctx, w: bytearray, pubkey: bytes, msg: StellarSignTx):
address = helpers.address_from_public_key(pubkey)
writers.write_pubkey(w, address)
if helpers.public_key_from_address(msg.source_account) != pubkey:
raise ProcessError('Stellar: source account does not match address_n')
raise ProcessError("Stellar: source account does not match address_n")
writers.write_uint32(w, msg.fee)
writers.write_uint64(w, msg.sequence_number)
@ -80,11 +79,11 @@ async def _memo(ctx, w: bytearray, msg: StellarSignTx):
writers.write_uint32(w, msg.memo_type)
if msg.memo_type == consts.MEMO_TYPE_NONE:
# nothing is serialized
memo_confirm_text = ''
memo_confirm_text = ""
elif msg.memo_type == consts.MEMO_TYPE_TEXT:
# Text: 4 bytes (size) + up to 28 bytes
if len(msg.memo_text) > 28:
raise ProcessError('Stellar: max length of a memo text is 28 bytes')
raise ProcessError("Stellar: max length of a memo text is 28 bytes")
writers.write_string(w, msg.memo_text)
memo_confirm_text = msg.memo_text
elif msg.memo_type == consts.MEMO_TYPE_ID:
@ -96,7 +95,7 @@ async def _memo(ctx, w: bytearray, msg: StellarSignTx):
writers.write_bytes(w, bytearray(msg.memo_hash))
memo_confirm_text = hexlify(msg.memo_hash).decode()
else:
raise ProcessError('Stellar invalid memo type')
raise ProcessError("Stellar invalid memo type")
await layout.require_confirm_memo(ctx, msg.memo_type, memo_confirm_text)

View File

@ -1,13 +1,14 @@
import ustruct
from .helpers import public_key_from_address
def write_uint32(w, n: int):
write_bytes(w, ustruct.pack('>L', n))
write_bytes(w, ustruct.pack(">L", n))
def write_uint64(w, n: int):
write_bytes(w, ustruct.pack('>Q', n))
write_bytes(w, ustruct.pack(">Q", n))
def write_string(w, s: str):