Exemplo n.º 1
0
    def stream_serialize(self, f):
        OutPoint.stream_serialize(self.prev_out, f)
        f.write(struct.pack(b'<I', self.sequence))

        f.write(struct.pack(b'<q', self.value))
        f.write(struct.pack(b'<I', self.block_height))
        f.write(struct.pack(b'<I', self.block_index))
        BytesSerializer.stream_serialize(self.sig_script, f)
Exemplo n.º 2
0
 def serialize_field(self, tx, attr, fmt, num_bytes, f):
     if fmt not in ['inputs', 'outputs', 'bytes']:
         f.write(struct.pack(fmt, getattr(tx, attr)))
     elif fmt == 'inputs':
         VectorSerializer.stream_serialize(CMutableTxIn, tx.vin, f)
     elif fmt == 'outputs':
         VectorSerializer.stream_serialize(CMutableTxOut, tx.vout, f)
     elif fmt == 'bytes':
         BytesSerializer.stream_serialize(getattr(tx, attr), f)
Exemplo n.º 3
0
 def stream_serialize(self, f):
     super(Block, self).stream_serialize(f)
     for attr, fmt, num_bytes, _ in self.block_fields:
         if fmt not in ['bytes', 'vectortx']:
             f.write(struct.pack(fmt, getattr(self, attr)))
         elif fmt == 'bytes':
             BytesSerializer.stream_serialize(getattr(self, attr), f)
         elif fmt == 'vectortx':
             VectorSerializer.stream_serialize(Transaction, getattr(self, attr), f)
Exemplo n.º 4
0
 def stream_serialize(self, f):
     for attr, fmt, num_bytes, _ in self.fields:
         if fmt not in ["inputs", "outputs", "bytes"]:
             f.write(struct.pack(fmt, getattr(self, attr)))
         elif fmt == "inputs":
             VectorSerializer.stream_serialize(CTxIn, self.vin, f)
         elif fmt == "outputs":
             VectorSerializer.stream_serialize(CTxOut, self.vout, f)
         elif fmt == "bytes":
             BytesSerializer.stream_serialize(getattr(self, attr), f)
Exemplo n.º 5
0
 def stream_serialize(self, f):
     for attr, fmt, num_bytes, _ in self.fields:
         if fmt not in ['inputs', 'outputs', 'bytes']:
             f.write(struct.pack(fmt, getattr(self, attr)))
         elif fmt == 'inputs':
             VectorSerializer.stream_serialize(CTxIn, self.vin, f)
         elif fmt == 'outputs':
             VectorSerializer.stream_serialize(CTxOut, self.vout, f)
         elif fmt == 'bytes':
             BytesSerializer.stream_serialize(getattr(self, attr), f)
Exemplo n.º 6
0
 def stream_serialize(self, f, **kwargs):
     state = kwargs['state'] if 'state' in kwargs else False
     if state is True:
         if self.seal_type is not None:
             self.seal_type.stream_serialize_state(self.state, f)
         elif self.state is not None:
             BytesSerializer.stream_serialize(self.state, f)
         else:
             raise SchemaError(
                 f'''Unable to consensus-serialize sealed state: no binary state and no schema seal type are 
                 provided for the value `{self.dict_state}`
                 ''')
     else:
         self.outpoint.stream_serialize(f, short=True)
