はじめに
こんにちは。新規事業開発室の山口 (@yamarkz) です。
今回はEthereumのディフィカルティとその調整の仕組み。 そしてディフィカルティボムと呼ばれるコンセンサスアルゴリズムについて紹介します。
ディフィカルティとは
ディフィカルティ(採掘難易度)とは、ブロックをチェーンに繋ぐ際に行うマイニング (証明作業) 時に用いる指標のことです。
ディフィカルティの基準値よりも低いハッシュ値をハッシュ計算で算出できた場合に一定計算量が注ぎ込まれたブロックと見なされチェーンに繋がれるブロックとなります。この一定計算量が注ぎ込まれたかどうかを判定する基準値がディフィカルティです。
Ethereumのディフィカルティは、Etherscan というサイトで確認することができます。
BitcoinやEthereumのディフィカルティはマイニングに要する時間が一定の基準値に保たれるように調整されます。Bitcoinではおおよそ10分。Ethereumではおおよそ13秒前後になるように調整されます。
Bitcoinでは、2016ブロック(おおよそ2週間)ごとにあるRetarget Periodという期間ごとにディフィカルティの調整が行われます。
Ethereumでは、親ブロックのディフィカルティと、親ブロックが生成にかかった時間を元に毎ブロックごとにディフィカルティが調整されます。 マイニングの詳細はMiningとEthashで詳細に解説されています。
Bitcoinのディフィカルティに関しては下記の記事で詳しく紹介されています。
次にEthereumのディフィカルティの算出方法を見ていきます。
Ethereumのディフィカルティ算出方法
Ethereumのディフィカルティは毎ブロックごとに計算されます。
この計算には「親ブロックのディフィカルティ値」と「ブロック生成にかかった時間」が用いられます。実際の算出ロジックはgethクライアントの場合、 consensus.go に定義されています。
計算式は Frontier、Homestead、Metoropolisとそれぞれのメジャーバージョンでディフィカルティの算出方法が異なっています。
計算式は以下の通りです。
Frontier
block_diff = parent_diff + parent_diff // 2048 * (1 if block_timestamp - parent_timestamp < 13 else -1) + int(2**((block.number // 100000) - 2))
Homestead
adj_factor = max(1 - ((timestamp - parent.timestamp) // 10), -99)
child_diff = int(max(parent.difficulty + (parent.difficulty // BLOCK_DIFF_FACTOR) * adj_factor, min(parent.difficulty, MIN_DIFF)))
Frontierではブロック生成時間が13秒からどれくらい離れているか考慮されていませんでした。1秒後に採掘されたブロックは、12秒後に採掘されたブロックと同じとディフィカルティになります。
Homesteadからは「親ブロックの生成時間」と「ディフィカルティ」から最適化されたディフィカルティを算出する仕組みに変更され、より安定したブロック生成時間が担保されるようになります。
この変更に関する詳細はEIP-2に記載されています。
Metropolis (Byzantium)
adj_factor = max(1 + len(parent.uncles) - ((timestamp - parent.timestamp) // 9), -99)
child_diff = int(max(parent.difficulty + (parent.difficulty // BLOCK_DIFF_FACTOR) *adj_factor, min(parent.difficulty, MIN_DIFF)))
Byzantiumでも変更が加えられ、ディフィカルティ算出にuncleブロックも考慮されるようになりました。 uncleブロックを含めることにより、より正確に難易度が算出されるようになりました。
この変更の詳細内容はEIP-100に記載されています。また、変更内容の提案はこちらで行われました。
この様に、Ethereumのディフィカルティ調整のロジックはメジャーアップデートを重ねる毎に改善が加えられてきています。
次にディフィカルティ調整に関連した機能として存在する ディフィカルティボム と呼ばれるコンセンサスアルゴリズムと、その影響によって生じる アイスエイジ と呼ばれる現象について紹介します。
ディフィカルティボムとアイスエイジ
上の図はEthereumの1ブロックあたりの生成時間の推移を表したグラフです。
グラフでは10月17日にかけてブロックの生成時間が段階的に上昇しています。 ブロック生成時間上昇の背景には、ディフィカルティ調整アルゴリズムであるディフィカルティボムの存在があります。 ディフィカルティボムの影響でブロック生成に30秒前後必要になる状況になりました。 普段のブロック生成時間が15秒前後なので、2倍の時間がかかっていることになります。 このディフィカルティの上昇によりブロック生成が遅くなる状況は、 アイスエイジ(氷河期) と呼ばれています。
ディフィカルティボムとは
ディフィカルティボムは2015年9月7日に導入されたコンセンサスアルゴリズムです。 Frontierが2015年7月30日にリリースされたので、Ethereumが世に出てすぐに実装されました。
ディフィカルティボムに発動トリガーなどはなく、実装がリリースされた段階で作用が始まります。
アルゴリズムはブロック高に応じてディフィカルティが指数関数的に増加していきます。 ディフィカルティが調整値に対して増加されるのでマイニングにかかる時間が徐々伸びていきます。
ディフィカルティボムを導入した背景にはPoWからPoSへ移行する計画があります。
Ethereumは現在Proof of Workシステムで動いていますが、SelenityバージョンでコンセンサスシステムをProof of Stakeへ移行する計画があります。 この計画はEthereumが構想の段階から考えられていたものです。 Ethereumがワールドコンピュータとなり、計算力を提供するプラットフォームとして進化を続ける中でPoSは必要なシステムであり、Ethereumが今後大きく発展していくために必要な移行です。 このPoSへの移行をスムーズに行う為に導入されたアルゴリズムがディフィカルティボムです。
「スムーズに行う」 という部分が重要で、これは移行のハードフォークを実施した際に旧チェーンと新チェーンでネットワークが分裂するリスクを最小限に抑える狙いがあります。 PoSへの移行は既存のPoWを行うマイナーの存在がなくなることになります。(代わりにステイクを行うバリデーターという存在が出て来ます) 経済合理性を求めネットワークに参加しているマイナーからすると利益を得る機会が失われるPoSへの移行は望ましくありません。
仮にPoSへ移行するタイミングでマイナーの同意が得られずハードフォークが実施され、マイナーが報酬を得られる旧チェーンでマイニングを続けた場合、 ネットワークの分裂が起きます。この分裂により、旧チェーンと新チェーンどちらがメインチェーン進んでいくのかわからず、Ethereum自体に混乱が生まれる可能性があります。
また、PoSへの移行はワールドコンピュータとしての発展を目指すEthereumにとって必要なことであるにも関わらず、マイナーの経済合理性を理由に移行が難しくなるのはEthereum開発チームの意向に反しています。
こういった混沌とした状況を避けるために開発チームはディフィカルティボムを導入し、仮に旧チェーンでマイニングを続けたとしても、ディフィカルティボムが作用することで徐々にマイニングにかかるコストが大きくなり、最終的に利益を生むことができない状況が作られる様にしました。
EthereumのPoWからPoSへの移行は下のスライドで紹介しました。
アイスエイジとは
Ethereumのアイスエイジとは、ディフィカルティボムの影響によりマイニングのブロック生成時間が徐々に遅くなる現象のことです。 アイスエイジと表現するのは、ディフィカルティの上昇によりブロック生成にかかる時間が増加することでトランザクションの承認速度が遅くなるのと、ブロック生成の機会が減り1日あたりのブロック報酬額が減ることから、チェーンの凍結に例えられ、アイスエイジという表現がされています。
上記の図を見ると2017年10月16日にかけて1日あたりのブロック生成報酬の額が減っているのがわかります。
この状況は本来想定されていない状況でした。というのも、ディフィカルティボムは本来PoSヘの移行時に作用する機能として導入されたにも関わらず、導入予定のPoSの実装がほとんどできていなかったからです。 結果、本来移行時に導入するPoSのシステムが完成していない状況で、移行時に作用するシステムが動き始めてしまうという状況になってしまいました。
この状況が作られた背景には2016年のセキュリティ対応のしわ寄せが絡んで来ます。
余談ですが、Ethereumでは現在1日あたり15億の資産が生まれています。すごい...
86400秒 (1日) / 15秒(1ブロック生成) = 5,760ブロック
3ETH * 5,760ブロック = 17,280ETH
9万 * 17,280ETH = 15億5520万円
2016年のEthereum
2016年はEthereumにとって大変な一年になりました。
- Homesteadハードフォークの実施
- DAO事件と救済ハードフォークの実施
- DEVCON2開催中にEthereumネットワークが脆弱性を突かれDoS攻撃を受ける
- DoS攻撃に対する対応として2度のハードフォークの実施
- 公式ウォレットMistに脆弱性が見つかり修正対応
2016年のEthereumはリリースされて一年に満たない時期でシステム的にも未熟な部分が多く、脆弱性を突かれたセキュリティ問題の対応に追われました。 その結果、本来計画上進めるはずだったPoSの研究開発に着手することができませんでした。 上記の対応によるPoSの研究開発の後ろ倒しが影響し、本来想定していない状況でディフィカルティが上昇し始めアイスエイジが起きます。
ディフィカルティボムの調整とマイニング報酬の減少
上述の通り、計画とは大きく異なった状況になった結果ディフィカルティボムの影響が予期せぬ形で現れ始めました。 この状況に対してEthereumの開発チームはディフィカルティボムの延期と、マイニング報酬を減らす対応を行います。 対応は2017年10月16日に実施されたByzantiumハードフォークで適用されました。
ディフィカルティボムの延期は300万ブロック分延期することになりました。この300万ブロックとはおおよそ1年4ヶ月ほどで、これにより次にブロック生成時間に30秒以上要するのは2018年末頃と見積もられています。延期対応の実装は偽のブロック番号(fake_block_number)を処理に含めることで対応している。実装はこちら。
さらに、Byzantiumではマイニングの報酬が5ETHから3ETHに減らす対応も行われました。Ethereumは発行上限が決められていないインフレトークンでしたが、マイニング報酬を徐々に減らしていくことでトークンの希少性を上げ、プラットフォームへの投資を促す狙いがあると言われています。
この対応に対する具体的な内容は EIP-649に記載されています。 また、EIP-649に対するPull Requestではマイニング報酬調整に対するEthereumとしての経済循環の最適値はどこか深く議論されており、とても勉強になるので一読することをおすすめします。
まとめ
- Ethereumのディフィカルティは毎ブロックごとに算出され、算出には「親ブロックの生成時間」「ディフィカルティ」「uncleブロックの値」を用いて算出される
- ディフィカルティの算出方法はバージョンごとに異なっており、改善されてきている。
- PoSへの移行をスムーズに進めるためにディフィカルティボムを導入したが、予期せぬ状況で作用してしまい、作用を延期する対応を行なった
参考
- EIP-2
- EIP-100
- EIP-609
- EIP-649
- EIP-649 Pull Request
- Byzantium HF Announcement
- Ethereum Ice Age
- Geth consensus logic
- Etherscan
- Ethereum Wiki Mining
- Ethereum Wiki Ethash
最後に
今回はEthereumのディフィカルティに関連した内容を紹介しました。 ディフィカルティ調整の仕組みが知りたく調べていたのですが、関連した内容が多く存在しそれらもまとめて調べていくと大きな問題とそれに対する解決にまでに至りとても理解が深まりました。 まだまだ、Ethereumの仕組みで理解できていない部分が多いので引き続き気になった部分を調べていきたいなと思っています。
宣伝
Gunosyではブロックチェーンを始めとしてスマートスピーカー、VR/ARと言った新規領域での研究・開発を進めており、メンバーを募集しています。
少し話を聞いてみたい!という方も歓迎していますので、下記のリンクからの応募お待ちしております。
また弊社Gunosyでは、blockchain.tokyo を主催するなど、ブロックチェーンや仮想通貨に関する調査を行っています。
本日、弊社Gunosyを会場としてイベントを開催する予定です。残念ながら今回の募集は終了してしまいました。次回は来月開催する予定です。イベントグループへメンバー登録をしていただくとイベント参加者募集の通知が来るので、こちらもぜひ登録してみてください。