UDP hole punchingの実装をしてみる
ラジコンをLTE回線を使って制御できたら面白そうだなと思いいろいろ調べてる。
BeagleBone BlackとL-03Dを組み合わせてL-03DにIIJmioのIIJ BIC SIMを差せばインターネット経由でBeagleBone Blackを遠隔操作をする事が出来るはずです。あとはBeagleBone Blackをラジコンに載せればラジコンをインターネットを経由で遠隔操作できます。しかしこれには一つ問題があります。その問題とはIIJmioのsimを使用した場合BeagleBone Blackに割り振られるIPv4アドレスがプライベートIPアドレスとなってしまう事です。プライベートIPv4アドレスが割り振られたという事はBeagleBone Blackに割り振られたIPv4アドレスが分かったところでインターネット側からの通信はIIJmioのNATに阻まれてBeagleBone Blackにアクセスする事は通常出来ません。
この場合UDPホールパンチングというテクニックを使用するとプライベートIPアドレスが割り振られたBeagleBone Blackと直接通信する事ができます。UDPホールパンチングについては他のサイトに詳しい解説があるのでここでは省略します。そこでUDPホールパンチングを行うサーバーとクライアント(以下nodeと呼ぶ)を自分で実装しgithub.comに公開しました。
holepunchの解説
ビルドコマンド等についてはレポジトリ内のREADMEを参照ください。
このholepunchはlibeventを使用していますのでまずlibeventをインストールしてください。
次にPCを3台用意します。一つはUDPホールパンチングの仕組み上必要となるマッチングサーバーです。このサーバーだけはグローバルIPアドレスが必要です。残りの二つは実際に直接通信するPCとなります。この二つのPCは双方ともプライベートIPでも問題ありません。
このholepunchの実装ではstunを使用せず独自のプロトコルで通信を行います。通信相手の識別には任意で設定可能な文字列keyを使用します。この文字列keyの一致したPC同士で直接通信をする事ができます。
おおまかな通信手順
実際に使用する
サーバ上で
$ ./holepunch server
nodeA上で
$ ./holepunch node example.com foo
nodeB上でも同じコマンドを実行
$ ./holepunch node example.com foo
通信が確立したら、各nodeのターミナル上で文字を入力しEnterで入力した文字列を相手に送信する事が出来ます。