From a0d02c7ffa86916f56dcdd77fd0eea6b5289c3cf Mon Sep 17 00:00:00 2001 From: Otis Date: Thu, 15 Jul 2021 13:16:25 +1000 Subject: [PATCH] Add moneropy local file --- base58.py | 168 ++++++++++++++++++++++++++++++++++++++++++++++++++++ observer.py | 4 +- 2 files changed, 170 insertions(+), 2 deletions(-) create mode 100644 base58.py diff --git a/base58.py b/base58.py new file mode 100644 index 0000000..e761870 --- /dev/null +++ b/base58.py @@ -0,0 +1,168 @@ +# MoneroPy - A python toolbox for Monero +# Copyright (C) 2016 The MoneroPy Developers. +# +# MoneroPy is released under the BSD 3-Clause license. Use and redistribution of +# this software is subject to the license terms in the LICENSE file found in the +# top-level directory of this distribution. + +__alphabet = [ord(s) for s in '123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz'] +__b58base = 58 +__UINT64MAX = 2**64 +__encodedBlockSizes = [0, 2, 3, 5, 6, 7, 9, 10, 11] +__fullBlockSize = 8 +__fullEncodedBlockSize = 11 + +def _hexToBin(hex): + if len(hex) % 2 != 0: + return "Hex string has invalid length!" + return [int(hex[i*2:i*2+2], 16) for i in range(len(hex)//2)] + +def _binToHex(bin): + return "".join([("0" + hex(int(bin[i])).split('x')[1])[-2:] for i in range(len(bin))]) + +def _strToBin(a): + return [ord(s) for s in a] + +def _binToStr(bin): + return ''.join([chr(bin[i]) for i in range(len(bin))]) + +def _uint8be_to_64(data): + l_data = len(data) + + if l_data < 1 or l_data > 8: + return "Invalid input length" + + res = 0 + switch = 9 - l_data + for i in range(l_data): + if switch == 1: + res = res << 8 | data[i] + elif switch == 2: + res = res << 8 | data[i] + elif switch == 3: + res = res << 8 | data[i] + elif switch == 4: + res = res << 8 | data[i] + elif switch == 5: + res = res << 8 | data[i] + elif switch == 6: + res = res << 8 | data[i] + elif switch == 7: + res = res << 8 | data[i] + elif switch == 8: + res = res << 8 | data[i] + else: + return "Impossible condition" + return res + +def _uint64_to_8be(num, size): + res = [0] * size; + if size < 1 or size > 8: + return "Invalid input length" + + twopow8 = 2**8 + for i in range(size-1,-1,-1): + res[i] = num % twopow8 + num = num // twopow8 + + return res + +def encode_block(data, buf, index): + l_data = len(data) + + if l_data < 1 or l_data > __fullEncodedBlockSize: + return "Invalid block length: " + str(l_data) + + num = _uint8be_to_64(data) + i = __encodedBlockSizes[l_data] - 1 + + while num > 0: + remainder = num % __b58base + num = num // __b58base + buf[index+i] = __alphabet[remainder]; + i -= 1 + + return buf + +def encode(hex): + '''Encode hexadecimal string as base58 (ex: encoding a Monero address).''' + data = _hexToBin(hex) + l_data = len(data) + + if l_data == 0: + return "" + + full_block_count = l_data // __fullBlockSize + last_block_size = l_data % __fullBlockSize + res_size = full_block_count * __fullEncodedBlockSize + __encodedBlockSizes[last_block_size] + + res = [0] * res_size + for i in range(res_size): + res[i] = __alphabet[0] + + for i in range(full_block_count): + res = encode_block(data[(i*__fullBlockSize):(i*__fullBlockSize+__fullBlockSize)], res, i * __fullEncodedBlockSize) + + if last_block_size > 0: + res = encode_block(data[(full_block_count*__fullBlockSize):(full_block_count*__fullBlockSize+last_block_size)], res, full_block_count * __fullEncodedBlockSize) + + return _binToStr(res) + +def decode_block(data, buf, index): + l_data = len(data) + + if l_data < 1 or l_data > __fullEncodedBlockSize: + return "Invalid block length: " + l_data + + res_size = __encodedBlockSizes.index(l_data) + if res_size <= 0: + return "Invalid block size" + + res_num = 0 + order = 1 + for i in range(l_data-1, -1, -1): + digit = __alphabet.index(data[i]) + if digit < 0: + return "Invalid symbol" + + product = order * digit + res_num + if product > __UINT64MAX: + return "Overflow" + + res_num = product + order = order * __b58base + + if res_size < __fullBlockSize and 2**(8 * res_size) <= res_num: + return "Overflow 2" + + tmp_buf = _uint64_to_8be(res_num, res_size) + for i in range(len(tmp_buf)): + buf[i+index] = tmp_buf[i] + + return buf + +def decode(enc): + '''Decode a base58 string (ex: a Monero address) into hexidecimal form.''' + enc = _strToBin(enc) + l_enc = len(enc) + + if l_enc == 0: + return "" + + full_block_count = l_enc // __fullEncodedBlockSize + last_block_size = l_enc % __fullEncodedBlockSize + last_block_decoded_size = __encodedBlockSizes.index(last_block_size) + + if last_block_decoded_size < 0: + return "Invalid encoded length" + + data_size = full_block_count * __fullBlockSize + last_block_decoded_size + + data = [0] * data_size + for i in range(full_block_count): + data = decode_block(enc[(i*__fullEncodedBlockSize):(i*__fullEncodedBlockSize+__fullEncodedBlockSize)], data, i * __fullBlockSize) + + if last_block_size > 0: + data = decode_block(enc[(full_block_count*__fullEncodedBlockSize):(full_block_count*__fullEncodedBlockSize+last_block_size)], data, full_block_count * __fullBlockSize) + + return _binToHex(data) \ No newline at end of file diff --git a/observer.py b/observer.py index 0151447..224c282 100644 --- a/observer.py +++ b/observer.py @@ -21,7 +21,7 @@ from io import BytesIO import pysodium import nacl.encoding import nacl.hash -import moneropy.base58 as b58 +import base58 import sha3 import config import local_config @@ -514,7 +514,7 @@ def show_ons(name, more_details=False): val = network + val + checksum - ons_data[ons_type]['mapping'] = b58.encode(val.hex()) + ons_data[ons_type]['mapping'] = base58.encode(val.hex()) continue if ons_types[ons_type] == 2: