Mastering Bitcoin 第5章をまとめます。

ビットコインのトランザクションは送金の内容を表現したものです。
「AさんからBさんに◯◯BTC送る」ということがが記録されています。

トランザクションのライフサイクル

[ウォレット] ⇛ [bitcoinネットワーク] ⇛ [マイナー] ⇛ [ブロックチェーン]
生成     ⇛ 伝搬         ⇛ 確認    ⇛ 記録

ウォレットで署名され生成されたトランザクションはbitcoinネットワークの幾つかのノードに送信(ブロードキャストと言う)されます。
トランザクションを受け取ったノードはそれを検証して問題なければ他のノードにも伝達します。
それを補足したマイナーが内容の正しさを確認し、マイナーがブロックを生成する際にそのブロックに保存されます。

bitcoinではトランザクション、つまり誰が誰にいくら送ったかのみをブロックチェーンに保存します。誰が今いくら持っているかは過去全てのトランザクションから算出します。銀行残高のような値はチェーンのどこにもありません。

実際のトランザクション

トランザクションはbitcoinネットワークにブロードキャストされるので誰でも見ることが可能です。過去全ての取引が確認できます。
blockchain.info などで確かめられます。
https://blockchain.info/ja/tx/7487af2183aa53f8683cfe65a000d36bf86aba39e0409422391570e2619e2e14
(↑これは適当に見つけたトランザクション)

トランザクションの概要

一つのトランザクションは大きく分けてトランザクションアウトプットとトランザクションインプットの2つから成り立ちます。

[イン&アウトの図]

トランザクションもbitcoinとは違った形ではありますが、連鎖しています。
アウトプットが次のトランザクションのインプットから参照されます。

トランザクションアウトプット

アウトプットの構造です。

サイズ フィールド名 説明
8 byte Amount satoshi単位(10-8 bitcoin)のbitcoin額
1-9 byte (VarInt) Locking-Script Size 次に続くlocking scriptのバイト長
可変サイズ Locking-Script アウトプットを使用するために必要な条件を定義したscript

送るBTCの量(ここでの単位はsatochi=1億分の1BTC)とLocking Scriptで成り立ちます。
Locking Scriptとはこのアウトプットされるbitcoinの使用条件と言い換える事ができます。詳細は後述しますがscriptと呼ばれる言語を用いて正しいかどうか確かめます。
一つのトランザクションで送り先が複数ある場合はアウトプットもその数分だけ存在します。

UTXO:未使用トランザクションアウトプット

全てのトランザクションアウトプットはまずUTXOになります。これはその名の通りまだトランザクションインプットによって参照されていないアウトプットです。

トランザクションインプット

インプットの構造です。

サイズ フィールド名 説明
32 byte Transaction Hash 使われるUTXOを含むトランザクションハッシュ
4 byte Output Index 使われるUTXOのトランザクション内インデックス、一番最初のアウトプットの場合は0
1-9 byte (VarInt) Unlocking-Script Size unlocking-scriptのバイト長
可変サイズ Unlocking-Script UTXOのlocking scriptを満たすscript
4 byte Sequence Number 現在トランザクション置き換えは使用不可になっている、0xFFFFFFFF に設定

インプットではどのUTXOを使用するかを指定します。またそのアウトプットの使用条件を満たすUnlocking Scriptも記載します。
一つのトランザクションで使用するUTXOが複数ある場合はその数分のインプットが存在します。

おつりと手数料

おつり

トランザクションインプットではUTXOを指定しますが、例えば1BTC分のUTXOのうち0.5BTCだけ使用するといった使い方はできません。1BTCまるごとトランザクションインプットに取り込みます。もし0.5BTCだけ送りたい場合は、自分への0.5BTC分のアウトプットも一緒に含んでトランザクションを生成します。1BTC払って0.5BTCお釣りとしてもらうイメージです。

手数料

手数料はインプットの総量からアウトプットの総量を引いたものとして自動的に決まります。
トランザクションには手数料を明示する部分はありません。
例えばこちらの実際のトランザクションでも合計インプットより合計アウトプットの少しがちいさいです。
https://blockchain.info/ja/tx/7487af2183aa53f8683cfe65a000d36bf86aba39e0409422391570e2619e2e14

この差額はブロック生成に成功したマイナーに渡ります。

先程のおつりの例でもし自分への0.5BTCのおつりのアウトプットトランザクションを含めなければ、全部マイナーにプレゼントすることになります。実際には手数料計算はウォレットがやってくれます。

scriptによる検証

前述したとおり、トランザクションアウトプットではLoking Script、トランザクションインプットではUnlocking Scriptを記載しています。
* Loking ScriptとUnloking Scriptは2つ繋げて一つのプログラムになる
* ノードがスクリプトをbitcoin scriptとして実行して正しいか確認
* 正しいとはスクリプトの実行結果がTRUEであること
* scriptの形式はいくつかあり、もっとも使われているのはP2PKHである

