• OpenFlow PacketOut消息机制


    OpenFlow PacketOut消息机制

    前言

    由于最近实验的进行,遇到一个比较棘手的问题,就是利用控制器主动发送packet消息的问题,期间遇到一些问题,后来在RYU群中得到群友左木的帮助成功解决,记录一下这些问题,由于是昨天的问题,就没有把错误截图给截下来了(不想在重做一遍了)。

    实验工具

    • RYU
    • mininet
    • wireshark

    问题描述与解决

    ryu指南中的packetout消息(OF1.3)

    class ryu.ofproto.ofproto_v1_3_parser.OFPPacketOut(datapath, buffer_id=None, in_port=None, actions=None, data=None, actions_len=None)
    

    Packet-Out message

    The controller uses this message to send a packet out throught the switch.

    Attribute Description
    buffer_id ID assigned by datapath (OFP_NO_BUFFER if none)
    in_port Packet's input port or OFPP_CONTROLLER
    actions list of OpenFlow action class
    data Packet data of a binary type value or an instances of packet.Packet.

    Example:

    def send_packet_out(self, datapath, buffer_id, in_port):
        ofp = datapath.ofproto
        ofp_parser = datapath.ofproto_parser
    
        actions = [ofp_parser.OFPActionOutput(ofp.OFPP_FLOOD, 0)]
        req = ofp_parser.OFPPacketOut(datapath, buffer_id,
                                      in_port, actions)
        datapath.send_msg(req)
    

    于是我照猫画虎的来下来如下代码:

            ofp = datapath.ofproto
            ofp_parser = datapath.ofproto_parser
            actions = [ofp_parser.OFPActionOutput(port=1)]
            req = ofp_parser.OFPPacketOut(datapath=datapath, buffer_id=ofp.OFP_NO_BUFFER, in_port=1,
                                          actions=actions)
            datapath.send_msg(req)
    

    这样下来运行也没有错误,可是就是无法在端口一抓到包,心生疑惑又在控制器的那一端抓了一次,结果抓到了这个包。后来在群友耐心指导下,原来是没加data下去,所以在端口一无法抓到包。


    于是我就构造了一个arp报文重新发了一次,改了一下代码

            ofp = datapath.ofproto
            ofp_parser = datapath.ofproto_parser
            e = ethernet.ethernet(dst='00:00:00:00:ff:ff',
                                  src='08:60:6e:7f:74:e7',
                                  ethertype=ether.ETH_TYPE_ARP)
            
            a = arp.arp(hwtype=1, proto=0x0800, hlen=6, plen=4, opcode=2,
                        src_mac='08:60:6e:7f:74:e7', src_ip='192.0.2.1',
                        dst_mac='00:00:00:00:00:00', dst_ip='192.0.2.2')
            p = packet.Packet()
            p.add_protocol(e)
            p.add_protocol(a)
            p.serialize()
            
            actions = [ofp_parser.OFPActionOutput(1)]
            req = ofp_parser.OFPPacketOut(datapath=datapath, buffer_id=ofp.OFP_NO_BUFFER, in_port=1,
                                          actions=actions, data=p)
            datapath.send_msg(req)
    

    这回确实是抓到了,可是又心生疑惑,我明明有一条流表,为什么这个包不会先匹配一下流表吗?于是又向群友求助,原来是:

    Action 是一个行动列表定义交换机如何处理数据包的字段。可包括包修改,组处理和一
    个输出端口。 一个 OFPT_PACKET_OUT 行动清单消息也可以指定 OFPP_TABLE 保留端口
    作为输出行动来处理 OpenFlow 流水线中的数据包,从第一个流表开始(见 4.5) 。如果
    OFPP_TABLE 被指定,in_port 作为查找时流表的入端口。

    于是我又改了一下代码,把动作改成output到OFPP_TABLE去

           ofp = datapath.ofproto
            ofp_parser = datapath.ofproto_parser
            e = ethernet.ethernet(dst='00:00:00:00:ff:ff',
                                  src='08:60:6e:7f:74:e7',
                                  ethertype=ether.ETH_TYPE_ARP)
    
            a = arp.arp(hwtype=1, proto=0x0800, hlen=6, plen=4, opcode=2,
                        src_mac='08:60:6e:7f:74:e7', src_ip='192.0.2.1',
                        dst_mac='00:00:00:00:00:00', dst_ip='192.0.2.2')
            p = packet.Packet()
            p.add_protocol(e)
            p.add_protocol(a)
            p.serialize()
            actions = [ofp_parser.OFPActionOutput(port=ofp.OFPP_TABLE)]
            req = ofp_parser.OFPPacketOut(datapath=datapath, buffer_id=ofp.OFP_NO_BUFFER, in_port=1,
                                          actions=actions, data=p)
            datapath.send_msg(req)
    

    这下确实是大功告成了。


    途中也遇到了一个疑惑,buffer_id的作用,相信的可以看这篇Openflow细节理解之—Buffer_id篇

    总结

    如果是OpenFlow消息交互的问题,还是得回归OpenFlow白皮书。

  • 相关阅读:
    IO 单个文件的多线程拷贝
    day30 进程 同步 异步 阻塞 非阻塞 并发 并行 创建进程 守护进程 僵尸进程与孤儿进程 互斥锁
    day31 进程间通讯,线程
    d29天 上传电影练习 UDP使用 ScketServer模块
    d28 scoket套接字 struct模块
    d27网络编程
    d24 反射,元类
    d23 多态,oop中常用的内置函数 类中常用内置函数
    d22 封装 property装饰器 接口 抽象类 鸭子类型
    d21天 继承
  • 原文地址:https://www.cnblogs.com/wpqwpq/p/6576555.html
Copyright © 2020-2023  润新知