用語集 / マイニングとコンセンサス
前ブロックヘッダーハッシュ
- 前ブロックヘッダーハッシュとは?
- 前ブロックヘッダーハッシュとは、すべてのブロックヘッダーに含まれる32バイトのフィールドで、そのブロックの親ブロックを指し示すものであり、ブロックの集まりを1本のチェーンにする唯一のつなぎ目です。
各ブロックは後ろ向きにのみ指し示し、前向きに指し示すことはありません。ポインターがハッシュ計算の対象となる80バイトの中にあるため、古いブロックの内容を少しでも編集するとそのハッシュが変わり、その上に構築されたすべてのブロックが壊れます。したがって、1年前の支払いを取り消すには、およそ52,000ブロック分のプルーフ・オブ・ワークをやり直す必要があります。ビットコインを不変だと人々が言うときの意味は、データの削除に関する何らかの規則ではなく、この点にあります。
仕組み
前ブロックヘッダーハッシュは、親ブロックの80バイトのヘッダーに対してSHA-256を2回実行することで生成され、ブロックが外部に対して保持する唯一の参照です。
親ブロックのヘッダーにはそのまた親のハッシュが含まれ、それが最初まで続くため、32バイトのフィールド1つで、その背後にある履歴全体が確定します。先端を検証したノードは、そこに至るチェーンが内部的に整合していることを暗黙のうちに検証したことになります。昨年の夏にマイニングされたブロック内のトランザクションを改ざんすると、そのブロックのヘッダーハッシュが変わり、子ブロックが保持するそのコピーは一致しなくなり、子ブロックは無効となり、その後のすべてのブロックも無効になります。損傷を修復するには、それらのブロックをすべて再マイニングする必要があり、その速さはおよそ1日144ブロック、1年で52,560ブロックです。
ジェネシスブロックは例外であり、そうならざるを得ません。その前には何も存在しないため、このフィールドは32バイトのゼロです。
ブロック内の何ものも前向きに指し示すことはありません。Bitcoin Coreがnextblockhashを報告するとき、それはブロックではなく自身のインデックスを読んでいるのであり、まさにそのため、再編成の際にこの値は変化し得る一方で、前ブロックヘッダーハッシュは決して変化しません。2つのブロックが同じ親ブロックを指し示すことも、エラーではありません。それがデータの観点から見たフォークの姿であり、ネットワークはどちらかのポインターを誤りと宣言するのではなく、累積作業量の多いブランチを優先することでこれを解決します。
表示される場所
前ブロックヘッダーハッシュは、何を見ているかによって若干異なる名前で表示されます。
Bitcoin Coreはgetblockheaderとgetblockでこれをpreviousblockhashとして返します。ブロック0の場合、指し示す親ブロックが存在しないため、このフィールドは応答に単に含まれません。ブロックエクスプローラーは通常、これをPrevious Blockというラベルにしてリンク化しており、これによって履歴をクリックでさかのぼることができます。
また、これはヘッダーチェーンの同期の実質的な中身でもあります。ヘッダーをダウンロードするノードは、各ヘッダーについて2つのことを確認します。すなわち、このヘッダーが直前のヘッダーを指し示していること、そしてそのハッシュがターゲットを満たしていることです。そのチェーンが整合して初めて、ノードはブロック本体を要求し始めます。軽量ウォレットはこれ以上先へは進まず、リンクと作業量だけを保持し、それ以外は何も保持しません。
このフィールドを手作業で構築する場合には、自分の目を疑うことになると覚悟してください。ヘッダー内のバイトは、ハッシュが通常表記される順序では書かれていないからです。
前ブロックヘッダーハッシュvs内部バイト順
前ブロックヘッダーハッシュは、一般に引用される順序とは逆のバイト順で保存されており、このことがヘッダーを手作業で検証しようとするほぼすべての人を戸惑わせます。ブロック1は親ブロックのハッシュを6fe28c0ab6f1b372c1a6a246ae63f74f931e8365e15a089c68d6190000000000として保持しています。これは、よく知られたジェネシスハッシュ000000000019d6689c085ae165831e934ff763ae46a2a6c172b3f1b60a8ce26fを1バイトずつ逆順に書いたものです。プルーフ・オブ・ワークが生み出す先頭のゼロは、生のフィールドでは末尾に付きます。両者が見た目で一致しないときでも、何も問題はありません。バイトを逆順にすれば一致します。