<p>From what I can tell, by testing your script, is that it is failing on Segwit transactions. This would make sense, if you haven't accounted for it, because it changes what is used to produce the <code>tx hash</code>. This was introduced with <a href="https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki#specification" rel="nofollow noreferrer">BIP141</a>. Currently, not all transactions are required to be in this format, so you will have to account for both. The <code>txid</code> still uses the entire transaction structure, this is why you might notice bitcoin-core rpc calls will return a different <code>txid</code> than the <code>tx hash</code> (<code>wtxid</code>) for segwit transactions.</p>

<blockquote>
  <p>Definition of <strong>txid</strong> remains unchanged: the double SHA256 of the
  traditional serialization format:</p>
  
  <p><code>[nVersion][txins][txouts][nLockTime]</code></p>
  
  <p>A new <strong>wtxid</strong> is defined: the double SHA256 of the new serialization
  with witness data:</p>
  
  <p><code>[nVersion][marker][flag][txins][txouts][witness][nLockTime]</code></p>
</blockquote>

<p>see <a href="https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki#specification" rel="nofollow noreferrer">BIP141</a></p>

<p>What you'll need to do is look for the segwit flag <code>0x01</code> in the serialized transaction. It's an optional 2-byte array right after the first version bytes, see <a href="https://en.bitcoin.it/wiki/Transaction" rel="nofollow noreferrer">https://en.bitcoin.it/wiki/Transaction</a></p>

CC BY-SA 4.0
2018-09-15T15:25:49.420Z
Actualloy, You can see I hash the content from tx start to locktime. It looks is compatible with BIP141.
self.raw_bytes = blockchain.read(cur_pos - start_pos)
self.tx_hash = hash_tx(self.raw_bytes)
Carpemer
CC BY-SA 4.0
2018-09-15T15:44:10.560Z
Fixed, we should use varint but int1 to parse the witness. Thanks!
Carpemer
CC BY-SA 4.0
2018-09-15T12:05:35.770Z
2018-09-15T12:27:22.170Z
2018-09-15T12:27:22.170Z
JBaczuk
<p>I wrote some python code to parse the block data, all the result are fine, until block01095.dat, block #498557.</p>

<p>The code to deal with Transaction is:</p>

<pre><code>class Tx: 
  def __init__(self, blockchain):
    start_pos = blockchain.tell()
    self.version = uint4(blockchain)
    check_pos = blockchain.tell()
    # For segwit
    # https://en.bitcoin.it/wiki/Transaction
    dummy1 = uint1(blockchain)
    dummy2 = uint1(blockchain)
    if dummy1 != 0 or dummy2 != 1:
      blockchain.seek(check_pos)
    self.inCount = varint(blockchain)
    self.inputs = []
    self.seq = 1
    for i in range(0, self.inCount):
      self.inputs.append(TxInput(blockchain, i))
    self.outCount = varint(blockchain)
    self.outputs = []
    if self.outCount &gt; 0:
      for i in range(0, self.outCount):
        self.outputs.append(TxOutput(blockchain, i))
    # For segwit
    if dummy1 == 0 and dummy2 == 1:
      for i in range(0, self.inCount): 
        num_op = uint1(blockchain)
        for n in range(0, num_op):
          op_code=uint1(blockchain)
          _ = hashStr(blockchain.read(op_code))
    self.lockTime = uint4(blockchain)
    cur_pos = blockchain.tell()
    blockchain.seek(start_pos)
    self.raw_bytes = blockchain.read(cur_pos - start_pos)
    self.tx_hash = hash_tx(self.raw_bytes)
    print(self.tx_hash)
</code></pre>

<p>Full code is in:
<a href="https://github.com/keviny/bitcoin-block-parser/blob/master/block.py" rel="nofollow noreferrer">https://github.com/keviny/bitcoin-block-parser/blob/master/block.py</a></p>

<p>The last transaction in #498556 is <a href="https://www.blockchain.com/btc/tx/0baa42c9852b4edd9437e8c3fd38bd0dd89d977fe80ac7648961cf8ff33a2dbf" rel="nofollow noreferrer">https://www.blockchain.com/btc/tx/0baa42c9852b4edd9437e8c3fd38bd0dd89d977fe80ac7648961cf8ff33a2dbf</a>
which is ok to parse. </p>

<p>But in #498557 I can never create the right tx hash anymore. 
The first tx hash I get from block #498557 is 
<a href="https://www.blockchain.com/btc/tx/2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8" rel="nofollow noreferrer">https://www.blockchain.com/btc/tx/2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8</a>
which is not a valid tx hash in blockchain.info.</p>

<p>Actually, the first three hash I got are:
2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8
e0a7e07ccb9b126bd20b5b134d41ec5f8b70bdb5408a263619ca3b8b3a90512d
6c695c567d14bce39a8e58359a2a5d26dc2bcbd9a83f043b5dbc1800c56f84c8
None of above can be used in blockchain.info.</p>

<p>I suspect there is some format change from this block. </p>

<p>Does Anyone here know any background about this issue?</p>

