blob: 4138111d26f45cf5b2b039d8c9f2c40a12013e94 [file] [log] [blame]
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -07001package org.onlab.onos.provider.of.host.impl;
2
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -07003import org.junit.After;
4import org.junit.Before;
5import org.junit.Test;
6import org.onlab.onos.net.ConnectPoint;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -07007import org.onlab.onos.net.HostId;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -07008import org.onlab.onos.net.host.HostDescription;
9import org.onlab.onos.net.host.HostProvider;
10import org.onlab.onos.net.host.HostProviderRegistry;
11import org.onlab.onos.net.host.HostProviderService;
12import org.onlab.onos.net.provider.AbstractProviderService;
13import org.onlab.onos.net.provider.ProviderId;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070014import org.onlab.onos.net.topology.Topology;
tom61359e92014-09-16 15:50:27 -070015import org.onlab.onos.net.topology.TopologyServiceAdapter;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070016import org.onlab.onos.of.controller.Dpid;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070017import org.onlab.onos.of.controller.OpenFlowPacketContext;
tom61359e92014-09-16 15:50:27 -070018import org.onlab.onos.of.controller.OpenflowControllerAdapter;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070019import org.onlab.onos.of.controller.PacketListener;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070020import org.onlab.packet.ARP;
21import org.onlab.packet.Ethernet;
Ayaka Koshibea9c199f2014-09-16 16:21:40 -070022import org.onlab.packet.MacAddress;
23import org.onlab.packet.VlanId;
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070024import org.projectfloodlight.openflow.protocol.OFMessage;
25import org.projectfloodlight.openflow.types.OFPort;
26
tom61359e92014-09-16 15:50:27 -070027import java.util.Set;
28
29import static org.junit.Assert.*;
30
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070031public class OpenFlowHostProviderTest {
32
33 private static final Integer INPORT = 10;
34 private static final Dpid DPID1 = new Dpid(100);
35 private static final Dpid DPID2 = new Dpid(200);
36 private static final Dpid DPID3 = new Dpid(300);
37
Ayaka Koshibea9c199f2014-09-16 16:21:40 -070038 private static final VlanId VLAN = VlanId.vlanId();
39 private static final MacAddress MAC = MacAddress.valueOf("00:00:11:00:00:01");
40 private static final MacAddress BCMAC = MacAddress.valueOf("ff:ff:ff:ff:ff:ff");
tom43526fc2014-09-16 15:12:22 -070041 private static final byte[] IP = new byte[]{10, 0, 0, 1};
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -070042
43 private OpenFlowHostProvider provider = new OpenFlowHostProvider();
44 private TestHostRegistry hostService = new TestHostRegistry();
45 private TestController controller = new TestController();
46 private TestTopologyService topoService = new TestTopologyService();
47 private TestHostProviderService providerService;
48
49 @Before
50 public void setUp() {
51 provider.providerRegistry = hostService;
52 provider.controller = controller;
53 provider.topologyService = topoService;
54 provider.activate();
55 }
56
57 @Test
58 public void basics() {
59 assertNotNull("registration expected", providerService);
60 assertEquals("incorrect provider", provider, providerService.provider());
61 }
62
63 @Test
64 public void events() {
65 // new host
66 controller.processPacket(DPID1, null);
67 assertNotNull("new host expected", providerService.added);
68 assertNull("host motion unexpected", providerService.moved);
69
70 // the host moved to new switch
71 controller.processPacket(DPID2, null);
72 assertNotNull("host motion expected", providerService.moved);
73
74 // the host was misheard on a spine
75 controller.processPacket(DPID3, null);
76 assertNull("host misheard on spine switch", providerService.spine);
77 }
78
79 @After
80 public void tearDown() {
81 provider.deactivate();
82 provider.providerRegistry = null;
83 provider.controller = null;
84 }
85
86 private class TestHostRegistry implements HostProviderRegistry {
87
88 @Override
89 public HostProviderService register(HostProvider provider) {
90 providerService = new TestHostProviderService(provider);
91 return providerService;
92 }
93
94 @Override
95 public void unregister(HostProvider provider) {
96 }
97
98 @Override
99 public Set<ProviderId> getProviders() {
100 return null;
101 }
102
103 }
104
105 private class TestHostProviderService
106 extends AbstractProviderService<HostProvider>
107 implements HostProviderService {
108
109 Dpid added = null;
110 Dpid moved = null;
111 Dpid spine = null;
112
113 protected TestHostProviderService(HostProvider provider) {
114 super(provider);
115 }
116
117 @Override
118 public void hostDetected(HostId hostId, HostDescription hostDescription) {
119 Dpid descr = Dpid.dpid(hostDescription.location().deviceId().uri());
120 if (added == null) {
121 added = descr;
122 } else if ((moved == null) && !descr.equals(added)) {
123 moved = descr;
124 } else {
125 spine = descr;
126 }
127 }
128
129 @Override
130 public void hostVanished(HostId hostId) {
131 }
132
133 }
134
tom61359e92014-09-16 15:50:27 -0700135 private class TestController extends OpenflowControllerAdapter {
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700136 PacketListener pktListener;
137
138 @Override
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700139 public void addPacketListener(int priority, PacketListener listener) {
140 pktListener = listener;
141 }
142
143 @Override
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700144 public void processPacket(Dpid dpid, OFMessage msg) {
tom61359e92014-09-16 15:50:27 -0700145 OpenFlowPacketContext ctx = new TestPacketContext(dpid);
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700146 pktListener.handlePacket(ctx);
147 }
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700148 }
149
tom61359e92014-09-16 15:50:27 -0700150 private class TestTopologyService extends TopologyServiceAdapter {
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700151 @Override
152 public boolean isInfrastructure(Topology topology,
tom43526fc2014-09-16 15:12:22 -0700153 ConnectPoint connectPoint) {
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700154 //simulate DPID3 as an infrastructure switch
155 if (Dpid.dpid(connectPoint.deviceId().uri()).equals(DPID3)) {
156 return true;
157 }
158 return false;
159 }
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700160 }
161
162 private class TestPacketContext implements OpenFlowPacketContext {
163
164 protected Dpid swid;
165
166 public TestPacketContext(Dpid dpid) {
167 swid = dpid;
168 }
169
170 @Override
171 public boolean blocked() {
172 return false;
173 }
174
175 @Override
176 public void send() {
177 }
178
179 @Override
180 public void build(OFPort outPort) {
181 }
182
183 @Override
184 public void build(Ethernet ethFrame, OFPort outPort) {
185 }
186
187 @Override
188 public Ethernet parsed() {
189 // just things we (and serializers) need
190 ARP arp = new ARP();
191 arp.setSenderProtocolAddress(IP)
tom43526fc2014-09-16 15:12:22 -0700192 .setSenderHardwareAddress(MAC.toBytes())
193 .setTargetHardwareAddress(BCMAC.toBytes())
194 .setTargetProtocolAddress(IP);
Ayaka Koshibecc4c4c82014-09-16 11:23:37 -0700195
196 Ethernet eth = new Ethernet();
197 eth.setEtherType(Ethernet.TYPE_ARP)
198 .setVlanID(VLAN.toShort())
199 .setSourceMACAddress(MAC.toBytes())
200 .setDestinationMACAddress(BCMAC.getAddress())
201 .setPayload(arp);
202
203 return eth;
204 }
205
206 @Override
207 public byte[] unparsed() {
208 return null;
209 }
210
211 @Override
212 public Dpid dpid() {
213 return swid;
214 }
215
216 @Override
217 public Integer inPort() {
218 return INPORT;
219 }
220
221 }
222}