messages.py raw

   1  #!/usr/bin/env python3
   2  # Copyright (c) 2010 ArtForz -- public domain half-a-node
   3  # Copyright (c) 2012 Jeff Garzik
   4  # Copyright (c) 2010-2022 The Limenka developers
   5  # Distributed under the MIT software license, see the accompanying
   6  # file COPYING or http://www.opensource.org/licenses/mit-license.php.
   7  """Limenka test framework primitive and message structures
   8  
   9  CBlock, CTransaction, CBlockHeader, CTxIn, CTxOut, etc....:
  10      data structures that should map to corresponding structures in
  11      limenka/primitives
  12  
  13  msg_block, msg_tx, msg_headers, etc.:
  14      data structures that represent network messages
  15  
  16  ser_*, deser_*: functions that handle serialization/deserialization.
  17  
  18  Classes use __slots__ to ensure extraneous attributes aren't accidentally added
  19  by tests, compromising their intended effect.
  20  """
  21  from base64 import b32decode, b32encode
  22  import copy
  23  import hashlib
  24  from io import BytesIO
  25  import math
  26  import random
  27  import socket
  28  import time
  29  import unittest
  30  
  31  from test_framework.crypto.siphash import siphash256
  32  from test_framework.util import assert_equal
  33  
  34  MAX_LOCATOR_SZ = 101
  35  MAX_BLOCK_WEIGHT = 4000000
  36  DEFAULT_BLOCK_RESERVED_WEIGHT = 8000
  37  MINIMUM_BLOCK_RESERVED_WEIGHT = 2000
  38  MAX_BLOOM_FILTER_SIZE = 36000
  39  MAX_BLOOM_HASH_FUNCS = 50
  40  
  41  COIN = 100000000  # 1 btc in satoshis
  42  MAX_MONEY = 21000000 * COIN
  43  
  44  MAX_BIP125_RBF_SEQUENCE = 0xfffffffd  # Sequence number that is rbf-opt-in (BIP 125) and csv-opt-out (BIP 68)
  45  MAX_SEQUENCE_NONFINAL = 0xfffffffe  # Sequence number that is csv-opt-out (BIP 68)
  46  SEQUENCE_FINAL = 0xffffffff  # Sequence number that disables nLockTime if set for every input of a tx
  47  
  48  MAX_PROTOCOL_MESSAGE_LENGTH = 4000000  # Maximum length of incoming protocol messages
  49  MAX_HEADERS_RESULTS = 2000  # Number of headers sent in one getheaders result
  50  MAX_INV_SIZE = 50000  # Maximum number of entries in an 'inv' protocol message
  51  
  52  NODE_NONE = 0
  53  NODE_NETWORK = (1 << 0)
  54  NODE_BLOOM = (1 << 2)
  55  NODE_WITNESS = (1 << 3)
  56  NODE_COMPACT_FILTERS = (1 << 6)
  57  NODE_NETWORK_LIMITED = (1 << 10)
  58  NODE_P2P_V2 = (1 << 11)
  59  NODE_REPLACE_BY_FEE = (1 << 26)
  60  NODE_REDUCED_DATA = (1 << 27)
  61  
  62  MSG_TX = 1
  63  MSG_BLOCK = 2
  64  MSG_FILTERED_BLOCK = 3
  65  MSG_CMPCT_BLOCK = 4
  66  MSG_WTX = 5
  67  MSG_WITNESS_FLAG = 1 << 30
  68  MSG_TYPE_MASK = 0xffffffff >> 2
  69  MSG_WITNESS_TX = MSG_TX | MSG_WITNESS_FLAG
  70  
  71  FILTER_TYPE_BASIC = 0
  72  
  73  WITNESS_SCALE_FACTOR = 4
  74  
  75  DEFAULT_ANCESTOR_LIMIT = 25    # default max number of in-mempool ancestors
  76  DEFAULT_DESCENDANT_LIMIT = 25  # default max number of in-mempool descendants
  77  
  78  # Default setting for -datacarriersize. 80 bytes of data, +1 for OP_RETURN, +2 for the pushdata opcodes.
  79  MAX_OP_RETURN_RELAY = 83
  80  
  81  DEFAULT_MEMPOOL_EXPIRY_HOURS = 336  # hours
  82  
  83  MAGIC_BYTES = {
  84      "mainnet": b"\xf9\xbe\xb4\xd9",   # mainnet
  85      "testnet3": b"\x0b\x11\x09\x07",  # testnet3
  86      "regtest": b"\xfa\xbf\xb5\xda",   # regtest
  87      "signet": b"\x0a\x03\xcf\x40",    # signet
  88  }
  89  
  90  def sha256(s):
  91      return hashlib.sha256(s).digest()
  92  
  93  
  94  def sha3(s):
  95      return hashlib.sha3_256(s).digest()
  96  
  97  
  98  def hash256(s):
  99      return sha256(sha256(s))
 100  
 101  
 102  def ser_compact_size(l):
 103      r = b""
 104      if l < 253:
 105          r = l.to_bytes(1, "little")
 106      elif l < 0x10000:
 107          r = (253).to_bytes(1, "little") + l.to_bytes(2, "little")
 108      elif l < 0x100000000:
 109          r = (254).to_bytes(1, "little") + l.to_bytes(4, "little")
 110      else:
 111          r = (255).to_bytes(1, "little") + l.to_bytes(8, "little")
 112      return r
 113  
 114  
 115  def deser_compact_size(f):
 116      nit = int.from_bytes(f.read(1), "little")
 117      if nit == 253:
 118          nit = int.from_bytes(f.read(2), "little")
 119      elif nit == 254:
 120          nit = int.from_bytes(f.read(4), "little")
 121      elif nit == 255:
 122          nit = int.from_bytes(f.read(8), "little")
 123      return nit
 124  
 125  
 126  def deser_string(f):
 127      nit = deser_compact_size(f)
 128      return f.read(nit)
 129  
 130  
 131  def ser_string(s):
 132      return ser_compact_size(len(s)) + s
 133  
 134  
 135  def deser_uint256(f):
 136      return int.from_bytes(f.read(32), 'little')
 137  
 138  
 139  def ser_uint256(u):
 140      return u.to_bytes(32, 'little')
 141  
 142  
 143  def uint256_from_str(s):
 144      return int.from_bytes(s[:32], 'little')
 145  
 146  
 147  def uint256_from_compact(c):
 148      nbytes = (c >> 24) & 0xFF
 149      v = (c & 0xFFFFFF) << (8 * (nbytes - 3))
 150      return v
 151  
 152  
 153  # deser_function_name: Allow for an alternate deserialization function on the
 154  # entries in the vector.
 155  def deser_vector(f, c, deser_function_name=None):
 156      nit = deser_compact_size(f)
 157      r = []
 158      for _ in range(nit):
 159          t = c()
 160          if deser_function_name:
 161              getattr(t, deser_function_name)(f)
 162          else:
 163              t.deserialize(f)
 164          r.append(t)
 165      return r
 166  
 167  
 168  # ser_function_name: Allow for an alternate serialization function on the
 169  # entries in the vector (we use this for serializing the vector of transactions
 170  # for a witness block).
 171  def ser_vector(l, ser_function_name=None):
 172      r = ser_compact_size(len(l))
 173      for i in l:
 174          if ser_function_name:
 175              r += getattr(i, ser_function_name)()
 176          else:
 177              r += i.serialize()
 178      return r
 179  
 180  
 181  def deser_uint256_vector(f):
 182      nit = deser_compact_size(f)
 183      r = []
 184      for _ in range(nit):
 185          t = deser_uint256(f)
 186          r.append(t)
 187      return r
 188  
 189  
 190  def ser_uint256_vector(l):
 191      r = ser_compact_size(len(l))
 192      for i in l:
 193          r += ser_uint256(i)
 194      return r
 195  
 196  
 197  def deser_string_vector(f):
 198      nit = deser_compact_size(f)
 199      r = []
 200      for _ in range(nit):
 201          t = deser_string(f)
 202          r.append(t)
 203      return r
 204  
 205  
 206  def ser_string_vector(l):
 207      r = ser_compact_size(len(l))
 208      for sv in l:
 209          r += ser_string(sv)
 210      return r
 211  
 212  
 213  def deser_block_spent_outputs(f):
 214      nit = deser_compact_size(f)
 215      return [deser_vector(f, CTxOut) for _ in range(nit)]
 216  
 217  
 218  def from_hex(obj, hex_string):
 219      """Deserialize from a hex string representation (e.g. from RPC)
 220  
 221      Note that there is no complementary helper like e.g. `to_hex` for the
 222      inverse operation. To serialize a message object to a hex string, simply
 223      use obj.serialize().hex()"""
 224      obj.deserialize(BytesIO(bytes.fromhex(hex_string)))
 225      return obj
 226  
 227  
 228  def tx_from_hex(hex_string):
 229      """Deserialize from hex string to a transaction object"""
 230      return from_hex(CTransaction(), hex_string)
 231  
 232  
 233  # like from_hex, but without the hex part
 234  def from_binary(cls, stream):
 235      """deserialize a binary stream (or bytes object) into an object"""
 236      # handle bytes object by turning it into a stream
 237      was_bytes = isinstance(stream, bytes)
 238      if was_bytes:
 239          stream = BytesIO(stream)
 240      obj = cls()
 241      obj.deserialize(stream)
 242      if was_bytes:
 243          assert len(stream.read()) == 0
 244      return obj
 245  
 246  
 247  # Objects that map to limenkad objects, which can be serialized/deserialized
 248  
 249  
 250  class CAddress:
 251      __slots__ = ("net", "ip", "nServices", "port", "time")
 252  
 253      # see https://github.com/limenka/bips/blob/master/bip-0155.mediawiki
 254      NET_IPV4 = 1
 255      NET_IPV6 = 2
 256      NET_TORV3 = 4
 257      NET_I2P = 5
 258      NET_CJDNS = 6
 259  
 260      ADDRV2_NET_NAME = {
 261          NET_IPV4: "IPv4",
 262          NET_IPV6: "IPv6",
 263          NET_TORV3: "TorV3",
 264          NET_I2P: "I2P",
 265          NET_CJDNS: "CJDNS"
 266      }
 267  
 268      ADDRV2_ADDRESS_LENGTH = {
 269          NET_IPV4: 4,
 270          NET_IPV6: 16,
 271          NET_TORV3: 32,
 272          NET_I2P: 32,
 273          NET_CJDNS: 16
 274      }
 275  
 276      I2P_PAD = "===="
 277  
 278      def __init__(self):
 279          self.time = 0
 280          self.nServices = 1
 281          self.net = self.NET_IPV4
 282          self.ip = "0.0.0.0"
 283          self.port = 0
 284  
 285      def __eq__(self, other):
 286          return self.net == other.net and self.ip == other.ip and self.nServices == other.nServices and self.port == other.port and self.time == other.time
 287  
 288      def deserialize(self, f, *, with_time=True):
 289          """Deserialize from addrv1 format (pre-BIP155)"""
 290          if with_time:
 291              # VERSION messages serialize CAddress objects without time
 292              self.time = int.from_bytes(f.read(4), "little")
 293          self.nServices = int.from_bytes(f.read(8), "little")
 294          # We only support IPv4 which means skip 12 bytes and read the next 4 as IPv4 address.
 295          f.read(12)
 296          self.net = self.NET_IPV4
 297          self.ip = socket.inet_ntoa(f.read(4))
 298          self.port = int.from_bytes(f.read(2), "big")
 299  
 300      def serialize(self, *, with_time=True):
 301          """Serialize in addrv1 format (pre-BIP155)"""
 302          assert self.net == self.NET_IPV4
 303          r = b""
 304          if with_time:
 305              # VERSION messages serialize CAddress objects without time
 306              r += self.time.to_bytes(4, "little")
 307          r += self.nServices.to_bytes(8, "little")
 308          r += b"\x00" * 10 + b"\xff" * 2
 309          r += socket.inet_aton(self.ip)
 310          r += self.port.to_bytes(2, "big")
 311          return r
 312  
 313      def deserialize_v2(self, f):
 314          """Deserialize from addrv2 format (BIP155)"""
 315          self.time = int.from_bytes(f.read(4), "little")
 316  
 317          self.nServices = deser_compact_size(f)
 318  
 319          self.net = int.from_bytes(f.read(1), "little")
 320          assert self.net in self.ADDRV2_NET_NAME
 321  
 322          address_length = deser_compact_size(f)
 323          assert address_length == self.ADDRV2_ADDRESS_LENGTH[self.net]
 324  
 325          addr_bytes = f.read(address_length)
 326          if self.net == self.NET_IPV4:
 327              self.ip = socket.inet_ntoa(addr_bytes)
 328          elif self.net == self.NET_IPV6:
 329              self.ip = socket.inet_ntop(socket.AF_INET6, addr_bytes)
 330          elif self.net == self.NET_TORV3:
 331              prefix = b".onion checksum"
 332              version = bytes([3])
 333              checksum = sha3(prefix + addr_bytes + version)[:2]
 334              self.ip = b32encode(addr_bytes + checksum + version).decode("ascii").lower() + ".onion"
 335          elif self.net == self.NET_I2P:
 336              self.ip = b32encode(addr_bytes)[0:-len(self.I2P_PAD)].decode("ascii").lower() + ".b32.i2p"
 337          elif self.net == self.NET_CJDNS:
 338              self.ip = socket.inet_ntop(socket.AF_INET6, addr_bytes)
 339          else:
 340              raise Exception("Address type not supported")
 341  
 342          self.port = int.from_bytes(f.read(2), "big")
 343  
 344      def serialize_v2(self):
 345          """Serialize in addrv2 format (BIP155)"""
 346          assert self.net in self.ADDRV2_NET_NAME
 347          r = b""
 348          r += self.time.to_bytes(4, "little")
 349          r += ser_compact_size(self.nServices)
 350          r += self.net.to_bytes(1, "little")
 351          r += ser_compact_size(self.ADDRV2_ADDRESS_LENGTH[self.net])
 352          if self.net == self.NET_IPV4:
 353              r += socket.inet_aton(self.ip)
 354          elif self.net == self.NET_IPV6:
 355              r += socket.inet_pton(socket.AF_INET6, self.ip)
 356          elif self.net == self.NET_TORV3:
 357              sfx = ".onion"
 358              assert self.ip.endswith(sfx)
 359              r += b32decode(self.ip[0:-len(sfx)], True)[0:32]
 360          elif self.net == self.NET_I2P:
 361              sfx = ".b32.i2p"
 362              assert self.ip.endswith(sfx)
 363              r += b32decode(self.ip[0:-len(sfx)] + self.I2P_PAD, True)
 364          elif self.net == self.NET_CJDNS:
 365              r += socket.inet_pton(socket.AF_INET6, self.ip)
 366          else:
 367              raise Exception("Address type not supported")
 368          r += self.port.to_bytes(2, "big")
 369          return r
 370  
 371      def __repr__(self):
 372          return ("CAddress(nServices=%i net=%s addr=%s port=%i)"
 373                  % (self.nServices, self.ADDRV2_NET_NAME[self.net], self.ip, self.port))
 374  
 375  
 376  class CInv:
 377      __slots__ = ("hash", "type")
 378  
 379      typemap = {
 380          0: "Error",
 381          MSG_TX: "TX",
 382          MSG_BLOCK: "Block",
 383          MSG_TX | MSG_WITNESS_FLAG: "WitnessTx",
 384          MSG_BLOCK | MSG_WITNESS_FLAG: "WitnessBlock",
 385          MSG_FILTERED_BLOCK: "filtered Block",
 386          MSG_CMPCT_BLOCK: "CompactBlock",
 387          MSG_WTX: "WTX",
 388      }
 389  
 390      def __init__(self, t=0, h=0):
 391          self.type = t
 392          self.hash = h
 393  
 394      def deserialize(self, f):
 395          self.type = int.from_bytes(f.read(4), "little")
 396          self.hash = deser_uint256(f)
 397  
 398      def serialize(self):
 399          r = b""
 400          r += self.type.to_bytes(4, "little")
 401          r += ser_uint256(self.hash)
 402          return r
 403  
 404      def __repr__(self):
 405          return "CInv(type=%s hash=%064x)" \
 406              % (self.typemap[self.type], self.hash)
 407  
 408      def __eq__(self, other):
 409          return isinstance(other, CInv) and self.hash == other.hash and self.type == other.type
 410  
 411  
 412  class CBlockLocator:
 413      __slots__ = ("nVersion", "vHave")
 414  
 415      def __init__(self):
 416          self.vHave = []
 417  
 418      def deserialize(self, f):
 419          int.from_bytes(f.read(4), "little", signed=True)  # Ignore version field.
 420          self.vHave = deser_uint256_vector(f)
 421  
 422      def serialize(self):
 423          r = b""
 424          r += (0).to_bytes(4, "little", signed=True)  # Limenka ignores the version field. Set it to 0.
 425          r += ser_uint256_vector(self.vHave)
 426          return r
 427  
 428      def __repr__(self):
 429          return "CBlockLocator(vHave=%s)" % (repr(self.vHave))
 430  
 431  
 432  class COutPoint:
 433      __slots__ = ("hash", "n")
 434  
 435      def __init__(self, hash=0, n=0):
 436          self.hash = hash
 437          self.n = n
 438  
 439      def deserialize(self, f):
 440          self.hash = deser_uint256(f)
 441          self.n = int.from_bytes(f.read(4), "little")
 442  
 443      def serialize(self):
 444          r = b""
 445          r += ser_uint256(self.hash)
 446          r += self.n.to_bytes(4, "little")
 447          return r
 448  
 449      def __repr__(self):
 450          return "COutPoint(hash=%064x n=%i)" % (self.hash, self.n)
 451  
 452  
 453  class CTxIn:
 454      __slots__ = ("nSequence", "prevout", "scriptSig")
 455  
 456      def __init__(self, outpoint=None, scriptSig=b"", nSequence=0):
 457          if outpoint is None:
 458              self.prevout = COutPoint()
 459          else:
 460              self.prevout = outpoint
 461          self.scriptSig = scriptSig
 462          self.nSequence = nSequence
 463  
 464      def deserialize(self, f):
 465          self.prevout = COutPoint()
 466          self.prevout.deserialize(f)
 467          self.scriptSig = deser_string(f)
 468          self.nSequence = int.from_bytes(f.read(4), "little")
 469  
 470      def serialize(self):
 471          r = b""
 472          r += self.prevout.serialize()
 473          r += ser_string(self.scriptSig)
 474          r += self.nSequence.to_bytes(4, "little")
 475          return r
 476  
 477      def __repr__(self):
 478          return "CTxIn(prevout=%s scriptSig=%s nSequence=%i)" \
 479              % (repr(self.prevout), self.scriptSig.hex(),
 480                 self.nSequence)
 481  
 482  
 483  class CTxOut:
 484      __slots__ = ("nValue", "scriptPubKey")
 485  
 486      def __init__(self, nValue=0, scriptPubKey=b""):
 487          self.nValue = nValue
 488          self.scriptPubKey = scriptPubKey
 489  
 490      def deserialize(self, f):
 491          self.nValue = int.from_bytes(f.read(8), "little", signed=True)
 492          self.scriptPubKey = deser_string(f)
 493  
 494      def serialize(self):
 495          r = b""
 496          r += self.nValue.to_bytes(8, "little", signed=True)
 497          r += ser_string(self.scriptPubKey)
 498          return r
 499  
 500      def __repr__(self):
 501          return "CTxOut(nValue=%i.%08i scriptPubKey=%s)" \
 502              % (self.nValue // COIN, self.nValue % COIN,
 503                 self.scriptPubKey.hex())
 504  
 505  
 506  class CScriptWitness:
 507      __slots__ = ("stack",)
 508  
 509      def __init__(self):
 510          # stack is a vector of strings
 511          self.stack = []
 512  
 513      def __repr__(self):
 514          return "CScriptWitness(%s)" % \
 515                 (",".join([x.hex() for x in self.stack]))
 516  
 517      def is_null(self):
 518          if self.stack:
 519              return False
 520          return True
 521  
 522  
 523  class CTxInWitness:
 524      __slots__ = ("scriptWitness",)
 525  
 526      def __init__(self):
 527          self.scriptWitness = CScriptWitness()
 528  
 529      def deserialize(self, f):
 530          self.scriptWitness.stack = deser_string_vector(f)
 531  
 532      def serialize(self):
 533          return ser_string_vector(self.scriptWitness.stack)
 534  
 535      def __repr__(self):
 536          return repr(self.scriptWitness)
 537  
 538      def is_null(self):
 539          return self.scriptWitness.is_null()
 540  
 541  
 542  class CTxWitness:
 543      __slots__ = ("vtxinwit",)
 544  
 545      def __init__(self):
 546          self.vtxinwit = []
 547  
 548      def deserialize(self, f):
 549          for i in range(len(self.vtxinwit)):
 550              self.vtxinwit[i].deserialize(f)
 551  
 552      def serialize(self):
 553          r = b""
 554          # This is different than the usual vector serialization --
 555          # we omit the length of the vector, which is required to be
 556          # the same length as the transaction's vin vector.
 557          for x in self.vtxinwit:
 558              r += x.serialize()
 559          return r
 560  
 561      def __repr__(self):
 562          return "CTxWitness(%s)" % \
 563                 (';'.join([repr(x) for x in self.vtxinwit]))
 564  
 565      def is_null(self):
 566          for x in self.vtxinwit:
 567              if not x.is_null():
 568                  return False
 569          return True
 570  
 571  
 572  class CTransaction:
 573      __slots__ = ("hash", "nLockTime", "version", "sha256", "vin", "vout",
 574                   "wit")
 575  
 576      def __init__(self, tx=None):
 577          if tx is None:
 578              self.version = 2
 579              self.vin = []
 580              self.vout = []
 581              self.wit = CTxWitness()
 582              self.nLockTime = 0
 583              self.sha256 = None
 584              self.hash = None
 585          else:
 586              self.version = tx.version
 587              self.vin = copy.deepcopy(tx.vin)
 588              self.vout = copy.deepcopy(tx.vout)
 589              self.nLockTime = tx.nLockTime
 590              self.sha256 = tx.sha256
 591              self.hash = tx.hash
 592              self.wit = copy.deepcopy(tx.wit)
 593  
 594      def deserialize(self, f):
 595          self.version = int.from_bytes(f.read(4), "little")
 596          self.vin = deser_vector(f, CTxIn)
 597          flags = 0
 598          if len(self.vin) == 0:
 599              flags = int.from_bytes(f.read(1), "little")
 600              # Not sure why flags can't be zero, but this
 601              # matches the implementation in limenkad
 602              if (flags != 0):
 603                  self.vin = deser_vector(f, CTxIn)
 604                  self.vout = deser_vector(f, CTxOut)
 605          else:
 606              self.vout = deser_vector(f, CTxOut)
 607          if flags != 0:
 608              self.wit.vtxinwit = [CTxInWitness() for _ in range(len(self.vin))]
 609              self.wit.deserialize(f)
 610          else:
 611              self.wit = CTxWitness()
 612          self.nLockTime = int.from_bytes(f.read(4), "little")
 613          self.sha256 = None
 614          self.hash = None
 615  
 616      def serialize_without_witness(self):
 617          r = b""
 618          r += self.version.to_bytes(4, "little")
 619          r += ser_vector(self.vin)
 620          r += ser_vector(self.vout)
 621          r += self.nLockTime.to_bytes(4, "little")
 622          return r
 623  
 624      # Only serialize with witness when explicitly called for
 625      def serialize_with_witness(self):
 626          flags = 0
 627          if not self.wit.is_null():
 628              flags |= 1
 629          r = b""
 630          r += self.version.to_bytes(4, "little")
 631          if flags:
 632              dummy = []
 633              r += ser_vector(dummy)
 634              r += flags.to_bytes(1, "little")
 635          r += ser_vector(self.vin)
 636          r += ser_vector(self.vout)
 637          if flags & 1:
 638              if (len(self.wit.vtxinwit) != len(self.vin)):
 639                  # vtxinwit must have the same length as vin
 640                  self.wit.vtxinwit = self.wit.vtxinwit[:len(self.vin)]
 641                  for _ in range(len(self.wit.vtxinwit), len(self.vin)):
 642                      self.wit.vtxinwit.append(CTxInWitness())
 643              r += self.wit.serialize()
 644          r += self.nLockTime.to_bytes(4, "little")
 645          return r
 646  
 647      # Regular serialization is with witness -- must explicitly
 648      # call serialize_without_witness to exclude witness data.
 649      def serialize(self):
 650          return self.serialize_with_witness()
 651  
 652      def getwtxid(self):
 653          return hash256(self.serialize())[::-1].hex()
 654  
 655      # Recalculate the txid (transaction hash without witness)
 656      def rehash(self):
 657          self.sha256 = None
 658          self.calc_sha256()
 659          return self.hash
 660  
 661      # We will only cache the serialization without witness in
 662      # self.sha256 and self.hash -- those are expected to be the txid.
 663      def calc_sha256(self, with_witness=False):
 664          if with_witness:
 665              # Don't cache the result, just return it
 666              return uint256_from_str(hash256(self.serialize_with_witness()))
 667  
 668          if self.sha256 is None:
 669              self.sha256 = uint256_from_str(hash256(self.serialize_without_witness()))
 670          self.hash = hash256(self.serialize_without_witness())[::-1].hex()
 671  
 672      def is_valid(self):
 673          self.calc_sha256()
 674          for tout in self.vout:
 675              if tout.nValue < 0 or tout.nValue > 21000000 * COIN:
 676                  return False
 677          return True
 678  
 679      # Calculate the transaction weight using witness and non-witness
 680      # serialization size (does NOT use sigops).
 681      def get_weight(self):
 682          with_witness_size = len(self.serialize_with_witness())
 683          without_witness_size = len(self.serialize_without_witness())
 684          return (WITNESS_SCALE_FACTOR - 1) * without_witness_size + with_witness_size
 685  
 686      def get_vsize(self):
 687          return math.ceil(self.get_weight() / WITNESS_SCALE_FACTOR)
 688  
 689      def __repr__(self):
 690          return "CTransaction(version=%i vin=%s vout=%s wit=%s nLockTime=%i)" \
 691              % (self.version, repr(self.vin), repr(self.vout), repr(self.wit), self.nLockTime)
 692  
 693  
 694  class CBlockHeader:
 695      __slots__ = ("hash", "hashMerkleRoot", "hashPrevBlock", "nBits", "nNonce",
 696                   "nTime", "nVersion", "sha256")
 697  
 698      def __init__(self, header=None):
 699          if header is None:
 700              self.set_null()
 701          else:
 702              self.nVersion = header.nVersion
 703              self.hashPrevBlock = header.hashPrevBlock
 704              self.hashMerkleRoot = header.hashMerkleRoot
 705              self.nTime = header.nTime
 706              self.nBits = header.nBits
 707              self.nNonce = header.nNonce
 708              self.sha256 = header.sha256
 709              self.hash = header.hash
 710              self.calc_sha256()
 711  
 712      def set_null(self):
 713          self.nVersion = 4
 714          self.hashPrevBlock = 0
 715          self.hashMerkleRoot = 0
 716          self.nTime = 0
 717          self.nBits = 0
 718          self.nNonce = 0
 719          self.sha256 = None
 720          self.hash = None
 721  
 722      def deserialize(self, f):
 723          self.nVersion = int.from_bytes(f.read(4), "little", signed=True)
 724          self.hashPrevBlock = deser_uint256(f)
 725          self.hashMerkleRoot = deser_uint256(f)
 726          self.nTime = int.from_bytes(f.read(4), "little")
 727          self.nBits = int.from_bytes(f.read(4), "little")
 728          self.nNonce = int.from_bytes(f.read(4), "little")
 729          self.sha256 = None
 730          self.hash = None
 731  
 732      def serialize(self):
 733          r = b""
 734          r += self.nVersion.to_bytes(4, "little", signed=True)
 735          r += ser_uint256(self.hashPrevBlock)
 736          r += ser_uint256(self.hashMerkleRoot)
 737          r += self.nTime.to_bytes(4, "little")
 738          r += self.nBits.to_bytes(4, "little")
 739          r += self.nNonce.to_bytes(4, "little")
 740          return r
 741  
 742      def calc_sha256(self):
 743          if self.sha256 is None:
 744              r = b""
 745              r += self.nVersion.to_bytes(4, "little", signed=True)
 746              r += ser_uint256(self.hashPrevBlock)
 747              r += ser_uint256(self.hashMerkleRoot)
 748              r += self.nTime.to_bytes(4, "little")
 749              r += self.nBits.to_bytes(4, "little")
 750              r += self.nNonce.to_bytes(4, "little")
 751              self.sha256 = uint256_from_str(hash256(r))
 752              self.hash = hash256(r)[::-1].hex()
 753  
 754      def rehash(self):
 755          self.sha256 = None
 756          self.calc_sha256()
 757          return self.sha256
 758  
 759      def __repr__(self):
 760          return "CBlockHeader(nVersion=%i hashPrevBlock=%064x hashMerkleRoot=%064x nTime=%s nBits=%08x nNonce=%08x)" \
 761              % (self.nVersion, self.hashPrevBlock, self.hashMerkleRoot,
 762                 time.ctime(self.nTime), self.nBits, self.nNonce)
 763  
 764  BLOCK_HEADER_SIZE = len(CBlockHeader().serialize())
 765  assert_equal(BLOCK_HEADER_SIZE, 80)
 766  
 767  class CBlock(CBlockHeader):
 768      __slots__ = ("vtx",)
 769  
 770      def __init__(self, header=None):
 771          super().__init__(header)
 772          self.vtx = []
 773  
 774      def deserialize(self, f):
 775          super().deserialize(f)
 776          self.vtx = deser_vector(f, CTransaction)
 777  
 778      def serialize(self, with_witness=True):
 779          r = b""
 780          r += super().serialize()
 781          if with_witness:
 782              r += ser_vector(self.vtx, "serialize_with_witness")
 783          else:
 784              r += ser_vector(self.vtx, "serialize_without_witness")
 785          return r
 786  
 787      # Calculate the merkle root given a vector of transaction hashes
 788      @classmethod
 789      def get_merkle_root(cls, hashes):
 790          while len(hashes) > 1:
 791              newhashes = []
 792              for i in range(0, len(hashes), 2):
 793                  i2 = min(i+1, len(hashes)-1)
 794                  newhashes.append(hash256(hashes[i] + hashes[i2]))
 795              hashes = newhashes
 796          return uint256_from_str(hashes[0])
 797  
 798      def calc_merkle_root(self):
 799          hashes = []
 800          for tx in self.vtx:
 801              tx.calc_sha256()
 802              hashes.append(ser_uint256(tx.sha256))
 803          return self.get_merkle_root(hashes)
 804  
 805      def calc_witness_merkle_root(self):
 806          # For witness root purposes, the hash of the
 807          # coinbase, with witness, is defined to be 0...0
 808          hashes = [ser_uint256(0)]
 809  
 810          for tx in self.vtx[1:]:
 811              # Calculate the hashes with witness data
 812              hashes.append(ser_uint256(tx.calc_sha256(True)))
 813  
 814          return self.get_merkle_root(hashes)
 815  
 816      def is_valid(self):
 817          self.calc_sha256()
 818          target = uint256_from_compact(self.nBits)
 819          if self.sha256 > target:
 820              return False
 821          for tx in self.vtx:
 822              if not tx.is_valid():
 823                  return False
 824          if self.calc_merkle_root() != self.hashMerkleRoot:
 825              return False
 826          return True
 827  
 828      def solve(self):
 829          self.rehash()
 830          target = uint256_from_compact(self.nBits)
 831          while self.sha256 > target:
 832              self.nNonce += 1
 833              self.rehash()
 834  
 835      # Calculate the block weight using witness and non-witness
 836      # serialization size (does NOT use sigops).
 837      def get_weight(self):
 838          with_witness_size = len(self.serialize(with_witness=True))
 839          without_witness_size = len(self.serialize(with_witness=False))
 840          return (WITNESS_SCALE_FACTOR - 1) * without_witness_size + with_witness_size
 841  
 842      def __repr__(self):
 843          return "CBlock(nVersion=%i hashPrevBlock=%064x hashMerkleRoot=%064x nTime=%s nBits=%08x nNonce=%08x vtx=%s)" \
 844              % (self.nVersion, self.hashPrevBlock, self.hashMerkleRoot,
 845                 time.ctime(self.nTime), self.nBits, self.nNonce, repr(self.vtx))
 846  
 847  
 848  class PrefilledTransaction:
 849      __slots__ = ("index", "tx")
 850  
 851      def __init__(self, index=0, tx = None):
 852          self.index = index
 853          self.tx = tx
 854  
 855      def deserialize(self, f):
 856          self.index = deser_compact_size(f)
 857          self.tx = CTransaction()
 858          self.tx.deserialize(f)
 859  
 860      def serialize(self, with_witness=True):
 861          r = b""
 862          r += ser_compact_size(self.index)
 863          if with_witness:
 864              r += self.tx.serialize_with_witness()
 865          else:
 866              r += self.tx.serialize_without_witness()
 867          return r
 868  
 869      def serialize_without_witness(self):
 870          return self.serialize(with_witness=False)
 871  
 872      def serialize_with_witness(self):
 873          return self.serialize(with_witness=True)
 874  
 875      def __repr__(self):
 876          return "PrefilledTransaction(index=%d, tx=%s)" % (self.index, repr(self.tx))
 877  
 878  
 879  # This is what we send on the wire, in a cmpctblock message.
 880  class P2PHeaderAndShortIDs:
 881      __slots__ = ("header", "nonce", "prefilled_txn", "prefilled_txn_length",
 882                   "shortids", "shortids_length")
 883  
 884      def __init__(self):
 885          self.header = CBlockHeader()
 886          self.nonce = 0
 887          self.shortids_length = 0
 888          self.shortids = []
 889          self.prefilled_txn_length = 0
 890          self.prefilled_txn = []
 891  
 892      def deserialize(self, f):
 893          self.header.deserialize(f)
 894          self.nonce = int.from_bytes(f.read(8), "little")
 895          self.shortids_length = deser_compact_size(f)
 896          for _ in range(self.shortids_length):
 897              # shortids are defined to be 6 bytes in the spec, so append
 898              # two zero bytes and read it in as an 8-byte number
 899              self.shortids.append(int.from_bytes(f.read(6) + b'\x00\x00', "little"))
 900          self.prefilled_txn = deser_vector(f, PrefilledTransaction)
 901          self.prefilled_txn_length = len(self.prefilled_txn)
 902  
 903      # When using version 2 compact blocks, we must serialize with_witness.
 904      def serialize(self, with_witness=False):
 905          r = b""
 906          r += self.header.serialize()
 907          r += self.nonce.to_bytes(8, "little")
 908          r += ser_compact_size(self.shortids_length)
 909          for x in self.shortids:
 910              # We only want the first 6 bytes
 911              r += x.to_bytes(8, "little")[0:6]
 912          if with_witness:
 913              r += ser_vector(self.prefilled_txn, "serialize_with_witness")
 914          else:
 915              r += ser_vector(self.prefilled_txn, "serialize_without_witness")
 916          return r
 917  
 918      def __repr__(self):
 919          return "P2PHeaderAndShortIDs(header=%s, nonce=%d, shortids_length=%d, shortids=%s, prefilled_txn_length=%d, prefilledtxn=%s" % (repr(self.header), self.nonce, self.shortids_length, repr(self.shortids), self.prefilled_txn_length, repr(self.prefilled_txn))
 920  
 921  
 922  # P2P version of the above that will use witness serialization (for compact
 923  # block version 2)
 924  class P2PHeaderAndShortWitnessIDs(P2PHeaderAndShortIDs):
 925      __slots__ = ()
 926      def serialize(self):
 927          return super().serialize(with_witness=True)
 928  
 929  # Calculate the BIP 152-compact blocks shortid for a given transaction hash
 930  def calculate_shortid(k0, k1, tx_hash):
 931      expected_shortid = siphash256(k0, k1, tx_hash)
 932      expected_shortid &= 0x0000ffffffffffff
 933      return expected_shortid
 934  
 935  
 936  # This version gets rid of the array lengths, and reinterprets the differential
 937  # encoding into indices that can be used for lookup.
 938  class HeaderAndShortIDs:
 939      __slots__ = ("header", "nonce", "prefilled_txn", "shortids", "use_witness")
 940  
 941      def __init__(self, p2pheaders_and_shortids = None):
 942          self.header = CBlockHeader()
 943          self.nonce = 0
 944          self.shortids = []
 945          self.prefilled_txn = []
 946          self.use_witness = False
 947  
 948          if p2pheaders_and_shortids is not None:
 949              self.header = p2pheaders_and_shortids.header
 950              self.nonce = p2pheaders_and_shortids.nonce
 951              self.shortids = p2pheaders_and_shortids.shortids
 952              last_index = -1
 953              for x in p2pheaders_and_shortids.prefilled_txn:
 954                  self.prefilled_txn.append(PrefilledTransaction(x.index + last_index + 1, x.tx))
 955                  last_index = self.prefilled_txn[-1].index
 956  
 957      def to_p2p(self):
 958          if self.use_witness:
 959              ret = P2PHeaderAndShortWitnessIDs()
 960          else:
 961              ret = P2PHeaderAndShortIDs()
 962          ret.header = self.header
 963          ret.nonce = self.nonce
 964          ret.shortids_length = len(self.shortids)
 965          ret.shortids = self.shortids
 966          ret.prefilled_txn_length = len(self.prefilled_txn)
 967          ret.prefilled_txn = []
 968          last_index = -1
 969          for x in self.prefilled_txn:
 970              ret.prefilled_txn.append(PrefilledTransaction(x.index - last_index - 1, x.tx))
 971              last_index = x.index
 972          return ret
 973  
 974      def get_siphash_keys(self):
 975          header_nonce = self.header.serialize()
 976          header_nonce += self.nonce.to_bytes(8, "little")
 977          hash_header_nonce_as_str = sha256(header_nonce)
 978          key0 = int.from_bytes(hash_header_nonce_as_str[0:8], "little")
 979          key1 = int.from_bytes(hash_header_nonce_as_str[8:16], "little")
 980          return [ key0, key1 ]
 981  
 982      # Version 2 compact blocks use wtxid in shortids (rather than txid)
 983      def initialize_from_block(self, block, nonce=0, prefill_list=None, use_witness=False):
 984          if prefill_list is None:
 985              prefill_list = [0]
 986          self.header = CBlockHeader(block)
 987          self.nonce = nonce
 988          self.prefilled_txn = [ PrefilledTransaction(i, block.vtx[i]) for i in prefill_list ]
 989          self.shortids = []
 990          self.use_witness = use_witness
 991          [k0, k1] = self.get_siphash_keys()
 992          for i in range(len(block.vtx)):
 993              if i not in prefill_list:
 994                  tx_hash = block.vtx[i].sha256
 995                  if use_witness:
 996                      tx_hash = block.vtx[i].calc_sha256(with_witness=True)
 997                  self.shortids.append(calculate_shortid(k0, k1, tx_hash))
 998  
 999      def __repr__(self):
