Bitcoin Core触ってみた! 消えたBitcoin

執行役員付の湯浅です(十月一日より)。

さっそく前回の続きをやっていきましょう。blog.engineer.adways.net

前回のおさらい

Bitcoin Coreとは、Bitcoinのプログラムです。
Docker上にコンテナを立て、bitcoindをregtestで動作させる。
bitcoin-cliというコマンドラインインターフェイスを用いて、マイニングの実行や送金を行う。
Docker上にBitcoinのネットワークを構築して、遊んでみる。←いまここ

....続き
さきほどから、bitcoin_1のみを使っています。

ここら辺でbitcoin_2の出番です

まず、bitcoin_1で、接続されている数を表示します。
bitcoin-cli getconnectioncount

    root@bitcoin_1:/# bitcoin-cli getconnectioncount
    0

0ですね。

次に、bitcoin_2のconfを編集します。
起動時にbitcoin_1のノードを追加させます。
そしてbitcoindを起動します。

echo "addnode=bitcoin_1" >> ~/.bitcoin/bitcoin.conf

    root@bitcoin_2:/# echo "addnode=bitcoin_1" >> ~/.bitcoin/bitcoin.conf
    root@bitcoin_2:/# cat ~/.bitcoin/bitcoin.conf
    rpcuser=test
    rpcpassword=test
    regtest=1
    addnode=bitcoin_1
    root@bitcoin_2:/# bitcoind -daemon
    Bitcoin server starting

bitcoin_2のbitcoindも起動しました。

bitcoin_1で接続数を確認しましょう。
さきほど、0でしたが変化はあったのでしょうか。
bitcoin-cli getconnectioncount

    root@bitcoin_1:/# bitcoin-cli getconnectioncount
    1

増えてる・・・!

bitcoin_1にて詳細を確認してみましょう。
bitcoin-cli getpeerinfo

bitcoin_2がbitcoin_1の18444ポートに対して、接続してきています。
では、bitcoin_1からbitcoin_2に対しての接続を設立します。

bitcoin-cli addnode bitcoin_2 add

    root@bitcoin_1:/# bitcoin-cli addnode bitcoin_2 add
    root@bitcoin_1:/# bitcoin-cli getconnectioncount
    2

2つのノードの間で、2つの接続が確認されました。

bitcoin_2にアカウントを作成し、そこに対して送金をしてみましょう。

    root@bitcoin_2:~# bitcoin-cli getnewaddress mywallet2
    2NDc3Fmy6ezMn7f4kZgKtvn4Q9fv2QeGgqB

    root@bitcoin_1:/# bitcoin-cli sendtoaddress 2NDc3Fmy6ezMn7f4kZgKtvn4Q9fv2QeGgqB1000c1d034ee12729079fc6f59cc09781f8b14f3d63d4c9ca4ed64c81307f9ec5244

    root@bitcoin_2:~# bitcoin-cli generate 1
    root@bitcoin_2:~# bitcoin-cli listaccounts
    {
      "": 0.00000000,
      "mywallet2": 1000.00000000
    }

ネットワークを通じたノード間での送金を確認しました。
もうだいぶ、詳しくなったのではないでしょうか。
ドヤしてくださいね。

消えたBitcoin問題

昨今でも、Monacoinで被害があったケースをregtestで試してみたいと思います。
Bitcoinでは、もっとも長いチェーンを正とします。
なので、bitcoin_2で1ブロックしか掘っていませんが、
bitcoin-cli getblockcount をbitcoin_2で行うと。

    root@bitcoin_2:~# bitcoin-cli getblockcount
    203

203とbitcoin_1で掘っていたブロックの後に足されています。
つまり、長いブロックをネットワークにつなげちゃえば良いのです。

bitcoin_3の出番です

別のターミナルを開いてください。
docker exec -it bitcoin_3 /bin/bash
bitcoin_3のコンテナの中に入ります。
bitcoin daemonを起動します。
250ブロックマイニングします。
そして、bitcoin_1に接続します。
bitcoin_1でblock数と残高を確認します。

bitcoind --daemon
bitcoin-cli generate 250
bitcoin-cli addnode bitcoin_1 add

    root@bitcoin_3:/# bitcoind -daemon
    root@bitcoin_3:/# bitcoin-cli generate 250
    root@bitcoin_3:/# bitcoin-cli addnode bitcoin_1 add

さて、250ブロックをマイニングしました。
bitcoin_1のコンテナの中に入ります。
bitcoin_1で確認してみます。

bitcoin-cli getblockcount
bitcoin-cli getbalance

    root@bitcoin_1:/# bitcoin-cli getblockcount
    250
    root@bitcoin_1:/# bitcoin-cli getbalance
    0.00000000

0です。

残高0です。
bitcoin_1で行われていた取引は、すべて消えてしまいました。
これは、一番長いブロックを正とするためです。
今まであったブロックチェーンよりも長いブロックチェーンがネットワークに接続されたため、bitcoin_1とbitcoin_2にあった、取引はすべて吹っ飛びました。
MonaCoinなどで発生したReorgと呼ばれる現象です。
最も長いチェーンを正とするブロックチェーンの構造的な弱点を狙った攻撃になります。
バグではなく、仕様です。
恐ろしいですね。

まとめ

前回と今回でBitcoin Coreについて学びました。
基本的なコマンドラインや、Dockerを用いたテストネットの構築の仕方を習得できたと思います。
想定している読者はエンジニアなので、黒い画面にコマンドをカタカタ打ち込むのは好きだと思います。
是非、Bitcoin Coreに触れて暗号通貨、ひいてはブロックチェーンについて興味を持ち、日本、いや、それどころか世界に影響を与えちゃいましょう!