mirror of
https://github.com/trezor/trezor-firmware.git
synced 2024-12-16 19:38:09 +00:00
85 lines
2.2 KiB
Python
85 lines
2.2 KiB
Python
from micropython import const
|
|
|
|
from trezor import ui
|
|
from trezor.messages import ButtonRequestType
|
|
from trezor.ui.text import Text
|
|
|
|
from apps.common import HARDENED
|
|
from apps.common.confirm import require_confirm
|
|
|
|
if False:
|
|
from typing import Any, Callable, List
|
|
from trezor import wire
|
|
from apps.common import seed
|
|
|
|
|
|
async def validate_path(
|
|
ctx: wire.Context,
|
|
validate_func: Callable[..., bool],
|
|
keychain: seed.Keychain,
|
|
path: List[int],
|
|
curve: str,
|
|
**kwargs: Any,
|
|
) -> None:
|
|
keychain.validate_path(path, curve)
|
|
if not validate_func(path, **kwargs):
|
|
await show_path_warning(ctx, path)
|
|
|
|
|
|
async def show_path_warning(ctx: wire.Context, path: List[int]) -> None:
|
|
text = Text("Confirm path", ui.ICON_WRONG, ui.RED)
|
|
text.normal("Path")
|
|
text.mono(*break_address_n_to_lines(path))
|
|
text.normal("is unknown.")
|
|
text.normal("Are you sure?")
|
|
await require_confirm(ctx, text, ButtonRequestType.UnknownDerivationPath)
|
|
|
|
|
|
def validate_path_for_get_public_key(path: list, slip44_id: int) -> bool:
|
|
"""
|
|
Checks if path has at least three hardened items and slip44 id matches.
|
|
The path is allowed to have more than three items, but all the following
|
|
items have to be non-hardened.
|
|
"""
|
|
length = len(path)
|
|
if length < 3 or length > 5:
|
|
return False
|
|
if path[0] != 44 | HARDENED:
|
|
return False
|
|
if path[1] != slip44_id | HARDENED:
|
|
return False
|
|
if path[2] < HARDENED or path[2] > 20 | HARDENED:
|
|
return False
|
|
if length > 3 and is_hardened(path[3]):
|
|
return False
|
|
if length > 4 and is_hardened(path[4]):
|
|
return False
|
|
return True
|
|
|
|
|
|
def is_hardened(i: int) -> bool:
|
|
if i & HARDENED:
|
|
return True
|
|
else:
|
|
return False
|
|
|
|
|
|
def break_address_n_to_lines(address_n: list) -> list:
|
|
def path_item(i: int) -> str:
|
|
if i & HARDENED:
|
|
return str(i ^ HARDENED) + "'"
|
|
else:
|
|
return str(i)
|
|
|
|
lines = []
|
|
path_str = "m/" + "/".join([path_item(i) for i in address_n])
|
|
|
|
per_line = const(17)
|
|
while len(path_str) > per_line:
|
|
i = path_str[:per_line].rfind("/")
|
|
lines.append(path_str[:i])
|
|
path_str = path_str[i:]
|
|
lines.append(path_str)
|
|
|
|
return lines
|