Attribution: This lab uses OpenDaylight (Karaf distribution) and Mininet. OpenDaylight is licensed under the Eclipse Public License (EPL). Mininet is distributed under its respective license. This repository contains lab instructions and scripts for educational use.
Continue with what we had on previous lab, we will install OpenDaylight as the SDN controller to connect with Mininet to read the network statistics.
By the end of this lab, students will be able to:
-
Deploy an SDN testbed by installing and launching OpenDaylight and connecting a Mininet topology using OpenFlow 1.3.
-
Verify controller–switch connectivity by checking listening ports (e.g., 6653 for OpenFlow and 8181 for RESTCONF) and interpreting Mininet connection messages.
-
Enable required OpenDaylight features (OpenFlow plugin, topology discovery, table-miss enforcer, REST services) and explain why a controller may appear “running” but not accept OpenFlow connections until plugins are installed.
-
Capture and identify OpenFlow control traffic (e.g., HELLO/FEATURES requests, PACKET_IN/PACKET_OUT) using Wireshark and select the correct interface/namespace to monitor.
-
Query OpenDaylight northbound APIs to retrieve network state (nodes, topology, flows) and interpret JSON responses using tools like jq.
-
Distinguish OpenDaylight data stores by comparing config vs operational (non-config) flow state, and explain why flow entries may appear in one but not the other.
-
Reason about SDN control-plane workflow: how southbound events (switch connect, discovery, packet-in) propagate into controller state and become visible through northbound APIs.
Memory: >= 8GB
Storage: 50GB
CPU: 2 cores, AMD64 Architecture
Installation Disc: ubuntu-22.04.4-desktop-amd64.iso
An Instant Virtual Network on your Laptop (or other PC)
-
Install and Configure Java
(1) Install Java
sudo apt-get install openjdk-17-jdk(2) Configure JAVA_HOME to /etc/profile
sudo vim /etc/profile(3) Add the following to the end of /etc/profile
JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64 PATH=$PATH:$HOME/bin:$JAVA_HOME/bin export JAVA_HOME export JRE_HOME export PATH(4) Make JAVE_HOME valid and Test JAVA Version
source /etc/profile java -version -
Install OpenDaylight
(1) Download OpenDaylight Calcium
wget https://nexus.opendaylight.org/content/repositories/opendaylight.release/org/opendaylight/integration/karaf/0.20.1/karaf-0.20.1.zip(2) Extract it to $HOME
unzip karaf-0.20.1.zip(3) Configure ODL-0.20.1 Environment
cd karaf-0.20.1/bin vim setenv(4) Add the following to the setenv file
export JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64 -
Run OpenDaylight. In a system terminal:
sudo ./karaf -
Connect Mininet to OpenDaylight
(1) Run Mininet with Customized Topology and Connect to Controller
sudo mn --custom ~/custom_mn/topo-2sw-2host.py --topo mytopo --switch ovsk,protocols=OpenFlow13 --controller remote,ip=127.0.0.1,port=6653NOTE: We can also have a remote controller building in another VM. If so, we connect Mininet to the remote controller with the $IP_ODL of that VM. The $IP_ODL can be known with the command
ifconfigon the OpenDaylight VM.Question: Is the connection successful?
If the connection between ODL and mininet is successful, the mininet terminal shows:
*** Creating network *** Adding controller *** Adding hosts: ...Otherwise, there will be
Unable to connect the remote controller at $IP_ODLafter*** Adding controllerHow to debug?(2) Check Listening Ports. Open another terminal
sudo lsof -i -P -n | grep LISTENQuestion: What do you observe?
(3) Install OpenFlow Plugins in OpenDaylight terminal
opendaylight-user@root>:feature:install odl-openflowplugin-app-topology-lldp-discovery odl-openflowplugin-app-table-miss-enforcer odl-openflowplugin-flow-services odl-openflowplugin-flow-services-rest odl-openflowplugin-app-topology-manager odl-openflowplugin-app-lldp-speaker(4) Check Listening Ports again.
sudo lsof -i -P -n | grep LISTENNOTE: If
tcp *:6653 (LISTEN)andtcp *:8181 (LISTEN)do not show, shut down OpenDaylight withControl+Dand restartsudo ./karaf(5) Re-run Mininet:
sudo mn --custom ~/custom_mn/topo-2sw-2host.py --topo mytopo --switch ovsk,protocols=OpenFlow13 --controller remote,ip=127.0.0.1,port=6653Question: Is the connection successful this time?
-
Capture OpenFlow messages
sudo wiresharkQuestion: Which interface do we monitor?
-
Read network statistics from the northbound API of OpenDaylight
(1) Create
datafolder. In a terminal,mkdir data(2) Request nodes (switches)
Refer to
req_nodes.shRead nodes file:
sudo vim data/nodes.shIn vim, press
Ctrl+:, then type%!jq .for better json file reading.(3) Request topology
Refer to
odl/req_topo.shRead topology file
-
Config Data Store & Nonconfig Data Store
(1) Request the data store of a switch
Refer to
odl/req_flows.sh, we will need to figure out what to put as a variable following./req_flows.sh.Question: What value do we put as the variable?
Read the
flows.jsonfile, keep in mind what you see.(2) Request the nonconfig data store of a switch
Refer to
odl/req_nonconfig_flows.shRead the
nonconfig_flows.jsonfile, keep in mind what you see.(3) Request the config data store of the same switch
Refer to
odl/req_config_flows.shRead the
config_flows.jsonfile, keep in mind what you see.Question: Why?
(4) Configure a flow entry on the mininet end, repeat (1)(2)(3) steps, reason about the config data store & nonconfig data store design of OpenDaylight.