2019 SDN第五次上机作业

作业链接

1.浏览RYU官网学习RYU控制器的安装和RYU开发入门教程,提交对于教程代

码的理解,包括但不限于:

安装RYU控制器并测试

安装教程

安装过程及遇到各种问题解决方案

描述官方教程实现了一个什么样的交换机功能?

官方教程实现了一个交换机功能:将接收到的数据包发送到所有端口的。

控制器设定交换机支持什么版本的OpenFlow?

OpenFlow v1.0

#dp.ofproto和dp.ofproto_parser是代表Ryu和交换机协商的OpenFlow协议的对象
from ryu.ofproto import ofproto_v1_0 OFP_VERSIONS = [ofproto_v1_0.OFP_VERSION] ofp = dp.ofproto ofp_parser = dp.ofproto_parser

控制器设定了交换机如何处理数据包?

  • 交换机处理数据包的代码如下所示:
@set_ev_cls(ofp_event.EventOFPPacketIn, MAIN_DISPATCHER)
  • 当ryu控制器接收到数据包时,通过set_ev_cls来告知交换机,调用新增函数packet_in_handler来处理数据包。其中第一个参数ofp_event.EventOFPPacketIn指示应调用此函数的事件类型;第二个参数MAIN_DISPATCHER指示开关的状态,使用 MAIN_DISPATCHER作为第二个参数表示仅在协商完成后才调用此函数。
def packet_in_handler(self, ev):
msg = ev.msg
dp = msg.datapath
ofp = dp.ofproto
ofp_parser = dp.ofproto_parser actions = [ofp_parser.OFPActionOutput(ofp.OFPP_FLOOD)]
out = ofp_parser.OFPPacketOut(
datapath=dp, buffer_id=msg.buffer_id, in_port=msg.in_port,
actions=actions)
dp.send_msg(out)

​新方法'packet_in_handler'已添加到L2Switch类。当Ryu收到OpenFlow packet_in消息时,将调用此方法。

packet_in_handler函数:

  • ev.msg是表示packet_in数据结构的对象。
  • msg.dp是代表数据路径(开关)的对象。
  • dp.ofproto和dp.ofproto_parser是代表Ryu和交换机协商的OpenFlow协议的对象。
  • OFPActionOutput类与packet_out消息一起使用,以指定要从中发送数据包的交换机端口。该应用程序使用OFPP_FLOOD标志来指示应在所有端口上发送数据包。
  • OFPPacketOut类用于构建packet_out消息。
  • 如果使用OpenFlow消息类对象调用Datapath类的send_msg方法,则Ryu会生成联机数据格式并将其发送到交换机。

2.根据官方教程和提供的示例代码(SimpleSwitch.py),将具有自学习功能的#

交换机代码(SelfLearning.py)补充完整:

  • SimpleSwitch.py代码:
from ryu.base import app_manager
from ryu.controller import ofp_event
from ryu.controller.handler import MAIN_DISPATCHER
from ryu.controller.handler import set_ev_cls
from ryu.ofproto import ofproto_v1_0 from ryu.lib.packet import packet
from ryu.lib.packet import ethernet
from ryu.lib.packet import ether_types
from ryu.lib.packet import ipv4 class SimpleSwitch(app_manager.RyuApp):
OFP_VERSIONS = [ofproto_v1_0.OFP_VERSION] def __init__(self, *args, **kwargs):
super(SimpleSwitch, self).__init__(*args, **kwargs) @set_ev_cls(ofp_event.EventOFPPacketIn, MAIN_DISPATCHER)
def _packet_in_handler(self, ev):
msg = ev.msg
datapath = msg.datapath
ofproto = datapath.ofproto pkt = packet.Packet(msg.data)
eth = pkt.get_protocol(ethernet.ethernet) if eth.ethertype == ether_types.ETH_TYPE_LLDP:
#ignore lldp packet
return
if eth.ethertype == ether_types.ETH_TYPE_IPV6:
#ignore ipv6 packet
return print ("PACKET_IN:") print (eth.ethertype)
print ("ethernet:")
print ("eth_src=",eth.src)
print ("eth_dst=",eth.dst) if eth.ethertype == ether_types.ETH_TYPE_IP:
_ipv4 = pkt.get_protocol(ipv4.ipv4)
print ("ipv4:")
print ("ip_src=",_ipv4.src)
print ("ip_dst=",_ipv4.dst) dpid = datapath.id out_port = ofproto.OFPP_FLOOD
actions = [datapath.ofproto_parser.OFPActionOutput(out_port)] data = None out = datapath.ofproto_parser.OFPPacketOut(datapath=datapath, buffer_id=msg.buffer_id, in_port=msg.in_port, actions=actions, data=data)
datapath.send_msg(out)
print ("PACKET_OUT...")
print

补充后的具有自学习功能的交换机代码如下(共有四处地方需要补充):

