使用Postman下发流表

任务目的

1、掌握OpenFlow流表相关知识,理解SDN网络中L2,L3,L4层流表的概念。
2、学习并熟练掌握Postman工具下发L2,L3,L4层流表。

任务环境

设备名称 软件环境(镜像) 硬件环境
控制器 Ubuntu 14.04桌面版
OpenDaylight Lithium
CPU:2核 内存:4G 磁盘:20G
交换机 Ubuntu 14.04命令行版
Open vSwitch 2.3.1
CPU:1核 内存:2G 磁盘:20G
主机 Ubuntu14.04桌面版 CPU:1核 内存:2G 磁盘:20G

注:系统默认的账户为root/root@openlab,openlab/user@openlab。

任务内容

1、学习OpenFlow流表的组成,包头域的解析流程及流表的匹配流程。
2、OpenDaylight控制器对接Open vSwitch交换机。
3、使用Postman工具,下发相应的L2,L3,L4层流表,并验证。

实验原理

SDN的设计目标之一就是将网络设备的控制功能与转发功能进行分离,进而将控制功能全部集中到远程的控制器上完成,而SDN交换机只负责在本地做简单高速的数据转发。在SDN交换机运行的过程中,其数据转发的依据就是流表。

一、 流表结构

所谓流表,其实可被视作是SDN对网络设备的数据转发功能的一种抽象。在传统网络设备中,交换机和路由器的数据转发需要依赖设备中保存的二层MAC地址转发表或者三层的IP地址路由表,SDN交换机中使用的流表也是如此,不过在它的表项中整合了网络中各个层次的网络配置信息,从而在进行数据转发时可以使用更丰富的规则。其流表中的每个表项结果如下图所示:

OpenFlow1.3流表的每个表项由6部分组成:

1、匹配域:匹配域即OpenFlow1.0流表中的包头域,用于对交换机接收到的数据包的包头内容进行匹配。在OpenFlow1.0中,流表的包头域中包括了12个元组(Tuple),相关内容如下图所示:

入端口 目的MAC地址 以太网类型 VLAN ID VLAN 优先级 源IP地址 目的IP地址 IP协议 IP TOS位 TCP/UDP源端口 TCP/UDP目的端口
Ingress Port Ehter Des Ether Type VLAN ID VLAN Priority IP Src IP Dst IP Proto IP TOS bits TCP/UDP Src Port TCP/UDP Dst Port

如上图所示,匹配域中用于和交换机接收到的数据包进行匹配的元组涵盖了ISO网络模型中的第二至第四层的网络配置信息。每一个元组中的数值可以是一个确定的值或者是“ANY”以支持对任意值的匹配。另外,如果交换机能够在IP地址相关元组上支持子网掩码的话,将有助于实现更精确的匹配。

2、优先级:流表项的匹配次序。

3、计数器:计数器可以针对交换机中每条流表、每个数据流、每个设备端口、每个转发队列进行维护,用于统计数据流表的相关信息。

4、Instructions指令集:每个流表项都包含一组指令,当一个数据包匹配表项时指令会被执行。这些指令可以更改数据包,动作集或者流表处理。

5、超时:最大时间计数或流有效时间

6、cookie:由控制器选择的不透明数据值。控制器用来过滤流统计数据、流改变和流删除。但处理数据包时不能使用。

二、 匹配域解析流程

当SDN交换机接收到一个数据包时,将按照优先级从table0依次匹配其本地保存的流表中的表项,并以发生具有最高优先级的匹配表项作为匹配结果,并根据相应的动作对数据包进行操作。同时,一旦匹配成功,对应的计数器将更新;而如果没能找到匹配的表项,则将数据包转发给控制器。
OpenFlow交换机对数据包头的解析和匹配过程的细节操作如图所示:

  1. 初始化包头域,按照包头域的组成—设置每个字段,其中入端口是接收数据包的物理端口。

  2. 如果数据包类型是VLAN(0x8100),那么就使用VLAN
    ID和PCP字段进行表查找,解封以太网类型为先的以太网类型解析做准备。

  3. (可选)如果是ARP数据包(0x0806),那么匹配字段就可能包含IP源和目的地址。

  4. 如果是IP数据包(0x0800),那么匹配字段就会包含IP首部。如果IP数据包的分段偏移量不为0或者设置了多个分段bit位,那么将所有传输端口设为0。如果IP数据包在IP协议族中的编号为6或者17(分别是TCP/UDP类型),那么匹配字段包含传输端口。如果编号为1(ICMP数据包)则包含Type和Code字段。

三、 OpenFlow1.3流表匹配流程

OpenFlow1.3匹配流程图与之前版本相比多了一个table-miss流表项,事实上此前版本就已经存在table-miss概念,只是没有在流程图中呈现出来而已。Of1.3版本的匹配流程大致如下图所示:

