def test_decode_check(self):
     for a, b in self.vectors:
         self.assertEqual(base58.decode_check(b), unhexlify(a))
     for a, b in self.vectors_graphene:
         self.assertEqual(
             base58.decode_check(b, digestfunc=digestfunc_graphene),
             unhexlify(a))
Exemplo n.º 2
0
async def layout_verify_message(ctx, msg):
    from trezor.messages.Success import Success
    from trezor.crypto.curve import secp256k1
    from trezor.crypto.hashlib import ripemd160, sha256
    from trezor.crypto import base58
    from ..common import address_type
    from ..common import coins
    from ..common.signverify import message_digest

    coin_name = msg.coin_name or 'Bitcoin'
    coin = coins.by_name(coin_name)

    digest = message_digest(coin, msg.message)
    pubkey = secp256k1.verify_recover(msg.signature, digest)

    if not pubkey:
        raise ValueError('Invalid signature')

    raw_address = base58.decode_check(msg.address)
    at, pkh = address_type.split(coin, raw_address)
    pkh2 = ripemd160(sha256(pubkey).digest()).digest()

    if pkh != pkh2:
        raise ValueError('Invalid signature')

    ui.display.clear()
    ui.display.text(10, 30, 'Verifying message', ui.BOLD, ui.LIGHT_GREEN,
                    ui.BG)
    ui.display.text(10, 60, msg.message, ui.MONO, ui.FG, ui.BG)
    ui.display.text(10, 80, msg.address, ui.MONO, ui.FG, ui.BG)

    return Success(message='Message verified')
Exemplo n.º 3
0
def output_derive_script(address: str, coin: CoinInfo) -> bytes:
    if coin.bech32_prefix and address.startswith(coin.bech32_prefix):
        # p2wpkh or p2wsh
        witprog = common.decode_bech32_address(coin.bech32_prefix, address)
        return output_script_native_p2wpkh_or_p2wsh(witprog)

    if (not utils.BITCOIN_ONLY and coin.cashaddr_prefix is not None
            and address.startswith(coin.cashaddr_prefix + ":")):
        prefix, addr = address.split(":")
        version, data = cashaddr.decode(prefix, addr)
        if version == cashaddr.ADDRESS_TYPE_P2KH:
            version = coin.address_type
        elif version == cashaddr.ADDRESS_TYPE_P2SH:
            version = coin.address_type_p2sh
        else:
            raise wire.DataError("Unknown cashaddr address type")
        raw_address = bytes([version]) + data
    else:
        try:
            raw_address = base58.decode_check(address, coin.b58_hash)
        except ValueError:
            raise wire.DataError("Invalid address")

    if address_type.check(coin.address_type, raw_address):
        # p2pkh
        pubkeyhash = address_type.strip(coin.address_type, raw_address)
        script = output_script_p2pkh(pubkeyhash)
        return script
    elif address_type.check(coin.address_type_p2sh, raw_address):
        # p2sh
        scripthash = address_type.strip(coin.address_type_p2sh, raw_address)
        script = output_script_p2sh(scripthash)
        return script

    raise wire.DataError("Invalid address type")