Exemplo n.º 7
0
 def stream_deserialize_value(self, f):
     lut = {
         FieldType.Type.u8: lambda: ser_read(f, 1),
         FieldType.Type.u16: lambda: struct.unpack(b'<H', ser_read(f, 2))[0],
         FieldType.Type.u32: lambda: struct.unpack(b'<I', ser_read(f, 4))[0],
         FieldType.Type.u64: lambda: struct.unpack(b'<Q', ser_read(f, 8))[0],
         FieldType.Type.i8: lambda: ser_read(f, 1),
         FieldType.Type.i16: lambda: struct.unpack(b'<h', ser_read(f, 2))[0],
         FieldType.Type.i32: lambda: struct.unpack(b'<i', ser_read(f, 4))[0],
         FieldType.Type.i64: lambda: struct.unpack(b'<q', ser_read(f, 8))[0],
         FieldType.Type.vi: lambda: VarIntSerializer.stream_deserialize(f),
         FieldType.Type.fvi: lambda: FlagVarIntSerializer.stream_deserialize(f),
         FieldType.Type.str: lambda: VarStringSerializer.stream_deserialize(f).decode('utf-8'),
         FieldType.Type.bytes: lambda: BytesSerializer.stream_deserialize(f),
         FieldType.Type.sha256: lambda: Hash256Id.stream_deserialize(f),
         FieldType.Type.sha256d: lambda: Hash256Id.stream_deserialize(f),
         FieldType.Type.ripmd160: lambda: Hash160Id.stream_deserialize(f),
         FieldType.Type.hash160: lambda: Hash160Id.stream_deserialize(f),
         FieldType.Type.pubkey: lambda: PubKey.stream_deserialize(f),
         FieldType.Type.ecdsa: lambda: None,
     }
     if self.type in lut.keys():
         return lut[self.type]()
     else:
         raise NotImplementedError()
Exemplo n.º 8
0
    def stream_deserialize(cls, f):
        prev_out = OutPoint.stream_deserialize(f)
        sequence = struct.unpack(b'<I', ser_read(f, 4))[0]

        value = struct.unpack(b'<q', ser_read(f, 8))[0]
        block_height = struct.unpack(b'<I', ser_read(f, 4))[0]
        block_index = struct.unpack(b'<I', ser_read(f, 4))[0]
        sig_script = BytesSerializer.stream_deserialize(f)
        return cls(prev_out, sequence, value, block_height, block_index, sig_script)
Exemplo n.º 9
0
 def deserialize_field(self, tx, kwargs, attr, fmt, num_bytes, f):
     if fmt not in ['inputs', 'outputs', 'bytes']:
         kwargs[attr] = struct.unpack(fmt, ser_read(f, num_bytes))[0]
     elif fmt == 'inputs':
         kwargs[attr] = VectorSerializer.stream_deserialize(CMutableTxIn, f)
     elif fmt == 'outputs':
         kwargs[attr] = VectorSerializer.stream_deserialize(CMutableTxOut, f)
     elif fmt == 'bytes':
         kwargs[attr] =  BytesSerializer.stream_deserialize(f)
Exemplo n.º 10
0
    def deserialize_witness(self, f):
        value = struct.unpack(b'<q', ser_read(f, 8))[0]
        block_height = struct.unpack(b'<I', ser_read(f, 4))[0]
        block_index = struct.unpack(b'<I', ser_read(f, 4))[0]
        sig_script = BytesSerializer.stream_deserialize(f)

        self.value = value
        self.block_height = block_height
        self.block_index = block_index
        self.sig_script = sig_script
Exemplo n.º 11
0
    def stream_deserialize(cls, f):
        self = super(Block, cls).stream_deserialize(f)
        for attr, fmt, num_bytes, _ in self.block_fields:
            if fmt not in ['bytes', 'vectortx']:
                setattr(self, attr, struct.unpack(fmt, ser_read(f, num_bytes))[0])
            elif fmt == 'bytes':
                setattr(self, attr, BytesSerializer.stream_deserialize(f))
            elif fmt == 'vectortx':
                setattr(self, attr, VectorSerializer.stream_deserialize(Transaction, f))

        setattr(self, 'vMerkleTree', tuple(Block.build_merkle_tree_from_txs(getattr(self, 'vtx'))))
        return self
Exemplo n.º 12
0
 def stream_deserialize(cls, f):
     self = cls()
     for attr, fmt, num_bytes, _ in self.fields:
         if fmt not in ['inputs', 'outputs', 'bytes']:
             setattr(self, attr, struct.unpack(fmt, ser_read(f, num_bytes))[0])
         elif fmt == 'inputs':
             setattr(self, attr, VectorSerializer.stream_deserialize(CTxIn, f))
         elif fmt == 'outputs':
             setattr(self, attr, VectorSerializer.stream_deserialize(CTxOut, f))
         elif fmt == 'bytes':
             setattr(self, attr, BytesSerializer.stream_deserialize(f))
     return self