Loking Scriptは送金先のアドレスに対応する秘密鍵を保持している者でないと作れないUnloking Scriptと結合して実行された場合にTRUEが返ってくるようなスクリプトのことです。

scriptの使用はbitcoin wikiにあります。Script - Bitcoin Wiki

標準的なトランザクションscript

P2PKH (Pay-to-Public-Key-Hash)

スクリプト 内容
locking script OP_DUP OP_HASH160 <Public Key Hash A> OP_EQUALVERIFY OP_CHECKSIG
unloking script <Signature A> <Public Key A>
検証されるスクリプト <Signature A> <Public Key A> OP_DUP OP_HASH160 <Public Key Hash A>
OP_EQUALVERIFY OP_CHECKSIG

P2PK (Pay-to-Public-Key)

P2PKHが使用できるように更新されていない古いマイニングソフトウェアで使われています。

スクリプト 内容
locking script <Public Key A> OP_CHECKSIG
unloking script <Signature from Private Key A>
検証されるスクリプト <Signature from Private Key A> <Public Key A> OP_CHECKSIG

マルチシグネチャ

N個の公開鍵とM個の署名が入っているscriptです。
MofNと表現します。Nはキーの総数、Mは必要な署名の数です。例えば2of3なら3個の公開鍵に対して2個の署名を用いないといけません。

  • 複数人で管理するアドレスで一定数以上の許可がないと動かせないアドレス
  • 個人で1ofNのアドレスを管理すると一つキーをなくしてもバックアップとして働く

マルチシグネチャの一般的なlocking script

M <Public Key 1> <Public Key 2> ... <Public Key N> N OP_CHECKMULTISIG

2of3のloking scriptとunlocking script

// loking script
2 <Public Key A> <Public Key B> <Public Key C> 3 OP_CHECKMULTISIG

//unlocking script
OP_0 <Signature B> <Signature C>

P2SH (Pay-to-Script-Hash)

複雑なトランザクションscriptをはるかに簡単化した新しい種類のトランザクションです。
主にマルチシグネチャなどのスクリプトが長くなってしまう場合に使用します。

P2SHの仕様はBIP0016で定められています。
bips/bip-0016.mediawiki at master · bitcoin/bips

P2SHはlocking scriptにスクリプトのハッシュを設置することで実現します。
P2SHを使う支払いでは、ハッシュを得たlocking scriptのことを Redeem Script と呼んでいます。
redeem scriptをunlocking scriptで提示することで資金をアンロックします。

2of3のマルチシグのスクリプトをP2SHで作成する例
スクリプト 内容
redeem script 2 <Public Key A> <Public Key B> <Public Key C> 3 OP_CHECJMULTISIG
locking script OP_HASH160 <redeem script hash> OP_EQUAL
unlocking script OP_0 <Signature A> <Signature B> <redeem script>

検証はP2PKHとは違って2段階で行われます。
1段階目
reddem scriptとlocking scriptを繋げたスクリプトが検証されます

redeem script + locking script
= <redeem script> + OP_HASH160 <redeem script hash> OP_EQUAL

2段階目
1段目の検証が問題なければunlocking scriptを検証します。

OP_0 <Signature A> <Signature B> <redeem script>

これは下記のスクリプトはマルチシグネチャスクリプトそのものです。

P2SHアドレス
スクリプトをハッシュしたものをbase58エンコードすることでアドレスとして使用します。エンコード後のアドレスの先頭は3となり、P2SHアドレスであることを表現しています。
このアドレスを送信者に教えることで支払い側のウォレットは通常のアドレスと同じように扱うことができます。

P2SHのメリット

P2SHはlocking scriptを複雑なまま直接扱うことに比べて以下の利点があります。

  • より短いフィンガープリントで複雑なscriptを置き換えることで、トランザクションのデータサイズを小さくする
  • scriptがアドレスとして実装されることで、送り主と送り主のウォレットはP2SHに関する複雑な実装をする必要がない
  • P2SHは、scriptを構成する負担を送り手ではなく受け手側に移している
  • P2SHは、アウトプットが持つ長いscript(これはUTXOセットに含まれるためメモリを圧迫する)をインプット側(ブロックチェーン上にのみ保存される)に移すことでデータストレージの負担をインプット側に移している
  • P2SHは、支払い時点に生じる長いscriptを資金が使われる時点で生じるようにすることで、データストレージの負担が生じる時刻を移している
  • P2SHは、送り手が長いscriptを伴って資金を送るときに負担するトランザクション手数料を、受け手がredeem scriptを使って資金を使うときに負担するように変更している

CHECKLOCKTIMEVERIFYで指定期間まで資金を凍結 - Develop with pleasure!

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です