Exemplo n.º 4
0
def output_derive_script(o: TxOutputType, coin: CoinInfo, root: bip32.HDNode) -> bytes:

    if o.script_type == OutputScriptType.PAYTOOPRETURN:
        # op_return output
        if o.amount != 0:
            raise SigningError(
                FailureType.DataError, "OP_RETURN output with non-zero amount"
            )
        return output_script_paytoopreturn(o.op_return_data)

    if o.address_n:
        # change output
        if o.address:
            raise SigningError(FailureType.DataError, "Address in change output")
        o.address = get_address_for_change(o, coin, root)
    else:
        if not o.address:
            raise SigningError(FailureType.DataError, "Missing address")

    if coin.bech32_prefix and o.address.startswith(coin.bech32_prefix):
        # p2wpkh or p2wsh
        witprog = decode_bech32_address(coin.bech32_prefix, o.address)
        return output_script_native_p2wpkh_or_p2wsh(witprog)

    if coin.cashaddr_prefix is not None and o.address.startswith(
        coin.cashaddr_prefix + ":"
    ):
        prefix, addr = o.address.split(":")
        version, data = cashaddr.decode(prefix, addr)
        if version == cashaddr.ADDRESS_TYPE_P2KH:
            version = coin.address_type
        elif version == cashaddr.ADDRESS_TYPE_P2SH:
            version = coin.address_type_p2sh
        else:
            raise ValueError("Unknown cashaddr address type")
        raw_address = bytes([version]) + data
    else:
        raw_address = base58.decode_check(o.address, coin.b58_hash)

    if address_type.check(coin.address_type, raw_address):
        # p2pkh
        pubkeyhash = address_type.strip(coin.address_type, raw_address)
        script = output_script_p2pkh(pubkeyhash)
        if coin.bip115:
            script += script_replay_protection_bip115(
                o.block_hash_bip115, o.block_height_bip115
            )
        return script

    elif address_type.check(coin.address_type_p2sh, raw_address):
        # p2sh
        scripthash = address_type.strip(coin.address_type_p2sh, raw_address)
        script = output_script_p2sh(scripthash)
        if coin.bip115:
            script += script_replay_protection_bip115(
                o.block_hash_bip115, o.block_height_bip115
            )
        return script

    raise SigningError(FailureType.DataError, "Invalid address type")
Exemplo n.º 5
0
def output_derive_script(o: TxOutputType, coin: CoinType, root) -> bytes:

    if o.script_type == OutputScriptType.PAYTOOPRETURN:
        if o.amount != 0:
            raise SigningError(FailureType.DataError,
                               'OP_RETURN output with non-zero amount')
        return output_script_paytoopreturn(o.op_return_data)

    if o.address_n:  # change output
        if o.address:
            raise SigningError(FailureType.DataError,
                               'Address in change output')
        o.address = get_address_for_change(o, coin, root)
    else:
        if not o.address:
            raise SigningError(FailureType.DataError, 'Missing address')

    if coin.bech32_prefix and o.address.startswith(
            coin.bech32_prefix):  # p2wpkh or p2wsh
        witprog = decode_bech32_address(coin.bech32_prefix, o.address)
        return output_script_native_p2wpkh_or_p2wsh(witprog)

    raw_address = base58.decode_check(o.address)

    if address_type.check(coin.address_type, raw_address):  # p2pkh
        pubkeyhash = address_type.strip(coin.address_type, raw_address)
        return output_script_p2pkh(pubkeyhash)

    elif address_type.check(coin.address_type_p2sh, raw_address):  # p2sh
        scripthash = address_type.strip(coin.address_type_p2sh, raw_address)
        return output_script_p2sh(scripthash)

    raise SigningError(FailureType.DataError, 'Invalid address type')
Exemplo n.º 6
0
def output_paytoaddress_extract_raw_address(
        o: TxOutputType, coin: CoinType, root, p2sh: bool=False) -> bytes:
    addr_type = coin.address_type_p2sh if p2sh else coin.address_type
    # TODO: dont encode/decode more then necessary
    if o.address_n is not None:
        node = node_derive(root, o.address_n)
        address = node.address(addr_type)
        return base58.decode_check(address)
    if o.address:
        raw = base58.decode_check(o.address)
        if not address_type.check(addr_type, raw):
            raise SigningError(FailureType.SyntaxError,
                               'Invalid address type')
        return raw
    raise SigningError(FailureType.SyntaxError,
                       'Missing address')
Exemplo n.º 7
0
def address_to_script_type(address: str, coin: CoinInfo) -> InputScriptType:
    # Determines the script type from a non-multisig address.

    if coin.bech32_prefix and address.startswith(coin.bech32_prefix):
        witver, _ = common.decode_bech32_address(coin.bech32_prefix, address)
        if witver == 0:
            return InputScriptType.SPENDWITNESS
        elif witver == 1:
            return InputScriptType.SPENDTAPROOT
        else:
            raise wire.DataError("Invalid address")

    if (not utils.BITCOIN_ONLY and coin.cashaddr_prefix is not None
            and address.startswith(coin.cashaddr_prefix + ":")):
        return InputScriptType.SPENDADDRESS

    try:
        raw_address = base58.decode_check(address, coin.b58_hash)
    except ValueError:
        raise wire.DataError("Invalid address")

    if address_type.check(coin.address_type, raw_address):
        # p2pkh
        return InputScriptType.SPENDADDRESS
    elif address_type.check(coin.address_type_p2sh, raw_address):
        # p2sh
        return InputScriptType.SPENDP2SHWITNESS

    raise wire.DataError("Invalid address")
