def make_verify_request(self, work, diff, verify=True): boundary = ethash.difficulty_to_boundary(diff) byte_verify = b"\x01" if verify else b"\x00" # requests are bytes bytes_reqs = [ self.key.keypair_bytes.public, # 33 bytes byte_verify, # 1 bytes work["header"], # 32 bytes boundary, # 32 bytes ] # convert to bytes to sign bytes_to_sign = b"".join(bytes_reqs) assert len(bytes_to_sign) == 33 + 1 + 32 * 2 signature = self.key.sign( bytes_to_sign) # signature is hex string, len 128 assert len(signature) == 128 signature = "0x" + signature # convert to hex string starts with "0x" req = [crypto.bytes_to_hex_str_0x(b) for b in bytes_reqs] # append signature req.append(signature) return req
def make_work_request(self, work, diff): timeout = crypto.int_to_bytes(self.pow_timeout, n_bytes=4) boundary = ethash.difficulty_to_boundary(diff) # requests are bytes bytes_reqs = [ self.key.keypair_bytes.public, # 33 bytes work["header"], # 32 bytes work["block_num"], # 8 bytes boundary, # 32 bytes timeout, # 4 bytes ] # convert to bytes to sign bytes_to_sign = b"".join(bytes_reqs) assert len(bytes_to_sign) == 33 + 32 * 2 + 8 + 4 signature = self.key.sign( bytes_to_sign) # signature is hex string, len 128 assert len(signature) == 128 signature = "0x" + signature # convert to hex string starts with "0x" req = [crypto.bytes_to_hex_str_0x(b) for b in bytes_reqs] # append signature req.append(signature) return req
def test_pow(self): block_num = 22 header = crypto.hex_str_to_bytes("372eca2454ead349c3df0ab5d00b0b706b23e49d469387db91811cee0358fc6d") excepted_result = crypto.hex_str_to_bytes("00000b184f1fdd88bfd94c86c39e65db0c36144d5e43f745f722196e730cb614") excepted_mix = b'/t\xcd\xeb\x19\x8a\xf0\xb9\xab\xe6]"\xd3r\xe2/\xb2\xd4t7\x17t\xa9X<\x1c\xc4\'\xa0y9\xf5' nonce = 0x495732e0ed7a801c boundary20 = ethash.difficulty_to_boundary(20) boundary21 = ethash.difficulty_to_boundary(21) calc_mix_digest, calc_result = ethash.pow_hash(block_num, header, nonce) assert calc_result == excepted_result assert calc_mix_digest == excepted_mix assert ethash.verify_pow_work(block_num, header, excepted_mix, nonce, boundary20) assert not ethash.verify_pow_work(block_num, header, excepted_mix, nonce, boundary21) assert ethash.verify_pow_work(0, header, excepted_mix, nonce, boundary20) assert ethash.verify_pow_work(29999, header, excepted_mix, nonce, boundary20) assert not ethash.verify_pow_work(30000, header, excepted_mix, nonce, boundary20) assert not ethash.verify_pow_work(30001, header, excepted_mix, nonce, boundary20)
def add_new_work(block_num, difficulty, timeout, node=0): print(f"Generate a work for block {block_num}, difficulty {difficulty}") header = crypto.rand_hex_str_0x(64) seed = crypto.bytes_to_hex_str_0x(ethash.block_num_to_seed(block_num)) boundary = crypto.bytes_to_hex_str_0x( ethash.difficulty_to_boundary(difficulty)) print(f" header : {header}") print(f" seed : {seed}") print(f" boundary : {boundary}") pub_key = debug_data.nodes[node][0] print(f"save work, timeout = {timeout}, pub_key = {pub_key}") work = pow.PowWork.new_work(header, seed, boundary, pub_key=pub_key, signature="", timeout=timeout) work = work.save() if work: print(f"success, {work}") else: print(f"failed")
def test_tools(self): for i in range(256): assert ethash.boundary_to_difficulty(ethash.difficulty_to_boundary(i)) == i