blob: 24d5f58302e2ff871f5675b2e3e6f20a72f548fd [file] [log] [blame]
sanghoshin94872a12015-10-16 18:04:34 +09001/*
2 * Copyright 2015 Open Networking Laboratory
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16package org.onosproject.openstackswitching;
17
sanghoshin46297d22015-11-03 17:51:24 +090018import com.google.common.collect.ImmutableSet;
sanghoshin94872a12015-10-16 18:04:34 +090019import com.google.common.collect.Lists;
sanghoshin94872a12015-10-16 18:04:34 +090020import org.apache.felix.scr.annotations.Activate;
21import org.apache.felix.scr.annotations.Component;
22import org.apache.felix.scr.annotations.Deactivate;
23import org.apache.felix.scr.annotations.Reference;
24import org.apache.felix.scr.annotations.ReferenceCardinality;
25import org.apache.felix.scr.annotations.Service;
26import org.onlab.packet.Ethernet;
sanghoshin94872a12015-10-16 18:04:34 +090027import org.onlab.packet.Ip4Address;
sanghoshin65723ae2015-11-17 22:07:21 +090028import org.onlab.packet.IpAddress;
sanghoshin94872a12015-10-16 18:04:34 +090029import org.onosproject.core.ApplicationId;
30import org.onosproject.core.CoreService;
danielbb83ebc2015-10-29 15:13:06 +090031import org.onosproject.dhcp.DhcpService;
sanghoshin65723ae2015-11-17 22:07:21 +090032import org.onosproject.event.AbstractEvent;
sanghoshin94872a12015-10-16 18:04:34 +090033import org.onosproject.net.Device;
34import org.onosproject.net.DeviceId;
sanghoshin65723ae2015-11-17 22:07:21 +090035import org.onosproject.net.Host;
sanghoshin94872a12015-10-16 18:04:34 +090036import org.onosproject.net.Port;
sanghoshin46297d22015-11-03 17:51:24 +090037import org.onosproject.net.config.ConfigFactory;
38import org.onosproject.net.config.NetworkConfigEvent;
39import org.onosproject.net.config.NetworkConfigListener;
40import org.onosproject.net.config.NetworkConfigRegistry;
sanghoshin94872a12015-10-16 18:04:34 +090041import org.onosproject.net.device.DeviceEvent;
42import org.onosproject.net.device.DeviceListener;
43import org.onosproject.net.device.DeviceService;
sanghoshinf25d2e02015-11-11 23:07:17 +090044import org.onosproject.net.driver.DriverService;
sanghoshin65723ae2015-11-17 22:07:21 +090045import org.onosproject.net.flow.FlowEntry;
46import org.onosproject.net.flow.FlowRuleService;
47import org.onosproject.net.flow.criteria.Criterion;
48import org.onosproject.net.flow.criteria.IPCriterion;
49import org.onosproject.net.flow.instructions.Instruction;
50import org.onosproject.net.flow.instructions.L2ModificationInstruction;
sanghoshin94872a12015-10-16 18:04:34 +090051import org.onosproject.net.flowobjective.FlowObjectiveService;
sanghoshin65723ae2015-11-17 22:07:21 +090052import org.onosproject.net.host.HostEvent;
53import org.onosproject.net.host.HostListener;
54import org.onosproject.net.host.HostService;
sanghoshin94872a12015-10-16 18:04:34 +090055import org.onosproject.net.packet.InboundPacket;
56import org.onosproject.net.packet.PacketContext;
57import org.onosproject.net.packet.PacketProcessor;
58import org.onosproject.net.packet.PacketService;
59import org.slf4j.Logger;
60import org.slf4j.LoggerFactory;
sanghoshin94872a12015-10-16 18:04:34 +090061import java.util.List;
sanghoshin46297d22015-11-03 17:51:24 +090062import java.util.Collection;
sanghoshin65723ae2015-11-17 22:07:21 +090063import java.util.NoSuchElementException;
sanghoshin46297d22015-11-03 17:51:24 +090064import java.util.Set;
sanghoshin94872a12015-10-16 18:04:34 +090065import java.util.concurrent.ExecutorService;
66import java.util.concurrent.Executors;
sanghoshin46297d22015-11-03 17:51:24 +090067import java.util.stream.Collectors;
68
69import static org.onosproject.net.config.basics.SubjectFactories.APP_SUBJECT_FACTORY;
sanghoshinf6735b22015-12-17 18:23:53 +090070import static org.onlab.util.Tools.groupedThreads;
sanghoshin94872a12015-10-16 18:04:34 +090071
72@SuppressWarnings("ALL")
73@Service
74@Component(immediate = true)
75/**
sanghoshin46297d22015-11-03 17:51:24 +090076 * Populates forwarding rules for VMs created by Openstack.
sanghoshin94872a12015-10-16 18:04:34 +090077 */
78public class OpenstackSwitchingManager implements OpenstackSwitchingService {
79
80 private static Logger log = LoggerFactory
81 .getLogger(OpenstackSwitchingManager.class);
82
83 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
84 protected CoreService coreService;
85
86 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
87 protected PacketService packetService;
88
89 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
90 protected DeviceService deviceService;
91
92 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshin65723ae2015-11-17 22:07:21 +090093 protected HostService hostService;
94
95 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshin94872a12015-10-16 18:04:34 +090096 protected FlowObjectiveService flowObjectiveService;
97
danielbb83ebc2015-10-29 15:13:06 +090098 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshinf25d2e02015-11-11 23:07:17 +090099 protected DhcpService dhcpService;
100
101 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshin46297d22015-11-03 17:51:24 +0900102 protected NetworkConfigRegistry cfgService;
103
104 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshinf25d2e02015-11-11 23:07:17 +0900105 protected DriverService driverService;
sanghoshin94872a12015-10-16 18:04:34 +0900106
sanghoshinf6735b22015-12-17 18:23:53 +0900107 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
sanghoshin65723ae2015-11-17 22:07:21 +0900108 protected FlowRuleService flowRuleService;
109
sanghoshin94872a12015-10-16 18:04:34 +0900110 private ApplicationId appId;
sanghoshin46297d22015-11-03 17:51:24 +0900111 private boolean doNotPushFlows;
sanghoshinf25d2e02015-11-11 23:07:17 +0900112 private Ip4Address neutronServer;
113 private Ip4Address keystoneServer;
114 private String userName;
115 private String password;
sanghoshin94872a12015-10-16 18:04:34 +0900116 private OpenstackArpHandler arpHandler;
sanghoshinf25d2e02015-11-11 23:07:17 +0900117 private OpenstackRestHandler restHandler;
danielbb83ebc2015-10-29 15:13:06 +0900118
sanghoshinf6735b22015-12-17 18:23:53 +0900119 private ExecutorService deviceEventExcutorService =
120 Executors.newSingleThreadExecutor(groupedThreads("onos/openstackswitching", "device-event"));
121 private ExecutorService networkEventExcutorService =
122 Executors.newSingleThreadExecutor(groupedThreads("onos/openstackswitching", "config-event"));
sanghoshin94872a12015-10-16 18:04:34 +0900123
124 private InternalPacketProcessor internalPacketProcessor = new InternalPacketProcessor();
125 private InternalDeviceListener internalDeviceListener = new InternalDeviceListener();
sanghoshin46297d22015-11-03 17:51:24 +0900126 private InternalConfigListener internalConfigListener = new InternalConfigListener();
sanghoshin65723ae2015-11-17 22:07:21 +0900127 private InternalHostListener internalHostListener = new InternalHostListener();
sanghoshin46297d22015-11-03 17:51:24 +0900128 private final Set<ConfigFactory> factories = ImmutableSet.of(
129 new ConfigFactory<ApplicationId, OpenstackSwitchingConfig>(APP_SUBJECT_FACTORY,
130 OpenstackSwitchingConfig.class,
131 "openstackswitching") {
132 @Override
133 public OpenstackSwitchingConfig createConfig() {
134 return new OpenstackSwitchingConfig();
135 }
136 }
137 );
sanghoshin94872a12015-10-16 18:04:34 +0900138
139 @Activate
140 protected void activate() {
141 appId = coreService
142 .registerApplication("org.onosproject.openstackswitching");
sanghoshinf25d2e02015-11-11 23:07:17 +0900143
144 factories.forEach(cfgService::registerConfigFactory);
sanghoshin94872a12015-10-16 18:04:34 +0900145 packetService.addProcessor(internalPacketProcessor, PacketProcessor.director(1));
146 deviceService.addListener(internalDeviceListener);
sanghoshin65723ae2015-11-17 22:07:21 +0900147 hostService.addListener(internalHostListener);
sanghoshin46297d22015-11-03 17:51:24 +0900148 cfgService.addListener(internalConfigListener);
danielbb83ebc2015-10-29 15:13:06 +0900149
sanghoshinf25d2e02015-11-11 23:07:17 +0900150 internalConfigListener.configureNetwork();
sanghoshin46297d22015-11-03 17:51:24 +0900151
sanghoshin94872a12015-10-16 18:04:34 +0900152 log.info("Started");
153 }
154
155 @Deactivate
156 protected void deactivate() {
157 packetService.removeProcessor(internalPacketProcessor);
158 deviceService.removeListener(internalDeviceListener);
sanghoshin46297d22015-11-03 17:51:24 +0900159 cfgService.removeListener(internalConfigListener);
sanghoshin65723ae2015-11-17 22:07:21 +0900160 factories.forEach(cfgService::unregisterConfigFactory);
sanghoshin94872a12015-10-16 18:04:34 +0900161
162 deviceEventExcutorService.shutdown();
163
164 log.info("Stopped");
165 }
166
167 @Override
168 public void createPorts(OpenstackPort openstackPort) {
sanghof2ca7e5c2015-12-23 16:02:43 +0900169 if (!openstackPort.fixedIps().isEmpty()) {
170 registerDhcpInfo(openstackPort);
171 }
sanghoshin94872a12015-10-16 18:04:34 +0900172 }
173
174 @Override
sanghoshin65723ae2015-11-17 22:07:21 +0900175 public void deletePort(String uuid) {
sanghoshin94872a12015-10-16 18:04:34 +0900176
177 }
178
179 @Override
sanghoshin65723ae2015-11-17 22:07:21 +0900180 public void updatePort(OpenstackPort openstackPort) {
sanghoshin94872a12015-10-16 18:04:34 +0900181 }
182
183 @Override
184 public void createNetwork(OpenstackNetwork openstackNetwork) {
sanghoshin94872a12015-10-16 18:04:34 +0900185 }
186
danielbb83ebc2015-10-29 15:13:06 +0900187 @Override
188 public void createSubnet(OpenstackSubnet openstackSubnet) {
danielbb83ebc2015-10-29 15:13:06 +0900189 }
190
sanghoshin46297d22015-11-03 17:51:24 +0900191 @Override
192 public Collection<OpenstackPort> ports(String networkId) {
sanghoshinf25d2e02015-11-11 23:07:17 +0900193 Collection<OpenstackPort> ports = restHandler.getPorts();
194 List<OpenstackPort> portList = ports.stream()
sanghoshin46297d22015-11-03 17:51:24 +0900195 .filter(p -> p.networkId().equals(networkId))
196 .collect(Collectors.toList());
197
198 return portList;
199 }
200
201 @Override
sanghoshinf25d2e02015-11-11 23:07:17 +0900202 public OpenstackPort port(Port port) {
203 Collection<OpenstackPort> ports = restHandler.getPorts();
204 String uuid = port.annotations().value("portName").substring(3);
205 return ports.stream()
sanghoshin46297d22015-11-03 17:51:24 +0900206 .filter(p -> p.id().startsWith(uuid))
sanghoshinf25d2e02015-11-11 23:07:17 +0900207 .findFirst().orElse(null);
208 }
209
210 @Override
211 public OpenstackPort port(String portId) {
212 Collection<OpenstackPort> ports = restHandler.getPorts();
213 return ports.stream()
214 .filter(p -> p.id().equals(portId))
215 .findFirst().orElse(null);
sanghoshin46297d22015-11-03 17:51:24 +0900216 }
217
218 @Override
219 public OpenstackNetwork network(String networkId) {
sanghoshinf4ffb942015-12-10 11:28:24 +0900220 try {
221 Collection<OpenstackSubnet> subnets = restHandler.getSubnets().stream()
222 .filter(s -> s.networkId().equals(networkId))
223 .collect(Collectors.toList());
224
225 Collection<OpenstackNetwork> networks = restHandler.getNetworks();
226 OpenstackNetwork openstackNetwork = networks.stream()
227 .filter(n -> n.id().equals(networkId))
228 .findFirst().get();
229
230 return OpenstackNetwork.builder()
231 .id(openstackNetwork.id())
232 .name(openstackNetwork.name())
233 .networkType(openstackNetwork.networkType())
234 .segmentId(openstackNetwork.segmentId())
235 .tenantId(openstackNetwork.tenantId())
236 .subnets(subnets)
237 .build();
238 } catch (NoSuchElementException e) {
239 log.warn("There is no network infor for net ID {}", networkId);
240 return null;
241 }
242 }
243
244 @Override
245 public OpenstackSubnet subnet(String subnetId) {
246 Collection<OpenstackSubnet> subnets = restHandler.getSubnets();
247 try {
248 return subnets.stream()
249 .filter(s -> s.id().equals(subnetId))
250 .findFirst().get();
251 } catch (NoSuchElementException e) {
252 log.warn("There is no subnet info for subnet ID {}", subnetId);
253 return null;
254 }
sanghoshin46297d22015-11-03 17:51:24 +0900255 }
256
sanghoshin94872a12015-10-16 18:04:34 +0900257 private void processDeviceAdded(Device device) {
danielbb83ebc2015-10-29 15:13:06 +0900258 log.debug("device {} is added", device.id());
sanghoshin94872a12015-10-16 18:04:34 +0900259 }
260
261 private void processPortAdded(Device device, Port port) {
sanghoshin65723ae2015-11-17 22:07:21 +0900262 if (!port.annotations().value("portName").equals("vxlan")
263 && port.isEnabled() && !doNotPushFlows) {
sanghoshinf25d2e02015-11-11 23:07:17 +0900264 OpenstackSwitchingRulePopulator rulePopulator =
265 new OpenstackSwitchingRulePopulator(appId, flowObjectiveService,
266 deviceService, restHandler, driverService);
267 rulePopulator.populateSwitchingRules(device, port);
sanghoshin94872a12015-10-16 18:04:34 +0900268 }
269 }
270
271 private void processPortRemoved(Device device, Port port) {
danielbb83ebc2015-10-29 15:13:06 +0900272 log.debug("port {} is removed", port.toString());
sanghoshin94872a12015-10-16 18:04:34 +0900273 }
274
sanghoshin075e3e72015-11-25 16:34:29 +0900275 private void initializeFlowRules() {
276 OpenstackSwitchingRulePopulator rulePopulator =
277 new OpenstackSwitchingRulePopulator(appId, flowObjectiveService,
278 deviceService, restHandler, driverService);
279
280 deviceService.getDevices().forEach(device -> {
281 log.debug("device {} num of ports {} ", device.id(),
282 deviceService.getPorts(device.id()).size());
283 deviceService.getPorts(device.id()).stream()
284 .filter(port -> port.annotations().value("portName").startsWith("tap"))
285 .forEach(vmPort -> {
286 OpenstackPort osPort = rulePopulator.openstackPort(vmPort);
287 if (osPort != null) {
Hyunsun Moonbe5c24c2015-12-10 22:26:35 -0800288 if (!doNotPushFlows) {
289 rulePopulator.populateSwitchingRules(device, vmPort);
290 }
sanghoshin075e3e72015-11-25 16:34:29 +0900291 registerDhcpInfo(osPort);
292 } else {
293 log.warn("No openstackPort information for port {}", vmPort);
294 }
295 }
296 );
297 }
298 );
299 }
300
sanghoshin65723ae2015-11-17 22:07:21 +0900301 private void processHostRemoved(Host host) {
302 log.debug("host {} was removed", host.toString());
303
304 try {
305 if (!doNotPushFlows) {
306 IpAddress hostIp = host.ipAddresses().stream().
307 filter(ip -> ip.isIp4()).findAny().orElse(null);
308 OpenstackSwitchingRulePopulator rulePopulator =
309 new OpenstackSwitchingRulePopulator(appId, flowObjectiveService,
310 deviceService, restHandler, driverService);
311 rulePopulator.removeSwitchingRules(host.location().deviceId(),
312 hostIp.getIp4Address());
313 }
314
315 dhcpService.removeStaticMapping(host.mac());
316 } catch (NoSuchElementException e) {
317 log.error("No IP address is assigned.");
318 }
319 }
320
321 private long getVniFromFlowRules(DeviceId deviceId, Ip4Address hostIp) {
322
323 for (FlowEntry flowEntry: flowRuleService.getFlowEntries(deviceId)) {
324 Criterion c = flowEntry.selector().getCriterion(Criterion.Type.IPV4_DST);
325 if (c != null) {
326 IPCriterion destIpCriterion = (IPCriterion) c;
327 if (destIpCriterion.ip().getIp4Prefix().address().equals(hostIp)) {
328 for (Instruction i : flowEntry.treatment().immediate()) {
329 if (i.type().equals(Instruction.Type.L2MODIFICATION)) {
330 L2ModificationInstruction l2m = (L2ModificationInstruction) i;
331 if (l2m.subtype().equals(L2ModificationInstruction.L2SubType.TUNNEL_ID)) {
332 L2ModificationInstruction.ModTunnelIdInstruction setTunnelInstr =
333 (L2ModificationInstruction.ModTunnelIdInstruction) l2m;
334 return setTunnelInstr.tunnelId();
335 }
336 }
337 }
338 }
339 }
340 }
341
342 return 0;
343 }
344
sanghoshin46297d22015-11-03 17:51:24 +0900345 private void registerDhcpInfo(OpenstackPort openstackPort) {
346 Ip4Address ip4Address;
347 Ip4Address subnetMask;
348 Ip4Address dhcpServer;
349 Ip4Address gatewayIPAddress;
350 Ip4Address domainServer;
351 OpenstackSubnet openstackSubnet;
352
353 ip4Address = (Ip4Address) openstackPort.fixedIps().values().toArray()[0];
354
sanghoshinf25d2e02015-11-11 23:07:17 +0900355 openstackSubnet = restHandler.getSubnets().stream()
sanghoshin46297d22015-11-03 17:51:24 +0900356 .filter(n -> n.networkId().equals(openstackPort.networkId()))
357 .findFirst().get();
358
359 subnetMask = Ip4Address.valueOf(buildSubnetMask(openstackSubnet.cidr()));
360 gatewayIPAddress = Ip4Address.valueOf(openstackSubnet.gatewayIp());
361 dhcpServer = gatewayIPAddress;
362 // TODO: supports multiple DNS servers
363 if (openstackSubnet.dnsNameservers().isEmpty()) {
364 domainServer = Ip4Address.valueOf("8.8.8.8");
365 } else {
366 domainServer = openstackSubnet.dnsNameservers().get(0);
367 }
368 List<Ip4Address> options = Lists.newArrayList();
369 options.add(subnetMask);
370 options.add(dhcpServer);
371 options.add(gatewayIPAddress);
372 options.add(domainServer);
373
374 dhcpService.setStaticMapping(openstackPort.macAddress(), ip4Address, true, options);
375 }
376
377 private byte[] buildSubnetMask(String cidr) {
378 int prefix;
379 String[] parts = cidr.split("/");
380 prefix = Integer.parseInt(parts[1]);
381 int mask = 0xffffffff << (32 - prefix);
382 byte[] bytes = new byte[]{(byte) (mask >>> 24),
383 (byte) (mask >> 16 & 0xff), (byte) (mask >> 8 & 0xff), (byte) (mask & 0xff)};
384
385 return bytes;
386 }
387
sanghoshin94872a12015-10-16 18:04:34 +0900388
sanghoshin94872a12015-10-16 18:04:34 +0900389
390 private class InternalPacketProcessor implements PacketProcessor {
391
392 @Override
393 public void process(PacketContext context) {
394
395 if (context.isHandled()) {
396 return;
397 }
398
399 InboundPacket pkt = context.inPacket();
400 Ethernet ethernet = pkt.parsed();
401
Hyunsun Moonc98e7c52016-01-11 02:54:27 -0800402 if (ethernet != null && ethernet.getEtherType() == Ethernet.TYPE_ARP) {
sanghoshin94872a12015-10-16 18:04:34 +0900403 arpHandler.processPacketIn(pkt);
sanghoshin94872a12015-10-16 18:04:34 +0900404 }
405 }
406 }
407
sanghoshin65723ae2015-11-17 22:07:21 +0900408 private class InternalHostListener implements HostListener {
409
410 @Override
411 public void event(HostEvent hostEvent) {
412 deviceEventExcutorService.execute(new InternalEventHandler(hostEvent));
413 }
414 }
415
sanghoshin94872a12015-10-16 18:04:34 +0900416 private class InternalDeviceListener implements DeviceListener {
417
418 @Override
sanghoshin46297d22015-11-03 17:51:24 +0900419 public void event(DeviceEvent deviceEvent) {
420 deviceEventExcutorService.execute(new InternalEventHandler(deviceEvent));
sanghoshin94872a12015-10-16 18:04:34 +0900421 }
422 }
423
424 private class InternalEventHandler implements Runnable {
425
sanghoshin65723ae2015-11-17 22:07:21 +0900426 volatile AbstractEvent event;
sanghoshin94872a12015-10-16 18:04:34 +0900427
sanghoshin65723ae2015-11-17 22:07:21 +0900428 InternalEventHandler(AbstractEvent event) {
429 this.event = event;
sanghoshin94872a12015-10-16 18:04:34 +0900430 }
431
432 @Override
433 public void run() {
sanghoshin46297d22015-11-03 17:51:24 +0900434
sanghoshin65723ae2015-11-17 22:07:21 +0900435 if (event instanceof DeviceEvent) {
436 DeviceEvent deviceEvent = (DeviceEvent) event;
sanghoshin46297d22015-11-03 17:51:24 +0900437
sanghoshin65723ae2015-11-17 22:07:21 +0900438 switch (deviceEvent.type()) {
439 case DEVICE_ADDED:
440 processDeviceAdded((Device) deviceEvent.subject());
441 break;
442 case DEVICE_UPDATED:
443 Port port = (Port) deviceEvent.subject();
444 if (port.isEnabled()) {
445 processPortAdded((Device) deviceEvent.subject(), deviceEvent.port());
446 }
447 break;
448 case DEVICE_AVAILABILITY_CHANGED:
449 Device device = (Device) deviceEvent.subject();
450 if (deviceService.isAvailable(device.id())) {
451 processDeviceAdded(device);
452 }
453 break;
454 case PORT_ADDED:
sanghoshin94872a12015-10-16 18:04:34 +0900455 processPortAdded((Device) deviceEvent.subject(), deviceEvent.port());
sanghoshin65723ae2015-11-17 22:07:21 +0900456 break;
457 case PORT_UPDATED:
458 processPortAdded((Device) deviceEvent.subject(), deviceEvent.port());
459 break;
460 case PORT_REMOVED:
461 processPortRemoved((Device) deviceEvent.subject(), deviceEvent.port());
462 break;
463 default:
464 break;
465 }
466 } else if (event instanceof HostEvent) {
467 HostEvent hostEvent = (HostEvent) event;
468
469 switch (hostEvent.type()) {
470 case HOST_REMOVED:
471 processHostRemoved((Host) hostEvent.subject());
472 break;
473 default:
474 break;
475 }
sanghoshin94872a12015-10-16 18:04:34 +0900476 }
477 }
478 }
479
sanghoshin46297d22015-11-03 17:51:24 +0900480 private class InternalConfigListener implements NetworkConfigListener {
481
sanghoshinf25d2e02015-11-11 23:07:17 +0900482 public void configureNetwork() {
483 OpenstackSwitchingConfig cfg =
484 cfgService.getConfig(appId, OpenstackSwitchingConfig.class);
485 if (cfg == null) {
486 log.error("There is no openstack server information in config.");
487 return;
488 }
489 doNotPushFlows = cfg.doNotPushFlows();
490 restHandler = new OpenstackRestHandler(cfg);
Hyunsun Moonc98e7c52016-01-11 02:54:27 -0800491 arpHandler = new OpenstackArpHandler(restHandler, packetService, hostService);
sanghoshin075e3e72015-11-25 16:34:29 +0900492 initializeFlowRules();
sanghoshinf25d2e02015-11-11 23:07:17 +0900493 }
494
sanghoshin46297d22015-11-03 17:51:24 +0900495 @Override
496 public void event(NetworkConfigEvent event) {
497 if (((event.type() == NetworkConfigEvent.Type.CONFIG_ADDED ||
498 event.type() == NetworkConfigEvent.Type.CONFIG_UPDATED)) &&
499 event.configClass().equals(OpenstackSwitchingConfig.class)) {
sanghoshinf6735b22015-12-17 18:23:53 +0900500 networkEventExcutorService.execute(this::configureNetwork);
sanghoshin46297d22015-11-03 17:51:24 +0900501 }
502 }
sanghoshinf25d2e02015-11-11 23:07:17 +0900503
504 }
sanghoshin46297d22015-11-03 17:51:24 +0900505
sanghoshin94872a12015-10-16 18:04:34 +0900506 private final class PortInfo {
507 DeviceId deviceId;
508 String portName;
509 Ip4Address fixedIp;
510 Ip4Address hostIp;
511
512 private PortInfo(DeviceId deviceId, String portName, Ip4Address fixedIp,
513 Ip4Address hostIp) {
514 this.deviceId = deviceId;
515 this.portName = portName;
516 this.fixedIp = fixedIp;
517 this.hostIp = hostIp;
518 }
519 }
sanghoshin94872a12015-10-16 18:04:34 +0900520}