2 * Copyright (c) 2013, 2016 Red Hat, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.netvirt.openstack.netvirt;
11 import java.net.InetAddress;
12 import java.util.List;
14 import java.util.stream.Collectors;
16 import org.apache.commons.lang3.tuple.Pair;
17 import org.opendaylight.netvirt.openstack.netvirt.api.Action;
18 import org.opendaylight.netvirt.openstack.netvirt.api.BridgeConfigurationManager;
19 import org.opendaylight.netvirt.openstack.netvirt.api.ConfigurationService;
20 import org.opendaylight.netvirt.openstack.netvirt.api.Constants;
21 import org.opendaylight.netvirt.openstack.netvirt.api.EventDispatcher;
22 import org.opendaylight.netvirt.openstack.netvirt.api.L2ForwardingProvider;
23 import org.opendaylight.netvirt.openstack.netvirt.api.NetworkingProviderManager;
24 import org.opendaylight.netvirt.openstack.netvirt.api.NodeCacheListener;
25 import org.opendaylight.netvirt.openstack.netvirt.api.NodeCacheManager;
26 import org.opendaylight.netvirt.openstack.netvirt.api.OvsdbInventoryListener;
27 import org.opendaylight.netvirt.openstack.netvirt.api.OvsdbInventoryService;
28 import org.opendaylight.netvirt.openstack.netvirt.api.Southbound;
29 import org.opendaylight.netvirt.openstack.netvirt.api.TenantNetworkManager;
30 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronNetwork;
31 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronPort;
32 import org.opendaylight.netvirt.openstack.netvirt.translator.crud.INeutronNetworkCRUD;
33 import org.opendaylight.netvirt.openstack.netvirt.impl.DistributedArpService;
34 import org.opendaylight.netvirt.openstack.netvirt.impl.NeutronL3Adapter;
35 import org.opendaylight.netvirt.utils.servicehelper.ServiceHelper;
36 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.InterfaceTypeVxlan;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeAugmentation;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeAugmentation;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbTerminationPointAugmentation;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.Options;
42 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
43 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPoint;
44 import org.opendaylight.yangtools.yang.binding.DataObject;
45 import org.osgi.framework.ServiceReference;
46 import org.slf4j.Logger;
47 import org.slf4j.LoggerFactory;
50 * @author Madhu Venugopal
51 * @author Brent Salisbury
53 * @author Sam Hague (shague@redhat.com)
55 public class SouthboundHandler extends AbstractHandler
56 implements ConfigInterface, NodeCacheListener, OvsdbInventoryListener {
57 private static final Logger LOG = LoggerFactory.getLogger(SouthboundHandler.class);
59 // The implementation for each of these services is resolved by the OSGi Service Manager
60 private volatile ConfigurationService configurationService;
61 private volatile BridgeConfigurationManager bridgeConfigurationManager;
62 private volatile TenantNetworkManager tenantNetworkManager;
63 private volatile NetworkingProviderManager networkingProviderManager;
64 private volatile NeutronL3Adapter neutronL3Adapter;
65 private volatile DistributedArpService distributedArpService;
66 private volatile NodeCacheManager nodeCacheManager;
67 private volatile INeutronNetworkCRUD neutronNetworkCache;
68 private volatile OvsdbInventoryService ovsdbInventoryService;
69 private volatile Southbound southbound;
70 private volatile VLANProvider vlanProvider;
71 private volatile L2ForwardingProvider l2ForwardingProvider;
73 private SouthboundEvent.Type ovsdbTypeToSouthboundEventType(OvsdbType ovsdbType) {
74 SouthboundEvent.Type type = SouthboundEvent.Type.NODE;
78 type = SouthboundEvent.Type.NODE;
81 type = SouthboundEvent.Type.BRIDGE;
84 type = SouthboundEvent.Type.PORT;
87 type = SouthboundEvent.Type.CONTROLLER;
90 type = SouthboundEvent.Type.OPENVSWITCH;
93 LOG.warn("Invalid OvsdbType: {}", ovsdbType);
100 public void ovsdbUpdate(Node node, DataObject resourceAugmentationData, OvsdbType ovsdbType, Action action) {
101 LOG.debug("Received ovsdbUpdate for : {} with action : {} for the OVS node : {} Resource Data : {}",
102 ovsdbType, action, node, resourceAugmentationData);
103 enqueueEvent(new SouthboundEvent(node, resourceAugmentationData,
104 ovsdbTypeToSouthboundEventType(ovsdbType), action));
107 private void handleInterfaceUpdate (Node node, OvsdbTerminationPointAugmentation tp, Action action) {
108 NeutronNetwork network = tenantNetworkManager.getTenantNetwork(tp);
109 if (network != null && !network.getRouterExternal()) {
110 LOG.trace("InterfaceUpdate for OVS Node :{} OvsdbTerminationPointAugmentation :" + " {} for the network : {}", node, tp, network.getNetworkUUID());
111 if (bridgeConfigurationManager.createLocalNetwork(node, network)) {
112 networkingProviderManager.getProvider(node).handleInterfaceUpdate(network, node, tp);
115 LOG.debug("No tenant network found on node : {} for interface: {}", node, tp);
117 if (action.equals(Action.UPDATE)) {
118 distributedArpService.processInterfaceEvent(node, tp, network, false, action);
120 neutronL3Adapter.handleInterfaceEvent(node, tp, network, Action.UPDATE);
123 * Get dpid from node.
125 * @param node the {@link Node Node} of interest in the notification
128 private Long getDpidForIntegrationBridge(Node node) {
129 // Check if node is integration bridge; and only then return its dpid
130 if (southbound.getBridge(node, configurationService.getIntegrationBridgeName()) != null) {
131 return southbound.getDataPathId(node);
137 * Returns true, if the port is migrated else false.
139 * @param node the node associated with Neutron Port.
140 * @param neutronPort the port details.
141 * @return boolean true, if the port is migrated else false.
143 private boolean isMigratedPort(Node node, NeutronPort neutronPort) {
144 boolean isMigratedPort = false;
145 final Long dpId = getDpidForIntegrationBridge(node);
146 final Pair<Long, Uuid> nodeDpIdPair = neutronL3Adapter.getDpIdOfNeutronPort(neutronPort.getPortUUID());
147 Long dpIdNeutronPort = (nodeDpIdPair == null ? null : nodeDpIdPair.getLeft());
148 if(dpIdNeutronPort != null && !dpIdNeutronPort.equals(dpId)) {
149 isMigratedPort = true;
151 return isMigratedPort;
154 private void handleInterfaceDelete (Node node, OvsdbTerminationPointAugmentation intf,
155 boolean isLastInstanceOnNode, NeutronNetwork network) {
156 LOG.debug("handleInterfaceDelete: node: <{}>, isLastInstanceOnNode: {}, interface: <{}>",
157 node, isLastInstanceOnNode, intf);
159 final NeutronPort neutronPort = tenantNetworkManager.getTenantPort(intf);
160 boolean isMigratedPort = isMigratedPort(node, neutronPort);
161 distributedArpService.processInterfaceEvent(node, intf, network, isMigratedPort, Action.DELETE);
162 neutronL3Adapter.handleInterfaceEvent(node, intf, network, Action.DELETE);
163 programVLANNetworkFlowProvider(node, intf, network, neutronPort, false);
164 List<String> phyIfName = bridgeConfigurationManager.getAllPhysicalInterfaceNames(node);
165 if (isInterfaceOfInterest(intf, phyIfName)) {
166 // delete tunnel or physical interfaces
167 networkingProviderManager.getProvider(node).handleInterfaceDelete(network.getProviderNetworkType(),
168 network, node, intf, isLastInstanceOnNode, isMigratedPort);
169 } else if (network != null) {
170 // vlan doesn't need a tunnel endpoint
171 if (!network.getProviderNetworkType().equalsIgnoreCase(NetworkHandler.NETWORK_TYPE_VLAN) &&
172 configurationService.getTunnelEndPoint(node) == null) {
173 LOG.error("Tunnel end-point configuration missing. Please configure it in OpenVSwitch Table");
176 networkingProviderManager.getProvider(node).handleInterfaceDelete(network.getProviderNetworkType(),
177 network, node, intf, isLastInstanceOnNode, isMigratedPort);
183 public void triggerUpdates() {
184 List<Node> ovsdbNodes = southbound.readOvsdbTopologyNodes();
185 for (Node node : ovsdbNodes) {
186 ovsdbUpdate(node, node.getAugmentation(OvsdbNodeAugmentation.class),
187 OvsdbInventoryListener.OvsdbType.NODE, Action.ADD);
191 private void processPortDelete(Node node, OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation,
193 LOG.debug("processPortDelete for Node : {} ovsdbTerminationPointAugmentation : {}",
194 node, ovsdbTerminationPointAugmentation);
195 NeutronNetwork network;
196 if (context == null) {
197 network = tenantNetworkManager.getTenantNetwork(ovsdbTerminationPointAugmentation);
199 network = (NeutronNetwork)context;
201 List<String> phyIfName = bridgeConfigurationManager.getAllPhysicalInterfaceNames(node);
202 if (isInterfaceOfInterest(ovsdbTerminationPointAugmentation, phyIfName)) {
203 if (network != null) {
204 this.handleInterfaceDelete(node, ovsdbTerminationPointAugmentation, false, network);
206 LOG.warn("processPortDelete: network was null, ignoring update");
208 } else if (network != null && !network.getRouterExternal()) {
209 LOG.debug("Network {}: Delete interface {} attached to bridge {}", network.getNetworkUUID(),
210 ovsdbTerminationPointAugmentation.getInterfaceUuid(), node.getNodeId());
212 OvsdbBridgeAugmentation ovsdbBridgeAugmentation = southbound.getBridge(node);
213 if (ovsdbBridgeAugmentation != null) {
214 List<TerminationPoint> terminationPoints = node.getTerminationPoint();
215 if (!terminationPoints.isEmpty()){
216 boolean isLastInstanceOnNode = true;
217 for (TerminationPoint terminationPoint : terminationPoints) {
218 OvsdbTerminationPointAugmentation tpAugmentation =
219 terminationPoint.getAugmentation( OvsdbTerminationPointAugmentation.class);
220 if (tpAugmentation.getInterfaceUuid().equals(
221 ovsdbTerminationPointAugmentation.getInterfaceUuid())) {
224 NeutronNetwork neutronNetwork = tenantNetworkManager.getTenantNetwork(tpAugmentation);
225 if (neutronNetwork != null) {
226 String neutronNetworkSegId = neutronNetwork.getProviderSegmentationID();
227 String networkSegId = network.getProviderSegmentationID();
228 // vxlan ports should not be removed in table 110 flow entry
229 // unless last VM instance removed from the openstack node(Bug# 5813)
230 if (neutronNetworkSegId != null && neutronNetworkSegId.equals(networkSegId)) {
231 isLastInstanceOnNode = false;
236 this.handleInterfaceDelete(node, ovsdbTerminationPointAugmentation,
237 isLastInstanceOnNode, network);
240 } catch (Exception e) {
241 LOG.error("Error fetching Interface Rows for node {}", node, e);
243 } else if (network != null && network.getRouterExternal()) {
244 this.handleInterfaceDelete(node, ovsdbTerminationPointAugmentation, false, network);
246 //remove neutronPort from the CleanupCache, if it has the entry.
247 NeutronPort neutronPort = null;
248 String neutronPortId = southbound.getInterfaceExternalIdsValue(ovsdbTerminationPointAugmentation,
249 Constants.EXTERNAL_ID_INTERFACE_ID);
250 if (neutronPortId != null) {
251 LOG.trace("Clean up the NeutronPortCache for {} ", neutronPortId);
252 neutronPort = neutronL3Adapter.getPortFromCleanupCache(neutronPortId);
254 if (neutronPort != null) {
255 LOG.debug("Clean up the NeutronPortCache ");
256 neutronL3Adapter.removePortFromCleanupCache(neutronPort);
257 neutronL3Adapter.removeNetworkFromCleanupCache(neutronPort.getNetworkUUID());
259 LOG.trace("Nothing to Clean up in the NeutronPortCache ");
264 private boolean isInterfaceOfInterest(OvsdbTerminationPointAugmentation terminationPoint, List<String> phyIfName) {
265 LOG.trace("SouthboundHandler#isInterfaceOfInterest: Interface : {}", terminationPoint);
267 if(terminationPoint.getInterfaceType() == null){
268 // This is OK since eth ports don't have an interface type
271 return MdsalHelper.createOvsdbInterfaceType(
272 terminationPoint.getInterfaceType()).equals(NetworkHandler.NETWORK_TYPE_VXLAN)
274 MdsalHelper.createOvsdbInterfaceType(
275 terminationPoint.getInterfaceType()).equals(NetworkHandler.NETWORK_TYPE_GRE)
277 phyIfName.contains(terminationPoint.getName());
281 * Notification about an OpenFlow Node
283 * @param node the {@link Node Node} of interest in the notification
284 * @param action the {@link Action}
285 * @see NodeCacheListener#notifyNode
288 public void notifyNode (Node node, Action action) {
289 LOG.trace("notifyNode : action: {}, Node : {} ", action, node);
291 if ((action == Action.ADD) && (southbound.getBridge(node) != null)) {
292 networkingProviderManager.getProvider(node).initializeOFFlowRules(node);
299 * @param abstractEvent the {@link AbstractEvent} event to be handled.
300 * @see EventDispatcher
303 public void processEvent(AbstractEvent abstractEvent) {
304 if (!(abstractEvent instanceof SouthboundEvent)) {
305 LOG.error("processEvent Unable to process abstract event : {}", abstractEvent);
308 SouthboundEvent ev = (SouthboundEvent) abstractEvent;
309 LOG.trace("processEvent : {} for TransactionId : {}", ev, ev.getTransactionId());
310 switch (ev.getType()) {
312 processOvsdbNodeEvent(ev);
316 processBridgeEvent(ev);
320 processPortEvent(ev);
324 processOpenVSwitchEvent(ev);
328 LOG.warn("Unable to process type : {} action : {} for node : {}", ev.getType(), ev.getAction(), ev.getNode());
331 LOG.trace("processEvent exit : {} for TransactionId : {}", ev, ev.getTransactionId());
334 private void processOvsdbNodeEvent(SouthboundEvent ev) {
335 switch (ev.getAction()) {
337 processOvsdbNodeCreate(ev.getNode(), (OvsdbNodeAugmentation) ev.getAugmentationData());
340 processOvsdbNodeUpdate(ev.getNode(), (OvsdbNodeAugmentation) ev.getAugmentationData());
343 processOvsdbNodeDelete(ev.getNode(), (OvsdbNodeAugmentation) ev.getAugmentationData());
348 private void processOvsdbNodeCreate(Node node, OvsdbNodeAugmentation ovsdbNode) {
349 LOG.info("processOvsdb Node Create : {} ", ovsdbNode);
350 nodeCacheManager.nodeAdded(node);
351 bridgeConfigurationManager.prepareNode(node);
354 private void processOvsdbNodeUpdate(Node node, OvsdbNodeAugmentation ovsdbNode) {
355 LOG.info("processOvsdb Node Update : {} ", ovsdbNode);
356 nodeCacheManager.nodeAdded(node);
359 private void processOvsdbNodeDelete(Node node, OvsdbNodeAugmentation ovsdbNode) {
360 LOG.info("processOvsdb Node Delete : {} ", ovsdbNode);
361 nodeCacheManager.nodeRemoved(node);
363 * I don't think we want to do this yet
364 InstanceIdentifier<Node> bridgeNodeIid =
365 MdsalHelper.createInstanceIdentifier(ovsdbNode.getConnectionInfo(),
366 Constants.INTEGRATION_BRIDGE);
367 southbound.delete(LogicalDatastoreType.CONFIGURATION, bridgeNodeIid);
371 private void processPortEvent(SouthboundEvent ev) {
372 switch (ev.getAction()) {
375 processPortUpdate(ev.getNode(), (OvsdbTerminationPointAugmentation) ev.getAugmentationData(), ev.getAction());
378 processPortDelete(ev.getNode(), (OvsdbTerminationPointAugmentation) ev.getAugmentationData(), null);
383 private void processPortUpdate(Node node, OvsdbTerminationPointAugmentation port, Action action) {
384 LOG.debug("processPortUpdate : {} for the Node: {}", port, node);
385 NeutronNetwork network = tenantNetworkManager.getTenantNetwork(port);
386 if (network != null) {
387 final NeutronPort neutronPort = tenantNetworkManager.getTenantPort(port);
388 if (!network.getRouterExternal()) {
389 handleInterfaceUpdate(node, port, action);
390 } else if (action != null && action.equals(Action.UPDATE)) {
391 programVLANNetworkFlowProvider(node, port, network, neutronPort, true);
393 } else if (null != port.getInterfaceType() && null != port.getOfport()) {
394 // Filter Vxlan interface request and install table#110 unicast flow (Bug 7392).
395 if(port.getInterfaceType().equals(InterfaceTypeVxlan.class)) {
396 List<Options> optionList = port.getOptions();
397 if (null != optionList && !optionList.isEmpty()) {
398 optionList.stream().filter(option -> isRemoteIp(option)).forEach(option ->
399 handleTunnelOut(node, option.getValue(), port.getOfport()));
405 private boolean isRemoteIp(Options option) {
406 return option.getOption().equals(Constants.TUNNEL_ENDPOINT_KEY_REMOTE);
409 private void handleTunnelOut(Node node, String remoteIp, Long ofPort) {
410 List<Node> nodes = nodeCacheManager.getBridgeNodes();
411 if (null != nodes && !nodes.isEmpty()) {
412 nodes.stream().filter(dstnode -> isDstNode(node, dstnode, remoteIp)).forEach(dstnode ->
413 programTunnelOut(node, dstnode, ofPort));
417 private boolean isDstNode(Node node, Node dstnode, String remoteIp) {
418 if (!(node.getNodeId().getValue().equals(dstnode.getNodeId().getValue()))) {
419 InetAddress dst = configurationService.getTunnelEndPoint(dstnode);
420 String dstIp = dst.getHostAddress();
421 if (remoteIp.equals(dstIp)) {
428 private void programTunnelOut(Node node, Node dstnode, Long ofPort) {
429 List<OvsdbTerminationPointAugmentation> ports = southbound.readTerminationPointAugmentations(dstnode);
430 for (OvsdbTerminationPointAugmentation destport : ports) {
431 NeutronPort neutronPort = tenantNetworkManager.getTenantPort(destport);
432 if (neutronPort != null) {
433 final String networkUUID = neutronPort.getNetworkUUID();
434 NeutronNetwork neutronNetwork = neutronNetworkCache.getNetwork(networkUUID);
435 if (null == neutronNetwork) {
436 neutronNetwork = neutronL3Adapter.getNetworkFromCleanupCache(networkUUID);
438 final String segmentationId = neutronNetwork != null ? neutronNetwork.getProviderSegmentationID() : null;
439 final String macAddress = neutronPort.getMacAddress();
440 long dpid = getIntegrationBridgeOFDPID(node);
441 if (null != l2ForwardingProvider) {
442 l2ForwardingProvider.programTunnelOut(dpid, segmentationId, ofPort, macAddress, true);
448 private long getIntegrationBridgeOFDPID(Node node) {
450 if (southbound.getBridgeName(node).equals(configurationService.getIntegrationBridgeName())) {
451 dpid = southbound.getDataPathId(node);
456 private void programVLANNetworkFlowProvider(final Node node, final OvsdbTerminationPointAugmentation port,
457 final NeutronNetwork network, final NeutronPort neutronPort, final Boolean isWrite) {
458 if (neutronPort != null && neutronPort.getDeviceOwner().equalsIgnoreCase(Constants.OWNER_ROUTER_GATEWAY) &&
459 network.getProviderNetworkType().equalsIgnoreCase(NetworkHandler.NETWORK_TYPE_VLAN) &&
460 configurationService.isL3MultipleExternalNetworkEnabled()) {
461 vlanProvider.programProviderNetworkFlow(node, port, network, neutronPort, isWrite);
465 private void processOpenVSwitchEvent(SouthboundEvent ev) {
466 switch (ev.getAction()) {
469 processOpenVSwitchUpdate(ev.getNode());
476 private void processOpenVSwitchUpdate(Node node) {
477 LOG.debug("processOpenVSwitchUpdate : {}", node);
478 // TODO this node might be the OvsdbNode and not have termination points
479 // Would need to change listener or grab tp nodes in here.
480 List<TerminationPoint> terminationPoints = southbound.extractTerminationPoints(node);
481 for (TerminationPoint terminationPoint : terminationPoints) {
482 processPortUpdate(node, terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class), null);
486 private void processBridgeEvent(SouthboundEvent ev) {
487 switch (ev.getAction()) {
489 processBridgeCreate(ev.getNode(), (OvsdbBridgeAugmentation) ev.getAugmentationData());
492 processBridgeUpdate(ev.getNode(), (OvsdbBridgeAugmentation) ev.getAugmentationData());
495 processBridgeDelete(ev.getNode(), (OvsdbBridgeAugmentation) ev.getAugmentationData());
500 private void processBridgeCreate(Node node, OvsdbBridgeAugmentation bridge) {
501 LOG.debug("BridgeCreate : {} for the Node : {}", bridge, node);
502 String datapathId = southbound.getDatapathId(bridge);
503 // Having a datapathId means the ovsdb node has connected to ODL
504 if (datapathId != null) {
505 nodeCacheManager.nodeAdded(node);
507 LOG.debug("processBridgeCreate datapathId not found");
511 private void processBridgeUpdate(Node node, OvsdbBridgeAugmentation bridge) {
512 LOG.debug("BridgeUpdate : {} for the node : {}", bridge, node);
513 String datapathId = southbound.getDatapathId(bridge);
514 // Having a datapathId means the ovsdb node has connected to ODL
515 if (datapathId != null) {
516 nodeCacheManager.nodeAdded(node);
518 LOG.debug("processBridgeUpdate datapathId not found");
522 private void processBridgeDelete(Node node, OvsdbBridgeAugmentation bridge) {
523 LOG.debug("BridgeDelete: Delete bridge from config data store : {}"
524 +"Node : {}", bridge, node);
525 nodeCacheManager.nodeRemoved(node);
527 // Currently we only do not remove the integration bridge from configDS, which resolves
528 // bug 7461 where upon a rapid connection flap, the integration bridge is sometimes
529 // removed from the device due to ODL asynchronous processing of the connection flap.
530 if (bridge.getBridgeName() != null &&
531 !bridge.getBridgeName().getValue().equals(configurationService.getIntegrationBridgeName())) {
532 southbound.deleteBridge(node);
536 public void setDependencies(ServiceReference serviceReference) {
537 configurationService =
538 (ConfigurationService) ServiceHelper.getGlobalInstance(ConfigurationService.class, this);
539 networkingProviderManager =
540 (NetworkingProviderManager) ServiceHelper.getGlobalInstance(NetworkingProviderManager.class, this);
541 tenantNetworkManager =
542 (TenantNetworkManager) ServiceHelper.getGlobalInstance(TenantNetworkManager.class, this);
543 bridgeConfigurationManager =
544 (BridgeConfigurationManager) ServiceHelper.getGlobalInstance(BridgeConfigurationManager.class, this);
546 (NodeCacheManager) ServiceHelper.getGlobalInstance(NodeCacheManager.class, this);
547 nodeCacheManager.cacheListenerAdded(serviceReference, this);
549 (NeutronL3Adapter) ServiceHelper.getGlobalInstance(NeutronL3Adapter.class, this);
550 distributedArpService =
551 (DistributedArpService) ServiceHelper.getGlobalInstance(DistributedArpService.class, this);
553 (Southbound) ServiceHelper.getGlobalInstance(Southbound.class, this);
555 (EventDispatcher) ServiceHelper.getGlobalInstance(EventDispatcher.class, this);
556 eventDispatcher.eventHandlerAdded(serviceReference, this);
557 ovsdbInventoryService =
558 (OvsdbInventoryService) ServiceHelper.getGlobalInstance(OvsdbInventoryService.class, this);
559 ovsdbInventoryService.listenerAdded(this);
561 (VLANProvider) ServiceHelper.getGlobalInstance(VLANProvider.class, this);
562 l2ForwardingProvider =
563 (L2ForwardingProvider) ServiceHelper.getGlobalInstance(L2ForwardingProvider.class, this);
567 public void setDependencies(Object impl) {
568 if (impl instanceof INeutronNetworkCRUD) {
569 neutronNetworkCache = (INeutronNetworkCRUD)impl;
570 } else if (impl instanceof L2ForwardingProvider) {
571 l2ForwardingProvider = (L2ForwardingProvider)impl;