blob: 3c66bf875f799959864d5c636d5c80b65bb3c45f [file] [log] [blame]
tejeshwer degala3fe1ed52016-04-22 17:04:01 +05301/*
2 * Copyright 2016-present 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.isis.controller.impl.lsdb;
17
chidambar babu344dc812016-05-02 19:13:10 +053018import org.jboss.netty.buffer.ChannelBuffers;
tejeshwer degala3fe1ed52016-04-22 17:04:01 +053019import org.onosproject.isis.controller.IsisInterface;
20import org.onosproject.isis.controller.IsisLsdb;
21import org.onosproject.isis.controller.IsisLsdbAge;
22import org.onosproject.isis.controller.IsisLspBin;
23import org.onosproject.isis.controller.IsisMessage;
24import org.onosproject.isis.controller.IsisPduType;
25import org.onosproject.isis.controller.LspWrapper;
26import org.onosproject.isis.io.isispacket.pdu.LsPdu;
27import org.onosproject.isis.io.util.IsisConstants;
chidambar babu344dc812016-05-02 19:13:10 +053028import org.onosproject.isis.io.util.IsisUtil;
tejeshwer degala3fe1ed52016-04-22 17:04:01 +053029import org.slf4j.Logger;
30import org.slf4j.LoggerFactory;
31
32import java.util.Iterator;
33import java.util.List;
34import java.util.Map;
35import java.util.concurrent.ConcurrentHashMap;
36import java.util.concurrent.CopyOnWriteArrayList;
37
38/**
39 * Representation of ISIS link state database.
40 */
41public class DefaultIsisLsdb implements IsisLsdb {
42 private static final Logger log = LoggerFactory.getLogger(DefaultIsisLsdb.class);
43 private Map<String, LspWrapper> isisL1Db = new ConcurrentHashMap<>();
44 private Map<String, LspWrapper> isisL2Db = new ConcurrentHashMap<>();
45 private IsisLsdbAge lsdbAge = null;
chidambar babu344dc812016-05-02 19:13:10 +053046
47
tejeshwer degala3fe1ed52016-04-22 17:04:01 +053048 private int l1LspSeqNo = IsisConstants.STARTLSSEQUENCENUM;
49 private int l2LspSeqNo = IsisConstants.STARTLSSEQUENCENUM;
50
51 /**
52 * Creates an instance of ISIS LSDB.
53 */
54 public DefaultIsisLsdb() {
55 lsdbAge = new DefaultIsisLsdbAge();
56 }
57
58 /**
59 * Initializes the link state database.
60 */
61 public void initializeDb() {
62 lsdbAge.startDbAging();
63 }
64
65 /**
chidambar babu344dc812016-05-02 19:13:10 +053066 * Sets the level 1 link state sequence number.
67 *
68 * @param l1LspSeqNo link state sequence number
69 */
70 public void setL1LspSeqNo(int l1LspSeqNo) {
71 this.l1LspSeqNo = l1LspSeqNo;
72 }
73
74 /**
75 * Sets the level 2 link state sequence number.
76 *
77 * @param l2LspSeqNo link state sequence number
78 */
79 public void setL2LspSeqNo(int l2LspSeqNo) {
80 this.l2LspSeqNo = l2LspSeqNo;
81 }
sunish vk4b5ce002016-05-09 20:18:35 +053082
chidambar babu344dc812016-05-02 19:13:10 +053083 /**
tejeshwer degala3fe1ed52016-04-22 17:04:01 +053084 * Returns the LSDB LSP key.
85 *
86 * @param systemId system ID
87 * @return key
88 */
89 public String lspKey(String systemId) {
90 StringBuilder lspKey = new StringBuilder();
91 lspKey.append(systemId);
92 lspKey.append(".00");
93 lspKey.append("-");
94 lspKey.append("00");
95
96 return lspKey.toString();
97 }
98
sunish vk4b5ce002016-05-09 20:18:35 +053099
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530100 /**
101 * Returns the neighbor L1 database information.
102 *
103 * @return neighbor L1 database information
104 */
105 public Map<String, LspWrapper> getL1Db() {
106 return isisL1Db;
107 }
108
109 /**
110 * Returns the neighbor L2 database information.
111 *
112 * @return neighbor L2 database information
113 */
114 public Map<String, LspWrapper> getL2Db() {
115 return isisL2Db;
116 }
117
118 /**
119 * Returns the LSDB instance.
120 *
121 * @return LSDB instance
122 */
123 public IsisLsdb isisLsdb() {
124 return this;
125 }
126
127 /**
128 * Returns all LSPs (L1 and L2).
129 *
130 * @param excludeMaxAgeLsp exclude the max age LSPs
131 * @return List of LSPs
132 */
133 public List<LspWrapper> allLspHeaders(boolean excludeMaxAgeLsp) {
chidambar babu344dc812016-05-02 19:13:10 +0530134 List<LspWrapper> summaryList = new CopyOnWriteArrayList<>();
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530135 addLspToHeaderList(summaryList, excludeMaxAgeLsp, isisL1Db);
136 addLspToHeaderList(summaryList, excludeMaxAgeLsp, isisL2Db);
137
138 return summaryList;
139 }
140
141 /**
142 * Adds the LSPs to summary list.
143 *
144 * @param summaryList summary list
145 * @param excludeMaxAgeLsp exclude max age LSP
146 * @param lspMap map of LSP
147 */
148 private void addLspToHeaderList(List summaryList, boolean excludeMaxAgeLsp, Map lspMap) {
149 Iterator slotVals = lspMap.values().iterator();
150 while (slotVals.hasNext()) {
151 LspWrapper wrapper = (LspWrapper) slotVals.next();
152 if (excludeMaxAgeLsp) {
153 //if current age of lsa is max age or lsa present in Max Age bin
154 if (wrapper.remainingLifetime() != 0) {
155 addToList(wrapper, summaryList);
156 }
157 } else {
158 addToList(wrapper, summaryList);
159 }
160 }
161 }
162
163 /**
164 * Adds the LSPWrapper to summary list.
165 *
166 * @param wrapper LSP wrapper instance
167 * @param summList LSP summary list
168 */
169 private void addToList(LspWrapper wrapper, List summList) {
170 //set the current age
171 ((LsPdu) wrapper.lsPdu()).setRemainingLifeTime(wrapper.remainingLifetime());
172 summList.add(wrapper);
173 }
174
175 /**
176 * Finds the LSP from appropriate maps L1 or L2 based on type.
177 *
178 * @param pduType L1 or L2 LSP
179 * @param lspId LSP ID
180 * @return LSP wrapper object
181 */
182 public LspWrapper findLsp(IsisPduType pduType, String lspId) {
183 LspWrapper lspWrapper = null;
184
185 switch (pduType) {
186 case L1LSPDU:
187 lspWrapper = isisL1Db.get(lspId);
188 break;
189 case L2LSPDU:
190 lspWrapper = isisL2Db.get(lspId);
191 break;
192 default:
193 log.debug("Unknown LSP type..!!!");
194 break;
195 }
196
197 //set the current age
198 if (lspWrapper != null) {
199 //set the current age
200 ((DefaultLspWrapper) lspWrapper).lsPdu().setRemainingLifeTime(lspWrapper.remainingLifetime());
201 }
202
203 return lspWrapper;
204 }
205
206 /**
207 * Installs a new self-originated LSP.
208 *
209 * @return true if successfully added
210 */
211 public boolean addLsp(IsisMessage isisMessage, boolean isSelfOriginated, IsisInterface isisInterface) {
212 LsPdu lspdu = (LsPdu) isisMessage;
chidambar babu344dc812016-05-02 19:13:10 +0530213 if (isSelfOriginated) {
214 //Add length and checksum
215 byte[] lspBytes = lspdu.asBytes();
216 lspdu.setPduLength(lspBytes.length);
217 lspBytes = IsisUtil.addChecksum(lspBytes, IsisConstants.CHECKSUMPOSITION,
218 IsisConstants.CHECKSUMPOSITION + 1);
219 byte[] checkSum = {lspBytes[IsisConstants.CHECKSUMPOSITION], lspBytes[IsisConstants.CHECKSUMPOSITION + 1]};
220 lspdu.setCheckSum(ChannelBuffers.copiedBuffer(checkSum).readUnsignedShort());
221 }
sunish vk4b5ce002016-05-09 20:18:35 +0530222
223 DefaultLspWrapper lspWrapper = (DefaultLspWrapper) findLsp(lspdu.isisPduType(), lspdu.lspId());
224 if (lspWrapper == null) {
225 lspWrapper = new DefaultLspWrapper();
226 }
227
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530228 lspWrapper.setLspAgeReceived(IsisConstants.LSPMAXAGE - lspdu.remainingLifeTime());
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530229 lspWrapper.setLspType(IsisPduType.get(lspdu.pduType()));
230 lspWrapper.setLsPdu(lspdu);
231 lspWrapper.setAgeCounterWhenReceived(lsdbAge.ageCounter());
232 lspWrapper.setAgeCounterRollOverWhenAdded(lsdbAge.ageCounterRollOver());
233 lspWrapper.setSelfOriginated(isSelfOriginated);
234 lspWrapper.setIsisInterface(isisInterface);
235 lspWrapper.setLsdbAge(lsdbAge);
236 addLsp(lspWrapper, lspdu.lspId());
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530237
sunish vk4b5ce002016-05-09 20:18:35 +0530238 log.debug("Added LSp In LSDB: {}", lspWrapper);
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530239 return true;
240 }
241
242 /**
243 * Adds the LSP to L1 or L2 database.
244 *
245 * @param lspWrapper LSA wrapper instance
246 * @param key key
247 * @return True if added else false
248 */
249 private boolean addLsp(LspWrapper lspWrapper, String key) {
250 //Remove the lsa from bin if exist.
251 removeLspFromBin(lspWrapper);
252
253 switch (lspWrapper.lsPdu().isisPduType()) {
254 case L1LSPDU:
chidambar babu344dc812016-05-02 19:13:10 +0530255 isisL1Db.remove(key);
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530256 isisL1Db.put(key, lspWrapper);
257 break;
258 case L2LSPDU:
chidambar babu344dc812016-05-02 19:13:10 +0530259 isisL2Db.remove(key);
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530260 isisL2Db.put(key, lspWrapper);
261 break;
262 default:
263 log.debug("Unknown LSP type to add..!!!");
264 break;
265 }
266
267 //add it to bin
chidambar babu344dc812016-05-02 19:13:10 +0530268 Integer binNumber = lsdbAge.age2Bin(IsisConstants.LSPMAXAGE - lspWrapper.lspAgeReceived());
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530269 IsisLspBin lspBin = lsdbAge.getLspBin(binNumber);
270 if (lspBin != null) {
271 //remove from existing
272 lspWrapper.setBinNumber(binNumber);
273 lspBin.addIsisLsp(key, lspWrapper);
274 lsdbAge.addLspBin(binNumber, lspBin);
275 log.debug("Added Type {} LSP to LSDB and LSABin[{}], Remaining life time of LSA {}",
276 lspWrapper.lsPdu().isisPduType(),
277 binNumber, lspWrapper.remainingLifetime());
278 }
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530279 return false;
280 }
281
282 /**
283 * Removes LSP from Bin.
284 *
285 * @param lsaWrapper LSP wrapper instance
286 */
287 public void removeLspFromBin(LspWrapper lsaWrapper) {
288 if (lsaWrapper != null) {
289 lsdbAge.removeLspFromBin(lsaWrapper);
290 }
291 }
292
293 /**
294 * Returns new ,latest or old according to the type of ISIS message received.
295 *
296 * @param lsp1 LSP instance
297 * @param lsp2 LSP instance
298 * @return string status
299 */
300 public String isNewerOrSameLsp(IsisMessage lsp1, IsisMessage lsp2) {
301 LsPdu receivedLsp = (LsPdu) lsp1;
302 LsPdu lspFromDb = (LsPdu) lsp2;
chidambar babu344dc812016-05-02 19:13:10 +0530303 if (receivedLsp.sequenceNumber() > lspFromDb.sequenceNumber() ||
304 receivedLsp.checkSum() != lspFromDb.checkSum()) {
tejeshwer degala3fe1ed52016-04-22 17:04:01 +0530305 return "latest";
306 } else if (receivedLsp.sequenceNumber() < lspFromDb.sequenceNumber()) {
307 return "old";
308 } else if (receivedLsp.sequenceNumber() == lspFromDb.sequenceNumber()) {
309 return "same";
310 }
311
312 return "";
313 }
314
315 /**
316 * Returns the sequence number.
317 *
318 * @param lspType type of LSP
319 * @return sequence number
320 */
321 public int lsSequenceNumber(IsisPduType lspType) {
322 switch (lspType) {
323 case L1LSPDU:
324 return l1LspSeqNo++;
325 case L2LSPDU:
326 return l2LspSeqNo++;
327 default:
328 return IsisConstants.STARTLSSEQUENCENUM;
329 }
330 }
331
332 /**
333 * Deletes the given LSP.
334 *
335 * @param lspMessage LSP instance
336 */
337 public void deleteLsp(IsisMessage lspMessage) {
338 LsPdu lsp = (LsPdu) lspMessage;
339 String lspKey = lsp.lspId();
340 switch (lsp.isisPduType()) {
341 case L1LSPDU:
342 isisL1Db.remove(lspKey);
343 break;
344 case L2LSPDU:
345 isisL2Db.remove(lspKey);
346 break;
347 default:
348 log.debug("Unknown LSP type to remove..!!!");
349 break;
350 }
351 }
sunish vk4b5ce002016-05-09 20:18:35 +0530352}