SDN LABORATORY Fabrizio Granelli fabrizio.granelli@unitn.it Downloads for SDN Lab ¨ Download the VMs from https://github.com/mininet/openflow-tutorial/wiki/Installing-RequiredSoftware ¨ Verify software requirements: OS Type OS Version Virtualization Software X Server Terminal Windows 7+ VirtualBox Xming PuTTY Windows XP VirtualBox Xming PuTTY Mac OS X 10.7-10.9 Lion/Mountain Lion/ Mavericks VirtualBox download and install XQuartz Terminal.app (built in) VirtualBox X server already installed gnome terminal + SSH built in Linux Ubuntu 10.04+ Refer to https://github.com/mininet/openflow-tutorial/wiki/Home for more details OpenFlow building blocks oftrace oflops Monitoring/ debugging tools openseer Stanford Provided ENVI (GUI) NOX LAVI Beacon Expedient Commercial Switches HP, NEC, Pronto, Juniper.. and many more Aggregation n-Casting Helios Maestro Controller Applications SNAC Controller Slicing Software FlowVisor Stanford Provided Software Ref. Switch NetFPGA Broadcom Ref. Switch OpenWRT PCEngine WiFi AP OpenVSwitch OpenFlow Switches 3 Trend Computer Industry Network Industry Isolated “slices” Many operating systems, or Many versions 5 Open interface to hardware Open interface to hardware Switch Based Virtualization Exists for NEC, HP switches but not flexible enough 6 Research VLAN 2 Flow Table Controller Research VLAN 1 Flow Table Controller Production VLANs Normal L2/L3 Processing FlowVisor-based Virtualization Bob’s Controller Alice’s Controller Topology discovery is per slice Fabrizio’s Controller OpenFlow Protocol OpenFlow FlowVisor & Policy Control OpenFlow Switch OpenFlow Protocol OpenFlow Switch OpenFlow Switch 7 FlowVisor-based Virtualization 8 Separation not only by VLANs, but any L1-L4 pattern Multicast Broadcast OpenFlow Protocol dl_dst=FFFFFFFFFFFF tp_src=80, or tp_dst=80 OpenFlow FlowVisor & Policy Control OpenFlow Switch OpenFlow Protocol OpenFlow Switch http Load-balancer OpenFlow Switch FlowSpace: Maps Packets to Slices FlowVisor Message Handling Alice Controller Bob Controller Cathy Controller OpenFlow Policy Check: Is this rule allowed? Policy Check: Who controls this packet? FlowVisor OpenFlow Full Line Rate Forwarding Packet Packet OpenFlow Firmware Data Path Rule Exception Introduction to Mininet ¨ Mininet ¤ A network emulator which creates realistic virtual network ¤ Runs real kernel, switch and application code on a single machine ¤ Provides both Command Line Interface (CLI) and Application Programming Interface (API) n n ¤ CLI: interactive commanding API: automation Abstraction n Host: emulated as an OS level process n Switch: emulated by using software-based switch n E.g., Open vSwitch, SoftSwitch Mininet Installation (1/2) ¨ Mininet VM Installation ¤ The easiest and most fool-proof way of installing Mininet ¤ Procedures n Download the Mininet pre-installed VM image Download and install one of the hypervisors (e.g., VirtualBox, Qemu, VMware Workstation, VMware Fusion, or KVM) n Import VM image into selected hypervisor n ¨ Native Installation from Source ¤ Recommended OS: Ubuntu 11.10 and later ¤ Procedures n Download source from github $ git clone git://github.com/mininet/mininet n Full installation: Mininet + Open vSwtich + wireshark + etc. n Minimum installation: + Mininet + Open vSwitch $ mininet/util/install.sh -fnv $ mininet/util/install.sh -a Mininet Installation (2/2) ¨ Native Installation from Package ¤ ¤ Recommended OS: Ubuntu 12.04 and later Procedures n Remove all previously installed Mininet and Open vSwitch $ sudo rm -rf /usr/local/bin/mn /usr/local/bin/mnexec \ /usr/local/lib/python*/*/*mininet* \ /usr/local/bin/ovs-* /usr/local/sbin/ovs-* n Install Mininet package according to your Ubuntu version (choose one of them!) $ sudo apt-get install mininet $ sudo apt-get install mininet/quantal-backports $ sudo apt-get install mininet/precise-backports n Deactive OpenvSwitch controller if it is running $ sudo service openvswitch-controller stop $ sudo update-rc.d openvswitch-controller disable n You can also install additional software from mininet source $ git clone git://github.com/mininet/mininet $ mininet/util/install.sh -fw Ubuntu 13.04 Ubuntu 12.10 Ubuntu 12.04 Mininet Tutorial (1/7) ¨ Mininet Command Line Interface Usage ¤ Interact with hosts and switches n Start a minimal topology $ sudo mn n Start a minimal topology using a remote controller $ sudo mn --controller=remote,ip=[IP_ADDDR],port=[listening port] n Start a custom topology $ sudo mn --custom [topo_script_path] --topo=[topo_name] n Display nodes mininet> nodes n Display links mininet> net n Dump information about all nodes mininet> dump Mininet Tutorial (2/7) ¨ Mininet Command Line Interface Usage ¤ Interact with hosts and switches n Check the IP address of a certain node mininet> h1 ifconfig -a n Print the process list from a host process mininet> h1 ps -a ¤ Test connectivity between hosts n Verify the connectivity by pinging from host0 to host1 mininet> h1 ping -c 1 h2 n Verify the connectivity between all hosts mininet> pingall Mininet Tutorial (3/7) ¨ Mininet Command Line Interface Usage ¤ Run a regression test n Traffic receive preparation mininet> iperf -s -u -p [port_num] & n Traffic generation from client mininet> iperf -c [IP] -u -t [duration] -b [bandwidth] -p [port_num] & ¤ Link variations $ sudo mn -link tc,bw=[bandwidth],delay=[delay_in_millisecond] ¤ Python Interpreter n Print accessible local variables $ py locals() n Execute a method through invoking mininet API $ py [mininet_name_space].[method] Mininet Tutorial (4/7) ¨ Mininet Application Programming Interface Usage ¤ Low-level API: nodes and links n mininet.node.Node n n A virtual network node, which is a simply in a network namespace mininet.link.Link n Class Node Link A basic link, which is represented as a pair of nodes Method Description MAC/setMAC Return/Assign MAC address of a node or specific interface IP/setIP Return/Assign IP address of a node or specific interface cmd Send a command, wait for output, and return it terminate Send kill signal to Node and clean up after it Link Create a link to another node, make two new interfaces h1 = Host( 'h1' ) h2 = Host( 'h2' ) s1 = OVSSwitch( 's1', inNamespace=False ) c0 = Controller( 'c0', inNamespace=False ) Link( h1, s1 ) Link( h2, s1 ) h1.setIP( '10.1/8' ) h2.setIP( '10.2/8' ) c0.start() s1.start( [ c0 ] ) print h1.cmd( 'ping -c1', h2.IP() ) s1.stop() c0.stop() Mininet Tutorial (5/7) ¨ Mininet Application Programming Interface Usage ¤ Middle-level API: network object n mininet.net.Mininet n Class Net Network emulation with hosts spawned in network namespaces Method Description addHost Add a host to network addSwitch Add a switch to network addLink Link two nodes into together addController Add a controller to network getNodeByName Return node(s) with given name(s) start Start controller and switches stop Stop the controller, switches and hosts ping Ping between all specified hosts and return all data net = Mininet() h1 = net.addHost( 'h1' ) h2 = net.addHost( 'h2' ) s1 = net.addSwitch( 's1' ) c0 = net.addController( 'c0' ) net.addLink( h1, s1 ) net.addLink( h2, s1 ) net.start() print h1.cmd( 'ping -c1', h2.IP() ) CLI( net ) net.stop() Mininet Tutorial (6/7) ¨ Mininet Application Programming Interface Usage ¤ High-level API: topology templates n mininet.topo.Topo n Class Topo Data center network representation for structured multi-trees Method Description Methods similar to net E.g., addHost, addSwitch, addLink, addNode Add node to graph addPort Generate port mapping for new edge switches Return all switches Hosts/nodes/switches/links Return all hosts isSwitch Return true if node is a switch, return false otherwise class SingleSwitchTopo( Topo ): "Single Switch Topology" def build( self, count=1): hosts = [ self.addHost( 'h%d' % i ) for i in range( 1, count + 1 ) ] s1 = self.addSwitch( 's1' ) for h in hosts: self.addLink( h, s1 ) net = Mininet( topo=SingleSwitchTopo( 3 ) ) net.start() CLI( net ) net.stop() Mininet Tutorial (7/7) ¨ Mininet Application Programming Interface Usage ¤ Customized topology # cat custom.py LEN_DPID = 16 from mininet.topo import Topo class MyTopo( Topo ): def name_dpid( self, index ): dpid = '%02d' % ( index ) zeros = '0' * ( LEN_DPID - len( dpid ) ) name = 's%02d' % ( index ) return { 'name':name, 'dpid':zeros + dpid } def build( self, count=1): hosts = [ self.addHost( 'h%d' % i ) for i in range( 1, count + 1 ) ] s1 = self.addSwitch( **self.name_dpid(1) ) for h in hosts: self.addLink( h, s1 ) topos = { 'mytopo': MyTopo } # mn --custom custom.py --topo mytopo,3 *** Creating network *** Adding controller *** Adding hosts: More examples can be found here: h1 h2 h3 https://github.com/mininet/mininet/tree/master/examples Two Flow Insertion Methods ¨ Reactive Flow Insertion ¤ ¨ A non-matched packet reaches an OpenFlow switch, it is sent to the controller, based on the packet an appropriate flow is inserted Proactive Flow Insertion ¤ Flow can be inserted proactively by the controller in switches before packet arrive SRC DST ACT h1 h2 p1 OpenFlow Controller … acquire route SRC DST ACT h1 h2 p1 … insert flow host1 switch1 (reactive) switch2 (proactive) host2 Mininet OpenFlow tutorial ¨ Download the VMs from https://github.com/mininet/openflow-tutorial/wiki/Installing-RequiredSoftware ¨ Verify software requirements: OS Type OS Version Virtualization Software X Server Terminal Windows 7+ VirtualBox Xming PuTTY Windows XP VirtualBox Xming PuTTY Mac OS X 10.7-10.9 Lion/Mountain Lion/ Mavericks VirtualBox download and install XQuartz Terminal.app (built in) VirtualBox X server already installed gnome terminal + SSH built in Linux Ubuntu 10.04+ Refer to https://github.com/mininet/openflow-tutorial/wiki/Home for more details Mininet VM Setup ¨ Once you have downloaded the .ovf image, ¤ Start up VirtualBox, then select File>Import Appliance and select the .ovf image that you downloaded. ¨ You may also be able to simply double-click the .ovf file to open it up in your installed virtualization program. ¤ Next, ¨ press the "Import" button. This step will take a while - the unpacked image is about 3 GB. Setting up the VM for ssh access ¨ ¨ If you are running VirtualBox, you should make sure your VM has two network interfaces. One should be a NAT interface that it can use to access the Internet, and the other should be a host-only interface to enable it to communicate with the host machine. For example, your NAT interface could be eth0 and have a 10.x IP address, and your host-only interface could be eth1 and have a 192.168.x IP address. You should ssh into the host-only interface at its associated IP address. Both interfaces should be configured using DHCP. From the virtual machine console, log in to the VM, then enter: $ ifconfig -a ¨ You should see three interfaces(eth0, eth1, lo), Both eth0 and eth1 should have IP address assigned. If this is not the case, type $ sudo dhclient ethX ¨ For the access to the VM: $ ssh -X [user]@[Guest IP Here] Alternative: using the VM GUI ¨ Log in to the VM console window, and type: $ sudo apt-get update && sudo apt-get install xinit lxde virtualbox-guest-dkms ¨ At this point, you should be able to start an X11 session in the VM console window by typing: $ startx Development Tools ¨ ¨ ¨ ¨ ¨ ¨ ¨ OpenFlow Controller: sits above the OpenFlow interface. The OpenFlow reference distribution includes a controller that acts as an Ethernet learning switch in combination with an OpenFlow switch. You'll run it and look at messages being sent. Then, in the next section, you'll write our own controller on top of NOX or Beacon (platforms for writing controller applications). OpenFlow Switch: sits below the OpenFlow interface. The OpenFlow reference distribution includes a user-space software switch. Open vSwitch is another software but kernel-based switch, while there is a number of hardware switches available from Broadcom (Stanford Indigo release), HP, NEC, and others. ovs-ofctl: command-line utility that sends quick OpenFlow messages, useful for viewing switch port and flow stats or manually inserting flow entries. Wireshark: general (non-OF-specific) graphical utility for viewing packets. The OpenFlow reference distribution includes a Wireshark dissector, which parses OpenFlow messages sent to the OpenFlow default port (6633) in a conveniently readable way. iperf: general command-line utility for testing the speed of a single TCP connection. Mininet: network emulation platform. Mininet creates a virtual OpenFlow network controller, switches, hosts, and links - on a single real or virtual machine. More Mininet details can be found at the Mininet web page. cbench: utility for testing the flow setup rate of OpenFlow controllers. Start a simple network $ sudo mn --topo single,3 --mac --switch ovsk --controller remote What did we do? $ sudo mn --topo single,3 --mac --switch ovsk --controller remote ¨ ¨ ¨ ¨ ¨ Created 3 virtual hosts, each with a separate IP address. Created a single OpenFlow software switch in the kernel with 3 ports. Connected each virtual host to the switch with a virtual ethernet cable. Set the MAC address of each host equal to its IP. Configure the OpenFlow switch to connect to a remote controller. Some relevant mininet commands ¨ To see the list of nodes available, in the Mininet console, run: mininet> nodes ¨ To see a list of available commands, in the Mininet console, run: mininet> help ¨ To run a single command on a node, prepend the command with the name of the node. For example, to check the IP of a virtual host, in the Mininet console, run: mininet> h1 ifconfig ¨ The alternative - better for running interactive commands and watching debug output - is to spawn an xterm for one or more virtual hosts. In the Mininet console, run: mininet> xterm h1 h2 ¨ If Mininet is not working correctly (or has crashed and needs to be restarted), first quit Mininet if necessary (using the exit command, or controlD), and then try clearing any residual state or processes using: $ sudo mn -c ovs-ofctl example usage ¨ Create another terminal window: $ sudo ovs-ofctl show s1 ¨ ¨ The show command connects to the switch and dumps out its port state and capabilities. Here's a more useful command: $ sudo ovs-ofctl dump-flows s1 ¨ Since we haven't started any controller yet, the flow-table should be empty. Ping test ¨ Now, go back to the mininet console and try to ping h2 from h1. In the Mininet console: mininet> h1 ping -c3 h2 ¨ ¨ ¨ Note that the name of host h2 is automatically replaced when running commands in the Mininet console with its IP address (10.0.0.2). Do you get any replies? Why? Why not?As you saw before, switch flow table is empty. Besides that, there is no controller connected to the switch and therefore the switch doesn't know what to do with incoming traffic, leading to ping failure. Ping test – manual config ¨ You'll use ovs-ofctl to manually install the necessary flows. In your SSH terminal: # sudo ovs-ofctl add-flow s1 in_port=1,actions=output:2 # sudo ovs-ofctl add-flow s1 in_port=2,actions=output:1 ¨ This will forward packets coming at port 1 to port 2 and vice-versa. Verify by checking the flow-table: # ovs-ofctl dump-flows s1 ¨ Run the ping command again. In your mininet console: mininet> h1 ping -c3 h2 ¨ Do you get replies now? Check the flow-table again and look the statistics for each flow entry. Is this what you expected to see based on the ping traffic? Run Wireshark ¨ The VM image includes the OpenFlow Wireshark dissector preinstalled. Wireshark is extremely useful for watching OpenFlow protocol messages, as well as general debugging. $ sudo wireshark & ¨ ¨ ¨ ¨ You'll probably get a warning message for using wireshark with root access. Press OK. Now, set up a filter for OpenFlow control traffic, by using the ’tcp port 6653' filter (Capture->Options). Click on Capture->Interfaces in the menu bar. Click on the Start button next to 'lo', the loopback interface. You may see some packets going by. Press the apply button to apply the filter to all recorded traffic. (See https://wiki.wireshark.org/OpenFlow for more info on OF support in Wireshark) Start basic controller ¨ With the Wireshark dissector listening, start the OpenFlow reference controller. In your SSH terminal: $ sudo controller –v ptcp:6653 & ¨ ¨ This starts a simple controller that acts as a learning switch without installing any flow-entries. The parameters represent the listening port for the controller (6653) and the verbose option ‘-v’ You should see a bunch of messages displayed in Wireshark, from the Hello exchange onwards. Using the controller ¨ First, we need to delete the flowtable in the switch and the ARP tables in the hosts: sudo ovs-ofctl del-flows s1 mininet> h1 ip -s -s neigh flush all mininet> h2 ip -s -s neigh flush all ¨ Do the ping in the Mininet console: mininet> h1 ping -c1 h2 ¨ Repeat the command: what happens? Benchmark controller w/iperf ¨ ¨ We will benchmark the reference controller in mininet In the mininet console run: mininet> iperf ¨ ¨ This Mininet command runs an iperf TCP server on one virtual host, then runs an iperf client on a second virtual host. Once connected, they blast packets between each other and report the results. Now compare with the user-space switch. In the mininet console: mininet> exit ¨ Start the same Mininet with the user-space switch: $ sudo mn --topo single,3 --controller remote --switch user Benchmark controller w/iperf ¨ Run one more iperf test with the reference controller: mininet> iperf ¨ ¨ With the user-space switch, packets must cross from user-space to kernel-space and back on every hop, rather than staying in the kernel as they go through the switch. The user-space switch is easier to modify (no kernel oops'es to deal with), but slower for simulation. Exit Mininet: mininet> exit Slicing using FlowVisor ¨ See the following tutorial Any questions? Fabrizio Granelli fabrizio.granelli@unitn.it