From 257bef6ca06484315e961e0c44c5f0018cc14e65 Mon Sep 17 00:00:00 2001 From: Kevin Froman Date: Tue, 9 Feb 2021 23:02:19 +0000 Subject: [PATCH] added subprocess validator --- src/anonvdf-block-validator.py | 38 +++++++++++++++++++ src/blockio/__init__.py | 1 + src/blockio/subprocvalidate.py | 20 ++++++++++ .../default-plugins/torgossip/client.py | 2 +- .../torgossip/clientfuncs/__init__.py | 26 ++++++++++++- static-data/default_config.json | 18 ++++----- tests/test_blockio.py | 12 +++++- 7 files changed, 104 insertions(+), 13 deletions(-) create mode 100755 src/anonvdf-block-validator.py create mode 100644 src/blockio/subprocvalidate.py diff --git a/src/anonvdf-block-validator.py b/src/anonvdf-block-validator.py new file mode 100755 index 00000000..c0609661 --- /dev/null +++ b/src/anonvdf-block-validator.py @@ -0,0 +1,38 @@ +#!/usr/bin/env python +# This is a subprocess because block validation is somewhat CPU intensive + +from base64 import b85decode, b85encode +import os +from sys import argv, stdin, stderr, stdout, exit + +from kasten import Kasten +from kasten.exceptions import InvalidID +from onionrblocks.exceptions import BlockExpired +from onionrblocks.generators import AnonVDFGenerator + +block_hash = b85decode(argv[1]) + +block_bytes = b85decode(stdin.read()) + + +try: + Kasten( + block_hash, block_bytes, + AnonVDFGenerator, auto_check_generator=True) +except InvalidID: + stderr.write( + "Invalid block ID for " + + b85encode(block_hash).decode('utf-8')) +except ValueError as e: + # Supposed to be if rounds are not specifid in the block + stderr.write(e.message) +except BlockExpired: + stderr.write( + b85encode(block_hash).decode('utf-8') + " is expired") +else: + + with os.fdopen(stdout.fileno(), 'wb') as std: + std.write(b"valid") + exit(0) +stderr.flush() +exit(1) diff --git a/src/blockio/__init__.py b/src/blockio/__init__.py index 0cb504b8..661ab2c8 100644 --- a/src/blockio/__init__.py +++ b/src/blockio/__init__.py @@ -6,6 +6,7 @@ from .store import store_block from .load import load_block, list_blocks_by_type, list_all_blocks from .clean import clean_expired_blocks, clean_block_list_entries from . import subprocgenerate +from . import subprocvalidate """ This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by diff --git a/src/blockio/subprocvalidate.py b/src/blockio/subprocvalidate.py new file mode 100644 index 00000000..363fd707 --- /dev/null +++ b/src/blockio/subprocvalidate.py @@ -0,0 +1,20 @@ +import subprocess +import os +from base64 import b85encode +from onionrblocks.generators import anonvdf + + +_DIR = os.path.dirname(os.path.realpath(__file__)) + '/../' + + +def vdf_block(block_hash: bytes, block_data: bytes): + block_data = b85encode(block_data) + + p = subprocess.Popen( + [ + f'{_DIR}anonvdf-block-validator.py', + b85encode(block_hash)], stdout=subprocess.PIPE, stderr=subprocess.PIPE, stdin=subprocess.PIPE) + result = p.communicate(block_data) + if result[1]: + print(result[1]) + raise anonvdf.InvalidID() diff --git a/static-data/default-plugins/torgossip/client.py b/static-data/default-plugins/torgossip/client.py index 2570d794..bcda9324 100644 --- a/static-data/default-plugins/torgossip/client.py +++ b/static-data/default-plugins/torgossip/client.py @@ -18,7 +18,7 @@ from netcontroller.torcontrol import torcontroller if TYPE_CHECKING: from .peerdb import TorGossipPeers from stem.control import Controller -sys.path.insert(0, os.path.dirname(os.path.realpath(__file__))) +sys.path.insert(0, path.dirname(path.realpath(__file__))) from commands import GossipCommands """ diff --git a/static-data/default-plugins/torgossip/clientfuncs/__init__.py b/static-data/default-plugins/torgossip/clientfuncs/__init__.py index f6553056..99ad20d9 100644 --- a/static-data/default-plugins/torgossip/clientfuncs/__init__.py +++ b/static-data/default-plugins/torgossip/clientfuncs/__init__.py @@ -1,7 +1,29 @@ from typing import TYPE_CHECKING +import sys +import os + +import logger +from blockio import store_block, subprocvalidate +import onionrblocks +sys.path.insert(0, os.path.dirname(os.path.realpath(__file__))) +from commands import GossipCommands + if TYPE_CHECKING: from socket import socket -def download_blocks(sock: 'socket', offset: int): - sock.sendall() +def download_blocks(sock: 'socket', offset: int, block_type: str): + sock.sendall( + int(GossipCommands.LIST_BLOCKS_BY_TYPE_OFFSET).to_bytes( + 1, 'little') + str(offset).encode('utf-8') + + block_type.encode('utf-8')) + bl_hashs = sock.recv(600000) + hash = None + for i in range(len(bl_hashs)//64): + hash = bl[:(i*64) + 64] + sock.sendall( + int(GossipCommands.GET_BLOCK).to_bytes( + 1, 'little') + hash) + bl_content = sock.recv(10**6) + + diff --git a/static-data/default_config.json b/static-data/default_config.json index 0e3a31b2..6506956a 100755 --- a/static-data/default_config.json +++ b/static-data/default_config.json @@ -9,21 +9,21 @@ "allow_public_api_dns_rebinding": false, "announce_node": true, "bind_address": "", - "dev_mode": false, + "dev_mode": true, "display_header": true, "ephemeral_tunnels": false, "hide_created_blocks": true, - "insert_deniable_blocks": true, + "insert_deniable_blocks": false, "max_block_age": 2678400, - "minimum_block_pow": 5, - "minimum_send_pow": 5, + "minimum_block_pow": 1, + "minimum_send_pow": 1, "public_key": "", - "random_bind_ip": true, + "random_bind_ip": false, "security_level": 0, "show_notifications": true, "store_plaintext_blocks": true, "upload_mixing": false, - "use_bootstrap_list": true, + "use_bootstrap_list": false, "use_subprocess_pow_if_possible": true }, "log": { @@ -33,12 +33,12 @@ }, "file": { "output": true, - "remove_on_exit": true + "remove_on_exit": false }, "verbosity": "default" }, "onboarding": { - "done": false + "done": true }, "peers": { "max_connect": 1000, @@ -78,7 +78,7 @@ "tor": true }, "ui": { - "animated_background": true, + "animated_background": false, "public_remote_enabled": false, "public_remote_hosts": [], "theme": "dark" diff --git a/tests/test_blockio.py b/tests/test_blockio.py index d889610b..9fc8fb4b 100644 --- a/tests/test_blockio.py +++ b/tests/test_blockio.py @@ -11,6 +11,7 @@ import unittest import time from utils import identifyhome, createdirs from onionrsetup import setup_config, setup_default_plugins +import random createdirs.create_dirs() setup_config() @@ -24,7 +25,8 @@ from utils import identifyhome import safedb import blockio from blockio.clean.cleanblocklistentries import clean_block_list_entries -from blockio import subprocgenerate +from blockio import subprocgenerate, subprocvalidate + def _remove_db(path): try: @@ -35,6 +37,14 @@ def _remove_db(path): class TestBlockIO(unittest.TestCase): + def test_subproc_validate(self): + bl = blockcreator.create_anonvdf_block(b"hello" + int(3).to_bytes(1, "big"), b"txt" + int(3).to_bytes(1, "big"), 5) + invalid = os.urandom(64) + subprocvalidate.vdf_block(bl.id, bl.get_packed()) + + self.assertRaises(anonvdf.InvalidID, subprocvalidate.vdf_block, invalid, bl.get_packed()) + + def test_subproc_generate(self): db_file = identifyhome.identify_home() + 'test.db' db = safedb.SafeDB(db_file)