首先SDN交换机解析进入设备的报文,然后从table0开始匹配,按照优先级高低依次匹配该流表中的表项,一个报文在一个流表中只会匹配上一条流表项。通常根据报文的类型,报文头的字段例如源MAC地址、目的MAC地址、源IP地址、目的IP地址等进行匹配,大部分匹配还支持掩码进行更精确、灵活的匹配。也可以通过报文的入端口或者元数据信息来进行报文的匹配,一个流表项中可以同时存在多个匹配项,一个报文需要同时普票流表项中所有匹配项才能匹配该流表项。报文匹配按照现有的报文字段进行,比如前一个流表通过apply
actions改变了该报文的某个字段,则下一个表现按照修改后的字段进行匹配。如果匹配成功。则按照指令集里的动作更新动作集,活更新报文/匹配集字段,或更新元数据和计数器。根据指令是否继续前往下一个流表,不继续则终止匹配流程执行动作集,如果指令要去继续前往下一流表则继续匹配,下一个流表的ID需要比当前流表ID大。当报文匹配失败,如果存在无匹配流表项(table-miss)就按照该表项执行指令,一般是将报文转发给控制器、丢弃或者转发给其他流表。如果没有table-miss表项则默认丢弃该报文。

实验步骤

一、实验环境检查

步骤1 登录OpenDaylight控制器,确保服务已经启动成功,由于OpenDaylight组件过于庞大,所以启动比较慢,需等待一段时间,使用命令netstat -an|grep 6633查看端口是否处于监听状态:

步骤2 在保证控制器6633端口处于监听状态后,使用root用户登录交换机,查看交换机与控制器连接情况。执行以下命令:


如上图所示,当出现交换机与控制器连接不成功时,执行$ ovs-vsctl del-controller br-sw $ovs-vsctl set-controller br-sw tcp:20.0.1.3:6633手动重连,稍等一会后,重新查看连接状态,如下图所示controller下方显示“is_connected:true” 则表明连接成功。

步骤3 登录主机,查看主机IP地址。

主机1信息截图如下所示。

主机2信息截图如下所示。

步骤4 在两个主机上安装iPerf打流工具。登录主机后,使用如下命令安装iPerf打流工具。

$ sudo apt-get install iperf

步骤5 安装完成可以使用如下命令检查是否安装成功。

$ iperf -s

步骤6 执行Ctrl+c关闭iperf应用程序。

二、L2层流表下发与验证

L2层即对应OSI模型的二层,也就是说通过匹配源MAC(Ether source)、目的MAC地址(Ether dst)、以太网类型(Ether Type)VLAN id、VLAN优先级等字段来实现流的转发。本实验将基于源和目的MAC进行数据流的转发。

步骤1 登录控制器,在下方的“Application Finder”中搜索“postman”,并打开自带的Postman工具,如下图所示。

步骤2 打开Basic Auth页签,Username字段填写admin,Password字段填写admin完成认证。如下图所示。


步骤3 提交方式为GET,URL地址栏中输入http://127.0.0.1:8080/restconf/operational/network-topology:network-topology ,设置完成单击Send按钮,获取交换机id信息。如下图所示。

步骤4 下发第一条流表。

步骤5 单击页面右上角的“实验拓扑”按钮,查看主机与交换机的连接情况,如下图所示。


可知主机10.0.0.5与交换机的1端口连接,主机10.0.0.6与交换机的2端口连接。

步骤6 “body”中选择“raw”,格式为XML(application/xml),并填写如下消息体:

流表:匹配源MAC为fa:16:3e:b4:50:07,目的MAC为fa:16:3e:5c:04:6e的流量,出端口为2。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-source>
<address>fa:16:3e:b4:50:07</address>
</ethernet-source>
<ethernet-destination>
<address>fa:16:3e:5c:04:6e</address>
</ethernet-destination>
</ethernet-match>
</match>
<id>107</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>2</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

参数说明:

  • Priority:匹配流表的优先级。
  • flow-name:流表的名称。
  • idle-timeout:设定超时时间(seconds),参数为0表示永不超时。
  • hard-timeout:最大超时时间(seconds),参数为0表示永不超时。
  • match:匹配Fields。
  • instructions:修改action配置或pipeline处理。
  • ethernet-source:源MAC地址。
  • ethernet-destination:目的MAC地址。

步骤7 单击Send按钮,结果如下图所示。


说明:可根据用户需要设置流表超时时间,idle-timeout、hard-timeout同时设置为0表示永不超时。

步骤8 下发第二条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-source>
<address>fa:16:3e:5c:04:6e</address>
</ethernet-source>
<ethernet-destination>
<address>fa:16:3e:b4:50:07</address>
</ethernet-destination>
</ethernet-match>
</match>
<id>108</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>1</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤9 单击“Send”按钮,结果如下图所示。

步骤10 使用root用户登录交换机,查看流表,执行命令ovs-ofctl dump-flows br-sw如下图所示。

步骤11 登录主机1,ping主机2,如下图所示。

步骤12 再次查看交换机上的流表,可以看到匹配的流表为优先级200的流表,其n_bytes值随着ping而增加,如下图所示。

步骤13 停止主机上的ping操作。

步骤14 删除刚刚创建的流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/107 ,使用DELETE方法,如下图所示。

