2 * Copyright (c) 2015 Cisco Systems, 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.lispflowmapping.implementation.mapcache;
11 import java.util.AbstractMap.SimpleImmutableEntry;
12 import java.util.Date;
15 import org.opendaylight.lispflowmapping.interfaces.dao.ILispDAO;
16 import org.opendaylight.lispflowmapping.interfaces.dao.IRowVisitor;
17 import org.opendaylight.lispflowmapping.interfaces.dao.MappingEntry;
18 import org.opendaylight.lispflowmapping.interfaces.dao.SubKeys;
19 import org.opendaylight.lispflowmapping.interfaces.mapcache.IMapCache;
20 import org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.lispaddress.LispAddressContainer;
21 import org.opendaylight.lispflowmapping.lisp.util.LispAFIConvertor;
22 import org.opendaylight.lispflowmapping.lisp.util.MaskUtil;
23 import org.slf4j.Logger;
24 import org.slf4j.LoggerFactory;
27 * Simple map-cache that works with 'simple' addresses (see lisp-proto.yang). It can do longest prefix matching for IP
30 * @author Florin Coras
33 public class SimpleMapCache implements IMapCache {
34 private static final Logger LOG = LoggerFactory.getLogger(SimpleMapCache.class);
37 public SimpleMapCache(ILispDAO dao) {
41 public void addMapping(LispAddressContainer key, Object value, boolean shouldOverwrite) {
42 LispAddressContainer eid = MaskUtil.normalize(key);
43 dao.put(eid, new MappingEntry<>(SubKeys.REGDATE, new Date(System.currentTimeMillis())));
44 dao.put(eid, new MappingEntry<>(SubKeys.RECORD, value));
47 // Method returns the DAO entry (hash) corresponding to either the longest prefix match of eid, if eid is maskable,
48 // or the exact match otherwise. eid must be a 'simple' address
49 private Map<String, ?> getDaoEntryBest(LispAddressContainer key, ILispDAO dao) {
50 if (MaskUtil.isMaskable(key)) {
51 LispAddressContainer lookupKey;
52 short mask = MaskUtil.getMaskForAddress(key);
54 lookupKey = MaskUtil.normalize(key, mask);
56 Map<String, ?> entry = dao.get(lookupKey);
67 // Method returns the DAO entry (hash) corresponding to either the longest prefix match of eid, if eid is maskable,
68 // or the exact match otherwise. eid must be a 'simple' address
69 private SimpleImmutableEntry<LispAddressContainer, Map<String, ?>> getDaoPairEntryBest(LispAddressContainer key, ILispDAO dao) {
70 if (MaskUtil.isMaskable(key)) {
71 LispAddressContainer lookupKey;
72 short mask = MaskUtil.getMaskForAddress(key);
74 lookupKey = MaskUtil.normalize(key, mask);
76 Map<String, ?> entry = dao.get(lookupKey);
78 return new SimpleImmutableEntry<LispAddressContainer, Map<String, ?>>(lookupKey, entry);
83 Map<String, ?> entry = dao.get(key);
85 return new SimpleImmutableEntry<LispAddressContainer, Map<String, ?>>(key, entry);
92 // Returns the mapping corresponding to the longest prefix match for eid. eid must be a simple (maskable or not)
94 private Object getMappingLpmEid(LispAddressContainer eid, ILispDAO dao) {
95 Map<String, ?> daoEntry = getDaoEntryBest(eid, dao);
96 if (daoEntry != null) {
97 return daoEntry.get(SubKeys.RECORD);
103 // Returns the matched key and mapping corresponding to the longest prefix match for eid. eid must be a simple
104 // (maskable or not) address
105 private SimpleImmutableEntry<LispAddressContainer, Object> getMappingPairLpmEid(LispAddressContainer eid, ILispDAO dao) {
106 SimpleImmutableEntry<LispAddressContainer, Map<String, ?>> daoEntry = getDaoPairEntryBest(eid, dao);
107 if (daoEntry != null) {
108 return new SimpleImmutableEntry<LispAddressContainer, Object>(daoEntry.getKey(), daoEntry.getValue().get(
115 public Object getMapping(LispAddressContainer srcEid, LispAddressContainer dstEid) {
116 if (dstEid == null) {
119 return getMappingLpmEid(dstEid, dao);
122 public void removeMapping(LispAddressContainer eid, boolean overwrite) {
123 eid = MaskUtil.normalize(eid);
124 dao.removeSpecific(eid, SubKeys.RECORD);
127 public void addAuthenticationKey(LispAddressContainer eid, String key) {
128 eid = MaskUtil.normalize(eid);
129 dao.put(eid, new MappingEntry<String>(SubKeys.AUTH_KEY, key));
132 private String getAuthKeyLpm(LispAddressContainer prefix, ILispDAO db) {
133 short maskLength = MaskUtil.getMaskForAddress(prefix);
134 while (maskLength >= 0) {
135 LispAddressContainer key = MaskUtil.normalize(prefix, maskLength);
136 Object password = db.getSpecific(key, SubKeys.AUTH_KEY);
137 if (password != null && password instanceof String) {
138 return (String) password;
145 public String getAuthenticationKey(LispAddressContainer eid) {
146 if (MaskUtil.isMaskable(LispAFIConvertor.toAFI(eid))) {
147 return getAuthKeyLpm(eid, dao);
149 Object password = dao.getSpecific(eid, SubKeys.AUTH_KEY);
150 if (password != null && password instanceof String) {
151 return (String) password;
153 LOG.warn("Failed to find password!");
159 public void removeAuthenticationKey(LispAddressContainer eid) {
160 eid = MaskUtil.normalize(eid);
161 dao.removeSpecific(eid, SubKeys.AUTH_KEY);
164 public String printMappings() {
165 final StringBuffer sb = new StringBuffer();
166 sb.append("Keys\tValues\n");
167 dao.getAll(new IRowVisitor() {
170 public void visitRow(Object keyId, String valueKey, Object value) {
171 String key = keyId.getClass().getSimpleName() + "#" + keyId;
172 if (!lastKey.equals(key)) {
173 sb.append("\n" + key + "\t");
175 sb.append(valueKey + "=" + value + "\t");
180 return sb.toString();
184 public void updateMappingRegistration(LispAddressContainer key) {
185 Map<String, ?> daoEntry = getDaoEntryBest(key, dao);
186 if (daoEntry != null) {
187 dao.put(key, new MappingEntry<>(SubKeys.REGDATE, new Date(System.currentTimeMillis())));
192 public void addData(LispAddressContainer key, String subKey, Object data) {
193 LispAddressContainer normKey = MaskUtil.normalize(key);
194 dao.put(normKey, new MappingEntry<>(subKey, data));
198 public Object getData(LispAddressContainer key, String subKey) {
199 return dao.getSpecific(key, subKey);
203 public void removeData(LispAddressContainer key, String subKey) {
204 dao.removeSpecific(key, subKey);