blob: 0f74d561c8201e3dcadf296db5715fd2c670aedc [file] [log] [blame]
Dan Talayco942f5302012-04-12 22:32:34 -07001"""
2Prototype test cases related to operation under load
3
4It is recommended that these definitions be kept in their own
5namespace as different groups of tests will likely define
6similar identifiers.
7
Rich Lane477f4812012-10-04 22:49:00 -07008The switch is actively attempting to contact the controller at the address
9indicated in config.
Dan Talayco942f5302012-04-12 22:32:34 -070010
11In general these test cases make some assumption about the external
12configuration of the switch under test. For now, the assumption is
13that the first two OF ports are connected by a loopback cable.
14"""
15
16import copy
17
18import logging
19
20import unittest
21
Rich Lane477f4812012-10-04 22:49:00 -070022from oftest import config
Dan Talayco942f5302012-04-12 22:32:34 -070023import oftest.controller as controller
24import oftest.cstruct as ofp
25import oftest.message as message
26import oftest.dataplane as dataplane
27import oftest.action as action
28import oftest.parse as parse
Rich Laneb90a1c42012-10-05 09:16:05 -070029import oftest.base_tests as base_tests
Dan Talayco942f5302012-04-12 22:32:34 -070030import time
31
Rich Laneda3b5ad2012-10-03 09:05:32 -070032from oftest.testutils import *
Dan Talayco942f5302012-04-12 22:32:34 -070033
Rich Laneb90a1c42012-10-05 09:16:05 -070034class LoadBarrier(base_tests.SimpleProtocol):
Dan Talayco942f5302012-04-12 22:32:34 -070035 """
36 Test barrier under load with loopback
37
38 This test assumes there is a pair of ports on the switch with
39 a loopback cable connected and that spanning tree is disabled.
40 A flow is installed to cause a storm of packet-in messages
41 when a packet is sent to the loopbacked interface. After causing
42 this storm, a barrier request is sent.
43
44 The test succeeds if the barrier response is received. Otherwise
45 the test fails.
46 """
Rich Laned1d9c282012-10-04 22:07:10 -070047
48 priority = -1
49
Dan Talayco942f5302012-04-12 22:32:34 -070050 def runTest(self):
51 # Set up flow to send from port 1 to port 2 and copy to CPU
52 # Test parameter gives LB port base (assumes consecutive)
Rich Lane2014f9b2012-10-05 15:29:40 -070053 lb_port = test_param_get('lb_port', default=1)
54 barrier_count = test_param_get('barrier_count',
Dan Talayco942f5302012-04-12 22:32:34 -070055 default=10)
56
57 # Set controller to filter packet ins
58 self.controller.filter_packet_in = True
59 self.controller.pkt_in_filter_limit = 10
60
61 pkt = simple_tcp_packet()
Ed Swierk99a74de2012-08-22 06:40:54 -070062 match = packet_to_flow_match(self, pkt)
Dan Talayco942f5302012-04-12 22:32:34 -070063 match.wildcards &= ~ofp.OFPFW_IN_PORT
64 match.in_port = lb_port
65 act = action.action_output()
66 act.port = lb_port + 1
67
68 request = message.flow_mod()
69 request.match = match
70 request.hard_timeout = 2 * barrier_count
71
72 request.buffer_id = 0xffffffff
73 self.assertTrue(request.actions.add(act), "Could not add action")
74
75 act = action.action_output()
76 act.port = ofp.OFPP_CONTROLLER
77 self.assertTrue(request.actions.add(act), "Could not add action")
78
79 rv = self.controller.message_send(request)
80 self.assertTrue(rv != -1, "Error installing flow mod")
81 self.assertEqual(do_barrier(self.controller), 0, "Barrier failed")
82
83 # Create packet out and send to port lb_port + 1
84 msg = message.packet_out()
85 msg.data = str(pkt)
86 act = action.action_output()
87 act.port = lb_port + 1
88 self.assertTrue(msg.actions.add(act), 'Could not add action to msg')
Rich Lane9a003812012-10-04 17:17:59 -070089 logging.info("Sleeping before starting storm")
Dan Talayco942f5302012-04-12 22:32:34 -070090 time.sleep(1) # Root causing issue with fast disconnects
Rich Lane9a003812012-10-04 17:17:59 -070091 logging.info("Sending packet out to %d" % (lb_port + 1))
Dan Talayco942f5302012-04-12 22:32:34 -070092 rv = self.controller.message_send(msg)
93 self.assertTrue(rv == 0, "Error sending out message")
94
95 for idx in range(0, barrier_count):
96 self.assertEqual(do_barrier(self.controller), 0, "Barrier failed")
97 # To do: Add some interesting functionality here
Rich Lane9a003812012-10-04 17:17:59 -070098 logging.info("Barrier %d completed" % idx)
Dan Talayco942f5302012-04-12 22:32:34 -070099
100 # Clear the flow table when done
Rich Lane9a003812012-10-04 17:17:59 -0700101 logging.debug("Deleting all flows from switch")
102 rc = delete_all_flows(self.controller)
Dan Talayco942f5302012-04-12 22:32:34 -0700103 self.assertEqual(rc, 0, "Failed to delete all flows")
Dan Talaycod0832852012-10-10 09:49:53 -0700104
105class PacketInLoad(base_tests.SimpleDataPlane):
106 """
107 Generate lots of packet-in messages
108
109 Test packet-in function by sending lots of packets to the dataplane.
110 This test tracks the number of pkt-ins received but does not enforce
111 any requirements about the number received.
112 """
113 def runTest(self):
114 # Construct packet to send to dataplane
115 # Send packet to dataplane, once to each port
116 # Poll controller with expect message type packet in
117
118 rc = delete_all_flows(self.controller)
119 self.assertEqual(rc, 0, "Failed to delete all flows")
120 self.assertEqual(do_barrier(self.controller), 0, "Barrier failed")
121 out_count = 0
122 in_count = 0
123
124 of_ports = config["port_map"].keys()
125 for of_port in of_ports:
126 for pkt, pt in [
127 (simple_tcp_packet(), "simple TCP packet"),
128 (simple_tcp_packet(dl_vlan_enable=True,pktlen=108),
129 "simple tagged TCP packet"),
130 (simple_eth_packet(), "simple Ethernet packet"),
131 (simple_eth_packet(pktlen=40), "tiny Ethernet packet")]:
132
133 logging.info("PKT IN test with %s, port %s" % (pt, of_port))
134 for count in range(100):
135 out_count += 1
136 self.dataplane.send(of_port, str(pkt))
137 time.sleep(2)
138 while True:
139 (response, raw) = self.controller.poll(ofp.OFPT_PACKET_IN,
140 timeout=0)
141 if not response:
142 break
143 in_count += 1
144 logging.info("PacketInLoad Sent %d. Got %d." % (out_count, in_count))
145
146
147
148class PacketOutLoad(base_tests.SimpleDataPlane):
149 """
150 Generate lots of packet-out messages
151
152 Test packet-out function by sending lots of packet-out msgs
153 to the switch. This test tracks the number of packets received in
154 the dataplane, but does not enforce any requirements about the
155 number received.
156 """
157 def runTest(self):
158 # Construct packet to send to dataplane
159 # Send packet to dataplane
160 # Poll controller with expect message type packet in
161
162 rc = delete_all_flows(self.controller)
163 self.assertEqual(rc, 0, "Failed to delete all flows")
164
165 # These will get put into function
166 of_ports = config["port_map"].keys()
167 of_ports.sort()
168 out_count = 0
169 in_count = 0
170 xid = 100
171 for dp_port in of_ports:
172 for outpkt, opt in [
173 (simple_tcp_packet(), "simple TCP packet"),
174 (simple_eth_packet(), "simple Ethernet packet"),
175 (simple_eth_packet(pktlen=40), "tiny Ethernet packet")]:
176
177 logging.info("PKT OUT test with %s, port %s" % (opt, dp_port))
178 msg = message.packet_out()
179 msg.data = str(outpkt)
180 act = action.action_output()
181 act.port = dp_port
182 self.assertTrue(msg.actions.add(act), 'Could not add action to msg')
183
184 logging.info("PacketOutLoad to: " + str(dp_port))
185 for count in range(100):
186 msg.xid = xid
187 xid += 1
188 rv = self.controller.message_send(msg)
189 self.assertTrue(rv == 0, "Error sending out message")
190 out_count += 1
191
192 exp_pkt_arg = None
193 exp_port = None
194 time.sleep(2)
195 while True:
196 (of_port, pkt, pkt_time) = self.dataplane.poll(timeout=0)
197 if pkt is None:
198 break
199 in_count += 1
200 logging.info("PacketOutLoad Sent %d. Got %d." % (out_count, in_count))