blob: f0747ddd12b9ded19b81683bf59ac8c78fbe430f [file] [log] [blame]
Thomas Vachuska4f1a60c2014-10-28 13:39:07 -07001/*
2 * Copyright 2014 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 */
weibitf32383b2014-10-22 10:17:31 -070016package org.onlab.onos.net.intent.impl;
17
Thomas Vachuska425a2d72014-10-29 11:28:28 -070018import com.google.common.collect.Lists;
weibitf32383b2014-10-22 10:17:31 -070019import org.apache.felix.scr.annotations.Activate;
20import org.apache.felix.scr.annotations.Component;
21import org.apache.felix.scr.annotations.Deactivate;
22import org.apache.felix.scr.annotations.Reference;
23import org.apache.felix.scr.annotations.ReferenceCardinality;
Thomas Vachuskae0f804a2014-10-27 23:40:48 -070024import org.onlab.onos.core.ApplicationId;
25import org.onlab.onos.core.CoreService;
weibitf32383b2014-10-22 10:17:31 -070026import org.onlab.onos.net.ConnectPoint;
27import org.onlab.onos.net.Link;
weibitf32383b2014-10-22 10:17:31 -070028import org.onlab.onos.net.flow.DefaultFlowRule;
29import org.onlab.onos.net.flow.DefaultTrafficSelector;
weibit7e583462014-10-23 10:14:05 -070030import org.onlab.onos.net.flow.DefaultTrafficTreatment;
weibitf32383b2014-10-22 10:17:31 -070031import org.onlab.onos.net.flow.FlowRule;
32import org.onlab.onos.net.flow.FlowRuleBatchEntry;
Brian O'Connor086724e2014-10-23 15:47:32 -070033import org.onlab.onos.net.flow.FlowRuleBatchEntry.FlowRuleOperation;
weibitf32383b2014-10-22 10:17:31 -070034import org.onlab.onos.net.flow.FlowRuleBatchOperation;
35import org.onlab.onos.net.flow.FlowRuleService;
36import org.onlab.onos.net.flow.TrafficSelector;
37import org.onlab.onos.net.flow.TrafficTreatment;
weibitf32383b2014-10-22 10:17:31 -070038import org.onlab.onos.net.intent.IntentExtensionService;
39import org.onlab.onos.net.intent.IntentInstaller;
40import org.onlab.onos.net.intent.OpticalPathIntent;
weibit9e622ac2014-10-23 13:45:44 -070041import org.onlab.onos.net.resource.DefaultLinkResourceRequest;
weibit7e583462014-10-23 10:14:05 -070042import org.onlab.onos.net.resource.Lambda;
weibit9e622ac2014-10-23 13:45:44 -070043import org.onlab.onos.net.resource.LambdaResourceAllocation;
weibit7e583462014-10-23 10:14:05 -070044import org.onlab.onos.net.resource.LinkResourceAllocations;
45import org.onlab.onos.net.resource.LinkResourceRequest;
46import org.onlab.onos.net.resource.LinkResourceService;
weibit9e622ac2014-10-23 13:45:44 -070047import org.onlab.onos.net.resource.ResourceAllocation;
48import org.onlab.onos.net.resource.ResourceType;
weibit7e583462014-10-23 10:14:05 -070049import org.onlab.onos.net.topology.TopologyService;
weibitf32383b2014-10-22 10:17:31 -070050import org.slf4j.Logger;
51
Thomas Vachuska425a2d72014-10-29 11:28:28 -070052import java.util.List;
53
54import static org.onlab.onos.net.flow.DefaultTrafficTreatment.builder;
55import static org.slf4j.LoggerFactory.getLogger;
weibitf32383b2014-10-22 10:17:31 -070056
57/**
Thomas Vachuska425a2d72014-10-29 11:28:28 -070058 * Installer for {@link org.onlab.onos.net.intent.OpticalPathIntent optical path connectivity intents}.
weibitf32383b2014-10-22 10:17:31 -070059 */
weibitf32383b2014-10-22 10:17:31 -070060@Component(immediate = true)
61public class OpticalPathIntentInstaller implements IntentInstaller<OpticalPathIntent> {
weibitf32383b2014-10-22 10:17:31 -070062 private final Logger log = getLogger(getClass());
63
64 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
65 protected IntentExtensionService intentManager;
66
67 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
68 protected FlowRuleService flowRuleService;
69
70 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
71 protected CoreService coreService;
72
weibit7e583462014-10-23 10:14:05 -070073 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
74 protected TopologyService topologyService;
75
76 @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
77 protected LinkResourceService resourceService;
78
weibitf32383b2014-10-22 10:17:31 -070079 private ApplicationId appId;
80
weibit9e622ac2014-10-23 13:45:44 -070081 //final short WAVELENGTH = 80;
weibit7e583462014-10-23 10:14:05 -070082
weibitf32383b2014-10-22 10:17:31 -070083 @Activate
84 public void activate() {
85 appId = coreService.registerApplication("org.onlab.onos.net.intent");
86 intentManager.registerInstaller(OpticalPathIntent.class, this);
87 }
88
89 @Deactivate
90 public void deactivate() {
91 intentManager.unregisterInstaller(OpticalPathIntent.class);
92 }
93
94 @Override
weibit7e583462014-10-23 10:14:05 -070095 public List<FlowRuleBatchOperation> install(OpticalPathIntent intent) {
weibit9e622ac2014-10-23 13:45:44 -070096 LinkResourceAllocations allocations = assignWavelength(intent);
weibitf32383b2014-10-22 10:17:31 -070097
weibit9e622ac2014-10-23 13:45:44 -070098 TrafficSelector.Builder selectorBuilder = DefaultTrafficSelector.builder();
Brian O'Connor086724e2014-10-23 15:47:32 -070099 selectorBuilder.matchInport(intent.src().port());
weibitf32383b2014-10-22 10:17:31 -0700100
weibitf32383b2014-10-22 10:17:31 -0700101 List<FlowRuleBatchEntry> rules = Lists.newLinkedList();
Brian O'Connor086724e2014-10-23 15:47:32 -0700102 ConnectPoint prev = intent.src();
weibitf32383b2014-10-22 10:17:31 -0700103
weibit9e622ac2014-10-23 13:45:44 -0700104 //TODO throw exception if the lambda was not assigned successfully
105 for (Link link : intent.path().links()) {
106 Lambda la = null;
107 for (ResourceAllocation allocation : allocations.getResourceAllocation(link)) {
108 if (allocation.type() == ResourceType.LAMBDA) {
109 la = ((LambdaResourceAllocation) allocation).lambda();
110 break;
111 }
112 }
113
114 if (la == null) {
115 log.info("Lambda was not assigned successfully");
116 return null;
117 }
118
weibit253c8652014-10-23 16:30:03 -0700119 TrafficTreatment.Builder treatmentBuilder = DefaultTrafficTreatment.builder();
weibit9e622ac2014-10-23 13:45:44 -0700120 treatmentBuilder.setOutput(link.src().port());
weibit2543d5a2014-10-23 14:13:35 -0700121 treatmentBuilder.setLambda((short) la.toInt());
weibit9e622ac2014-10-23 13:45:44 -0700122
123 FlowRule rule = new DefaultFlowRule(prev.deviceId(),
Thomas Vachuska425a2d72014-10-29 11:28:28 -0700124 selectorBuilder.build(),
125 treatmentBuilder.build(),
126 100,
127 appId,
128 100,
129 true);
weibitaca14602014-10-24 10:26:26 -0700130
weibit7e583462014-10-23 10:14:05 -0700131 rules.add(new FlowRuleBatchEntry(FlowRuleOperation.ADD, rule));
weibit9e622ac2014-10-23 13:45:44 -0700132
weibit7e583462014-10-23 10:14:05 -0700133 prev = link.dst();
weibit9e622ac2014-10-23 13:45:44 -0700134 selectorBuilder.matchInport(link.dst().port());
weibit2543d5a2014-10-23 14:13:35 -0700135 selectorBuilder.matchLambda((short) la.toInt());
weibit7e583462014-10-23 10:14:05 -0700136 }
weibit9e622ac2014-10-23 13:45:44 -0700137
138 // build the last T port rule
139 TrafficTreatment treatmentLast = builder()
Brian O'Connor086724e2014-10-23 15:47:32 -0700140 .setOutput(intent.dst().port()).build();
141 FlowRule rule = new DefaultFlowRule(intent.dst().deviceId(),
Thomas Vachuska425a2d72014-10-29 11:28:28 -0700142 selectorBuilder.build(),
143 treatmentLast,
144 100,
145 appId,
146 100,
147 true);
weibit9e622ac2014-10-23 13:45:44 -0700148 rules.add(new FlowRuleBatchEntry(FlowRuleOperation.ADD, rule));
149
weibit7e583462014-10-23 10:14:05 -0700150 return Lists.newArrayList(new FlowRuleBatchOperation(rules));
151 }
weibitf32383b2014-10-22 10:17:31 -0700152
weibit9e622ac2014-10-23 13:45:44 -0700153 private LinkResourceAllocations assignWavelength(OpticalPathIntent intent) {
154 LinkResourceRequest.Builder request = DefaultLinkResourceRequest.builder(intent.id(),
Thomas Vachuska425a2d72014-10-29 11:28:28 -0700155 intent.path().links())
weibit9e622ac2014-10-23 13:45:44 -0700156 .addLambdaRequest();
157 LinkResourceAllocations retLambda = resourceService.requestResources(request.build());
158 return retLambda;
159 }
160
161 /*private Lambda assignWavelength(List<Link> links) {
weibit7e583462014-10-23 10:14:05 -0700162 // TODO More wavelength assignment algorithm
163 int wavenum = 0;
164 Iterator<Link> itrlink = links.iterator();
165 for (int i = 1; i <= WAVELENGTH; i++) {
166 wavenum = i;
167 boolean found = true;
168 while (itrlink.hasNext()) {
169 Link link = itrlink.next();
170 if (isWavelengthUsed(link, i)) {
171 found = false;
172 break;
173 }
174 }
175 // First-Fit wavelength assignment algorithm
176 if (found) {
177 break;
178 }
179 }
180
181 if (wavenum == 0) {
182 return null;
183 }
184
185 Lambda wave = Lambda.valueOf(wavenum);
186 return wave;
187 }
188
189 private boolean isWavelengthUsed(Link link, int i) {
190 Iterable<LinkResourceAllocations> wave = resourceService.getAllocations(link);
191 for (LinkResourceAllocations ir : wave) {
192 //if ir.resources().contains(i) {
193 //}
194 }
195 return false;
weibit9e622ac2014-10-23 13:45:44 -0700196 }*/
weibit7e583462014-10-23 10:14:05 -0700197
198 @Override
199 public List<FlowRuleBatchOperation> uninstall(OpticalPathIntent intent) {
Toshio Koide86160f52014-10-23 14:59:07 -0700200 LinkResourceAllocations allocations = resourceService.getAllocations(intent.id());
weibit9e622ac2014-10-23 13:45:44 -0700201
202 TrafficSelector.Builder selectorBuilder = DefaultTrafficSelector.builder();
Brian O'Connor086724e2014-10-23 15:47:32 -0700203 selectorBuilder.matchInport(intent.src().port());
weibit9e622ac2014-10-23 13:45:44 -0700204
205 TrafficTreatment.Builder treatmentBuilder = DefaultTrafficTreatment.builder();
206
weibit7e583462014-10-23 10:14:05 -0700207 List<FlowRuleBatchEntry> rules = Lists.newLinkedList();
Brian O'Connor086724e2014-10-23 15:47:32 -0700208 ConnectPoint prev = intent.src();
weibit9e622ac2014-10-23 13:45:44 -0700209
210 //TODO throw exception if the lambda was not retrieved successfully
211 for (Link link : intent.path().links()) {
212 Lambda la = null;
213 for (ResourceAllocation allocation : allocations.getResourceAllocation(link)) {
214 if (allocation.type() == ResourceType.LAMBDA) {
215 la = ((LambdaResourceAllocation) allocation).lambda();
216 break;
217 }
218 }
219
220 if (la == null) {
221 log.info("Lambda was not retrieved successfully");
222 return null;
223 }
224
225 treatmentBuilder.setOutput(link.src().port());
weibit2543d5a2014-10-23 14:13:35 -0700226 treatmentBuilder.setLambda((short) la.toInt());
weibit9e622ac2014-10-23 13:45:44 -0700227
228 FlowRule rule = new DefaultFlowRule(prev.deviceId(),
Thomas Vachuska425a2d72014-10-29 11:28:28 -0700229 selectorBuilder.build(),
230 treatmentBuilder.build(),
231 100,
232 appId,
233 100,
234 true);
weibitf32383b2014-10-22 10:17:31 -0700235 rules.add(new FlowRuleBatchEntry(FlowRuleOperation.REMOVE, rule));
weibit9e622ac2014-10-23 13:45:44 -0700236
weibitf32383b2014-10-22 10:17:31 -0700237 prev = link.dst();
weibit9e622ac2014-10-23 13:45:44 -0700238 selectorBuilder.matchInport(link.dst().port());
weibit2543d5a2014-10-23 14:13:35 -0700239 selectorBuilder.matchLambda((short) la.toInt());
weibitf32383b2014-10-22 10:17:31 -0700240 }
weibit9e622ac2014-10-23 13:45:44 -0700241
242 // build the last T port rule
243 TrafficTreatment treatmentLast = builder()
Brian O'Connor086724e2014-10-23 15:47:32 -0700244 .setOutput(intent.dst().port()).build();
245 FlowRule rule = new DefaultFlowRule(intent.dst().deviceId(),
Thomas Vachuska425a2d72014-10-29 11:28:28 -0700246 selectorBuilder.build(),
247 treatmentLast,
248 100,
249 appId,
250 100,
251 true);
weibit9e622ac2014-10-23 13:45:44 -0700252 rules.add(new FlowRuleBatchEntry(FlowRuleOperation.REMOVE, rule));
253
weibit7e583462014-10-23 10:14:05 -0700254 return Lists.newArrayList(new FlowRuleBatchOperation(rules));
weibitf32383b2014-10-22 10:17:31 -0700255 }
256
257}