Experiment 6: Open Source Controller Practice - Reeu

First, the experimental purpose

  1. Can independently deploy RYU controllers;
  2. Ability to understand the principle of hub-defined hub defined by the RYU controller;
  3. Ability to understand the Software definition of the RYU controller.

II, experimental environment

  1. Download virtual machine software Oracle VisualBox or VMware;
  2. Install Ubuntu 20.04 Desktop AMD64 in the virtual machine and complete the mininet;

Third, experimental requirements

(1) Basic requirements

  1. Complete the installation of the RYU controller.
  2. Build the SDN topology shown below, protocol uses Open Flow 1.0, and connects the RYU controller.

  3. View the network topology via the RYU graphical interface.



  4. Read the RYU documentation section, run and use TCPDUMP to verify that L2Switch, analysis, and POX’s HUB modules are different.

    h1 ping h2



    h1 ping h3



    Hub and L2Switch implementation are all flooded ICMP packets, and the flow table issued by L2Switch cannot be viewed, and HUB can view.

(2) Advanced requirements

Read RYU’s implementation of simple_switch.py ​​and simple_switch_1x.py, take Simple_Switch_13.py as an example, complete the annotation of its code, and answer the following questions:

SIMPLE_SWITCH13 Source Code and Comments

from ryu.base import app_manager
from ryu.controller import ofp_event
from ryu.controller.handler import CONFIG_DISPATCHER, MAIN_DISPATCHER
from ryu.controller.handler import set_ev_cls
from ryu.ofproto import ofproto_v1_3
from ryu.lib.packet import packet
from ryu.lib.packet import ethernet
from ryu.lib.packet import ether_types