Exemplo n.º 8
0
def address_to_cashaddr(address: str, coin: CoinInfo) -> str:
    raw = base58.decode_check(address, coin.b58_hash)
    version, data = raw[0], raw[1:]
    if version == coin.address_type:
        version = cashaddr.ADDRESS_TYPE_P2KH
    elif version == coin.address_type_p2sh:
        version = cashaddr.ADDRESS_TYPE_P2SH
    else:
        raise ValueError("Unknown cashaddr address type")
    return cashaddr.encode(coin.cashaddr_prefix, version, data)
Exemplo n.º 9
0
def output_script_sstxchange(addr: str) -> bytearray:
    try:
        raw_address = base58.decode_check(addr, blake256d_32)
    except ValueError:
        raise wire.DataError("Invalid address")

    w = utils.empty_bytearray(26)
    w.append(0xBD)  # OP_SSTXCHANGE
    scripts.write_output_script_p2pkh(w, raw_address[2:])
    return w
Exemplo n.º 10
0
def output_derive_script(
    o: TxOutputType, coin: coininfo.CoinInfo, keychain: seed.Keychain
) -> bytes:

    if o.script_type == OutputScriptType.PAYTOOPRETURN:
        return scripts.output_script_paytoopreturn(o.op_return_data)

    if o.address_n:
        # change output
        o.address = get_address_for_change(o, coin, keychain)

    if coin.bech32_prefix and o.address.startswith(coin.bech32_prefix):
        # p2wpkh or p2wsh
        witprog = addresses.decode_bech32_address(coin.bech32_prefix, o.address)
        return scripts.output_script_native_p2wpkh_or_p2wsh(witprog)

    if (
        not utils.BITCOIN_ONLY
        and coin.cashaddr_prefix is not None
        and o.address.startswith(coin.cashaddr_prefix + ":")
    ):
        prefix, addr = o.address.split(":")
        version, data = cashaddr.decode(prefix, addr)
        if version == cashaddr.ADDRESS_TYPE_P2KH:
            version = coin.address_type
        elif version == cashaddr.ADDRESS_TYPE_P2SH:
            version = coin.address_type_p2sh
        else:
            raise SigningError("Unknown cashaddr address type")
        raw_address = bytes([version]) + data
    else:
        try:
            raw_address = base58.decode_check(o.address, coin.b58_hash)
        except ValueError:
            raise SigningError(FailureType.DataError, "Invalid address")

    if address_type.check(coin.address_type, raw_address):
        # p2pkh
        pubkeyhash = address_type.strip(coin.address_type, raw_address)
        script = scripts.output_script_p2pkh(pubkeyhash)
        return script

    elif address_type.check(coin.address_type_p2sh, raw_address):
        # p2sh
        scripthash = address_type.strip(coin.address_type_p2sh, raw_address)
        script = scripts.output_script_p2sh(scripthash)
        return script

    raise SigningError(FailureType.DataError, "Invalid address type")
Exemplo n.º 11
0
def output_script_sstxchange(addr: str) -> bytearray:
    try:
        raw_address = base58.decode_check(addr, blake256d_32)
    except ValueError:
        raise wire.DataError("Invalid address")

    w = utils.empty_bytearray(26)
    w.append(0xBD)  # OP_SSTXCHANGE
    w.append(0x76)  # OP_DUP
    w.append(0xA9)  # OP_HASH160
    w.append(0x14)  # OP_DATA_20
    write_bytes_fixed(w, raw_address[2:], 20)
    w.append(0x88)  # OP_EQUALVERIFY
    w.append(0xAC)  # OP_CHECKSIG
    return w
 def test_valid_address(self):
     # b58 -> cashaddr
     for b58, ca in VALID_ADDRESS:
         data = base58.decode_check(b58)
         version = data[0]
         if version == 5:
             version = 8
         enc = cashaddr.encode('bitcoincash', version, data[1:])
         self.assertEqual(ca, enc)
     # cashaddr -> base58
     for b58, ca in VALID_ADDRESS:
         prefix, addr = ca.split(':')
         version, data = cashaddr.decode(prefix, addr)
         if version == 8:
             version = 5
         enc = base58.encode_check(bytes([version]) + data)
         self.assertEqual(b58, enc)