步骤15 单击Send按钮。

步骤16 删除第二条流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/108 ,使用DELETE方法,如下图所示。

步骤17 单击Send按钮。

三、L3层流表下发与验证

L3层对应OSI模型的三层,三层流表主要匹配的是IP包的协议类型和IP地址。

场景一 匹配源IP

步骤1 下发第一条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-source>10.0.0.5/32</ipv4-source>
</match>
<id>111</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>2</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤2 单击“Send”按钮,结果如下图所示。

步骤3 下发第二条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-source>10.0.0.6/32</ipv4-source>
</match>
<id>112</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>1</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤4 单击Send按钮,结果如下图所示。

步骤5 下发第三条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2054</type>
</ethernet-type>
</ethernet-match>
</match>
<id>113</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>NORMAL</output-node-connector>
<max-length>0</max-length>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤6 单击Send按钮,结果如下图所示。

步骤7 登录交换机查看流表,如下图所示。

步骤8 在主机上ping操作,如下图所示。

步骤9 交换机上再次查看流表,下发的流表被匹配,如下图所示。

步骤10 停止主机上的ping操作。

步骤11 删除刚刚创建的流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/111 ,使用DELETE方法,如下图所示。

步骤12 单击Send按钮。

步骤13 删除第二条流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/112 ,使用DELETE方法,如下图所示。

步骤14 单击Send按钮。

步骤15 删除第三条流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/113 ,使用DELETE方法,如下图所示。

步骤16 单击Send按钮。

场景二 匹配nw_proto字段

步骤1 下发第一条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-destination>10.0.0.6/32</ipv4-destination>
<ip-match>
<ip-protocol>1</ip-protocol>
</ip-match>
</match>
<id>114</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>2</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤2 单击Send按钮,结果如下图所示。

步骤3 下发第二条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-destination>10.0.0.5/32</ipv4-destination>
<ip-match>
<ip-protocol>1</ip-protocol>
</ip-match>
</match>
<id>115</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>1</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤4 单击“Send”按钮,结果如下:

步骤5 下发第三条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2054</type>
</ethernet-type>
</ethernet-match>
</match>
<id>116</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>NORMAL</output-node-connector>
<max-length>0</max-length>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤6 单击“Send”按钮,结果如下:

步骤7 登录交换机查看流表下发情况如下截图。

步骤8 在主机上ping操作。

步骤9 交换机上再次查看流表,下发的流表被匹配。

步骤10 停止主机上的ping操作。

步骤11 删除刚刚创建的流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/114 ,使用DELETE方法,如下图所示。

步骤12 单击Send按钮。

步骤13 删除第二条流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/115 ,使用DELETE方法,如下图所示。

步骤14 单击Send按钮。

步骤15 删除第三条流表,URL输入:http://127.0.0.1:8080/restconf/config/opendaylight-inventory:nodes/node/openflow:196695411516739/table/0/flow/116 ,使用DELETE方法,如下图所示。

步骤16 单击Send按钮。

四、L4层流表下发与验证

L4对应的OSI模型中的四层,即流表对应的TCP/UDP源端口(TCP/UDP src port)、TCP/UDP目的端口号(TCP/UDP dst port)字段。本实验匹配TCP目的端口。

步骤1 下发第一条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<tcp-destination-port>5001</tcp-destination-port>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-destination>10.0.0.6/32</ipv4-destination>
<ip-match>
<ip-protocol>6</ip-protocol>
</ip-match>
</match>
<id>117</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>2</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤2 单击Send按钮,结果如下图所示。

步骤3 下发第二条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2048</type>
</ethernet-type>
</ethernet-match>
<ipv4-destination>10.0.0.5/32</ipv4-destination>
<ip-match>
<ip-protocol>6</ip-protocol>
</ip-match>
</match>
<id>118</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>1</output-node-connector>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤4 单击Send按钮,结果如下图所示。

步骤5 下发第三条流表。

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<flow xmlns="urn:opendaylight:flow:inventory">
<priority>200</priority>
<flow-name>Foo1</flow-name>
<idle-timeout>0</idle-timeout>
<hard-timeout>0</hard-timeout>
<match>
<ethernet-match>
<ethernet-type>
<type>2054</type>
</ethernet-type>
</ethernet-match>
</match>
<id>119</id>
<table_id>0</table_id>
<instructions>
<instruction>
<order>0</order>
<apply-actions>
<action>
<order>0</order>
<output-action>
<output-node-connector>FLOOD</output-node-connector>
<max-length>0</max-length>
</output-action>
</action>
</apply-actions>
</instruction>
</instructions>
</flow>

步骤6 单击Send按钮,结果如下图所示。

步骤7 登录交换机查看流表下发情况如下图所示:

步骤8 登录主机2,使用命令iperf -s启用Iperf为服务端,如下图所示。

步骤9 登录主机1,使用命令iperf -c 10.0.0.6发送TCP请求,如下图所示。

步骤10 交换机上再次查看流表,下发的流表被匹配,如下图所示。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章