CC BY-SA 4.0
2018-09-14T14:53:10.117Z
How are you generating the tx hash? Any code you can provide?
JBaczuk
CC BY-SA 4.0
2018-09-15T00:07:36.643Z
@JBaczuk Update the code and link in the question.
Carpemer
CC BY-SA 4.0
2018-09-15T00:52:34.810Z
Are you saying that 2da6... is the hash you compute for the block's coinbase transaction?
Nate Eldredge
CC BY-SA 4.0
2018-09-15T02:20:51.327Z
Yes, the first three tx hash I got are: 
 2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8  
e0a7e07ccb9b126bd20b5b134d41ec5f8b70bdb5408a263619ca3b8b3a90512d  
6c695c567d14bce39a8e58359a2a5d26dc2bcbd9a83f043b5dbc1800c56f84c8
Carpemer
<transactions><segregated-witness>
Is there any format change in block #498557
Carpemer
# Is there any format change in block #498557

(Asked by: username_0 on 2018-09-14)

I wrote some python code to parse the block data, all the result are fine, until block01095.dat, block #498557.

The code to deal with Transaction is:

```
class Tx: 
  def __init__(self, blockchain):
    start_pos = blockchain.tell()
    self.version = uint4(blockchain)
    check_pos = blockchain.tell()
    # For segwit
    # https://en.bitcoin.it/wiki/Transaction
    dummy1 = uint1(blockchain)
    dummy2 = uint1(blockchain)
    if dummy1 != 0 or dummy2 != 1:
      blockchain.seek(check_pos)
    self.inCount = varint(blockchain)
    self.inputs = []
    self.seq = 1
    for i in range(0, self.inCount):
      self.inputs.append(TxInput(blockchain, i))
    self.outCount = varint(blockchain)
    self.outputs = []
    if self.outCount > 0:
      for i in range(0, self.outCount):
        self.outputs.append(TxOutput(blockchain, i))
    # For segwit
    if dummy1 == 0 and dummy2 == 1:
      for i in range(0, self.inCount): 
        num_op = uint1(blockchain)
        for n in range(0, num_op):
          op_code=uint1(blockchain)
          _ = hashStr(blockchain.read(op_code))
    self.lockTime = uint4(blockchain)
    cur_pos = blockchain.tell()
    blockchain.seek(start_pos)
    self.raw_bytes = blockchain.read(cur_pos - start_pos)
    self.tx_hash = hash_tx(self.raw_bytes)
    print(self.tx_hash)

```

Full code is in:
<https://github.com/keviny/bitcoin-block-parser/blob/master/block.py>

The last transaction in #498556 is <https://www.blockchain.com/btc/tx/0baa42c9852b4edd9437e8c3fd38bd0dd89d977fe80ac7648961cf8ff33a2dbf>
which is ok to parse.

But in #498557 I can never create the right tx hash anymore.
The first tx hash I get from block #498557 is
<https://www.blockchain.com/btc/tx/2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8>
which is not a valid tx hash in blockchain.info.

Actually, the first three hash I got are:
2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8
e0a7e07ccb9b126bd20b5b134d41ec5f8b70bdb5408a263619ca3b8b3a90512d
6c695c567d14bce39a8e58359a2a5d26dc2bcbd9a83f043b5dbc1800c56f84c8
None of above can be used in blockchain.info.

I suspect there is some format change from this block.

Does Anyone here know any background about this issue?

**Tags:** transactions, segregated-witness

> **Comments:**
> **username_1**: How are you generating the tx hash? Any code you can provide?  
> **username_0**: @username_1 Update the code and link in the question.  
> **username_2**: Are you saying that 2da6... is the hash you compute for the block's coinbase transaction?  
> **username_0**: Yes, the first three tx hash I got are:   2da60422e1de3e8e64742bb16db5d1e3b2a9813f754cff416e549d570b2ad0e8   e0a7e07ccb9b126bd20b5b134d41ec5f8b70bdb5408a263619ca3b8b3a90512d   6c695c567d14bce39a8e58359a2a5d26dc2bcbd9a83f043b5dbc1800c56f84c8  

---

## 1 answers

### Answer by username_1 on 2018-09-15. Score: 1 | Accepted answer

From what I can tell, by testing your script, is that it is failing on Segwit transactions. This would make sense, if you haven't accounted for it, because it changes what is used to produce the `tx hash`. This was introduced with [BIP141](https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki#specification). Currently, not all transactions are required to be in this format, so you will have to account for both. The `txid` still uses the entire transaction structure, this is why you might notice bitcoin-core rpc calls will return a different `txid` than the `tx hash` (`wtxid`) for segwit transactions.

> Definition of **txid** remains unchanged: the double SHA256 of the
> traditional serialization format:
>
> `[nVersion][txins][txouts][nLockTime]`
>
> A new **wtxid** is defined: the double SHA256 of the new serialization
> with witness data:
>
> `[nVersion][marker][flag][txins][txouts][witness][nLockTime]`

see [BIP141](https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki#specification)

What you'll need to do is look for the segwit flag `0x01` in the serialized transaction. It's an optional 2-byte array right after the first version bytes, see <https://en.bitcoin.it/wiki/Transaction>

> **Comments:**
> **username_0**: Actualloy, You can see I hash the content from tx start to locktime. It looks is compatible with BIP141. self.raw_bytes = blockchain.read(cur_pos - start_pos) self.tx_hash = hash_tx(self.raw_bytes)  
> **username_0**: Fixed, we should use varint but int1 to parse the witness. Thanks!  

---