Exemplo n.º 13
0
async def verify_message(ctx, msg):
    message = msg.message
    address = msg.address
    signature = msg.signature
    coin_name = msg.coin_name or 'Bitcoin'
    coin = coins.by_name(coin_name)

    await confirm_verify_message(ctx, message)

    digest = message_digest(coin, message)
    pubkey = secp256k1.verify_recover(signature, digest)

    if not pubkey:
        raise wire.FailureError(ProcessError, 'Invalid signature')

    raw_address = base58.decode_check(address)
    _, pkh = address_type.split(coin, raw_address)
    pkh2 = ripemd160(sha256(pubkey).digest()).digest()

    if pkh != pkh2:
        raise wire.FailureError(ProcessError, 'Invalid signature')

    return Success(message='Message verified')
Exemplo n.º 14
0
def pack_contract(contract, owner_address):
    """
    Pack Tron Proto3 Contract
    See: https://github.com/tronprotocol/protocol/blob/master/core/Tron.proto
    and https://github.com/tronprotocol/protocol/blob/master/core/Contract.proto
    """
    retc = bytearray()
    add_field(retc, 1, TYPE_VARINT)
    # contract message
    cmessage = bytearray()
    if contract.transfer_contract:
        write_varint(retc, 1)
        api = "TransferContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, bytes(contract.transfer_contract.to_address))
        add_field(cmessage, 3, TYPE_VARINT)
        write_varint(cmessage, contract.transfer_contract.amount)

    if contract.transfer_asset_contract:
        write_varint(retc, 2)
        api = "TransferAssetContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.transfer_asset_contract.asset_name)
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 3, TYPE_STRING)
        write_bytes_with_length(
            cmessage, bytes(contract.transfer_asset_contract.to_address)
        )
        add_field(cmessage, 4, TYPE_VARINT)
        write_varint(cmessage, contract.transfer_asset_contract.amount)

    if contract.vote_witness_contract:
        write_varint(retc, 4)
        api = "VoteWitnessContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

        # vote list
        for i in range(len(contract.vote_witness_contract.votes)):
            vote = bytearray()
            add_field(vote, 1, TYPE_STRING)
            write_bytes_with_length(
                vote, bytes(contract.vote_witness_contract.votes[i].vote_address)
            )
            add_field(vote, 2, TYPE_VARINT)
            write_varint(vote, contract.vote_witness_contract.votes[i].vote_count)
            # add to buffer
            add_field(cmessage, 2, TYPE_STRING)
            write_bytes_with_length(cmessage, vote)

    if contract.witness_create_contract:
        write_varint(retc, 5)
        api = "WitnessCreateContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.witness_create_contract.url)

    if contract.asset_issue_contract:
        write_varint(retc, 6)
        api = "AssetIssueContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.asset_issue_contract.name)
        add_field(cmessage, 3, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.asset_issue_contract.abbr)
        add_field(cmessage, 4, TYPE_VARINT)
        write_varint(cmessage, contract.asset_issue_contract.total_supply)
        # asset frozen list
        for i in range(len(contract.asset_issue_contract.frozen_supply)):
            listarr = bytearray()
            add_field(listarr, 1, TYPE_VARINT)
            write_varint(
                listarr, contract.asset_issue_contract.frozen_supply[i].frozen_amount
            )
            add_field(listarr, 2, TYPE_VARINT)
            write_varint(
                listarr, contract.asset_issue_contract.frozen_supply[i].frozen_days
            )
            # add to vote list
            add_field(cmessage, 5, TYPE_STRING)
            write_bytes_with_length(cmessage, listarr)

        add_field(cmessage, 6, TYPE_VARINT)
        write_varint(cmessage, contract.asset_issue_contract.trx_num)
        add_field(cmessage, 8, TYPE_VARINT)
        write_varint(cmessage, contract.asset_issue_contract.num)
        add_field(cmessage, 9, TYPE_VARINT)
        write_varint(cmessage, contract.asset_issue_contract.start_time)
        add_field(cmessage, 10, TYPE_VARINT)
        write_varint(cmessage, contract.asset_issue_contract.end_time)
        add_field(cmessage, 20, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.asset_issue_contract.description)
        add_field(cmessage, 21, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.asset_issue_contract.url)

    if contract.witness_update_contract:
        write_varint(retc, 8)
        api = "WitnessUpdateContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 12, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.witness_update_contract.update_url)

    if contract.participate_asset_issue_contract:
        write_varint(retc, 9)
        api = "ParticipateAssetIssueContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(
            cmessage, bytes(contract.participate_asset_issue_contract.to_address)
        )
        add_field(cmessage, 3, TYPE_STRING)
        write_bytes_with_length(
            cmessage, contract.participate_asset_issue_contract.asset_name
        )
        add_field(cmessage, 4, TYPE_VARINT)
        write_varint(cmessage, contract.participate_asset_issue_contract.amount)

    if contract.account_update_contract:
        write_varint(retc, 10)
        api = "AccountUpdateContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.account_update_contract.account_name)
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

    if contract.freeze_balance_contract:
        write_varint(retc, 11)
        api = "FreezeBalanceContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_VARINT)
        write_varint(cmessage, contract.freeze_balance_contract.frozen_balance)
        add_field(cmessage, 3, TYPE_VARINT)
        write_varint(cmessage, contract.freeze_balance_contract.frozen_duration)

    if contract.unfreeze_balance_contract:
        write_varint(retc, 12)
        api = "UnfreezeBalanceContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

    if contract.withdraw_balance_contract:
        write_varint(retc, 13)
        api = "WithdrawBalanceContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

    if contract.unfreeze_asset_contract:
        write_varint(retc, 14)
        api = "UnfreezeAssetContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

    if contract.update_asset_contract:
        write_varint(retc, 15)
        api = "UpdateAssetContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.update_asset_contract.description)
        add_field(cmessage, 3, TYPE_STRING)
        write_bytes_with_length(cmessage, contract.update_asset_contract.url)

    if contract.proposal_create_contract:
        write_varint(retc, 16)
        api = "ProposalCreateContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))

        # Parameters list
        for i in range(len(contract.proposal_create_contract.parameters)):
            pair = bytearray()
            add_field(pair, 1, TYPE_VARINT)
            write_varint(pair, contract.proposal_create_contract.parameters[i].key)
            add_field(pair, 2, TYPE_VARINT)
            write_varint(pair, contract.proposal_create_contract.parameters[i].value)
            # add to buffer
            add_field(cmessage, 2, TYPE_STRING)
            write_bytes_with_length(cmessage, pair)

    if contract.proposal_approve_contract:
        write_varint(retc, 17)
        api = "ProposalApproveContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_VARINT)
        write_varint(cmessage, contract.proposal_approve_contract.proposal_id)
        add_field(cmessage, 3, TYPE_VARINT)
        write_varint(cmessage, contract.proposal_approve_contract.is_add_approval)

    if contract.proposal_delete_contract:
        write_varint(retc, 18)
        api = "ProposalDeleteContract"

        add_field(cmessage, 1, TYPE_STRING)
        write_bytes_with_length(cmessage, base58.decode_check(owner_address))
        add_field(cmessage, 2, TYPE_VARINT)
        write_varint(cmessage, contract.proposal_delete_contract.proposal_id)

    # write API
    capi = bytearray()
    add_field(capi, 1, TYPE_STRING)
    write_bytes_with_length(capi, "type.googleapis.com/protocol." + api)

    # extend to capi
    add_field(capi, 2, TYPE_STRING)
    write_bytes_with_length(capi, cmessage)

    # extend to contract
    add_field(retc, 2, TYPE_STRING)
    write_bytes_with_length(retc, capi)
    return retc
Exemplo n.º 15
0
def base58_decode_check(enc, prefix=None):
    decoded = base58.decode_check(enc)
    if prefix is not None:
        decoded = decoded[len(TEZOS_PREFIX_BYTES[prefix]):]
    return decoded
Exemplo n.º 16
0
def base58_decode_check(enc: str, prefix: str | None = None) -> bytes:
    decoded = base58.decode_check(enc)
    if prefix is not None:
        decoded = decoded[len(TEZOS_PREFIX_BYTES[prefix]) :]
    return decoded