1000          return "HeaderAndShortIDs(header=%s, nonce=%d, shortids=%s, prefilledtxn=%s" % (repr(self.header), self.nonce, repr(self.shortids), repr(self.prefilled_txn))
1001  
1002  
1003  class BlockTransactionsRequest:
1004      __slots__ = ("blockhash", "indexes")
1005  
1006      def __init__(self, blockhash=0, indexes = None):
1007          self.blockhash = blockhash
1008          self.indexes = indexes if indexes is not None else []
1009  
1010      def deserialize(self, f):
1011          self.blockhash = deser_uint256(f)
1012          indexes_length = deser_compact_size(f)
1013          for _ in range(indexes_length):
1014              self.indexes.append(deser_compact_size(f))
1015  
1016      def serialize(self):
1017          r = b""
1018          r += ser_uint256(self.blockhash)
1019          r += ser_compact_size(len(self.indexes))
1020          for x in self.indexes:
1021              r += ser_compact_size(x)
1022          return r
1023  
1024      # helper to set the differentially encoded indexes from absolute ones
1025      def from_absolute(self, absolute_indexes):
1026          self.indexes = []
1027          last_index = -1
1028          for x in absolute_indexes:
1029              self.indexes.append(x-last_index-1)
1030              last_index = x
1031  
1032      def to_absolute(self):
1033          absolute_indexes = []
1034          last_index = -1
1035          for x in self.indexes:
1036              absolute_indexes.append(x+last_index+1)
1037              last_index = absolute_indexes[-1]
1038          return absolute_indexes
1039  
1040      def __repr__(self):
1041          return "BlockTransactionsRequest(hash=%064x indexes=%s)" % (self.blockhash, repr(self.indexes))
1042  
1043  
1044  class BlockTransactions:
1045      __slots__ = ("blockhash", "transactions")
1046  
1047      def __init__(self, blockhash=0, transactions = None):
1048          self.blockhash = blockhash
1049          self.transactions = transactions if transactions is not None else []
1050  
1051      def deserialize(self, f):
1052          self.blockhash = deser_uint256(f)
1053          self.transactions = deser_vector(f, CTransaction)
1054  
1055      def serialize(self, with_witness=True):
1056          r = b""
1057          r += ser_uint256(self.blockhash)
1058          if with_witness:
1059              r += ser_vector(self.transactions, "serialize_with_witness")
1060          else:
1061              r += ser_vector(self.transactions, "serialize_without_witness")
1062          return r
1063  
1064      def __repr__(self):
1065          return "BlockTransactions(hash=%064x transactions=%s)" % (self.blockhash, repr(self.transactions))
1066  
1067  
1068  class CPartialMerkleTree:
1069      __slots__ = ("nTransactions", "vBits", "vHash")
1070  
1071      def __init__(self):
1072          self.nTransactions = 0
1073          self.vHash = []
1074          self.vBits = []
1075  
1076      def deserialize(self, f):
1077          self.nTransactions = int.from_bytes(f.read(4), "little")
1078          self.vHash = deser_uint256_vector(f)
1079          vBytes = deser_string(f)
1080          self.vBits = []
1081          for i in range(len(vBytes) * 8):
1082              self.vBits.append(vBytes[i//8] & (1 << (i % 8)) != 0)
1083  
1084      def serialize(self):
1085          r = b""
1086          r += self.nTransactions.to_bytes(4, "little")
1087          r += ser_uint256_vector(self.vHash)
1088          vBytesArray = bytearray([0x00] * ((len(self.vBits) + 7)//8))
1089          for i in range(len(self.vBits)):
1090              vBytesArray[i // 8] |= self.vBits[i] << (i % 8)
1091          r += ser_string(bytes(vBytesArray))
1092          return r
1093  
1094      def __repr__(self):
1095          return "CPartialMerkleTree(nTransactions=%d, vHash=%s, vBits=%s)" % (self.nTransactions, repr(self.vHash), repr(self.vBits))
1096  
1097  
1098  class CMerkleBlock:
1099      __slots__ = ("header", "txn")
1100  
1101      def __init__(self):
1102          self.header = CBlockHeader()
1103          self.txn = CPartialMerkleTree()
1104  
1105      def deserialize(self, f):
1106          self.header.deserialize(f)
1107          self.txn.deserialize(f)
1108  
1109      def serialize(self):
1110          r = b""
1111          r += self.header.serialize()
1112          r += self.txn.serialize()
1113          return r
1114  
1115      def __repr__(self):
1116          return "CMerkleBlock(header=%s, txn=%s)" % (repr(self.header), repr(self.txn))
1117  
1118  
1119  # Objects that correspond to messages on the wire
1120  class msg_version:
1121      __slots__ = ("addrFrom", "addrTo", "nNonce", "relay", "nServices",
1122                   "nStartingHeight", "nTime", "nVersion", "strSubVer")
1123      msgtype = b"version"
1124  
1125      def __init__(self):
1126          self.nVersion = 0
1127          self.nServices = 0
1128          self.nTime = int(time.time())
1129          self.addrTo = CAddress()
1130          self.addrFrom = CAddress()
1131          self.nNonce = random.getrandbits(64)
1132          self.strSubVer = ''
1133          self.nStartingHeight = -1
1134          self.relay = 0
1135  
1136      def deserialize(self, f):
1137          self.nVersion = int.from_bytes(f.read(4), "little", signed=True)
1138          self.nServices = int.from_bytes(f.read(8), "little")
1139          self.nTime = int.from_bytes(f.read(8), "little", signed=True)
1140          self.addrTo = CAddress()
1141          self.addrTo.deserialize(f, with_time=False)
1142  
1143          self.addrFrom = CAddress()
1144          self.addrFrom.deserialize(f, with_time=False)
1145          self.nNonce = int.from_bytes(f.read(8), "little")
1146          self.strSubVer = deser_string(f).decode('utf-8')
1147  
1148          self.nStartingHeight = int.from_bytes(f.read(4), "little", signed=True)
1149  
1150          # Relay field is optional for version 70001 onwards
1151          # But, unconditionally check it to match behaviour in limenkad
1152          self.relay = int.from_bytes(f.read(1), "little")  # f.read(1) may return an empty b''
1153  
1154      def serialize(self):
1155          r = b""
1156          r += self.nVersion.to_bytes(4, "little", signed=True)
1157          r += self.nServices.to_bytes(8, "little")
1158          r += self.nTime.to_bytes(8, "little", signed=True)
1159          r += self.addrTo.serialize(with_time=False)
1160          r += self.addrFrom.serialize(with_time=False)
1161          r += self.nNonce.to_bytes(8, "little")
1162          r += ser_string(self.strSubVer.encode('utf-8'))
1163          r += self.nStartingHeight.to_bytes(4, "little", signed=True)
1164          r += self.relay.to_bytes(1, "little")
1165          return r
1166  
1167      def __repr__(self):
1168          return 'msg_version(nVersion=%i nServices=%i nTime=%s addrTo=%s addrFrom=%s nNonce=0x%016X strSubVer=%s nStartingHeight=%i relay=%i)' \
1169              % (self.nVersion, self.nServices, time.ctime(self.nTime),
1170                 repr(self.addrTo), repr(self.addrFrom), self.nNonce,
1171                 self.strSubVer, self.nStartingHeight, self.relay)
1172  
1173  
1174  class msg_verack:
1175      __slots__ = ()
1176      msgtype = b"verack"
1177  
1178      def __init__(self):
1179          pass
1180  
1181      def deserialize(self, f):
1182          pass
1183  
1184      def serialize(self):
1185          return b""
1186  
1187      def __repr__(self):
1188          return "msg_verack()"
1189  
1190  
1191  class msg_addr:
1192      __slots__ = ("addrs",)
1193      msgtype = b"addr"
1194  
1195      def __init__(self):
1196          self.addrs = []
1197  
1198      def deserialize(self, f):
1199          self.addrs = deser_vector(f, CAddress)
1200  
1201      def serialize(self):
1202          return ser_vector(self.addrs)
1203  
1204      def __repr__(self):
1205          return "msg_addr(addrs=%s)" % (repr(self.addrs))
1206  
1207  
1208  class msg_addrv2:
1209      __slots__ = ("addrs",)
1210      msgtype = b"addrv2"
1211  
1212      def __init__(self):
1213          self.addrs = []
1214  
1215      def deserialize(self, f):
1216          self.addrs = deser_vector(f, CAddress, "deserialize_v2")
1217  
1218      def serialize(self):
1219          return ser_vector(self.addrs, "serialize_v2")
1220  
1221      def __repr__(self):
1222          return "msg_addrv2(addrs=%s)" % (repr(self.addrs))
1223  
1224  
1225  class msg_sendaddrv2:
1226      __slots__ = ()
1227      msgtype = b"sendaddrv2"
1228  
1229      def __init__(self):
1230          pass
1231  
1232      def deserialize(self, f):
1233          pass
1234  
1235      def serialize(self):
1236          return b""
1237  
1238      def __repr__(self):
1239          return "msg_sendaddrv2()"
1240  
1241  
1242  class msg_inv:
1243      __slots__ = ("inv",)
1244      msgtype = b"inv"
1245  
1246      def __init__(self, inv=None):
1247          if inv is None:
1248              self.inv = []
1249          else:
1250              self.inv = inv
1251  
1252      def deserialize(self, f):
1253          self.inv = deser_vector(f, CInv)
1254  
1255      def serialize(self):
1256          return ser_vector(self.inv)
1257  
1258      def __repr__(self):
1259          return "msg_inv(inv=%s)" % (repr(self.inv))
1260  
1261  
1262  class msg_getdata:
1263      __slots__ = ("inv",)
1264      msgtype = b"getdata"
1265  
1266      def __init__(self, inv=None):
1267          self.inv = inv if inv is not None else []
1268  
1269      def deserialize(self, f):
1270          self.inv = deser_vector(f, CInv)
1271  
1272      def serialize(self):
1273          return ser_vector(self.inv)
1274  
1275      def __repr__(self):
1276          return "msg_getdata(inv=%s)" % (repr(self.inv))
1277  
1278  
1279  class msg_getblocks:
1280      __slots__ = ("locator", "hashstop")
1281      msgtype = b"getblocks"
1282  
1283      def __init__(self):
1284          self.locator = CBlockLocator()
1285          self.hashstop = 0
1286  
1287      def deserialize(self, f):
1288          self.locator = CBlockLocator()
1289          self.locator.deserialize(f)
1290          self.hashstop = deser_uint256(f)
1291  
1292      def serialize(self):
1293          r = b""
1294          r += self.locator.serialize()
1295          r += ser_uint256(self.hashstop)
1296          return r
1297  
1298      def __repr__(self):
1299          return "msg_getblocks(locator=%s hashstop=%064x)" \
1300              % (repr(self.locator), self.hashstop)
1301  
1302  
1303  class msg_tx:
1304      __slots__ = ("tx",)
1305      msgtype = b"tx"
1306  
1307      def __init__(self, tx=None):
1308          if tx is None:
1309              self.tx = CTransaction()
1310          else:
1311              self.tx = tx
1312  
1313      def deserialize(self, f):
1314          self.tx.deserialize(f)
1315  
1316      def serialize(self):
1317          return self.tx.serialize_with_witness()
1318  
1319      def __repr__(self):
1320          return "msg_tx(tx=%s)" % (repr(self.tx))
1321  
1322  class msg_wtxidrelay:
1323      __slots__ = ()
1324      msgtype = b"wtxidrelay"
1325  
1326      def __init__(self):
1327          pass
1328  
1329      def deserialize(self, f):
1330          pass
1331  
1332      def serialize(self):
1333          return b""
1334  
1335      def __repr__(self):
1336          return "msg_wtxidrelay()"
1337  
1338  
1339  class msg_no_witness_tx(msg_tx):
1340      __slots__ = ()
1341  
1342      def serialize(self):
1343          return self.tx.serialize_without_witness()
1344  
1345  
1346  class msg_block:
1347      __slots__ = ("block",)
1348      msgtype = b"block"
1349  
1350      def __init__(self, block=None):
1351          if block is None:
1352              self.block = CBlock()
1353          else:
1354              self.block = block
1355  
1356      def deserialize(self, f):
1357          self.block.deserialize(f)
1358  
1359      def serialize(self):
1360          return self.block.serialize()
1361  
1362      def __repr__(self):
1363          return "msg_block(block=%s)" % (repr(self.block))
1364  
1365  
1366  # for cases where a user needs tighter control over what is sent over the wire
1367  # note that the user must supply the name of the msgtype, and the data
1368  class msg_generic:
1369      __slots__ = ("msgtype", "data")
1370  
1371      def __init__(self, msgtype, data=None):
1372          self.msgtype = msgtype
1373          self.data = data
1374  
1375      def serialize(self):
1376          return self.data
1377  
1378      def __repr__(self):
1379          return "msg_generic()"
1380  
1381  
1382  class msg_no_witness_block(msg_block):
1383      __slots__ = ()
1384      def serialize(self):
1385          return self.block.serialize(with_witness=False)
1386  
1387  
1388  class msg_getaddr:
1389      __slots__ = ()
1390      msgtype = b"getaddr"
1391  
1392      def __init__(self):
1393          pass
1394  
1395      def deserialize(self, f):
1396          pass
1397  
1398      def serialize(self):
1399          return b""
1400  
1401      def __repr__(self):
1402          return "msg_getaddr()"
1403  
1404  
1405  class msg_ping:
1406      __slots__ = ("nonce",)
1407      msgtype = b"ping"
1408  
1409      def __init__(self, nonce=0):
1410          self.nonce = nonce
1411  
1412      def deserialize(self, f):
1413          self.nonce = int.from_bytes(f.read(8), "little")
1414  
1415      def serialize(self):
1416          r = b""
1417          r += self.nonce.to_bytes(8, "little")
1418          return r
1419  
1420      def __repr__(self):
1421          return "msg_ping(nonce=%08x)" % self.nonce
1422  
1423  
1424  class msg_pong:
1425      __slots__ = ("nonce",)
1426      msgtype = b"pong"
1427  
1428      def __init__(self, nonce=0):
1429          self.nonce = nonce
1430  
1431      def deserialize(self, f):
1432          self.nonce = int.from_bytes(f.read(8), "little")
1433  
1434      def serialize(self):
1435          r = b""
1436          r += self.nonce.to_bytes(8, "little")
1437          return r
1438  
1439      def __repr__(self):
1440          return "msg_pong(nonce=%08x)" % self.nonce
1441  
1442  
1443  class msg_mempool:
1444      __slots__ = ()
1445      msgtype = b"mempool"
1446  
1447      def __init__(self):
1448          pass
1449  
1450      def deserialize(self, f):
1451          pass
1452  
1453      def serialize(self):
1454          return b""
1455  
1456      def __repr__(self):
1457          return "msg_mempool()"
1458  
1459  
1460  class msg_notfound:
1461      __slots__ = ("vec", )
1462      msgtype = b"notfound"
1463  
1464      def __init__(self, vec=None):
1465          self.vec = vec or []
1466  
1467      def deserialize(self, f):
1468          self.vec = deser_vector(f, CInv)
1469  
1470      def serialize(self):
1471          return ser_vector(self.vec)
1472  
1473      def __repr__(self):
1474          return "msg_notfound(vec=%s)" % (repr(self.vec))
1475  
1476  
1477  class msg_sendheaders:
1478      __slots__ = ()
1479      msgtype = b"sendheaders"
1480  
1481      def __init__(self):
1482          pass
1483  
1484      def deserialize(self, f):
1485          pass
1486  
1487      def serialize(self):
1488          return b""
1489  
1490      def __repr__(self):
1491          return "msg_sendheaders()"
1492  
1493  
1494  # getheaders message has
1495  # number of entries
1496  # vector of hashes
1497  # hash_stop (hash of last desired block header, 0 to get as many as possible)
1498  class msg_getheaders:
1499      __slots__ = ("hashstop", "locator",)
1500      msgtype = b"getheaders"
1501  
1502      def __init__(self):
1503          self.locator = CBlockLocator()
1504          self.hashstop = 0
1505  
1506      def deserialize(self, f):
1507          self.locator = CBlockLocator()
1508          self.locator.deserialize(f)
1509          self.hashstop = deser_uint256(f)
1510  
1511      def serialize(self):
1512          r = b""
1513          r += self.locator.serialize()
1514          r += ser_uint256(self.hashstop)
1515          return r
1516  
1517      def __repr__(self):
1518          return "msg_getheaders(locator=%s, stop=%064x)" \
1519              % (repr(self.locator), self.hashstop)
1520  
1521  
1522  # headers message has
1523  # <count> <vector of block headers>
1524  class msg_headers:
1525      __slots__ = ("headers",)
1526      msgtype = b"headers"
1527  
1528      def __init__(self, headers=None):
1529          self.headers = headers if headers is not None else []
1530  
1531      def deserialize(self, f):
1532          # comment in limenkad indicates these should be deserialized as blocks
1533          blocks = deser_vector(f, CBlock)
1534          for x in blocks:
1535              self.headers.append(CBlockHeader(x))
1536  
1537      def serialize(self):
1538          blocks = [CBlock(x) for x in self.headers]
1539          return ser_vector(blocks)
1540  
1541      def __repr__(self):
1542          return "msg_headers(headers=%s)" % repr(self.headers)
1543  
1544  
1545  class msg_merkleblock:
1546      __slots__ = ("merkleblock",)
1547      msgtype = b"merkleblock"
1548  
1549      def __init__(self, merkleblock=None):
1550          if merkleblock is None:
1551              self.merkleblock = CMerkleBlock()
1552          else:
1553              self.merkleblock = merkleblock
1554  
1555      def deserialize(self, f):
1556          self.merkleblock.deserialize(f)
1557  
1558      def serialize(self):
1559          return self.merkleblock.serialize()
1560  
1561      def __repr__(self):
1562          return "msg_merkleblock(merkleblock=%s)" % (repr(self.merkleblock))
1563  
1564  
1565  class msg_filterload:
1566      __slots__ = ("data", "nHashFuncs", "nTweak", "nFlags")
1567      msgtype = b"filterload"
1568  
1569      def __init__(self, data=b'00', nHashFuncs=0, nTweak=0, nFlags=0):
1570          self.data = data
1571          self.nHashFuncs = nHashFuncs
1572          self.nTweak = nTweak
1573          self.nFlags = nFlags
1574  
1575      def deserialize(self, f):
1576          self.data = deser_string(f)
1577          self.nHashFuncs = int.from_bytes(f.read(4), "little")
1578          self.nTweak = int.from_bytes(f.read(4), "little")
1579          self.nFlags = int.from_bytes(f.read(1), "little")
1580  
1581      def serialize(self):
1582          r = b""
1583          r += ser_string(self.data)
1584          r += self.nHashFuncs.to_bytes(4, "little")
1585          r += self.nTweak.to_bytes(4, "little")
1586          r += self.nFlags.to_bytes(1, "little")
1587          return r
1588  
1589      def __repr__(self):
1590          return "msg_filterload(data={}, nHashFuncs={}, nTweak={}, nFlags={})".format(
1591              self.data, self.nHashFuncs, self.nTweak, self.nFlags)
1592  
1593  
1594  class msg_filteradd:
1595      __slots__ = ("data")
1596      msgtype = b"filteradd"
1597  
1598      def __init__(self, data):
1599          self.data = data
1600  
1601      def deserialize(self, f):
1602          self.data = deser_string(f)
1603  
1604      def serialize(self):
1605          r = b""
1606          r += ser_string(self.data)
1607          return r
1608  
1609      def __repr__(self):
1610          return "msg_filteradd(data={})".format(self.data)
1611  
1612  
1613  class msg_filterclear:
1614      __slots__ = ()
1615      msgtype = b"filterclear"
1616  
1617      def __init__(self):
1618          pass
1619  
1620      def deserialize(self, f):
1621          pass
1622  
1623      def serialize(self):
1624          return b""
1625  
1626      def __repr__(self):
1627          return "msg_filterclear()"
1628  
1629  
1630  class msg_feefilter:
1631      __slots__ = ("feerate",)
1632      msgtype = b"feefilter"
1633  
1634      def __init__(self, feerate=0):
1635          self.feerate = feerate
1636  
1637      def deserialize(self, f):
1638          self.feerate = int.from_bytes(f.read(8), "little")
1639  
1640      def serialize(self):
1641          r = b""
1642          r += self.feerate.to_bytes(8, "little")
1643          return r
1644  
1645      def __repr__(self):
1646          return "msg_feefilter(feerate=%08x)" % self.feerate
1647  
1648  
1649  class msg_sendcmpct:
1650      __slots__ = ("announce", "version")
1651      msgtype = b"sendcmpct"
1652  
1653      def __init__(self, announce=False, version=1):
1654          self.announce = announce
1655          self.version = version
1656  
1657      def deserialize(self, f):
1658          self.announce = bool(int.from_bytes(f.read(1), "little"))
1659          self.version = int.from_bytes(f.read(8), "little")
1660  
1661      def serialize(self):
1662          r = b""
1663          r += int(self.announce).to_bytes(1, "little")
1664          r += self.version.to_bytes(8, "little")
1665          return r
1666  
1667      def __repr__(self):
1668          return "msg_sendcmpct(announce=%s, version=%lu)" % (self.announce, self.version)
1669  
1670  
1671  class msg_cmpctblock:
1672      __slots__ = ("header_and_shortids",)
1673      msgtype = b"cmpctblock"
1674  
1675      def __init__(self, header_and_shortids = None):
1676          self.header_and_shortids = header_and_shortids
1677  
1678      def deserialize(self, f):
1679          self.header_and_shortids = P2PHeaderAndShortIDs()
1680          self.header_and_shortids.deserialize(f)
1681  
1682      def serialize(self):
1683          r = b""
1684          r += self.header_and_shortids.serialize()
1685          return r
1686  
1687      def __repr__(self):
1688          return "msg_cmpctblock(HeaderAndShortIDs=%s)" % repr(self.header_and_shortids)
1689  
1690  
1691  class msg_getblocktxn:
1692      __slots__ = ("block_txn_request",)
1693      msgtype = b"getblocktxn"
1694  
1695      def __init__(self):
1696          self.block_txn_request = None
1697  
1698      def deserialize(self, f):
1699          self.block_txn_request = BlockTransactionsRequest()
1700          self.block_txn_request.deserialize(f)
1701  
1702      def serialize(self):
1703          r = b""
1704          r += self.block_txn_request.serialize()
1705          return r
1706  
1707      def __repr__(self):
1708          return "msg_getblocktxn(block_txn_request=%s)" % (repr(self.block_txn_request))
1709  
1710  
1711  class msg_blocktxn:
1712      __slots__ = ("block_transactions",)
1713      msgtype = b"blocktxn"
1714  
1715      def __init__(self):
1716          self.block_transactions = BlockTransactions()
1717  
1718      def deserialize(self, f):
1719          self.block_transactions.deserialize(f)
1720  
1721      def serialize(self):
1722          r = b""
1723          r += self.block_transactions.serialize()
1724          return r
1725  
1726      def __repr__(self):
1727          return "msg_blocktxn(block_transactions=%s)" % (repr(self.block_transactions))
1728  
1729  
1730  class msg_no_witness_blocktxn(msg_blocktxn):
1731      __slots__ = ()
1732  
1733      def serialize(self):
1734          return self.block_transactions.serialize(with_witness=False)
1735  
1736  
1737  class msg_getcfilters:
1738      __slots__ = ("filter_type", "start_height", "stop_hash")
1739      msgtype =  b"getcfilters"
1740  
1741      def __init__(self, filter_type=None, start_height=None, stop_hash=None):
1742          self.filter_type = filter_type
1743          self.start_height = start_height
1744          self.stop_hash = stop_hash
1745  
1746      def deserialize(self, f):
1747          self.filter_type = int.from_bytes(f.read(1), "little")
1748          self.start_height = int.from_bytes(f.read(4), "little")
1749          self.stop_hash = deser_uint256(f)
1750  
1751      def serialize(self):
1752          r = b""
1753          r += self.filter_type.to_bytes(1, "little")
1754          r += self.start_height.to_bytes(4, "little")
1755          r += ser_uint256(self.stop_hash)
1756          return r
1757  
1758      def __repr__(self):
1759          return "msg_getcfilters(filter_type={:#x}, start_height={}, stop_hash={:x})".format(
1760              self.filter_type, self.start_height, self.stop_hash)
1761  
1762  class msg_cfilter:
1763      __slots__ = ("filter_type", "block_hash", "filter_data")
1764      msgtype =  b"cfilter"
1765  
1766      def __init__(self, filter_type=None, block_hash=None, filter_data=None):
1767          self.filter_type = filter_type
1768          self.block_hash = block_hash
1769          self.filter_data = filter_data
1770  
1771      def deserialize(self, f):
1772          self.filter_type = int.from_bytes(f.read(1), "little")
1773          self.block_hash = deser_uint256(f)
1774          self.filter_data = deser_string(f)
1775  
1776      def serialize(self):
1777          r = b""
1778          r += self.filter_type.to_bytes(1, "little")
1779          r += ser_uint256(self.block_hash)
1780          r += ser_string(self.filter_data)
1781          return r
1782  
1783      def __repr__(self):
1784          return "msg_cfilter(filter_type={:#x}, block_hash={:x})".format(
1785              self.filter_type, self.block_hash)
1786  
1787  class msg_getcfheaders:
1788      __slots__ = ("filter_type", "start_height", "stop_hash")
1789      msgtype =  b"getcfheaders"
1790  
1791      def __init__(self, filter_type=None, start_height=None, stop_hash=None):
1792          self.filter_type = filter_type
1793          self.start_height = start_height
1794          self.stop_hash = stop_hash
1795  
1796      def deserialize(self, f):
1797          self.filter_type = int.from_bytes(f.read(1), "little")
1798          self.start_height = int.from_bytes(f.read(4), "little")
1799          self.stop_hash = deser_uint256(f)
1800  
1801      def serialize(self):
1802          r = b""
1803          r += self.filter_type.to_bytes(1, "little")
1804          r += self.start_height.to_bytes(4, "little")
1805          r += ser_uint256(self.stop_hash)
1806          return r
1807  
1808      def __repr__(self):
1809          return "msg_getcfheaders(filter_type={:#x}, start_height={}, stop_hash={:x})".format(
1810              self.filter_type, self.start_height, self.stop_hash)
1811  
1812  class msg_cfheaders:
1813      __slots__ = ("filter_type", "stop_hash", "prev_header", "hashes")
1814      msgtype =  b"cfheaders"
1815  
1816      def __init__(self, filter_type=None, stop_hash=None, prev_header=None, hashes=None):
1817          self.filter_type = filter_type
1818          self.stop_hash = stop_hash
1819          self.prev_header = prev_header
1820          self.hashes = hashes
1821  
1822      def deserialize(self, f):
1823          self.filter_type = int.from_bytes(f.read(1), "little")
1824          self.stop_hash = deser_uint256(f)
1825          self.prev_header = deser_uint256(f)
1826          self.hashes = deser_uint256_vector(f)
1827  
1828      def serialize(self):
1829          r = b""
1830          r += self.filter_type.to_bytes(1, "little")
1831          r += ser_uint256(self.stop_hash)
1832          r += ser_uint256(self.prev_header)
1833          r += ser_uint256_vector(self.hashes)
1834          return r
1835  
1836      def __repr__(self):
1837          return "msg_cfheaders(filter_type={:#x}, stop_hash={:x})".format(
1838              self.filter_type, self.stop_hash)
1839  
1840  class msg_getcfcheckpt:
1841      __slots__ = ("filter_type", "stop_hash")
1842      msgtype =  b"getcfcheckpt"
1843  
1844      def __init__(self, filter_type=None, stop_hash=None):
1845          self.filter_type = filter_type
1846          self.stop_hash = stop_hash
1847  
1848      def deserialize(self, f):
1849          self.filter_type = int.from_bytes(f.read(1), "little")
1850          self.stop_hash = deser_uint256(f)
1851  
1852      def serialize(self):
1853          r = b""
1854          r += self.filter_type.to_bytes(1, "little")
1855          r += ser_uint256(self.stop_hash)
1856          return r
1857  
1858      def __repr__(self):
1859          return "msg_getcfcheckpt(filter_type={:#x}, stop_hash={:x})".format(
1860              self.filter_type, self.stop_hash)
1861  
1862  class msg_cfcheckpt:
1863      __slots__ = ("filter_type", "stop_hash", "headers")
1864      msgtype =  b"cfcheckpt"
1865  
1866      def __init__(self, filter_type=None, stop_hash=None, headers=None):
1867          self.filter_type = filter_type
1868          self.stop_hash = stop_hash
1869          self.headers = headers
1870  
1871      def deserialize(self, f):
1872          self.filter_type = int.from_bytes(f.read(1), "little")
1873          self.stop_hash = deser_uint256(f)
1874          self.headers = deser_uint256_vector(f)
1875  
1876      def serialize(self):
1877          r = b""
1878          r += self.filter_type.to_bytes(1, "little")
1879          r += ser_uint256(self.stop_hash)
1880          r += ser_uint256_vector(self.headers)
1881          return r
1882  
1883      def __repr__(self):
1884          return "msg_cfcheckpt(filter_type={:#x}, stop_hash={:x})".format(
1885              self.filter_type, self.stop_hash)
1886  
1887  class msg_sendtxrcncl:
1888      __slots__ = ("version", "salt")
1889      msgtype = b"sendtxrcncl"
1890  
1891      def __init__(self):
1892          self.version = 0
1893          self.salt = 0
1894  
1895      def deserialize(self, f):
1896          self.version = int.from_bytes(f.read(4), "little")
1897          self.salt = int.from_bytes(f.read(8), "little")
1898  
1899      def serialize(self):
1900          r = b""
1901          r += self.version.to_bytes(4, "little")
1902          r += self.salt.to_bytes(8, "little")
1903          return r
1904  
1905      def __repr__(self):
1906          return "msg_sendtxrcncl(version=%lu, salt=%lu)" %\
1907              (self.version, self.salt)
1908  
1909  class TestFrameworkScript(unittest.TestCase):
1910      def test_addrv2_encode_decode(self):
1911          def check_addrv2(ip, net):
1912              addr = CAddress()
1913              addr.net, addr.ip = net, ip
1914              ser = addr.serialize_v2()
1915              actual = CAddress()
1916              actual.deserialize_v2(BytesIO(ser))
1917              self.assertEqual(actual, addr)
1918  
1919          check_addrv2("1.65.195.98", CAddress.NET_IPV4)
1920          check_addrv2("2001:41f0::62:6974:636f:696e", CAddress.NET_IPV6)
1921          check_addrv2("2bqghnldu6mcug4pikzprwhtjjnsyederctvci6klcwzepnjd46ikjyd.onion", CAddress.NET_TORV3)
1922          check_addrv2("255fhcp6ajvftnyo7bwz3an3t4a4brhopm3bamyh2iu5r3gnr2rq.b32.i2p", CAddress.NET_I2P)
1923          check_addrv2("fc32:17ea:e415:c3bf:9808:149d:b5a2:c9aa", CAddress.NET_CJDNS)
1924