Exemple #1
0
 def __init__(self, genesis_creation_time):
     self.genesis_creation_time = genesis_creation_time
     self.blocks_by_hash = {}
     self.blocks_by_number = {}
     signed_genesis_block = SignedBlock()
     signed_genesis_block.set_block(self.genesis_block())
     self.add_signed_block(0, signed_genesis_block)
Exemple #2
0
 def handle_block_message(self, node_id, raw_signed_block):
     current_block_number = self.dag.get_current_timeframe_block_number()
     current_validator = self.permissions.get_permission(
         self.dag, current_block_number)
     signed_block = SignedBlock()
     signed_block.parse(raw_signed_block)
     print("Node ", self.node_id, "received block from node", node_id,
           "with block hash",
           signed_block.block.get_hash().hexdigest())
     if signed_block.verify_signature(current_validator.public_key):
         self.dag.add_signed_block(current_block_number, signed_block)
     else:
         self.network.gossip_malicious(current_validator.public_key)
Exemple #3
0
 def __init__(self, genesis_creation_time):
     self.blocks_by_hash = {}  # just hash map hash:block
     self.blocks_by_number = {
     }  # key is timeslot number, value is a list of blocks in this timeslot
     self.block_numbers_by_hash = {}
     self.transactions_by_hash = {}  # key is tx_hash, value is tx
     self.payments_by_hash = {}
     self.existing_links = []
     self.tops = {}
     self.new_block_listeners = []
     self.new_top_block_event_listeners = []
     self.genesis = Genesis(genesis_creation_time)
     signed_genesis_block = SignedBlock()
     signed_genesis_block.set_block(self.genesis)
     self.add_signed_block(0, signed_genesis_block)
Exemple #4
0
 def sign_block(block, private):
     block_hash = block.get_hash()
     signature = Private.sign(block_hash, private)
     signed_block = SignedBlock()
     signed_block.set_block(block)
     signed_block.set_signature(signature)
     return signed_block
Exemple #5
0
    def sign_block(self, private):  #TODO move somewhere more approptiate
        block = Block()
        block.prev_hashes = [*self.get_top_blocks()]
        block.timestamp = int(datetime.datetime.now().timestamp())
        block.randoms = []

        block_hash = block.get_hash().digest()
        signature = private.sign(block_hash, 0)[
            0]  #for some reason it returns tuple with second item being None
        signed_block = SignedBlock()
        signed_block.set_block(block)
        signed_block.set_signature(signature)
        current_block_number = self.get_current_timeframe_block_number()
        self.add_signed_block(current_block_number, signed_block)
        print(block_hash.hex(), " was added to blockchain under number ",
              current_block_number)
        return signed_block
Exemple #6
0
    def test_top_blocks(self):
        block1 = Block()
        block1.prev_hashes = [self.genesis_block().get_hash().digest()]
        block1.timestamp = 32452345234
        block1.randoms = []
        signed_block1 = SignedBlock()
        signed_block1.set_block(block1)
        self.add_signed_block(1, signed_block1)

        block2 = Block()
        block2.prev_hashes = [block1.get_hash().digest()]
        block2.timestamp = 32452345
        block2.randoms = []
        signed_block2 = SignedBlock()
        signed_block2.set_block(block2)
        self.add_signed_block(2, signed_block2)

        block3 = Block()
        block3.prev_hashes = [block1.get_hash().digest()]
        block3.timestamp = 1231827398
        block3.randoms = []
        signed_block3 = SignedBlock()
        signed_block3.set_block(block3)
        self.add_signed_block(3, signed_block3)

        for keyhash in self.blocks_by_hash:
            print(binascii.hexlify(keyhash))

        top_hashes = self.get_top_blocks()

        print("tops")
        for keyhash in top_hashes:
            print(binascii.hexlify(keyhash))
Exemple #7
0
    def handle_block_message(self, node_id, raw_signed_block):
        signed_block = SignedBlock()
        signed_block.parse(raw_signed_block)
        block_number = self.epoch.get_block_number_from_timestamp(
            signed_block.block.timestamp)
        self.logger.info(
            "Received block with number %s at timeslot %s with hash %s",
            block_number, self.epoch.get_current_timeframe_block_number(),
            signed_block.block.get_hash().hex())

        # CHECK_ANCESTOR
        blocks_by_hash = self.dag.blocks_by_hash
        is_orphan_block = False
        for prev_hash in signed_block.block.prev_hashes:  # by every previous hash
            if prev_hash not in blocks_by_hash:  # verify local ancestor for incoming block
                is_orphan_block = True

        # CHECK_ORPHAN_DISTANCE
        block_out_of_epoch = False
        epoch_end_block = self.epoch.get_epoch_end_block_number(
            self.epoch.current_epoch)
        if block_number >= epoch_end_block:
            # income block from future epoch, cant validate signer
            block_out_of_epoch = True

        # CHECK ALLOWED SIGNER
        if not block_out_of_epoch:  # if incoming block not out of current epoch
            allowed_signers = self.get_allowed_signers_for_block_number(
                block_number)
            allowed_pubkey = None
            for allowed_signer in allowed_signers:
                if signed_block.verify_signature(allowed_signer):
                    allowed_pubkey = allowed_signer
                    break
        else:
            allowed_pubkey = 'block_out_of_epoch'  # process block as orphan

        if allowed_pubkey:  # IF SIGNER ALLOWED
            if not is_orphan_block:  # PROCESS NORMAL BLOCK (same epoch)
                if self.epoch.is_new_epoch_upcoming(
                        block_number):  # CHECK IS NEW EPOCH
                    self.epoch.accept_tops_as_epoch_hashes()
                block_verifier = BlockAcceptor(
                    self.epoch, self.logger)  # VERIFY BLOCK AS NORMAL
                if block_verifier.check_if_valid(signed_block.block):
                    self.insert_verified_block(signed_block, allowed_pubkey)
                    return
            else:  # PROCESS ORPHAN BLOCK (same epoch)
                orphan_block_verifier = OrphanBlockAcceptor(
                    self.epoch, self.blocks_buffer, self.logger)
                if orphan_block_verifier.check_if_valid(signed_block.block):
                    self.blocks_buffer.append(signed_block)
                    self.logger.info("Orphan block added to buffer")
                    # for every parent for received block
                    for prev_hash in signed_block.block.prev_hashes:  # check received block ancestor
                        if prev_hash not in self.dag.blocks_by_hash:  # check parent in local dag
                            # if parent not exist in local DAG ask for parent
                            self.network.direct_request_block_by_hash(
                                self.node_id, node_id, prev_hash)

                if len(self.blocks_buffer) > 0:
                    self.process_block_buffer()
                    self.logger.info("Orphan block buffer process success")
        else:
            self.logger.error(
                "Received block from %d, but its signature is wrong", node_id)