Exemplo n.º 13
0
    def stream_serialize_value(self, value, f):
        if value is None:
            if self.type is FieldType.Type.str or self.type is FieldType.Type.bytes:
                f.write(bytes([0x00]))
            elif self.type is FieldType.Type.fvi:
                f.write(bytes([0xFF]))
            elif self.type in [FieldType.Type.sha256, FieldType.Type.sha256d]:
                f.write(bytes([0]*32))
            elif self.type in [FieldType.Type.ripmd160, FieldType.Type.hash160]:
                f.write(bytes([0]*20))
            elif self.type is FieldType.Type.pubkey:
                f.write(bytes([0x00]))
            elif self.type is FieldType.Type.ecdsa:
                f.write(bytes([0x00]))
            return

        lut = {
            FieldType.Type.u8: lambda x: f.write(bytes([x])),
            FieldType.Type.u16: lambda x: f.write(struct.pack(b'<H', x)),
            FieldType.Type.u32: lambda x: f.write(struct.pack(b'<I', x)),
            FieldType.Type.u64: lambda x: f.write(struct.pack(b'<Q', x)),
            FieldType.Type.i8: lambda x: f.write(bytes([x])),
            FieldType.Type.i16: lambda x: f.write(struct.pack(b'<h', x)),
            FieldType.Type.i32: lambda x: f.write(struct.pack(b'<i', x)),
            FieldType.Type.i64: lambda x: f.write(struct.pack(b'<q', x)),
            FieldType.Type.vi: lambda x: VarIntSerializer.stream_serialize(x, f),
            FieldType.Type.fvi: lambda x: FlagVarIntSerializer.stream_serialize((x, False), f),
            FieldType.Type.str: lambda x: VarStringSerializer.stream_serialize(x.encode('utf-8'), f),
            FieldType.Type.bytes: lambda x: BytesSerializer.stream_serialize(x, f),
            FieldType.Type.sha256: lambda x: x.stream_serealize(f),
            FieldType.Type.sha256d: lambda x: x.stream_serealize(f),
            FieldType.Type.ripmd160: lambda x: x.stream_serealize(f),
            FieldType.Type.hash160: lambda x: x.stream_serealize(f),
            FieldType.Type.pubkey: lambda x: x.stream_serealize(f),
            FieldType.Type.ecdsa: lambda _: None,
        }
        if self.type in lut.keys():
            if self.type in [FieldType.Type.sha256, FieldType.Type.sha256d,
                             FieldType.Type.ripmd160, FieldType.Type.hash160] and not issubclass(value, HashId):
                raise ValueError('in order to serialize hash value you need to provide an instance of HashId class')
            lut[self.type](value)
        else:
            raise NotImplementedError('ECDSA serialization is not implemented')
Exemplo n.º 14
0
 def stream_deserialize(cls, f):
     value = struct.unpack(b'<q', ser_read(f, 8))[0]
     version = struct.unpack(b'<H', ser_read(f, 2))[0]
     pk_script = BytesSerializer.stream_deserialize(f)
     return cls(value, version, pk_script)
Exemplo n.º 15
0
 def serialize_witness_value_signing(self, f):
     f.write(struct.pack(b'<q', self.value))
     BytesSerializer.stream_serialize(self.sig_script, f)
Exemplo n.º 16
0
 def serialize_witness_signing(self, f):
     BytesSerializer.stream_serialize(self.sig_script, f)
Exemplo n.º 17
0
 def serialize_witness(self, f):
     f.write(struct.pack(b'<q', self.value))
     f.write(struct.pack(b'<I', self.block_height))
     f.write(struct.pack(b'<I', self.block_index))
     BytesSerializer.stream_serialize(self.sig_script, f)
Exemplo n.º 18
0
 def stream_deserialize(cls, f):
     hash = ser_read(f, 32)
     vin = CTxIn.stream_deserialize(f)
     sig = BytesSerializer.stream_deserialize(f)
     height = struct.unpack(b"<I", ser_read(f, 4))[0]
     return cls(hash, vin, sig, height)
Exemplo n.º 19
0
    def deserialize_witness_value_signing(self, f):
        value = struct.unpack(b'<q', ser_read(f, 8))[0]
        sig_script = BytesSerializer.stream_deserialize(f)

        self.value = value
        self.sig_script = sig_script
