CHashWriter
does serialisation differently for different types of objects. src/serialize.h
describes this different behaviour in detail.
Here's a simple version for the new table bucketing algorithm in python. get_group()
assumes normal ipv4 addresses as input here.
ADDRMAN_NEW_BUCKETS_PER_SOURCE_GROUP = 64
ADDRMAN_NEW_BUCKET_COUNT = 1024
def get_group(ip):
ip_as_bytes = bytes(map(int, ip.split('.')))
return bytes([1]) + ip_as_bytes[:2]
def double_hash(bytes):
return sha256(sha256(bytes).digest()).digest()
def get_new_bucket(key, addr, src):
addr_group = get_group(addr)
src_group = get_group(src)
hash1 = int.from_bytes(double_hash(key + bytes([len(addr_group)]) + addr_group
+ bytes([len(src_group)]) + src_group)[:8], 'little')
hash1 = hash1 % ADDRMAN_NEW_BUCKETS_PER_SOURCE_GROUP
hash2 = int.from_bytes(double_hash(key + bytes([len(src_group)]) + src_group
+ hash1.to_bytes(8, 'little'))[:8], 'little')
return hash2 % ADDRMAN_NEW_BUCKET_COUNT
key = bytes.fromhex("41f758f2e5cc078d3795b4fc0cb60c2d735fa92cc020572bdc982dd2d564d11b")
addr = "250.1.2.1"
src = "250.1.2.1"
bucket = get_new_bucket(key, addr, src)
print("bucket is", bucket) # 786