from ryu.base import app_manager
from ryu.controller import ofp_event
from ryu.controller.handler import MAIN_DISPATCHER
from ryu.controller.handler import set_ev_cls
from ryu.ofproto import ofproto_v1_0 from ryu.lib.mac import haddr_to_bin
from ryu.lib.packet import packet
from ryu.lib.packet import ethernet
from ryu.lib.packet import ether_types class SimpleSwitch(app_manager.RyuApp):
# TODO define OpenFlow 1.0 version for the switch
# add your code here
OFP_VERSIONS=[ofproto_v1_0.OFP_VERSION] def __init__(self, *args, **kwargs):
super(SimpleSwitch, self).__init__(*args, **kwargs)
self.mac_to_port = {} def add_flow(self, datapath, in_port, dst, src, actions):
ofproto = datapath.ofproto match = datapath.ofproto_parser.OFPMatch(
in_port=in_port,
dl_dst=haddr_to_bin(dst), dl_src=haddr_to_bin(src)) mod = datapath.ofproto_parser.OFPFlowMod(
datapath=datapath, match=match, cookie=0,
command=ofproto.OFPFC_ADD, idle_timeout=0, hard_timeout=0,
priority=ofproto.OFP_DEFAULT_PRIORITY,
flags=ofproto.OFPFF_SEND_FLOW_REM, actions=actions)
# TODO send modified message out
# add your code here
datapath.send_msg(mod) @set_ev_cls(ofp_event.EventOFPPacketIn, MAIN_DISPATCHER)
def _packet_in_handler(self, ev):
msg = ev.msg
datapath = msg.datapath
ofproto = datapath.ofproto pkt = packet.Packet(msg.data)
eth = pkt.get_protocol(ethernet.ethernet) if eth.ethertype == ether_types.ETH_TYPE_LLDP:
# ignore lldp packet
return
if eth.ethertype == ether_types.ETH_TYPE_IPV6:
# ignore ipv6 packet
return dst = eth.dst
src = eth.src
dpid = datapath.id
self.mac_to_port.setdefault(dpid, {}) self.logger.info("packet in DPID:%s MAC_SRC:%s MAC_DST:%s IN_PORT:%s", dpid, src, dst, msg.in_port) # learn a mac address to avoid FLOOD next time.
self.mac_to_port[dpid][src] = msg.in_port if dst in self.mac_to_port[dpid]:
out_port = self.mac_to_port[dpid][dst]
else:
out_port = ofproto.OFPP_FLOOD # TODO define the action for output
# add your code here
actions=[datapath.ofproto_parser.OFPActionOutput(out_port)] # install a flow to avoid packet_in next time
if out_port != ofproto.OFPP_FLOOD:
self.logger.info("add flow s:DPID:%s Match:[ MAC_SRC:%s MAC_DST:%s IN_PORT:%s ], Action:[OUT_PUT:%s] ", dpid, src, dst, msg.in_port, out_port)
self.add_flow(datapath, msg.in_port, dst, src, actions) data = None
if msg.buffer_id == ofproto.OFP_NO_BUFFER:
data = msg.data # TODO define the OpenFlow Packet Out
# add your code here
out = datapath.ofproto_parser.OFPPacketOut(datapath=datapath,
buffer_id=msg.buffer_id,
in_port=msg.in_port, actions=actions,
data=data)
datapath.send_msg(out)
print ("PACKET_OUT...")

3.在mininet创建一个最简拓扑,并连接RYU控制器:

拓扑结构图如下所示:

  • 创建拓扑python脚本:
from mininet.topo import Topo
class MyTopo(Topo):
def __init__(self):
Topo.__init__(self)
h1 = self.addHost('h1')
h2 = self.addHost('h2')
s1 = self.addSwitch('s1')
self.addLink(h1, s1, 1, 1)
self.addLink(h2, s1, 1, 2)
topos = {'mytopo': (lambda: MyTopo())}
  • 使用命令运行python脚本
sudo mn --custom mytopo.py --topo mytopo --controller=remote,ip=127.0.0.1,port=6633 --switch ovsk,protocols=OpenFlow10

  • 未连接RYU控制器时查看s1的流表:
sudo ovs-ofctl dump-flows s1

  • 连接RYU控制器:
ryu-manager SelfLearning.py

  • 验证自学习交换机的功能,提交分析过程和验证结果:

  • 再次查看s1流表:

  • 在RYU控制器中可以看到目的主机的MAC地址、源主机的MAC地址、输入端口、输出端口等数据:

  • 使用wireshark抓包分析如下所示:

心得体会

这次实验安装占了大部分的时间,前前后后至少重装了十几次,Mininet,pip3,ryu,python各个版本之间莫名其妙的冲突,翻遍了全网的安装教程(心态爆炸),最后还找到了老师(旺得福)的安装博客(真是太巧了),最后终于安装成功,学到了好多个命令行的使用,真是太好了太惨了,最后总算摸透了各个路径,安装的配置更新。好在后面的具体操作部分不会很难,中间python文件缩进的问题又卡了很久(自闭了,以为代码不对,原来是缩进问题),后面在了老师发的实例和网上的教程之后和同学的帮助下,最后终于完成了。通过这次实验,我对交换机的自学习功能、ryu控制器的基本原理和使用方法也有了一定的了解。

