RouterBOARD (RB750GL)のOpenFlow化へのチャレンジ 〜OpenFlow動作確認編〜
前回は、RouterBOARD (RB750GL)のOpenvSwitch環境を構築しましたので、実際に、OpenFlowプロトコル動作させてみて、各種挙動を確認してみたいと思います。
◆OpenFlowコントローラ環境準備
OpenFlowを確認するためには、OpenFlowコントローラを構築する必要があります。
ここでは、Ryu Controllerを使用したOpenFlow動作確認環境を構築します。
1. Ryu Controllerインストール
"ubuntu 14.04 desktop"に、Ryu Controllerをインストールした際の手順を記載します。
ほかのOSでも動作すると思います。ちなみに、OS X Yosemiteでも問題なく動作しております。
tsubo@RyuSDN:~$ sudo apt-get install git tsubo@RyuSDN:~$ sudo apt-get install python-dev tsubo@RyuSDN:~$ sudo apt-get install python-pip tsubo@RyuSDN:~$ git clone https://github.com/osrg/ryu.git tsubo@RyuSDN:~$ cd ryu/tools/ tsubo@RyuSDN:~/ryu/tools$ sudo pip install -r pip-requires tsubo@RyuSDN:~/ryu$ cd .. tsubo@RyuSDN:~/ryu$ sudo python ./setup.py install tsubo@RyuSDN:~/ryu$ sudo pip install --upgrade six tsubo@RyuSDN:~/ryu$ ryu-manager --version ryu-manager 3.15
2. ネットワーク設定
Ryu ControllerとOpenvSwitchが通信できるように、ネットワーク設定を行っておきます。
ちなみに、ここでは、"192.168.0.0/24"とネットワークとしました。
- OpenvSwitch: 192.168.0.1
- Ryu Controller: 192.168.0.100
tsubo@RyuSDN:~$ ifconfig eth0 Link encap:Ethernet HWaddr 00:0c:29:e1:e9:32 inet addr:192.168.0.100 Bcast:192.168.0.255 Mask:255.255.255.0 inet6 addr: fe80::20c:29ff:fee1:e932/64 Scope:Link UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 RX packets:22771 errors:0 dropped:0 overruns:0 frame:0 TX packets:17676 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:1000 RX bytes:5252189 (5.2 MB) TX bytes:1375840 (1.3 MB) eth1 Link encap:Ethernet HWaddr 00:0c:29:e1:e9:3c inet addr:172.16.115.203 Bcast:172.16.115.255 Mask:255.255.255.0 inet6 addr: fe80::20c:29ff:fee1:e93c/64 Scope:Link UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 RX packets:40598 errors:0 dropped:0 overruns:0 frame:0 TX packets:21620 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:1000 RX bytes:17019999 (17.0 MB) TX bytes:2683644 (2.6 MB) lo Link encap:Local Loopback inet addr:127.0.0.1 Mask:255.0.0.0 inet6 addr: ::1/128 Scope:Host UP LOOPBACK RUNNING MTU:65536 Metric:1 RX packets:1346 errors:0 dropped:0 overruns:0 frame:0 TX packets:1346 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:156583 (156.5 KB) TX bytes:156583 (156.5 KB)
3. OpenFlow簡易ルータ構築
以前、ブログで紹介したOpenFllow簡易ルータを構築します。
まずは、OpenFlow簡易ルータのプログラム一式を以下のサイトからダウンロードします。
4. OpenFlow簡易ルータ起動
とりあえず、OpenFlow簡易ルータを起動しておきます。
tsubo@RyuSDN:~$ cd simpleRouter-0.1/ryu-app/ tsubo@RyuSDN:~/simpleRouter-0.1/ryu-app$ ryu-manager openflowRouter.py loading app openflowRouter.py loading app ryu.controller.ofp_handler creating context wsgi instantiating app None of SimpleMonitor creating context monitor instantiating app openflowRouter.py of OpenflowRouter instantiating app ryu.controller.ofp_handler of OFPHandler (5156) wsgi starting up on http://0.0.0.0:8080/
5. ルータコンフィグ設定の準備
今回l構築するルータ構成は、こんな感じを想定します。
OpenFlow簡易ルータを起動したら、別ターミナルから、ルータコンフィグ作業場所まで移動しておきます。
tsubo@RyuSDN:~$ cd simpleRouter-0.1/rest-client/ tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ls -l total 40 -rw-rw-r-- 1 tsubo tsubo 278 Nov 3 16:15 OpenFlow.ini -rw-rw-r-- 1 tsubo tsubo 933 Nov 3 14:33 common_func.py -rw-rw-r-- 1 tsubo tsubo 974 Nov 3 14:33 common_func.pyc -rwxrwxr-x 1 tsubo tsubo 1068 Nov 3 14:26 get_arp.sh -rwxrwxr-x 1 tsubo tsubo 1493 Nov 3 14:25 get_flow_stats.sh -rwxrwxr-x 1 tsubo tsubo 1170 Nov 3 14:27 get_interface.sh -rwxrwxr-x 1 tsubo tsubo 1630 Nov 3 14:28 get_port_stats.sh -rwxrwxr-x 1 tsubo tsubo 1114 Nov 3 16:18 post_gateway.sh -rwxrwxr-x 1 tsubo tsubo 2570 Nov 3 16:21 post_interface.sh -rwxrwxr-x 1 tsubo tsubo 924 Nov 3 15:10 put_ping.sh
つづいて、ルータコンフィグ設定を行います。
それでは、具体的にルータコンフィグ設定として、OpenFlow.iniファイルを編集します。
物理ポートとOpenFlowポートが一致していない点は、注意が必要です。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ vi OpenFlow.ini -------------------------- [Port2] port = "1" macaddress = "00:00:00:00:00:01" ipaddress = "192.168.100.100" opposite_ipaddress = "192.168.100.1" [Port3] port = "2" macaddress = "00:00:00:00:00:02" ipaddress = "192.168.101.100" opposite_ipaddress = "192.168.101.1" [Gateway] ipaddress = "192.168.100.1"
ちなみに、RB750GL上のOpenvSwitch側での物理ポートとOpenFlowポートとの関係を再掲しておきます。
root@OpenWrt:~# ovs-ofctl dump-ports-desc br0 --protocols=OpenFlow13 OFPST_PORT_DESC reply (OF1.3) (xid=0x2): 1(eth0.2): addr:d4:ca:6d:73:14:8b config: 0 state: 0 current: 1GB-FD AUTO_NEG advertised: 1GB-FD supported: 1GB-FD speed: 1000 Mbps now, 1000 Mbps max 2(eth0.3): addr:d4:ca:6d:73:14:8b config: 0 state: 0 current: 1GB-FD AUTO_NEG advertised: 1GB-FD supported: 1GB-FD speed: 1000 Mbps now, 1000 Mbps max LOCAL(br0): addr:d4:ca:6d:73:14:8b config: PORT_DOWN state: LINK_DOWN speed: 0 Mbps now, 0 Mbps max
6. ルータコンフィグ反映
実際に、ルータコンフィグ情報を、Ryu Controllerに反映します。
まずは、インタフェース情報からです。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./post_interface.sh ====================================================================== create_interface ====================================================================== /openflow/0000000000000001/interface { "interface": { "port": "1", "macaddress": "00:00:00:00:00:01", "ipaddress": "192.168.100.100", "opposite_ipaddress": "192.168.100.1" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 160 header: Date: Mon, 03 Nov 2014 08:29:33 GMT ---------- { "interface": { "macaddress": "00:00:00:00:00:01", "ipaddress": "192.168.100.100", "port": "1", "opposite_ipaddress": "192.168.100.1" }, "id": "0000000000000001" } ====================================================================== create_interface ====================================================================== /openflow/0000000000000001/interface { "interface": { "port": "2", "macaddress": "00:00:00:00:00:02", "ipaddress": "192.168.101.100", "opposite_ipaddress": "192.168.101.1" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 160 header: Date: Mon, 03 Nov 2014 08:29:38 GMT ---------- { "interface": { "macaddress": "00:00:00:00:00:02", "ipaddress": "192.168.101.100", "port": "2", "opposite_ipaddress": "192.168.101.1" }, "id": "0000000000000001" }
つづいて、DefaultGateway情報です。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./post_gateway.sh ====================================================================== create_gateway ====================================================================== /openflow/0000000000000001/gateway { "gateway": { "ipaddress": "192.168.100.1" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 69 header: Date: Mon, 03 Nov 2014 08:30:56 GMT ---------- { "id": "0000000000000001", "gateway": { "ipaddress": "192.168.100.1" } }
7. ルータコンフィグ結果確認
OpenFlow簡易ルータのポート情報を確認します。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./get_interface.sh ====================================================================== get_interface ====================================================================== /openflow/0000000000000001/interface ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 256 header: Date: Mon, 03 Nov 2014 08:32:01 GMT +++++++++++++++++++++++++++++++ 2014/11/03 17:32:01 : PortTable +++++++++++++++++++++++++++++++ portNo IpAddress MacAddress -------- --------------- ----------------- 1 192.168.100.100 00:00:00:00:00:01 2 192.168.101.100 00:00:00:00:00:02
つづいて、OpenFlow簡易ルータポート毎のAPR学習結果として、対向機器(PC.BBルータ)のMACアドレスが正しく表示されていることを確認します。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./get_arp.sh ====================================================================== get_arp ====================================================================== /openflow/0000000000000001/arp ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 238 header: Date: Mon, 03 Nov 2014 08:33:51 GMT +++++++++++++++++++++++++++++++ 2014/11/03 17:33:51 : ArpTable +++++++++++++++++++++++++++++++ portNo MacAddress IpAddress -------- ----------------- ------------ 1 10:66:82:93:c4:f0 192.168.100.1 2 00:23:81:14:e8:17 192.168.101.1
最後に、Flowエントリ情報を確認します。各Flowエントリでのパケット転送量も同時に確認できます。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./get_flow_stats.sh ====================================================================== get_flowstats ====================================================================== /openflow/0000000000000001/stats/flow ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 443 header: Date: Mon, 03 Nov 2014 08:34:44 GMT +++++++++++++++++++++++++++++++ 2014/11/03 17:34:44 : FlowStats +++++++++++++++++++++++++++++++ inPort ethSrc ethDst ipv4Dst packets bytes -------- ------------------ ------------------ --------------- -------- -------- 1 10:66:82:93:c4:f0 00:00:00:00:00:01 192.168.101.1 67 10506 2 00:23:81:14:e8:17 00:00:00:00:00:02 192.168.100.1 18 3803 * * * 0.0.0.0/0 430 143408
"0.0.0.0/0"が、DefaultGatewayに該当するFlowエントリになります。
このFlowエントリが表示されない場合には、原因として対向PC端末がネットワークにつながっていないことが想定されます。ネットワーク接続後に、OpenFlowコントローラ再起動からの再作業が必要になります。
以上で、OpenFlow簡易ルータ環境構築は、完了です。
◆OpenFlow動作確認
さっそく、OpenFlow動作確認してみます。
1. IPルーティング動作確認
まず、 IPルーティング動作を確認してみます。
PC端末(192.168.101.1)から、BBルータ(192.168.100.1)にpingを行ってみます。
Microsoft Windows [Version 6.1.7601] Copyright (c) 2009 Microsoft Corporation. All rights reserved. C:¥Users¥tsuboi>ping 192.168.100.1 192.168.100.1 に ping を送信しています 32 バイトのデータ: 192.168.100.1 からの応答: バイト数 =32 時間 =1ms TTL=255 192.168.100.1 からの応答: バイト数 =32 時間 <1ms TTL=255 192.168.100.1 からの応答: バイト数 =32 時間 <1ms TTL=255 192.168.100.1 からの応答: バイト数 =32 時間 <1ms TTL=255 192.168.100.1 の ping 統計: パケット数: 送信 = 4、受信 = 4、損失 = 0 (0% の損失)、 ラウンド トリップの概算時間 (ミリ秒): 最小 = 0ms、最大 = 1ms、平均 = 0ms
さらに、ARP情報を確認してみると、OpenFlow簡易ルータの物理ポート3番(OpenFlowポート2番)に設定したMACアドレスが表示されています。
C:¥Users¥tsuboi>arp -a インターフェイス: 192.168.101.1 --- 0xa インターネット アドレス 物理アドレス 種類 192.168.101.100 00-00-00-00-00-02 動的 192.168.101.255 ff-ff-ff-ff-ff-ff 静的 224.0.0.2 01-00-5e-00-00-02 静的 224.0.0.22 01-00-5e-00-00-16 静的 224.0.0.251 01-00-5e-00-00-fb 静的 224.0.0.252 01-00-5e-00-00-fc 静的 239.255.255.250 01-00-5e-7f-ff-fa 静的 255.255.255.255 ff-ff-ff-ff-ff-ff 静的
つづいて、internetにアクセスしてみます。
ひととり、Webブラウジング / Mail / Ustream / YouTube等が正しく動作するところまで確認できました。
2. OpenFlow簡易ルータ側での疎通診断
つぎに、疎通診断です。
OpenFlow簡易ルータから、BBルータ(192.168.100.1)にpingを行ってみます。
コマンド引数には、[宛先IPアドレス] , [OpenFlowポート番号], [転送データ]の順で指定します。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./put_ping.sh 192.168.100.1 1 From_Port2 ====================================================================== ping ====================================================================== /openflow/0000000000000001/ping { "ping": { "hostIp": "192.168.100.1", "data": "From_Port2", "outPort": "1" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 479 header: Date: Mon, 03 Nov 2014 08:15:56 GMT ---------- { "ping": [ "PING 192.168.100.1 : 10 data bytes", "ping ok ( 18 bytes from 192.168.100.1: icmp_req=1 ttl=255 data=[From_Port2] )", "ping ok ( 18 bytes from 192.168.100.1: icmp_req=2 ttl=255 data=[From_Port2] )", "ping ok ( 18 bytes from 192.168.100.1: icmp_req=3 ttl=255 data=[From_Port2] )", "ping ok ( 18 bytes from 192.168.100.1: icmp_req=4 ttl=255 data=[From_Port2] )", "ping ok ( 18 bytes from 192.168.100.1: icmp_req=5 ttl=255 data=[From_Port2] )" ], "id": "0000000000000001" }
事前に、PC端末側のFirewall設定を無効にして、OpenFlow簡易ルータからPC端末(192.168.101.1)にpingを行ってみます。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./put_ping.sh 192.168.101.1 2 From_Port3 ====================================================================== ping ====================================================================== /openflow/0000000000000001/ping { "ping": { "hostIp": "192.168.101.1", "data": "From_Port3", "outPort": "2" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 479 header: Date: Mon, 03 Nov 2014 08:16:21 GMT ---------- { "ping": [ "PING 192.168.101.1 : 10 data bytes", "ping ok ( 18 bytes from 192.168.101.1: icmp_req=1 ttl=128 data=[From_Port3] )", "ping ok ( 18 bytes from 192.168.101.1: icmp_req=2 ttl=128 data=[From_Port3] )", "ping ok ( 18 bytes from 192.168.101.1: icmp_req=3 ttl=128 data=[From_Port3] )", "ping ok ( 18 bytes from 192.168.101.1: icmp_req=4 ttl=128 data=[From_Port3] )", "ping ok ( 18 bytes from 192.168.101.1: icmp_req=5 ttl=128 data=[From_Port3] )" ], "id": "0000000000000001" }
ためしに、PC端末側のFirewall設定を有効にして、疎通確認を行ってみますと...
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./put_ping.sh 192.168.101.1 2 From_Port3 ====================================================================== ping ====================================================================== /openflow/0000000000000001/ping { "ping": { "hostIp": "192.168.101.1", "data": "From_Port3", "outPort": "2" } } ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 304 header: Date: Mon, 03 Nov 2014 08:17:24 GMT ---------- { "ping": [ "PING 192.168.101.1 : 10 data bytes", "ping ng ( Request Timeout for icmp_seq 1 )", "ping ng ( Request Timeout for icmp_seq 2 )", "ping ng ( Request Timeout for icmp_seq 3 )", "ping ng ( Request Timeout for icmp_seq 4 )", "ping ng ( Request Timeout for icmp_seq 5 )" ], "id": "0000000000000001" }
"ping ng"となり、疎通性NGがOpenFlow簡易ルータ側でも把握できました。
3. 統計情報の確認
最後に、統計情報の確認です。
しばらく、Internetにアクセスしたのちに、OpenFlowのFlowエントリのカウンタ値を確認してみます。
まずは、RB750GLのOpenvSwitch上で、Flowエントリをダンプします。
root@OpenWrt:~# ovs-ofctl dump-flows br0 --protocols=OpenFlow13 OFPST_FLOW reply (OF1.3) (xid=0x2): cookie=0x0, duration=2187.318s, table=0, n_packets=31449, n_bytes=6582008, priority=1,ip actions=set_field:00:00:00:00:00:01->eth_src,set_field:10:66:82:93:c4:f0->eth_dst,output:1,dec_ttl cookie=0x0, duration=2207.717s, table=0, n_packets=159, n_bytes=12108, priority=16,ip,nw_dst=192.168.100.100 actions=CONTROLLER:65535 cookie=0x0, duration=2202.700s, table=0, n_packets=45, n_bytes=2860, priority=16,ip,nw_dst=192.168.101.100 actions=CONTROLLER:65535 cookie=0x0, duration=2215.974s, table=0, n_packets=3187, n_bytes=644067, priority=0 actions=CONTROLLER:65535 cookie=0x0, duration=2202.687s, table=0, n_packets=48696, n_bytes=67103272, priority=255,ip,in_port=1,dl_src=10:66:82:93:c4:f0,dl_dst=00:00:00:00:00:01,nw_dst=192.168.101.1 actions=set_field:00:00:00:00:00:02->eth_src,set_field:00:23:81:14:e8:17->eth_dst,output:2,dec_ttl cookie=0x0, duration=2202.687s, table=0, n_packets=203, n_bytes=21422, priority=255,ip,in_port=2,dl_src=00:23:81:14:e8:17,dl_dst=00:00:00:00:00:02,nw_dst=192.168.100.1 actions=set_field:00:00:00:00:00:01->eth_src,set_field:10:66:82:93:c4:f0->eth_dst,output:1,dec_ttl
さらに、ほぼ同時のタイミングで、OpenFlow簡易ルータ上でも統計情報を取得してみます。
tsubo@RyuSDN:~/simpleRouter-0.1/rest-client$ ./get_flow_stats.sh ====================================================================== get_flowstats ====================================================================== /openflow/0000000000000001/stats/flow ---------- reply: 'HTTP/1.1 200 OK\r\n' header: Content-Type: application/json; charset=UTF-8 header: Content-Length: 454 header: Date: Mon, 03 Nov 2014 07:56:04 GMT +++++++++++++++++++++++++++++++ 2014/11/03 16:56:04 : FlowStats +++++++++++++++++++++++++++++++ inPort ethSrc ethDst ipv4Dst packets bytes -------- ------------------ ------------------ --------------- -------- -------- 1 10:66:82:93:c4:f0 00:00:00:00:00:01 192.168.101.1 48694 67103132 2 00:23:81:14:e8:17 00:00:00:00:00:02 192.168.100.1 203 21422 * * * 0.0.0.0/0 31441 6580664
OpenFlowスイッチ〜コントロール間でのflowエントリ上の統計情報の比較してみると、だいたいカウンタ値は一致していました。
微妙なズレの主要因は、OpenFlow〜OpenvSwirch間でのFlowStatsリクエスト発行間隔を10秒としているためです。
◆おわりに
ひととおり、OpenFlow動作を試してみましたが、問題なく動作するようです。
RouterBOARD (RB750GL)をOpenFlow化して、実際の家庭ネットワークにつないでみるとOpenFlowでのパケット転送がリアルに体感できて面白いと思います。