# Inherit Ryu.Base.App_manager.ryuApp# 基类 r.base.app_manager.ryuapp is a class that develops the APP must inherit.# can understand the environment of developing AppAp, and it is very convenient to register without registration.class SimpleSwitch13(app_manager.RyuApp):
    OFP_VERSIONS = [ofproto_v1_3.OFP_VERSION]  # Specify OpenFlow 1.3 versiondef __init__(self, *args, **kwargs):
        super(SimpleSwitch13, self).__init__(*args, **kwargs)
        self.mac_to_port = {} 
    # Define a list of MAC addresses, the MAC_TO_PORT table here is the corresponding switch two-layer communication query table# set_ev_cls Specify event categories to accept event messages and switches as parameters# SET_EV_CLS The first parameter indicates the function that the event should call, and the second parameter tells the switch that only after the switch handshake is completed, it can be called.# OFP_EVENT completes the definition of the event, so we can register the Handler, listen to the event, and respond in the function.# packet_in_handler method is used to handle the packet_in event.# @set_ev_cls修饰符用于告知RYU,被修饰的函数应该被调用。

    @set_ev_cls(ofp_event.EventOFPSwitchFeatures, CONFIG_DISPATCHER)
    def switch_features_handler(self, ev):
    	# ev. msg is an OpenFlow message category entity used to store corresponding events# msg.dataPath is the entity data used to store the OpenFlow switch Ryu.Controller.Controller.DataPath category Category DataPath = ev. msg.dataPath ofProto = DataPath.OfProto# ofproto Ryu.OfProto.OfProto_v1_3 Parser = DataPath.OfProto_Parser with the OpenFlow version# and OFPROTO, there is corresponding version Ryu.OfProto.ofproto_v1_3_parser, resolving the protocol to use   @set_ev_cls(ofp_event.EventOFPPacketIn, MAIN_DISPATCHER)
   def _packet_in_handler(self, ev):
       # If you hit this you might want to increase
       # the "miss_send_length" of your switch
       if ev.msg.msg_len < ev.msg.total_len:
           self.logger.debug("packet truncated: only %s of %s bytes",
                             ev.msg.msg_len, ev.msg.total_len)
        # Packages to the Controller can only transmit the Header section, and the remaining is in the buffer inter-efficiency.#, current (Jan 2014) Open vSwitch has a bug relationship, which will transmit all packets and will not only transfer Header.# This Logger.debug log is to prompt the packet_in package to the Controller to intercept the header section. I am so understanding here. If you have a mistake, please inform you.# In order to receive packets that handle unknown destinations, you need to perform packet-in event management MSG = ev. msg# There are MSG members in each event class EV, which is used to carry the data package of trigger events DataPath = msg.dataPath# MsG that has been formatted is actually a packet_in message, and Msg.DataPath can directly obtain the DataPath structure of packet_in packets.# DataPath is used to describe a switched bridge and a solid unit that communicates with the controller.# datapath.send_msg () function is used to send data to the specified DataPath.# Get DPID data via DataPath.ID. OFPROTO = DataPath.OfProto# DataPath.OfProto object is an OpenFlow protocol data structure object, member contains the data structure of the OpenFlow protocol, such as action type ofpp_flood parser = datapath.ofproto_Parser# DataPath.OFP_Parser is a data structure parsed in OpenFlow.# Update MAC Address Table In_Port = msg.match ['in_port']

       pkt = packet.Packet(msg.data)
       eth = pkt.get_protocols(ethernet.ethernet)[0] 
       # pkt.get_protocols Incoming Protocol parameters# Get the protocol list of the Ethernet.Ethernet class instance of the protocol, see the source code knows Lib.packet.packet / Ethernetif eth.ethertype == ether_types.ETH_TYPE_LLDP:
           # ignore lldp packet
       dst = eth.dst
       src = eth.src

       dpid = datapath.id
       self.mac_to_port.setdefault(dpid, {})
       # Specify the switch DPID, the default Mac_to_Port table is empty self.logger.info"packet in %s %s %s %s", dpid, src, dst, in_port)
       ​​# Log Information# learn a mac address to avoid FLOOD next time.
       self.mac_to_port[dpid][src] = in_port

   	# Judgment the connection port of the forwarded packet# Destination The MAC address is exhibited in the MAC address table, it is determined that the connection port number code is output.# Easeless If you do not exist in the MAC address table, an entity of the Output Action category and generate a FLODING (OFPP_FLOOD).if dst in self.mac_to_port[dpid]:
           out_port = self.mac_to_port[dpid][dst]
        # There is a destination address to find port numbers, otherwise floodingelse:
           out_port = ofproto.OFPP_FLOOD
   		# Prepare the flood packet_out instructions to the last else actions = [Parser.OfPactionoutput (out_port)]# install a flow to avoid packet_in next time
       if out_port != ofproto.OFPP_FLOOD:
           match = parser.OFPMatch(in_port=in_port, eth_dst=dst, eth_src=src)
           # verify if we have a valid buffer_id, if yes avoid to send both
           # flow_mod & packet_out
           if msg.buffer_id != ofproto.OFP_NO_BUFFER:
               self.add_flow(datapath, 1, match, actions, msg.buffer_id)
               return # No floodry to exit functionelse:
               self.add_flow(datapath, 1, match, actions)

   	# Find the MAC address in the MAC address table. If you find it, send a packet-out message, and transfer the packet. Data =None
       if msg.buffer_id == ofproto.OFP_NO_BUFFER:
       #, you want flooding to send Packet-Out, take it out of binary data of itself Data = msg.dataRequires Flooding Actions and MSG. Buffer_id is ready for out = parser.ofppacketout (datapath = datapath, buffer_id = msg.buffer_id, in_port = in_port, actions = actions, data = data) DataPath.send_msg (out)

A) What is the role of Mac_to_Port in the code?
Corresponding Switch Layer 2 communication query table.
B) Simple_Switch and Simple_Switch_13 What is the difference in DPID?
SIMPLE_SWITCH_13 is filled with 16 digits for DPID.
c) What is the function of Switch_FEATURE_HANDLER added in Simple_Switch_13?
Install the targetless flow table entry
D) How does simple_switch_13 implement flow rules?
After receiving the package, there is a MAC address for forwarding, there is no flooding.
e) Switch_features_handler and _packet_in_handler two events do not have to send the priority of the flow rule?
Switch_features_Handler sent priority = 0, Packet_in_handler sent the priority set to 1, switch_features_handler higher priority.

Experimental experience

This experiment foundation is relatively simple to follow the steps of the last experiment. During many difficulties during the period, they rely on the help of classmates, there are many receipts.