2019 SDN第五次上机作业的更多相关文章

  1. SDN第五次上机作业

    作业链接 1.建立拓扑,并连接上ODL控制器. 2.利用ODL下发组表.流表,实现建议负载均衡 查看s2接收的数据包都被drop掉了 在s1中下发组表 在s1中下发流表使组表生效 下发流表覆盖S2中d ...

  2. SDN第五次上机作业--基于组表的简单负载均衡

    0.作业链接 http://www.cnblogs.com/easteast/p/8125383.html 1.实验目的 1.搭建如下拓扑并连接控制器 2.下发相关流表和组表实现负载均衡 3.抓包分析 ...

  3. 2019 SDN第6次上机作业

    1.作业要求: 作业链接 参考资料: Ryu控制器的API文档:ryu.app.ofctl_rest Ryu的拓扑展示 助教博客:基于RYU restful api实现的VLAN网络虚拟化 2.具体操 ...

  4. 2019 SDN第四次上机作业

    作业博客链接:http://edu.cnblogs.com/campus/fzu/fzusdn2019/homework/10017 1. 解压安装OpenDayLight控制器(本次实验统一使用Be ...

  5. 2019 SDN第三次上机作业

    作业要求: 利用Mininet仿真平台构建给定的网络拓扑,配置主机h1和h2的IP地址(h1:10.0.0.1,h2:10.0.0.2),测试两台主机之间的网络连通性: 利用Wireshark工具,捕 ...

  6. 2019 SDN第3次上机作业

    0.报文类型与含义 1.Controller-to-Switch 报文 ​ Cortoller-to-Switch是由控制器初始化并下发给交换机的报文类型,其可能会要求交换机回复对应的报文,此类型报文 ...

  7. SDN 第五次上机作业

    1.搭建如下拓扑并连接控制器 2.下发相关流表和组表实现负载均衡 s1: s2: s3: s4: 3.抓包分析验证负载均衡 s4-eth1: s4-eth2: s4-eth3

  8. 17秋 SDN课程 第五次上机作业

    17秋 SDN课程 第五次上机作业 Project:https://github.com/Wasdns/new_balance Slide is available at https://github ...

  9. SDN第5次上机作业

    SDN第5次上机作业 实验目的 1.搭建如下拓扑并连接控制器 2.下发相关流表和组表实现负载均衡 3.抓包分析验证负载均衡 实验步骤 1.建立以下拓扑,并连接上ODL控制器. 提交要求:ODL拓扑界面 ...

随机推荐

  1. 解读HTTP/3

    技术的发展总是让人目不暇接,2018年10月,HTTP/3又发布了.虽然已经有一些中文技术媒体做了报道,但大多数是翻译的,而且内容大同小异.最近我专门学习了点关于HTTP/3的知识,在这里随便写写,和 ...

  2. 【开发工具】-解决Myeclipse 的 Server窗口报空指针错误

    Eclipse 或者 MyEclipse  查看 server面板的时候,报错,如图所示,错误 代码:java.lang.NullPointerException .另外,由于此错误,导致 项目不能够 ...

  3. ASP.Net超时时间已到解决办法-

    解决办法 1.在代码里面,把未关闭的连接关闭 2.扩大共享池,方法如下: 解决方法可以是修改连接池的连接生存期,因为默认值是60秒,即连接从应用程序被释放后可以在池中保存的时间. 具体操作步骤如下: ...

  4. Audio Queue Services Programming Guide(音频队列服务编程指南)

    Audio Queue Services 的苹果官方文档: https://developer.apple.com/library/ios/documentation/MusicAudio/Conce ...

  5. DOS命令_查询某个端口的占用情况并释放

    >netstat -aon | findstr “80″Proto   Local Address           Foreign Address         State         ...

  6. Hive函数集锦

    一.内置运算符 1关系运算符 2.算术运算符 3.逻辑运算符 4.复杂类型函数 5.复杂类型函数应用

  7. java系统化基础-day01-基础语法知识

    1.学前必看 该课程将系统化的讲解java基础,但是该课程并不适合零基础的学员,因为在整个java学习体系中我们是按照实际生产设计, 主体思路是以完成某个业务为主线,用到什么技术就学什么技术,即带着问 ...

  8. xshell 连接出现 The remote SSH server rejected X11 forwarding request

    如果本文对你有用,请爱心点个赞,提高排名,帮助更多的人.谢谢大家!❤ yum install xorg-x11-xauth 同时sshd的config文件开启X11Forwarding yes vim ...

  9. Java开发环境之MySql

    查看更多Java开发环境配置,请点击<Java开发环境配置大全> 叁章:MySql安装教程 1)去官网下载MySql安装包 https://www.mysql.com/downloads/ ...

  10. 使用Arduino开发板和ESP8266从互联网读取数据

    ESP8266-01是一款很强大的模块,可以满足我们任何IOT项目的需求.自发布以来,它已经形成了一个很强大的群体,并演变成一个易于使用.价格低廉且功能强大的Wi-Fi模块.另一个更受欢迎的开源平台是 ...