Modified model to support L3Prefix EP, GIC, EIC, ECC and EIG
[groupbasedpolicy.git] / renderers / ofoverlay / src / main / java / org / opendaylight / groupbasedpolicy / renderer / ofoverlay / OFOverlayRenderer.java
1 /*
2  * Copyright (c) 2014 Cisco Systems, Inc. and others.  All rights reserved.
3  *
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
7  */
8
9 package org.opendaylight.groupbasedpolicy.renderer.ofoverlay;
10
11 import java.util.concurrent.Executors;
12 import java.util.concurrent.ScheduledExecutorService;
13
14 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
15 import org.opendaylight.controller.md.sal.binding.api.DataChangeListener;
16 import org.opendaylight.controller.md.sal.common.api.data.AsyncDataBroker.DataChangeScope;
17 import org.opendaylight.controller.md.sal.common.api.data.AsyncDataChangeEvent;
18 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
19 import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
20 import org.opendaylight.groupbasedpolicy.resolver.PolicyResolver;
21 import org.opendaylight.groupbasedpolicy.renderer.ofoverlay.SfcManager;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.ofoverlay.rev140528.OfOverlayConfig;
23 import org.opendaylight.yangtools.concepts.ListenerRegistration;
24 import org.opendaylight.yangtools.yang.binding.DataObject;
25 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
26 import org.slf4j.Logger;
27 import org.slf4j.LoggerFactory;
28
29 import com.google.common.base.Optional;
30 import com.google.common.util.concurrent.FutureCallback;
31 import com.google.common.util.concurrent.Futures;
32 import com.google.common.util.concurrent.ListenableFuture;
33
34 /**
35  * Renderer that uses OpenFlow and OVSDB to implement an overlay network
36  * using Open vSwitch.
37  * @author readams
38  */
39 public class OFOverlayRenderer implements AutoCloseable, DataChangeListener {
40     private static final Logger LOG =
41             LoggerFactory.getLogger(OFOverlayRenderer.class);
42
43     private final DataBroker dataBroker;
44     private final PolicyResolver policyResolver;
45     private final SwitchManager switchManager;
46     private final EndpointManager endpointManager;
47     private final PolicyManager policyManager;
48     private final SfcManager sfcManager;
49
50     private final ScheduledExecutorService executor;
51
52     private static final InstanceIdentifier<OfOverlayConfig> configIid =
53             InstanceIdentifier.builder(OfOverlayConfig.class).build();
54
55     private OfOverlayConfig config;
56     ListenerRegistration<DataChangeListener> configReg;
57
58     public OFOverlayRenderer(DataBroker dataProvider,
59                              RpcProviderRegistry rpcRegistry) {
60         super();
61         this.dataBroker = dataProvider;
62
63         int numCPU = Runtime.getRuntime().availableProcessors();
64         //TODO: Consider moving to groupbasedpolicy-ofoverlay-config so as to be user configurable in distribution.
65         executor = Executors.newScheduledThreadPool(numCPU * 2);
66
67         switchManager = new SwitchManager(dataProvider, executor);
68         endpointManager = new EndpointManager(dataProvider, rpcRegistry,
69                                               executor, switchManager);
70         policyResolver = new PolicyResolver(dataProvider, executor);
71
72         policyManager = new PolicyManager(dataProvider,
73                                           policyResolver,
74                                           switchManager,
75                                           endpointManager,
76                                           rpcRegistry,
77                                           executor);
78         // TODO Move SfcManager out out ofoverlay renderer -- should be something
79         //       that's shared by renderers, not specific to ofoverlay
80         sfcManager = new SfcManager(dataProvider,
81                                     policyResolver,
82                                     rpcRegistry,
83                                     executor);
84
85
86         configReg =
87                 dataProvider.registerDataChangeListener(LogicalDatastoreType.CONFIGURATION,
88                                                         configIid,
89                                                         this,
90                                                         DataChangeScope.SUBTREE);
91         readConfig();
92         LOG.info("Initialized OFOverlay renderer");
93
94     }
95
96     // *************
97     // AutoCloseable
98     // *************
99
100     @Override
101     public void close() throws Exception {
102         executor.shutdownNow();
103         if (configReg != null) configReg.close();
104         if (policyResolver != null) policyResolver.close();
105         if (switchManager != null) switchManager.close();
106         if (endpointManager != null) endpointManager.close();
107         if (sfcManager != null) sfcManager.close();
108     }
109
110     // ******************
111     // DataChangeListener
112     // ******************
113
114     @Override
115     public void onDataChanged(AsyncDataChangeEvent<InstanceIdentifier<?>,
116                                                    DataObject> change) {
117         readConfig();
118     }
119
120     // **************
121     // Implementation
122     // **************
123
124     private void readConfig() {
125         ListenableFuture<Optional<OfOverlayConfig>> dao =
126                 dataBroker.newReadOnlyTransaction()
127                     .read(LogicalDatastoreType.CONFIGURATION, configIid);
128         Futures.addCallback(dao, new FutureCallback<Optional<OfOverlayConfig>>() {
129             @Override
130             public void onSuccess(final Optional<OfOverlayConfig> result) {
131                 if (!result.isPresent()) return;
132                 if (result.get() instanceof OfOverlayConfig) {
133                     config = (OfOverlayConfig)result.get();
134                     applyConfig();
135                 }
136             }
137
138             @Override
139             public void onFailure(Throwable t) {
140                 LOG.error("Failed to read configuration", t);
141             }
142         }, executor);
143     }
144
145     private void applyConfig() {
146         switchManager.setEncapsulationFormat(config.getEncapsulationFormat());
147         endpointManager.setLearningMode(config.getLearningMode());
148         policyManager.setLearningMode(config.getLearningMode());
149     }
150 }