Exemplo n.º 20
0
def RawSignatureHash1(script, txTo, inIdx, amount, hashtype):
    """Consensus-correct SignatureHash

    Returns (hash, err) to precisely match the consensus-critical behavior of
    the SIGHASH_SINGLE bug. (inIdx is *not* checked for validity)

    If you're just writing wallet software you probably want SignatureHash()
    instead.

    Ref: https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki
    """
    HASH_ONE = b'\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'

    if inIdx >= len(txTo.vin):
        return (HASH_ONE, "inIdx %d out of range (%d)" % (inIdx, len(txTo.vin)))
    txtmp = bitcoin.core.CMutableTransaction.from_tx(txTo)

    # Reusable parts for all the tx.
    # FIXME Compute them here is not a great idea
    hashPrevouts = b'\x00' * 32
    hashSequence = b'\x00' * 32
    hashOutputs = b'\x00' * 32

    if not hashtype & SIGHASH_ANYONECANPAY:
        data = []
        for vini in txTo.vin:
            data.append(vini.prevout.hash)  # TODO: serialize using the COutPoint primitives
            data.append(struct.pack(b'<I', vini.prevout.n))
        hashPrevouts = bitcoin.core.Hash(b''.join(data))

    if not hashtype & SIGHASH_ANYONECANPAY and hashtype & 0x1f not in (SIGHASH_SINGLE, SIGHASH_NONE):
        data = []
        for vini in txTo.vin:
            data.append(struct.pack(b'<I', vini.nSequence))

        hashSequence = bitcoin.core.Hash(b''.join(data))

    if hashtype & 0x1f not in (SIGHASH_SINGLE, SIGHASH_NONE):
        data = []
        f = io.BytesIO()
        for vouti in txTo.vout:
            vouti.stream_serialize(f)  # Serialize this using the tx serialization rules. TODO serialize

        data.append(f.getvalue())
        hashOutputs = bitcoin.core.Hash(b''.join(data))
    elif hashtype & 0x1f == SIGHASH_SINGLE and inIdx < len(txTo.vout):
        hashOutputs = bitcoin.core.Hash(txTo.vout[inIdx])  # TODO: serialize

    data = []
    hash_data = lambda: bitcoin.core.Hash(b''.join(data))

    data.append(struct.pack(b'<i', txTo.nVersion))
    data.append(hashPrevouts)
    data.append(hashSequence)
    # The input being signed (replacing the scriptSig with scriptCode + amount)
    # The prevout may already be contained in hashPrevout, and the nSequence
    # may already be contain in hashSequence.
    #ss << txTo.vin[nIn].prevout;

    # data.append(txTo.vin[inIdx].prevout)  # TODO serialize
    # Split: TODO temporary
    data.append(txTo.vin[inIdx].prevout.hash)
    data.append(struct.pack(b'<I', txTo.vin[inIdx].prevout.n))
    # ss << static_cast<const CScriptBase&>(scriptCode);
    data.append(BytesSerializer.serialize(script))  # TODO Remember: OP_CODESEPERATOR is not supported

    # ss << amount;
    data.append(struct.pack(b'<Q', amount))
    # ss << txTo.vin[nIn].nSequence;
    data.append(struct.pack(b'<I', txTo.vin[inIdx].nSequence))
    # // Outputs (none/one/all, depending on flags)
    # ss << hashOutputs;
    data.append(hashOutputs)
    # // Locktime
    # ss << txTo.nLockTime;
    data.append(struct.pack(b'<I', txTo.nLockTime))
    # // Sighash type
    # ss << nHashType;
    data.append(struct.pack(b'<I', hashtype))

    return (hash_data(), None)
Exemplo n.º 21
0
 def stream_serialize(self, f):
     f.write(self.hash)
     f.write(self.vin.stream_serialize())
     BytesSerializer.stream_serialize(self.sig, f)
     f.write(struct.pack(b"<I", self.height))
