def read(cls, read): prev_hash = read(32) prev_idx = read_le_uint32(read) script_sig = Script(read_varbytes(read)) sequence = read_le_uint32(read) kwargs = {'x_pubkeys': [], 'address': None, 'threshold': 0, 'signatures': []} if prev_hash != bytes(32): _parse_script_sig(script_sig.to_bytes(), kwargs) result = cls(prev_hash, prev_idx, script_sig, sequence, value=0, **kwargs) if not result.is_complete(): result.value = read_le_int64(read) return result
def read_extended(cls, read): '''Overridden to specialize reading the inputs.''' return cls( read_le_int32(read), read_list(read, XTxInput.read_extended), read_list(read, XTxOutput.read), read_le_uint32(read), )
def deserialize_headers(cls, f): """deserialize block headers into a list of dicts""" lst_headers = [] global headers_stream global hashes_stream # Store headers temporarily to memory as binary stream headers_stream.seek(0) headers_stream.write(f.read()) # make a list of block hashes for validating headers_stream.seek(0) count = bitcoinx.read_varint(headers_stream.read) # count of headers for i in range(count): header = headers_stream.read(80) # minus final txn count (1 byte) headers_stream.read(1) # discard txn count _hash = simple_spv.tools.get_block_hash(header) # calculates hash as part of validation hashes_stream.write(_hash + '\n') f.seek(0) number_headers = bitcoinx.read_varint(f.read) for i in range(number_headers): # TODO make into single function call for readability and reuse version = bitcoinx.read_le_int32(f.read) prev_block = bitcoinx.hash_to_hex_str(f.read(32)) merkle_root = bitcoinx.hash_to_hex_str(f.read(32)) timestamp = bitcoinx.read_le_uint32(f.read) bits = ut.int_to_hex(bitcoinx.read_le_uint32(f.read)) nonce = bitcoinx.read_le_uint32(f.read) txn_count = bitcoinx.read_varint(f.read) block_header = {'version': version, 'prev_block_hash': prev_block, 'merkle_root': merkle_root, 'timestamp': timestamp, 'bits': bits, 'nonce': nonce, 'txn_count': txn_count} lst_headers.append(block_header) return lst_headers
def deserialize_inv(cls, f): message = [] count = bitcoinx.read_varint(f.read) for i in range(count): inv_type = bitcoinx.read_le_uint32(f.read) inv_hash = bitcoinx.hash_to_hex_str(f.read(32)) inv_vector = {'count': count, 'inv_type': inv_type, 'inv_hash': inv_hash} message.append(inv_vector) return message
def deserialize_getheaders(cls, f): """for checking my own getheaders request""" version = bitcoinx.read_le_uint32(f.read) hash_count = bitcoinx.read_varint(f.read) block_locator_hashes = [] for i in range(hash_count): block_locator_hashes.append(bitcoinx.hash_to_hex_str(f.read(32))) hash_stop = bitcoinx.hash_to_hex_str(f.read(32)) message = {'version': version, 'hash_count': hash_count, 'block_locator_hashes': block_locator_hashes, 'hash_stop': hash_stop} return message
def deserialize_addr(cls, f): count = bitcoinx.read_varint(f.read) addresses = [] for i in range(count): timestamp = time.ctime(bitcoinx.read_le_uint32(f.read)) services = bitcoinx.read_le_uint64(f.read) reserved = f.read(12) # IPv6 IPv4 = socket.inet_ntoa(f.read(4)) port = bitcoinx.read_le_uint16(f.read) addresses.append({'timestamp': timestamp, 'services': services, 'IPv4': IPv4, 'port': port}) return addresses # count not returned by choice
def deserialize_message_header(cls, header): global checksum stream = io.BytesIO(header) magic = ut.bytes_to_hex(stream.read(4)) command = stream.read(12).decode('ascii').strip('\x00') length = bitcoinx.read_le_uint32(stream.read) try: checksum = ut.bytes_to_hex(stream.read(4)) decoded_header = {'magic': magic, 'command': command, 'length': length, 'checksum': checksum, } return decoded_header except Exception as e: print(e) print('reading in checksum failed...')