Exemplo n.º 22
0
    def stream_deserialize(cls, f, **kwargs):
        schema_obj = kwargs['schema_obj'] if 'schema_obj' in kwargs else None
        if not isinstance(schema_obj, Schema):
            raise ValueError(
                f'`schema_obj` parameter must be of Schema type; got `{schema_obj}` instead'
            )

        # Deserialize proof header
        # - version with flag
        (ver, flag) = FlagVarIntSerializer.stream_deserialize(f)
        # - fields common for root and upgrade proofs
        if flag:
            schema = Hash256Id.stream_deserialize(f)
            network = VarIntSerializer.stream_deserialize(f)
            if network is 0x00:
                format = ProofFormat.upgrade
            # - root-specific fields
            else:
                network = Network(network)
                format = ProofFormat.root
                root = OutPoint.stream_deserialize(f, short=False)
        else:
            format = ProofFormat.ordinary

        # Deserialize proof body
        # - reading proof type
        type_no = ser_read(f, 1)[0]

        # - reading `seal_sequence` structure
        seals = []
        seal_type_no = 0
        # -- we iterate over the seals until 0xFF (=FlagVarIntSerializer.Separator.EOF) byte is met
        while True:
            try:
                # -- reading seal with the current type number
                seal = Seal.stream_deserialize(f,
                                               type_no=seal_type_no,
                                               schema_obj=schema_obj)
            except BaseException as ex:
                # due to some strange bug, python 3 is unable to capture SeparatorByteSignal exception by its type,
                # and `isinstance(ex, SeparatorByteSignal)` returns False as well :(
                # so we have to capture generic exception and re-raise if it is not SeparatorByteSignal, which
                # can be determined only by the presence of its method
                if not callable(getattr(ex, "is_eol", None)):
                    raise
                if ex.is_eol():
                    # -- met 0xFE separator byte, increasing current type number
                    seal_type_no = seal_type_no + 1
                elif ex.is_eof():
                    # -- end of `seal_sequence` structure
                    break
            else:
                # -- otherwise append read seal to the list of seals
                seals.append(seal)

        # -- if we had zero seals implies proof of state destruction format
        if len(seals) is 0:
            format = ProofFormat.burn

        # - reading unparsed state and metadata bytes
        state = BytesSerializer.stream_deserialize(f)
        metadata = BytesSerializer.stream_deserialize(f)

        # Deserialize original public key
        pkcode = ser_read(f, 1)
        if pkcode is 0x00:
            pubkey = None
        else:
            buf = pkcode + ser_read(f, 32)
            pubkey = PubKey.deserialize(buf)

        # Deserialize prunable data
        try:
            pruned_flag = ser_read(f, 1)
        except:
            pruned_flag = 0x00

        txid, parents = None, None
        if pruned_flag & 0x01 > 0:
            txid = Hash256Id.stream_deserialize(f)
        if pruned_flag & 0x02 > 0:
            parents = VectorSerializer.stream_deserialize(Hash256Id, f)

        proof = Proof(schema_obj=schema_obj,
                      type_no=type_no,
                      ver=ver,
                      format=format,
                      schema=schema,
                      network=network,
                      root=root,
                      pubkey=pubkey,
                      fields=None,
                      seals=seals,
                      txid=txid,
                      parents=parents,
                      metadata=metadata,
                      state=state)

        # Parsing raw seals and metadata and resolving types against the provided Schema
        if 'schema_obj' in kwargs:
            schema_obj = kwargs['schema_obj']
        if isinstance(schema_obj, Schema):
            proof.resolve_schema(schema_obj)

        return proof
Exemplo n.º 23
0
 def stream_serialize(self, f):
     f.write(self.hash)
     f.write(self.vin.stream_serialize())
     BytesSerializer.stream_serialize(self.sig, f)
     f.write(struct.pack(b"<I", self.height))
Exemplo n.º 24
0
 def stream_serialize(self, f):
     f.write(struct.pack(b'<q', self.value))
     f.write(struct.pack(b'<H', self.version))
     BytesSerializer.stream_serialize(self.pk_script, f)
Exemplo n.º 25
0
 def stream_deserialize(cls, f):
     hash = ser_read(f, 32)
     vin = CTxIn.stream_deserialize(f)
     sig = BytesSerializer.stream_deserialize(f)
     height = struct.unpack(b"<I", ser_read(f, 4))[0]
     return cls(hash, vin, sig, height)
Exemplo n.º 26
0
 def deserialize_witness_signing(self, f):
     sig_script = BytesSerializer.stream_deserialize(f)
     self.sig_script = sig_script