blob: e8dbcb526bea164eb46867646cc605603874b6f3 [file] [log] [blame]
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001/*
Brian O'Connor5ab426f2016-04-09 01:19:45 -07002 * Copyright 2015-present Open Networking Laboratory
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07003 *
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.ovsdb.controller.driver;
17
andreaed976a42015-10-05 14:38:25 -070018import com.fasterxml.jackson.databind.JsonNode;
19import com.google.common.base.Function;
Pier Ventref5d72362016-07-17 12:02:14 +020020import com.google.common.collect.ImmutableList;
21import com.google.common.collect.ImmutableSet;
andreaed976a42015-10-05 14:38:25 -070022import com.google.common.collect.Lists;
23import com.google.common.collect.Maps;
24import com.google.common.collect.Sets;
25import com.google.common.util.concurrent.Futures;
26import com.google.common.util.concurrent.ListenableFuture;
27import com.google.common.util.concurrent.SettableFuture;
lishuai6c56f5e2015-11-17 16:38:19 +080028
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070029import io.netty.channel.Channel;
lishuai6c56f5e2015-11-17 16:38:19 +080030
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070031import org.onlab.packet.IpAddress;
andreaed976a42015-10-05 14:38:25 -070032import org.onosproject.net.DeviceId;
Hyunsun Moon1251e192016-06-07 16:57:05 -070033import org.onosproject.net.behaviour.BridgeDescription;
andreaed976a42015-10-05 14:38:25 -070034import org.onosproject.net.behaviour.ControllerInfo;
Pier Ventref5d72362016-07-17 12:02:14 +020035import org.onosproject.net.behaviour.MirroringStatistics;
36import org.onosproject.net.behaviour.MirroringName;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070037import org.onosproject.ovsdb.controller.OvsdbBridge;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070038import org.onosproject.ovsdb.controller.OvsdbClientService;
Hyunsun Moondd14e8e2016-06-09 16:17:32 -070039import org.onosproject.ovsdb.controller.OvsdbInterface;
40import org.onosproject.ovsdb.controller.OvsdbInterface.Type;
Pier Ventref5d72362016-07-17 12:02:14 +020041import org.onosproject.ovsdb.controller.OvsdbMirror;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070042import org.onosproject.ovsdb.controller.OvsdbNodeId;
43import org.onosproject.ovsdb.controller.OvsdbPort;
44import org.onosproject.ovsdb.controller.OvsdbPortName;
45import org.onosproject.ovsdb.controller.OvsdbPortNumber;
46import org.onosproject.ovsdb.controller.OvsdbRowStore;
47import org.onosproject.ovsdb.controller.OvsdbStore;
48import org.onosproject.ovsdb.controller.OvsdbTableStore;
Pier Ventref5d72362016-07-17 12:02:14 +020049
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070050import org.onosproject.ovsdb.rfc.jsonrpc.Callback;
51import org.onosproject.ovsdb.rfc.message.OperationResult;
52import org.onosproject.ovsdb.rfc.message.TableUpdates;
53import org.onosproject.ovsdb.rfc.notation.Condition;
54import org.onosproject.ovsdb.rfc.notation.Mutation;
CNluciusa66c3972015-09-06 20:31:29 +080055import org.onosproject.ovsdb.rfc.notation.OvsdbMap;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070056import org.onosproject.ovsdb.rfc.notation.OvsdbSet;
57import org.onosproject.ovsdb.rfc.notation.Row;
Jonathan Hart51539b82015-10-29 09:53:04 -070058import org.onosproject.ovsdb.rfc.notation.Uuid;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070059import org.onosproject.ovsdb.rfc.operations.Delete;
60import org.onosproject.ovsdb.rfc.operations.Insert;
61import org.onosproject.ovsdb.rfc.operations.Mutate;
62import org.onosproject.ovsdb.rfc.operations.Operation;
63import org.onosproject.ovsdb.rfc.operations.Update;
64import org.onosproject.ovsdb.rfc.schema.ColumnSchema;
65import org.onosproject.ovsdb.rfc.schema.DatabaseSchema;
66import org.onosproject.ovsdb.rfc.schema.TableSchema;
67import org.onosproject.ovsdb.rfc.table.Bridge;
68import org.onosproject.ovsdb.rfc.table.Controller;
69import org.onosproject.ovsdb.rfc.table.Interface;
Pier Ventref5d72362016-07-17 12:02:14 +020070import org.onosproject.ovsdb.rfc.table.Mirror;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070071import org.onosproject.ovsdb.rfc.table.OvsdbTable;
72import org.onosproject.ovsdb.rfc.table.Port;
73import org.onosproject.ovsdb.rfc.table.TableGenerator;
74import org.onosproject.ovsdb.rfc.utils.ConditionUtil;
75import org.onosproject.ovsdb.rfc.utils.FromJsonUtil;
76import org.onosproject.ovsdb.rfc.utils.JsonRpcWriterUtil;
77import org.onosproject.ovsdb.rfc.utils.MutationUtil;
78import org.slf4j.Logger;
79import org.slf4j.LoggerFactory;
80
andreaed976a42015-10-05 14:38:25 -070081import java.net.InetSocketAddress;
82import java.util.ArrayList;
Pier Ventref5d72362016-07-17 12:02:14 +020083
andreaed976a42015-10-05 14:38:25 -070084import java.util.HashSet;
85import java.util.Iterator;
86import java.util.List;
87import java.util.Map;
Pier Ventref5d72362016-07-17 12:02:14 +020088import java.util.Objects;
Hyunsun Moondd14e8e2016-06-09 16:17:32 -070089import java.util.Optional;
andreaed976a42015-10-05 14:38:25 -070090import java.util.Set;
91import java.util.concurrent.ConcurrentMap;
92import java.util.concurrent.ExecutionException;
jaegonkim01d7c912017-01-22 22:03:38 +090093import java.util.concurrent.TimeUnit;
94import java.util.concurrent.TimeoutException;
andreaed976a42015-10-05 14:38:25 -070095import java.util.concurrent.atomic.AtomicReference;
96import java.util.stream.Collectors;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -070097
Hyunsun Moon1251e192016-06-07 16:57:05 -070098import static org.onosproject.ovsdb.controller.OvsdbConstant.*;
99
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700100/**
101 * An representation of an ovsdb client.
102 */
Hyunsun Moon1251e192016-06-07 16:57:05 -0700103public class DefaultOvsdbClient implements OvsdbProviderService, OvsdbClientService {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700104
jaegonkim01d7c912017-01-22 22:03:38 +0900105 private static final int TRANSACTCONFIG_TIMEOUT = 3; //sec
106
Hyunsun Moon1251e192016-06-07 16:57:05 -0700107 private final Logger log = LoggerFactory.getLogger(DefaultOvsdbClient.class);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700108
109 private Channel channel;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700110 private OvsdbAgent agent;
111 private boolean connected;
112 private OvsdbNodeId nodeId;
113 private Callback monitorCallBack;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700114 private OvsdbStore ovsdbStore = new OvsdbStore();
115
116 private final Map<String, String> requestMethod = Maps.newHashMap();
Hyunsun Moon1251e192016-06-07 16:57:05 -0700117 private final Map<String, SettableFuture<? extends Object>> requestResult = Maps.newHashMap();
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700118 private final Map<String, DatabaseSchema> schema = Maps.newHashMap();
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700119
Pier Ventref5d72362016-07-17 12:02:14 +0200120
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700121 /**
122 * Creates an OvsdbClient.
123 *
124 * @param nodeId ovsdb node id
125 */
126 public DefaultOvsdbClient(OvsdbNodeId nodeId) {
127 this.nodeId = nodeId;
128 }
129
130 @Override
131 public OvsdbNodeId nodeId() {
132 return nodeId;
133 }
134
135 @Override
136 public void setAgent(OvsdbAgent agent) {
137 if (this.agent == null) {
138 this.agent = agent;
139 }
140 }
141
142 @Override
143 public void setChannel(Channel channel) {
144 this.channel = channel;
145 }
146
147 @Override
148 public void setConnection(boolean connected) {
149 this.connected = connected;
150 }
151
152 @Override
153 public boolean isConnected() {
154 return this.connected;
155 }
156
157 @Override
158 public void nodeAdded() {
159 this.agent.addConnectedNode(nodeId, this);
160 }
161
162 @Override
163 public void nodeRemoved() {
164 this.agent.removeConnectedNode(nodeId);
165 channel.disconnect();
166 }
167
168 /**
169 * Gets the ovsdb table store.
170 *
171 * @param dbName the ovsdb database name
172 * @return ovsTableStore, empty if table store is find
173 */
174 private OvsdbTableStore getTableStore(String dbName) {
175 if (ovsdbStore == null) {
176 return null;
177 }
178 return ovsdbStore.getOvsdbTableStore(dbName);
179 }
180
181 /**
182 * Gets the ovsdb row store.
183 *
andreaed976a42015-10-05 14:38:25 -0700184 * @param dbName the ovsdb database name
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700185 * @param tableName the ovsdb table name
Hyunsun Moon6125c612015-10-15 10:54:44 -0700186 * @return ovsRowStore, empty store if no rows exist in the table
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700187 */
188 private OvsdbRowStore getRowStore(String dbName, String tableName) {
189 OvsdbTableStore tableStore = getTableStore(dbName);
190 if (tableStore == null) {
191 return null;
192 }
Hyunsun Moon6125c612015-10-15 10:54:44 -0700193
194 OvsdbRowStore rowStore = tableStore.getRows(tableName);
195 if (rowStore == null) {
196 rowStore = new OvsdbRowStore();
197 }
198 return rowStore;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700199 }
200
201 /**
202 * Gets the ovsdb row.
203 *
andreaed976a42015-10-05 14:38:25 -0700204 * @param dbName the ovsdb database name
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700205 * @param tableName the ovsdb table name
andreaed976a42015-10-05 14:38:25 -0700206 * @param uuid the key of the row
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700207 * @return row, empty if row is find
208 */
209 @Override
210 public Row getRow(String dbName, String tableName, String uuid) {
211 OvsdbTableStore tableStore = getTableStore(dbName);
212 if (tableStore == null) {
213 return null;
214 }
215 OvsdbRowStore rowStore = tableStore.getRows(tableName);
216 if (rowStore == null) {
217 return null;
218 }
219 return rowStore.getRow(uuid);
220 }
221
222 @Override
223 public void removeRow(String dbName, String tableName, String uuid) {
224 OvsdbTableStore tableStore = getTableStore(dbName);
225 if (tableStore == null) {
226 return;
227 }
228 OvsdbRowStore rowStore = tableStore.getRows(tableName);
229 if (rowStore == null) {
230 return;
231 }
232 rowStore.deleteRow(uuid);
233 }
234
235 @Override
236 public void updateOvsdbStore(String dbName, String tableName, String uuid,
237 Row row) {
238 OvsdbTableStore tableStore = ovsdbStore.getOvsdbTableStore(dbName);
239 if (tableStore == null) {
240 tableStore = new OvsdbTableStore();
241 }
242 OvsdbRowStore rowStore = tableStore.getRows(tableName);
243 if (rowStore == null) {
244 rowStore = new OvsdbRowStore();
245 }
246 rowStore.insertRow(uuid, row);
247 tableStore.createOrUpdateTable(tableName, rowStore);
248 ovsdbStore.createOrUpdateOvsdbStore(dbName, tableStore);
249 }
250
Pier Ventref5d72362016-07-17 12:02:14 +0200251 /**
252 * Gets the Mirror uuid.
253 *
254 * @param mirrorName mirror name
255 * @return mirror uuid, empty if no uuid is found
256 */
257 @Override
258 public String getMirrorUuid(String mirrorName) {
259 DatabaseSchema dbSchema = schema.get(DATABASENAME);
260 OvsdbRowStore rowStore = getRowStore(DATABASENAME, MIRROR);
261 if (rowStore == null) {
262 log.warn("The mirror uuid is null");
263 return null;
264 }
265
266 ConcurrentMap<String, Row> mirrorTableRows = rowStore.getRowStore();
267 if (mirrorTableRows == null) {
268 log.warn("The mirror uuid is null");
269 return null;
270 }
271
272 for (String uuid : mirrorTableRows.keySet()) {
273 Mirror mirror = (Mirror) TableGenerator
274 .getTable(dbSchema, mirrorTableRows.get(uuid), OvsdbTable.MIRROR);
275 String name = mirror.getName();
276 if (name.contains(mirrorName)) {
277 return uuid;
278 }
279 }
280 log.warn("Mirroring not found");
281 return null;
282 }
283
284 /**
285 * Gets mirrors of the device.
286 *
287 * @param deviceId target device id
288 * @return set of mirroring; empty if no mirror is found
289 */
290 @Override
291 public Set<MirroringStatistics> getMirroringStatistics(DeviceId deviceId) {
292 Uuid bridgeUuid = getBridgeUuid(deviceId);
293 if (bridgeUuid == null) {
294 log.warn("Couldn't find bridge {} in {}", deviceId, nodeId.getIpAddress());
295 return null;
296 }
297
298 List<MirroringStatistics> mirrorings = getMirrorings(bridgeUuid);
299 if (mirrorings == null) {
300 log.warn("Couldn't find mirrors in {}", nodeId.getIpAddress());
301 return null;
302 }
303 return ImmutableSet.copyOf(mirrorings);
304 }
305
306 /**
307 * Helper method which retrieves mirrorings statistics using bridge uuid.
308 *
309 * @param bridgeUuid the uuid of the bridge
310 * @return the list of the mirrorings statistics.
311 */
312 private List<MirroringStatistics> getMirrorings(Uuid bridgeUuid) {
313 DatabaseSchema dbSchema = schema.get(DATABASENAME);
314 if (dbSchema == null) {
315 log.warn("Unable to retrieve dbSchema {}", DATABASENAME);
316 return null;
317 }
318 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
319 if (rowStore == null) {
320 log.warn("Unable to retrieve rowStore {} of {}", BRIDGE, DATABASENAME);
321 return null;
322 }
323
324 Row bridgeRow = rowStore.getRow(bridgeUuid.value());
325 Bridge bridge = (Bridge) TableGenerator.
326 getTable(dbSchema, bridgeRow, OvsdbTable.BRIDGE);
327
328 Set<Uuid> mirroringsUuids = (Set<Uuid>) ((OvsdbSet) bridge
329 .getMirrorsColumn().data()).set();
330
331 OvsdbRowStore mirrorRowStore = getRowStore(DATABASENAME, MIRROR);
332 if (mirrorRowStore == null) {
333 log.warn("Unable to retrieve rowStore {} of {}", MIRROR, DATABASENAME);
334 return null;
335 }
336
337 List<MirroringStatistics> mirroringStatistics = new ArrayList<>();
338 ConcurrentMap<String, Row> mirrorTableRows = mirrorRowStore.getRowStore();
339 mirrorTableRows.forEach((key, row) -> {
340 if (!mirroringsUuids.contains(Uuid.uuid(key))) {
341 return;
342 }
343 Mirror mirror = (Mirror) TableGenerator
344 .getTable(dbSchema, row, OvsdbTable.MIRROR);
345 mirroringStatistics.add(MirroringStatistics.mirroringStatistics(mirror.getName(),
346 (Map<String, Integer>) ((OvsdbMap) mirror
347 .getStatisticsColumn().data()).map()));
348 });
349 return ImmutableList.copyOf(mirroringStatistics);
350 }
351
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700352 @Override
353 public String getPortUuid(String portName, String bridgeUuid) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700354 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700355
Hyunsun Moon1251e192016-06-07 16:57:05 -0700356 Row bridgeRow = getRow(DATABASENAME, BRIDGE, bridgeUuid);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700357 Bridge bridge = (Bridge) TableGenerator.getTable(dbSchema, bridgeRow,
358 OvsdbTable.BRIDGE);
359 if (bridge != null) {
360 OvsdbSet setPorts = (OvsdbSet) bridge.getPortsColumn().data();
361 @SuppressWarnings("unchecked")
Jonathan Hart51539b82015-10-29 09:53:04 -0700362 Set<Uuid> ports = setPorts.set();
Jon Hallcbd1b392017-01-18 20:15:44 -0800363 if (ports == null || ports.isEmpty()) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700364 log.warn("The port uuid is null");
365 return null;
366 }
367
Jonathan Hart51539b82015-10-29 09:53:04 -0700368 for (Uuid uuid : ports) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700369 Row portRow = getRow(DATABASENAME, PORT, uuid.value());
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700370 Port port = (Port) TableGenerator.getTable(dbSchema, portRow,
371 OvsdbTable.PORT);
372 if (port != null && portName.equalsIgnoreCase(port.getName())) {
373 return uuid.value();
374 }
375 }
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700376 }
377 return null;
378 }
379
380 @Override
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700381 public String getBridgeUuid(String bridgeName) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700382 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700383 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700384 if (rowStore == null) {
385 log.debug("The bridge uuid is null");
386 return null;
387 }
388
389 ConcurrentMap<String, Row> bridgeTableRows = rowStore.getRowStore();
390 if (bridgeTableRows == null) {
391 log.debug("The bridge uuid is null");
392 return null;
393 }
394
395 for (String uuid : bridgeTableRows.keySet()) {
396 Bridge bridge = (Bridge) TableGenerator
Hyunsun Moon1251e192016-06-07 16:57:05 -0700397 .getTable(dbSchema, bridgeTableRows.get(uuid), OvsdbTable.BRIDGE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700398 if (bridge.getName().equals(bridgeName)) {
399 return uuid;
400 }
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700401 }
402 return null;
403 }
404
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700405 private String getOvsUuid(String dbName) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700406 OvsdbRowStore rowStore = getRowStore(DATABASENAME, DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700407 if (rowStore == null) {
408 log.debug("The bridge uuid is null");
409 return null;
410 }
411 ConcurrentMap<String, Row> ovsTableRows = rowStore.getRowStore();
412 if (ovsTableRows != null) {
413 for (String uuid : ovsTableRows.keySet()) {
414 Row row = ovsTableRows.get(uuid);
415 String tableName = row.tableName();
416 if (tableName.equals(dbName)) {
417 return uuid;
418 }
419 }
420 }
421 return null;
422 }
423
424 @Override
425 public void createPort(String bridgeName, String portName) {
426 String bridgeUuid = getBridgeUuid(bridgeName);
427 if (bridgeUuid == null) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700428 log.error("Can't find bridge {} in {}", bridgeName, nodeId.getIpAddress());
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700429 return;
430 }
431
Hyunsun Moon1251e192016-06-07 16:57:05 -0700432 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700433 String portUuid = getPortUuid(portName, bridgeUuid);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700434 Port port = (Port) TableGenerator.createTable(dbSchema, OvsdbTable.PORT);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700435 port.setName(portName);
436 if (portUuid == null) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700437 insertConfig(PORT, UUID, BRIDGE, PORTS, bridgeUuid, port.getRow());
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700438 }
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700439 }
440
441 @Override
442 public void dropPort(String bridgeName, String portName) {
443 String bridgeUuid = getBridgeUuid(bridgeName);
444 if (bridgeUuid == null) {
445 log.error("Could not find Bridge {} in {}", bridgeName, nodeId);
446 return;
447 }
448
449 String portUuid = getPortUuid(portName, bridgeUuid);
450 if (portUuid != null) {
451 log.info("Port {} delete", portName);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700452 deleteConfig(PORT, UUID, portUuid, BRIDGE, PORTS);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700453 }
454 }
455
Hyunsun Moon1251e192016-06-07 16:57:05 -0700456 @Deprecated
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700457 @Override
458 public void createBridge(String bridgeName) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700459 OvsdbBridge ovsdbBridge = OvsdbBridge.builder()
460 .name(bridgeName)
461 .build();
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700462
Hyunsun Moon1251e192016-06-07 16:57:05 -0700463 createBridge(ovsdbBridge);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700464 }
465
Hyunsun Moon1251e192016-06-07 16:57:05 -0700466 @Deprecated
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700467 @Override
lishuai6c56f5e2015-11-17 16:38:19 +0800468 public void createBridge(String bridgeName, String dpid, String exPortName) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700469 OvsdbBridge ovsdbBridge = OvsdbBridge.builder()
470 .name(bridgeName)
471 .failMode(BridgeDescription.FailMode.SECURE)
472 .datapathId(dpid)
473 .disableInBand()
474 .controllers(Lists.newArrayList(localController()))
475 .build();
lishuai6c56f5e2015-11-17 16:38:19 +0800476
Hyunsun Moon1251e192016-06-07 16:57:05 -0700477 createBridge(ovsdbBridge);
lishuai6c56f5e2015-11-17 16:38:19 +0800478
lishuai6c56f5e2015-11-17 16:38:19 +0800479 if (exPortName != null) {
480 createPort(bridgeName, exPortName);
481 }
Hyunsun Moon1251e192016-06-07 16:57:05 -0700482 }
lishuai6c56f5e2015-11-17 16:38:19 +0800483
Hyunsun Moon1251e192016-06-07 16:57:05 -0700484 @Deprecated
485 @Override
486 public boolean createBridge(String bridgeName, String dpid, List<ControllerInfo> controllers) {
487 OvsdbBridge ovsdbBridge = OvsdbBridge.builder()
488 .name(bridgeName)
489 .failMode(BridgeDescription.FailMode.SECURE)
490 .datapathId(dpid)
491 .disableInBand()
492 .controllers(controllers)
493 .build();
494
495 return createBridge(ovsdbBridge);
lishuai6c56f5e2015-11-17 16:38:19 +0800496 }
497
498 @Override
Hyunsun Moon1251e192016-06-07 16:57:05 -0700499 public boolean createBridge(OvsdbBridge ovsdbBridge) {
500 DatabaseSchema dbSchema = schema.get(DATABASENAME);
501 String ovsUuid = getOvsUuid(DATABASENAME);
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700502
503 if (dbSchema == null || ovsUuid == null) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700504 log.error("Can't find database Open_vSwitch");
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700505 return false;
506 }
507
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700508 Bridge bridge = (Bridge) TableGenerator.createTable(dbSchema, OvsdbTable.BRIDGE);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700509 bridge.setOtherConfig(ovsdbBridge.otherConfigs());
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700510
Hyunsun Moon1251e192016-06-07 16:57:05 -0700511 if (ovsdbBridge.failMode().isPresent()) {
512 String failMode = ovsdbBridge.failMode().get().name().toLowerCase();
513 bridge.setFailMode(Sets.newHashSet(failMode));
Bob zhoue9795fd2016-05-12 20:18:45 +0800514 }
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700515
Hyunsun Moon1251e192016-06-07 16:57:05 -0700516 String bridgeUuid = getBridgeUuid(ovsdbBridge.name());
Hyunsun Moon98025542016-03-08 04:36:02 -0800517 if (bridgeUuid == null) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700518 bridge.setName(ovsdbBridge.name());
519 bridgeUuid = insertConfig(
520 BRIDGE, UUID, DATABASENAME, BRIDGES,
521 ovsUuid, bridge.getRow());
Hyunsun Moon98025542016-03-08 04:36:02 -0800522 } else {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700523 // update the bridge if it's already existing
524 updateConfig(BRIDGE, UUID, bridgeUuid, bridge.getRow());
Hyunsun Moon98025542016-03-08 04:36:02 -0800525 }
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700526
Hyunsun Moon1251e192016-06-07 16:57:05 -0700527 if (bridgeUuid == null) {
528 log.warn("Failed to create bridge {} on {}", ovsdbBridge.name(), nodeId);
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700529 return false;
530 }
531
Hyunsun Moon1251e192016-06-07 16:57:05 -0700532 createPort(ovsdbBridge.name(), ovsdbBridge.name());
533 setControllersWithUuid(Uuid.uuid(bridgeUuid), ovsdbBridge.controllers());
534
535 log.info("Created bridge {}", ovsdbBridge.name());
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700536 return true;
537 }
538
Hyunsun Moon1251e192016-06-07 16:57:05 -0700539 @Override
540 public ControllerInfo localController() {
541 IpAddress ipAddress = IpAddress.valueOf(((InetSocketAddress)
542 channel.localAddress()).getAddress());
543 return new ControllerInfo(ipAddress, OFPORT, "tcp");
andreaed976a42015-10-05 14:38:25 -0700544 }
545
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700546 private void setControllersWithUuid(Uuid bridgeUuid, List<ControllerInfo> controllers) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700547 DatabaseSchema dbSchema = schema.get(DATABASENAME);
andreaed976a42015-10-05 14:38:25 -0700548 if (dbSchema == null) {
549 log.debug("There is no schema");
550 return;
551 }
552 List<Controller> oldControllers = getControllers(bridgeUuid);
553 if (oldControllers == null) {
554 log.warn("There are no controllers");
555 return;
556 }
557
Jonathan Hart51539b82015-10-29 09:53:04 -0700558 Set<Uuid> newControllerUuids = new HashSet<>();
andreaed976a42015-10-05 14:38:25 -0700559
560 Set<ControllerInfo> newControllers = new HashSet<>(controllers);
561 List<Controller> removeControllers = new ArrayList<>();
562 oldControllers.forEach(controller -> {
563 ControllerInfo controllerInfo = new ControllerInfo((String) controller.getTargetColumn().data());
564 if (newControllers.contains(controllerInfo)) {
565 newControllers.remove(controllerInfo);
566 newControllerUuids.add(controller.getRow().uuid());
567 } else {
568 removeControllers.add(controller);
569 }
570 });
Hyunsun Moon1251e192016-06-07 16:57:05 -0700571 OvsdbRowStore controllerRowStore = getRowStore(DATABASENAME, CONTROLLER);
andreaed976a42015-10-05 14:38:25 -0700572 if (controllerRowStore == null) {
573 log.debug("There is no controller table");
574 return;
575 }
576
Hyunsun Moon1251e192016-06-07 16:57:05 -0700577 removeControllers.forEach(c -> deleteConfig(CONTROLLER, UUID, c.getRow().uuid().value(),
578 BRIDGE, "controller"));
andreaed976a42015-10-05 14:38:25 -0700579 newControllers.stream().map(c -> {
580 Controller controller = (Controller) TableGenerator
581 .createTable(dbSchema, OvsdbTable.CONTROLLER);
582 controller.setTarget(c.target());
583 return controller;
584 }).forEach(c -> {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700585 String uuid = insertConfig(CONTROLLER, UUID, BRIDGE, "controller", bridgeUuid.value(),
andreaed976a42015-10-05 14:38:25 -0700586 c.getRow());
Jonathan Hart51539b82015-10-29 09:53:04 -0700587 newControllerUuids.add(Uuid.uuid(uuid));
andreaed976a42015-10-05 14:38:25 -0700588
589 });
590
Hyunsun Moon1251e192016-06-07 16:57:05 -0700591 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
andreaed976a42015-10-05 14:38:25 -0700592 if (rowStore == null) {
593 log.debug("There is no bridge table");
594 return;
595 }
596
597 Row bridgeRow = rowStore.getRow(bridgeUuid.value());
598 Bridge bridge = (Bridge) TableGenerator.getTable(dbSchema, bridgeRow, OvsdbTable.BRIDGE);
599 bridge.setController(OvsdbSet.ovsdbSet(newControllerUuids));
Hyunsun Moon1251e192016-06-07 16:57:05 -0700600 updateConfig(BRIDGE, UUID, bridgeUuid.value(), bridge.getRow());
andreaed976a42015-10-05 14:38:25 -0700601 }
602
andreaed976a42015-10-05 14:38:25 -0700603 @Override
604 public void setControllersWithDeviceId(DeviceId deviceId, List<ControllerInfo> controllers) {
Jonathan Hart51539b82015-10-29 09:53:04 -0700605 setControllersWithUuid(getBridgeUuid(deviceId), controllers);
andreaed976a42015-10-05 14:38:25 -0700606 }
607
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700608 @Override
609 public void dropBridge(String bridgeName) {
Jonathan Hart51539b82015-10-29 09:53:04 -0700610 String bridgeUuid = getBridgeUuid(bridgeName);
611 if (bridgeUuid == null) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700612 log.warn("Could not find bridge in node", nodeId.getIpAddress());
613 return;
614 }
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700615 deleteConfig(BRIDGE, UUID, bridgeUuid, DATABASENAME, BRIDGES);
616 }
617
Pier Ventref5d72362016-07-17 12:02:14 +0200618 /**
619 * Creates a mirror port. Mirrors the traffic
620 * that goes to selectDstPort or comes from
621 * selectSrcPort or packets containing selectVlan
622 * to mirrorPort or to all ports that trunk mirrorVlan.
623 *
624 * @param mirror the OVSDB mirror description
625 * @return true if mirror creation is successful, false otherwise
626 */
627 @Override
628 public boolean createMirror(String bridgeName, OvsdbMirror mirror) {
629
630 /**
631 * Retrieves bridge's uuid. It is necessary to update
632 * Bridge table.
633 */
634 String bridgeUuid = getBridgeUuid(bridgeName);
635 if (bridgeUuid == null) {
636 log.warn("Couldn't find bridge {} in {}", bridgeName, nodeId.getIpAddress());
637 return false;
638 }
639
640 OvsdbMirror.Builder mirrorBuilder = OvsdbMirror.builder();
641
642 mirrorBuilder.mirroringName(mirror.mirroringName());
643 mirrorBuilder.selectAll(mirror.selectAll());
644
645 /**
646 * Retrieves the uuid of the monitored dst ports.
647 */
648 mirrorBuilder.monitorDstPorts(mirror.monitorDstPorts().parallelStream()
649 .map(dstPort -> {
650 String dstPortUuid = getPortUuid(dstPort.value(), bridgeUuid);
651 if (dstPortUuid != null) {
652 return Uuid.uuid(dstPortUuid);
653 }
654 log.warn("Couldn't find port {} in {}",
655 dstPort.value(), nodeId.getIpAddress());
656 return null;
657 })
658 .filter(Objects::nonNull)
659 .collect(Collectors.toSet())
660 );
661
662 /**
663 * Retrieves the uuid of the monitored src ports.
664 */
665 mirrorBuilder.monitorSrcPorts(mirror.monitorSrcPorts().parallelStream()
666 .map(srcPort -> {
667 String srcPortUuid = getPortUuid(srcPort.value(), bridgeUuid);
668 if (srcPortUuid != null) {
669 return Uuid.uuid(srcPortUuid);
670 }
671 log.warn("Couldn't find port {} in {}",
672 srcPort.value(), nodeId.getIpAddress());
673 return null;
674 }).filter(Objects::nonNull)
675 .collect(Collectors.toSet())
676 );
677
678 mirrorBuilder.monitorVlans(mirror.monitorVlans());
679 mirrorBuilder.mirrorPort(mirror.mirrorPort());
680 mirrorBuilder.mirrorVlan(mirror.mirrorVlan());
681 mirrorBuilder.externalIds(mirror.externalIds());
682 mirror = mirrorBuilder.build();
683
Jon Hallcbd1b392017-01-18 20:15:44 -0800684 if (mirror.monitorDstPorts().isEmpty() &&
685 mirror.monitorSrcPorts().isEmpty() &&
686 mirror.monitorVlans().isEmpty()) {
Pier Ventref5d72362016-07-17 12:02:14 +0200687 log.warn("Invalid monitoring data");
688 return false;
689 }
690
691 DatabaseSchema dbSchema = schema.get(DATABASENAME);
692
693 Mirror mirrorEntry = (Mirror) TableGenerator.createTable(dbSchema, OvsdbTable.MIRROR);
694 mirrorEntry.setName(mirror.mirroringName());
695 mirrorEntry.setSelectDstPort(mirror.monitorDstPorts());
696 mirrorEntry.setSelectSrcPort(mirror.monitorSrcPorts());
697 mirrorEntry.setSelectVlan(mirror.monitorVlans());
698 mirrorEntry.setExternalIds(mirror.externalIds());
699
700 /**
701 * If mirror port, retrieves the uuid of the mirror port.
702 */
703 if (mirror.mirrorPort() != null) {
704
705 String outputPortUuid = getPortUuid(mirror.mirrorPort().value(), bridgeUuid);
706 if (outputPortUuid == null) {
707 log.warn("Couldn't find port {} in {}", mirror.mirrorPort().value(), nodeId.getIpAddress());
708 return false;
709 }
710
711 mirrorEntry.setOutputPort(Uuid.uuid(outputPortUuid));
712
713 } else if (mirror.mirrorVlan() != null) {
714
715 mirrorEntry.setOutputVlan(mirror.mirrorVlan());
716
717 } else {
718 log.warn("Invalid mirror, no mirror port and no mirror vlan");
719 return false;
720 }
721
722 ArrayList<Operation> operations = Lists.newArrayList();
723 Insert mirrorInsert = new Insert(dbSchema.getTableSchema("Mirror"), "Mirror", mirrorEntry.getRow());
724 operations.add(mirrorInsert);
725
726 // update the bridge table
727 Condition condition = ConditionUtil.isEqual(UUID, Uuid.uuid(bridgeUuid));
728 Mutation mutation = MutationUtil.insert(MIRRORS, Uuid.uuid("Mirror"));
729 List<Condition> conditions = Lists.newArrayList(condition);
730 List<Mutation> mutations = Lists.newArrayList(mutation);
731 operations.add(new Mutate(dbSchema.getTableSchema("Bridge"), conditions, mutations));
732
733 transactConfig(DATABASENAME, operations);
734 log.info("Created mirror {}", mirror.mirroringName());
735 return true;
736 }
737
738 /**
739 * Drops the configuration for mirror.
740 *
Ray Milkeyef794342016-11-09 16:20:29 -0800741 * @param mirroringName name of mirror to drop
Pier Ventref5d72362016-07-17 12:02:14 +0200742 */
743 @Override
744 public void dropMirror(MirroringName mirroringName) {
745 String mirrorUuid = getMirrorUuid(mirroringName.name());
746 if (mirrorUuid != null) {
747 log.info("Deleted mirror {}", mirroringName.name());
748 deleteConfig(MIRROR, UUID, mirrorUuid, BRIDGE, MIRRORS);
749 }
750 log.warn("Unable to delete {}", mirroringName.name());
751 return;
752 }
753
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700754 @Deprecated
755 @Override
756 public boolean createTunnel(String bridgeName, String ifaceName, String tunnelType,
757 Map<String, String> options) {
758 OvsdbInterface ovsdbIface = OvsdbInterface.builder()
759 .name(ifaceName)
760 .type(Type.valueOf(tunnelType))
761 .options(options)
762 .build();
763
764 return createInterface(bridgeName, ovsdbIface);
765 }
766
767 @Deprecated
768 @Override
769 public void dropTunnel(IpAddress srcIp, IpAddress dstIp) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700770 }
771
772 @Override
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700773 public boolean createInterface(String bridgeName, OvsdbInterface ovsdbIface) {
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700774 String bridgeUuid = getBridgeUuid(bridgeName);
775 if (bridgeUuid == null) {
776 log.warn("Couldn't find bridge {} in {}", bridgeName, nodeId.getIpAddress());
777 return false;
778 }
779
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700780 if (getPortUuid(ovsdbIface.name(), bridgeUuid) != null) {
781 log.warn("Interface {} already exists", ovsdbIface.name());
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700782 // remove existing one and re-create?
783 return false;
784 }
785
786 ArrayList<Operation> operations = Lists.newArrayList();
Hyunsun Moon1251e192016-06-07 16:57:05 -0700787 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700788
Hyunsun Moon89478662016-06-09 17:52:34 -0700789 // insert a new port with the interface name
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700790 Port port = (Port) TableGenerator.createTable(dbSchema, OvsdbTable.PORT);
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700791 port.setName(ovsdbIface.name());
792 Insert portInsert = new Insert(dbSchema.getTableSchema(PORT), PORT, port.getRow());
793 portInsert.getRow().put(INTERFACES, Uuid.uuid(INTERFACE));
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700794 operations.add(portInsert);
795
Hyunsun Moon89478662016-06-09 17:52:34 -0700796 // update the bridge table with the new port
Hyunsun Moon1251e192016-06-07 16:57:05 -0700797 Condition condition = ConditionUtil.isEqual(UUID, Uuid.uuid(bridgeUuid));
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700798 Mutation mutation = MutationUtil.insert(PORTS, Uuid.uuid(PORT));
799 List<Condition> conditions = Lists.newArrayList(condition);
800 List<Mutation> mutations = Lists.newArrayList(mutation);
801 operations.add(new Mutate(dbSchema.getTableSchema(BRIDGE), conditions, mutations));
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700802
Hyunsun Moon89478662016-06-09 17:52:34 -0700803 // insert an interface
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700804 Interface intf = (Interface) TableGenerator.createTable(dbSchema, OvsdbTable.INTERFACE);
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700805 intf.setName(ovsdbIface.name());
806 intf.setType(ovsdbIface.typeToString());
807 intf.setOptions(ovsdbIface.options());
808 Insert intfInsert = new Insert(dbSchema.getTableSchema(INTERFACE), INTERFACE, intf.getRow());
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700809 operations.add(intfInsert);
810
Hyunsun Moon1251e192016-06-07 16:57:05 -0700811 transactConfig(DATABASENAME, operations);
Hyunsun Moon89478662016-06-09 17:52:34 -0700812 log.info("Created interface {}", ovsdbIface);
Hyunsun Moon646d8c42015-10-08 20:32:44 -0700813 return true;
814 }
815
816 @Override
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700817 public boolean dropInterface(String ifaceName) {
818 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
819 if (rowStore == null) {
820 log.warn("Failed to get BRIDGE table");
821 return false;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700822 }
823
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700824 ConcurrentMap<String, Row> bridgeTableRows = rowStore.getRowStore();
825 if (bridgeTableRows == null) {
826 log.warn("Failed to get BRIDGE table rows");
827 return false;
828 }
829
830 // interface name is unique
831 Optional<String> bridgeId = bridgeTableRows.keySet().stream()
832 .filter(uuid -> getPortUuid(ifaceName, uuid) != null)
833 .findFirst();
834
835 if (bridgeId.isPresent()) {
836 String portId = getPortUuid(ifaceName, bridgeId.get());
837 deleteConfig(PORT, UUID, portId, BRIDGE, PORTS);
838 return true;
839 } else {
840 log.warn("Unable to find the interface with name {}", ifaceName);
841 return false;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700842 }
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700843 }
844
845 /**
846 * Delete transact config.
847 *
andreaed976a42015-10-05 14:38:25 -0700848 * @param childTableName child table name
849 * @param childColumnName child column name
850 * @param childUuid child row uuid
851 * @param parentTableName parent table name
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700852 * @param parentColumnName parent column
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700853 */
854 private void deleteConfig(String childTableName, String childColumnName,
andreaed976a42015-10-05 14:38:25 -0700855 String childUuid, String parentTableName,
856 String parentColumnName) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700857 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700858 TableSchema childTableSchema = dbSchema.getTableSchema(childTableName);
859
860 ArrayList<Operation> operations = Lists.newArrayList();
861 if (parentTableName != null && parentColumnName != null) {
862 TableSchema parentTableSchema = dbSchema
863 .getTableSchema(parentTableName);
864 ColumnSchema parentColumnSchema = parentTableSchema
865 .getColumnSchema(parentColumnName);
866 List<Mutation> mutations = Lists.newArrayList();
867 Mutation mutation = MutationUtil.delete(parentColumnSchema.name(),
Jonathan Hart51539b82015-10-29 09:53:04 -0700868 Uuid.uuid(childUuid));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700869 mutations.add(mutation);
870 List<Condition> conditions = Lists.newArrayList();
871 Condition condition = ConditionUtil.includes(parentColumnName,
Jonathan Hart51539b82015-10-29 09:53:04 -0700872 Uuid.uuid(childUuid));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700873 conditions.add(condition);
874 Mutate op = new Mutate(parentTableSchema, conditions, mutations);
875 operations.add(op);
876 }
877
878 List<Condition> conditions = Lists.newArrayList();
Jonathan Hart51539b82015-10-29 09:53:04 -0700879 Condition condition = ConditionUtil.isEqual(childColumnName, Uuid.uuid(childUuid));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700880 conditions.add(condition);
881 Delete del = new Delete(childTableSchema, conditions);
882 operations.add(del);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700883 transactConfig(DATABASENAME, operations);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700884 }
885
886 /**
887 * Update transact config.
888 *
andreaed976a42015-10-05 14:38:25 -0700889 * @param tableName table name
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700890 * @param columnName column name
andreaed976a42015-10-05 14:38:25 -0700891 * @param uuid uuid
892 * @param row the config data
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700893 */
894 private void updateConfig(String tableName, String columnName, String uuid,
andreaed976a42015-10-05 14:38:25 -0700895 Row row) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700896 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700897 TableSchema tableSchema = dbSchema.getTableSchema(tableName);
898
899 List<Condition> conditions = Lists.newArrayList();
Jonathan Hart51539b82015-10-29 09:53:04 -0700900 Condition condition = ConditionUtil.isEqual(columnName, Uuid.uuid(uuid));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700901 conditions.add(condition);
902
903 Update update = new Update(tableSchema, row, conditions);
904
905 ArrayList<Operation> operations = Lists.newArrayList();
906 operations.add(update);
907
Hyunsun Moon1251e192016-06-07 16:57:05 -0700908 transactConfig(DATABASENAME, operations);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700909 }
910
911 /**
912 * Insert transact config.
913 *
andreaed976a42015-10-05 14:38:25 -0700914 * @param childTableName child table name
915 * @param childColumnName child column name
916 * @param parentTableName parent table name
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700917 * @param parentColumnName parent column
andreaed976a42015-10-05 14:38:25 -0700918 * @param parentUuid parent uuid
919 * @param row the config data
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700920 * @return uuid, empty if no uuid is find
921 */
922 private String insertConfig(String childTableName, String childColumnName,
andreaed976a42015-10-05 14:38:25 -0700923 String parentTableName, String parentColumnName,
924 String parentUuid, Row row) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700925 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700926 TableSchema tableSchema = dbSchema.getTableSchema(childTableName);
927
Sho SHIMIZUff18f8c2016-03-11 14:43:53 -0800928 Insert insert = new Insert(tableSchema, childTableName, row);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700929
930 ArrayList<Operation> operations = Lists.newArrayList();
931 operations.add(insert);
932
933 if (parentTableName != null && parentColumnName != null) {
934 TableSchema parentTableSchema = dbSchema
935 .getTableSchema(parentTableName);
936 ColumnSchema parentColumnSchema = parentTableSchema
937 .getColumnSchema(parentColumnName);
938
939 List<Mutation> mutations = Lists.newArrayList();
940 Mutation mutation = MutationUtil.insert(parentColumnSchema.name(),
Sho SHIMIZUff18f8c2016-03-11 14:43:53 -0800941 Uuid.uuid(childTableName));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700942 mutations.add(mutation);
943
944 List<Condition> conditions = Lists.newArrayList();
Hyunsun Moon1251e192016-06-07 16:57:05 -0700945 Condition condition = ConditionUtil.isEqual(UUID, Uuid.uuid(parentUuid));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700946 conditions.add(condition);
947
948 Mutate op = new Mutate(parentTableSchema, conditions, mutations);
949 operations.add(op);
950 }
Hyunsun Moon1251e192016-06-07 16:57:05 -0700951 if (childTableName.equalsIgnoreCase(PORT)) {
952 log.debug("Handle port insert");
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700953 Insert intfInsert = handlePortInsertTable(row);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700954
955 if (intfInsert != null) {
956 operations.add(intfInsert);
957 }
958
959 Insert ins = (Insert) operations.get(0);
Hyunsun Moon1251e192016-06-07 16:57:05 -0700960 ins.getRow().put("interfaces", Uuid.uuid(INTERFACE));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700961 }
962
963 List<OperationResult> results;
964 try {
jaegonkim01d7c912017-01-22 22:03:38 +0900965 results = transactConfig(DATABASENAME, operations)
966 .get(TRANSACTCONFIG_TIMEOUT, TimeUnit.SECONDS);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700967 return results.get(0).getUuid().value();
jaegonkim01d7c912017-01-22 22:03:38 +0900968 } catch (TimeoutException e) {
969 log.warn("TimeoutException thrown while to get result");
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700970 } catch (InterruptedException e) {
971 log.warn("Interrupted while waiting to get result");
972 Thread.currentThread().interrupt();
973 } catch (ExecutionException e) {
974 log.error("Exception thrown while to get result");
975 }
976
977 return null;
978 }
979
jaegonkim01d7c912017-01-22 22:03:38 +0900980
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700981 /**
982 * Handles port insert.
983 *
andreaed976a42015-10-05 14:38:25 -0700984 * @param portRow row of port
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700985 * @return insert, empty if null
986 */
Hyunsun Moondd14e8e2016-06-09 16:17:32 -0700987 private Insert handlePortInsertTable(Row portRow) {
Hyunsun Moon1251e192016-06-07 16:57:05 -0700988 DatabaseSchema dbSchema = schema.get(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700989
Hyunsun Moon1251e192016-06-07 16:57:05 -0700990 TableSchema portTableSchema = dbSchema.getTableSchema(PORT);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700991 ColumnSchema portColumnSchema = portTableSchema.getColumnSchema("name");
992
993 String portName = (String) portRow.getColumn(portColumnSchema.name()).data();
Hyunsun Moon1251e192016-06-07 16:57:05 -0700994 Interface inf = (Interface) TableGenerator.createTable(dbSchema, OvsdbTable.INTERFACE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700995 inf.setName(portName);
996
Hyunsun Moon1251e192016-06-07 16:57:05 -0700997 TableSchema intfTableSchema = dbSchema.getTableSchema(INTERFACE);
998 return new Insert(intfTableSchema, INTERFACE, inf.getRow());
Sho SHIMIZUe4efe452015-08-26 15:06:55 -0700999 }
1000
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001001 @Override
1002 public ListenableFuture<DatabaseSchema> getOvsdbSchema(String dbName) {
1003 if (dbName == null) {
1004 return null;
1005 }
1006 DatabaseSchema databaseSchema = schema.get(dbName);
1007 if (databaseSchema == null) {
1008 List<String> dbNames = new ArrayList<String>();
1009 dbNames.add(dbName);
Hyunsun Moon1251e192016-06-07 16:57:05 -07001010 Function<JsonNode, DatabaseSchema> rowFunction = input -> {
1011 log.debug("Get ovsdb database schema {}", dbName);
1012 DatabaseSchema dbSchema = FromJsonUtil.jsonNodeToDbSchema(dbName, input);
1013 if (dbSchema == null) {
1014 log.debug("Get ovsdb database schema error");
1015 return null;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001016 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001017 schema.put(dbName, dbSchema);
1018 return dbSchema;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001019 };
1020
1021 ListenableFuture<JsonNode> input = getSchema(dbNames);
1022 if (input != null) {
1023 return Futures.transform(input, rowFunction);
1024 }
1025 return null;
1026 } else {
1027 return Futures.immediateFuture(databaseSchema);
1028 }
1029 }
1030
1031 @Override
1032 public ListenableFuture<TableUpdates> monitorTables(String dbName, String id) {
1033 if (dbName == null) {
1034 return null;
1035 }
1036 DatabaseSchema dbSchema = schema.get(dbName);
1037 if (dbSchema != null) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001038 Function<JsonNode, TableUpdates> rowFunction = input -> {
1039 log.debug("Get table updates");
1040 TableUpdates updates = FromJsonUtil.jsonNodeToTableUpdates(input, dbSchema);
1041 if (updates == null) {
1042 log.debug("Get table updates error");
1043 return null;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001044 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001045 return updates;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001046 };
1047 return Futures.transform(monitor(dbSchema, id), rowFunction);
1048 }
1049 return null;
1050 }
1051
Hyunsun Moondd14e8e2016-06-09 16:17:32 -07001052 private ListenableFuture<List<OperationResult>> transactConfig(String dbName,
1053 List<Operation> operations) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001054 if (dbName == null) {
1055 return null;
1056 }
1057 DatabaseSchema dbSchema = schema.get(dbName);
1058 if (dbSchema != null) {
andreaed976a42015-10-05 14:38:25 -07001059 Function<List<JsonNode>, List<OperationResult>> rowFunction = (input -> {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001060 log.debug("Get ovsdb operation result");
1061 List<OperationResult> result = FromJsonUtil.jsonNodeToOperationResult(input, operations);
andreaed976a42015-10-05 14:38:25 -07001062 if (result == null) {
1063 log.debug("The operation result is null");
1064 return null;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001065 }
andreaed976a42015-10-05 14:38:25 -07001066 return result;
1067 });
Hyunsun Moon1251e192016-06-07 16:57:05 -07001068 return Futures.transform(transact(dbSchema, operations), rowFunction);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001069 }
1070 return null;
1071 }
1072
1073 @Override
1074 public ListenableFuture<JsonNode> getSchema(List<String> dbnames) {
1075 String id = java.util.UUID.randomUUID().toString();
1076 String getSchemaString = JsonRpcWriterUtil.getSchemaStr(id, dbnames);
1077
1078 SettableFuture<JsonNode> sf = SettableFuture.create();
1079 requestResult.put(id, sf);
1080 requestMethod.put(id, "getSchema");
1081
1082 channel.writeAndFlush(getSchemaString);
1083 return sf;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001084 }
1085
1086 @Override
1087 public ListenableFuture<List<String>> echo() {
1088 String id = java.util.UUID.randomUUID().toString();
1089 String echoString = JsonRpcWriterUtil.echoStr(id);
1090
1091 SettableFuture<List<String>> sf = SettableFuture.create();
1092 requestResult.put(id, sf);
1093 requestMethod.put(id, "echo");
1094
1095 channel.writeAndFlush(echoString);
1096 return sf;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001097 }
1098
1099 @Override
1100 public ListenableFuture<JsonNode> monitor(DatabaseSchema dbSchema,
1101 String monitorId) {
1102 String id = java.util.UUID.randomUUID().toString();
1103 String monitorString = JsonRpcWriterUtil.monitorStr(id, monitorId,
1104 dbSchema);
1105
1106 SettableFuture<JsonNode> sf = SettableFuture.create();
1107 requestResult.put(id, sf);
1108 requestMethod.put(id, "monitor");
1109
1110 channel.writeAndFlush(monitorString);
1111 return sf;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001112 }
1113
1114 @Override
1115 public ListenableFuture<List<String>> listDbs() {
1116 String id = java.util.UUID.randomUUID().toString();
1117 String listDbsString = JsonRpcWriterUtil.listDbsStr(id);
1118
1119 SettableFuture<List<String>> sf = SettableFuture.create();
1120 requestResult.put(id, sf);
1121 requestMethod.put(id, "listDbs");
1122
1123 channel.writeAndFlush(listDbsString);
1124 return sf;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001125 }
1126
1127 @Override
1128 public ListenableFuture<List<JsonNode>> transact(DatabaseSchema dbSchema,
1129 List<Operation> operations) {
1130 String id = java.util.UUID.randomUUID().toString();
1131 String transactString = JsonRpcWriterUtil.transactStr(id, dbSchema,
1132 operations);
1133
1134 SettableFuture<List<JsonNode>> sf = SettableFuture.create();
1135 requestResult.put(id, sf);
1136 requestMethod.put(id, "transact");
1137
1138 channel.writeAndFlush(transactString);
1139 return sf;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001140 }
1141
andreaed976a42015-10-05 14:38:25 -07001142 @SuppressWarnings({"rawtypes", "unchecked"})
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001143 @Override
1144 public void processResult(JsonNode response) {
1145 log.debug("Handle result");
1146 String requestId = response.get("id").asText();
1147 SettableFuture sf = requestResult.get(requestId);
1148 if (sf == null) {
1149 log.debug("No such future to process");
1150 return;
1151 }
1152 String methodName = requestMethod.get(requestId);
Hyunsun Moon1251e192016-06-07 16:57:05 -07001153 sf.set(FromJsonUtil.jsonResultParser(response, methodName));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001154 }
1155
1156 @Override
1157 public void processRequest(JsonNode requestJson) {
1158 log.debug("Handle request");
1159 if (requestJson.get("method").asText().equalsIgnoreCase("echo")) {
1160 log.debug("handle echo request");
1161
1162 String replyString = FromJsonUtil.getEchoRequestStr(requestJson);
1163 channel.writeAndFlush(replyString);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001164 } else {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001165 FromJsonUtil.jsonCallbackRequestParser(requestJson, monitorCallBack);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001166 }
1167 }
1168
1169 @Override
1170 public void setCallback(Callback monitorCallback) {
1171 this.monitorCallBack = monitorCallback;
1172 }
1173
1174 @Override
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001175 public Set<OvsdbBridge> getBridges() {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001176 Set<OvsdbBridge> ovsdbBridges = new HashSet<>();
1177 OvsdbTableStore tableStore = getTableStore(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001178 if (tableStore == null) {
MaoJianweidac220d2016-07-04 22:37:52 +08001179 return ovsdbBridges;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001180 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001181 OvsdbRowStore rowStore = tableStore.getRows(BRIDGE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001182 if (rowStore == null) {
MaoJianweidac220d2016-07-04 22:37:52 +08001183 return ovsdbBridges;
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001184 }
1185 ConcurrentMap<String, Row> rows = rowStore.getRowStore();
1186 for (String uuid : rows.keySet()) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001187 Row row = getRow(DATABASENAME, BRIDGE, uuid);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001188 OvsdbBridge ovsdbBridge = getOvsdbBridge(row);
1189 if (ovsdbBridge != null) {
1190 ovsdbBridges.add(ovsdbBridge);
1191 }
1192 }
1193 return ovsdbBridges;
1194 }
1195
1196 @Override
andreaed976a42015-10-05 14:38:25 -07001197 public Set<ControllerInfo> getControllers(DeviceId openflowDeviceId) {
Jonathan Hart51539b82015-10-29 09:53:04 -07001198 Uuid bridgeUuid = getBridgeUuid(openflowDeviceId);
andreaed976a42015-10-05 14:38:25 -07001199 if (bridgeUuid == null) {
1200 log.warn("bad bridge Uuid");
1201 return null;
1202 }
1203 List<Controller> controllers = getControllers(bridgeUuid);
1204 if (controllers == null) {
1205 log.warn("bad list of controllers");
1206 return null;
1207 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001208 return controllers.stream().map(controller -> new ControllerInfo(
1209 (String) controller.getTargetColumn()
1210 .data())).collect(Collectors.toSet());
andreaed976a42015-10-05 14:38:25 -07001211 }
1212
Jonathan Hart51539b82015-10-29 09:53:04 -07001213 private List<Controller> getControllers(Uuid bridgeUuid) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001214 DatabaseSchema dbSchema = schema.get(DATABASENAME);
andreaed976a42015-10-05 14:38:25 -07001215 if (dbSchema == null) {
1216 return null;
1217 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001218 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
andreaed976a42015-10-05 14:38:25 -07001219 if (rowStore == null) {
1220 log.debug("There is no bridge table");
1221 return null;
1222 }
1223
1224 Row bridgeRow = rowStore.getRow(bridgeUuid.value());
1225 Bridge bridge = (Bridge) TableGenerator.
1226 getTable(dbSchema, bridgeRow, OvsdbTable.BRIDGE);
1227
1228 //FIXME remove log
1229 log.warn("type of controller column", bridge.getControllerColumn()
1230 .data().getClass());
Jonathan Hart51539b82015-10-29 09:53:04 -07001231 Set<Uuid> controllerUuids = (Set<Uuid>) ((OvsdbSet) bridge
andreaed976a42015-10-05 14:38:25 -07001232 .getControllerColumn().data()).set();
andreaed976a42015-10-05 14:38:25 -07001233
Hyunsun Moon1251e192016-06-07 16:57:05 -07001234 OvsdbRowStore controllerRowStore = getRowStore(DATABASENAME, CONTROLLER);
andreaed976a42015-10-05 14:38:25 -07001235 if (controllerRowStore == null) {
1236 log.debug("There is no controller table");
1237 return null;
1238 }
1239
1240 List<Controller> ovsdbControllers = new ArrayList<>();
1241 ConcurrentMap<String, Row> controllerTableRows = controllerRowStore.getRowStore();
1242 controllerTableRows.forEach((key, row) -> {
Jonathan Hart51539b82015-10-29 09:53:04 -07001243 if (!controllerUuids.contains(Uuid.uuid(key))) {
andreaed976a42015-10-05 14:38:25 -07001244 return;
1245 }
1246 Controller controller = (Controller) TableGenerator
1247 .getTable(dbSchema, row, OvsdbTable.CONTROLLER);
1248 ovsdbControllers.add(controller);
1249 });
1250 return ovsdbControllers;
1251 }
1252
1253
Jonathan Hart51539b82015-10-29 09:53:04 -07001254 private Uuid getBridgeUuid(DeviceId openflowDeviceId) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001255 DatabaseSchema dbSchema = schema.get(DATABASENAME);
andreaed976a42015-10-05 14:38:25 -07001256 if (dbSchema == null) {
1257 return null;
1258 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001259 OvsdbRowStore rowStore = getRowStore(DATABASENAME, BRIDGE);
andreaed976a42015-10-05 14:38:25 -07001260 if (rowStore == null) {
1261 log.debug("There is no bridge table");
1262 return null;
1263 }
1264
1265 ConcurrentMap<String, Row> bridgeTableRows = rowStore.getRowStore();
Jonathan Hart51539b82015-10-29 09:53:04 -07001266 final AtomicReference<Uuid> uuid = new AtomicReference<>();
andreaed976a42015-10-05 14:38:25 -07001267 for (Map.Entry<String, Row> entry : bridgeTableRows.entrySet()) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001268 Bridge bridge = (Bridge) TableGenerator.getTable(
1269 dbSchema,
1270 entry.getValue(),
1271 OvsdbTable.BRIDGE);
1272
1273 if (matchesDpid(bridge, openflowDeviceId)) {
Jonathan Hart51539b82015-10-29 09:53:04 -07001274 uuid.set(Uuid.uuid(entry.getKey()));
andreaed976a42015-10-05 14:38:25 -07001275 break;
1276 }
1277 }
1278 if (uuid.get() == null) {
1279 log.debug("There is no bridge for {}", openflowDeviceId);
1280 }
1281 return uuid.get();
andreaed976a42015-10-05 14:38:25 -07001282 }
1283
1284 private static boolean matchesDpid(Bridge b, DeviceId deviceId) {
1285 String ofDpid = deviceId.toString().replace("of:", "");
1286 Set ofDeviceIds = ((OvsdbSet) b.getDatapathIdColumn().data()).set();
1287 //TODO Set<String>
1288 return ofDeviceIds.contains(ofDpid);
1289 }
1290
1291 @Override
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001292 public Set<OvsdbPort> getPorts() {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001293 Set<OvsdbPort> ovsdbPorts = new HashSet<>();
1294 OvsdbTableStore tableStore = getTableStore(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001295 if (tableStore == null) {
1296 return null;
1297 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001298 OvsdbRowStore rowStore = tableStore.getRows(INTERFACE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001299 if (rowStore == null) {
1300 return null;
1301 }
1302 ConcurrentMap<String, Row> rows = rowStore.getRowStore();
1303 for (String uuid : rows.keySet()) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001304 Row row = getRow(DATABASENAME, INTERFACE, uuid);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001305 OvsdbPort ovsdbPort = getOvsdbPort(row);
1306 if (ovsdbPort != null) {
1307 ovsdbPorts.add(ovsdbPort);
1308 }
1309 }
1310 return ovsdbPorts;
1311 }
1312
1313 @Override
1314 public DatabaseSchema getDatabaseSchema(String dbName) {
1315 return schema.get(dbName);
1316 }
1317
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001318 private OvsdbPort getOvsdbPort(Row row) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001319 DatabaseSchema dbSchema = getDatabaseSchema(DATABASENAME);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001320 Interface intf = (Interface) TableGenerator
1321 .getTable(dbSchema, row, OvsdbTable.INTERFACE);
1322 if (intf == null) {
1323 return null;
1324 }
1325 long ofPort = getOfPort(intf);
1326 String portName = intf.getName();
1327 if ((ofPort < 0) || (portName == null)) {
1328 return null;
1329 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001330 return new OvsdbPort(new OvsdbPortNumber(ofPort), new OvsdbPortName(portName));
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001331 }
1332
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001333 private OvsdbBridge getOvsdbBridge(Row row) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001334 DatabaseSchema dbSchema = getDatabaseSchema(DATABASENAME);
1335 Bridge bridge = (Bridge) TableGenerator.getTable(dbSchema, row, OvsdbTable.BRIDGE);
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001336 if (bridge == null) {
1337 return null;
1338 }
1339
1340 OvsdbSet datapathIdSet = (OvsdbSet) bridge.getDatapathIdColumn().data();
1341 @SuppressWarnings("unchecked")
1342 Set<String> datapathIds = datapathIdSet.set();
Jon Hallcbd1b392017-01-18 20:15:44 -08001343 if (datapathIds == null || datapathIds.isEmpty()) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001344 return null;
1345 }
1346 String datapathId = (String) datapathIds.toArray()[0];
1347 String bridgeName = bridge.getName();
1348 if ((datapathId == null) || (bridgeName == null)) {
1349 return null;
1350 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001351 return OvsdbBridge.builder().name(bridgeName).datapathId(datapathId).build();
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001352 }
1353
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001354 private long getOfPort(Interface intf) {
1355 OvsdbSet ofPortSet = (OvsdbSet) intf.getOpenFlowPortColumn().data();
1356 @SuppressWarnings("unchecked")
1357 Set<Integer> ofPorts = ofPortSet.set();
Jon Hallcbd1b392017-01-18 20:15:44 -08001358 if (ofPorts == null || ofPorts.isEmpty()) {
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001359 log.debug("The ofport is null in {}", intf.getName());
1360 return -1;
1361 }
1362 // return (long) ofPorts.toArray()[0];
1363 Iterator<Integer> it = ofPorts.iterator();
1364 return Long.parseLong(it.next().toString());
1365 }
CNluciusa66c3972015-09-06 20:31:29 +08001366
1367 @Override
1368 public Set<OvsdbPort> getLocalPorts(Iterable<String> ifaceids) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001369 Set<OvsdbPort> ovsdbPorts = new HashSet<>();
1370 OvsdbTableStore tableStore = getTableStore(DATABASENAME);
CNluciusa66c3972015-09-06 20:31:29 +08001371 if (tableStore == null) {
1372 return null;
1373 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001374 OvsdbRowStore rowStore = tableStore.getRows(INTERFACE);
CNluciusa66c3972015-09-06 20:31:29 +08001375 if (rowStore == null) {
1376 return null;
1377 }
1378 ConcurrentMap<String, Row> rows = rowStore.getRowStore();
1379 for (String uuid : rows.keySet()) {
Hyunsun Moon1251e192016-06-07 16:57:05 -07001380 Row row = getRow(DATABASENAME, INTERFACE, uuid);
1381 DatabaseSchema dbSchema = getDatabaseSchema(DATABASENAME);
CNluciusa66c3972015-09-06 20:31:29 +08001382 Interface intf = (Interface) TableGenerator
1383 .getTable(dbSchema, row, OvsdbTable.INTERFACE);
1384 if (intf == null || getIfaceid(intf) == null) {
1385 continue;
1386 }
1387 String portName = intf.getName();
Hyunsun Moon1251e192016-06-07 16:57:05 -07001388 if (portName == null) {
1389 continue;
1390 }
CNluciusa66c3972015-09-06 20:31:29 +08001391 Set<String> ifaceidSet = Sets.newHashSet(ifaceids);
Hyunsun Moon1251e192016-06-07 16:57:05 -07001392 if (portName.startsWith(TYPEVXLAN) || !ifaceidSet.contains(getIfaceid(intf))) {
CNluciusa66c3972015-09-06 20:31:29 +08001393 continue;
1394 }
1395 long ofPort = getOfPort(intf);
Hyunsun Moon1251e192016-06-07 16:57:05 -07001396 if (ofPort < 0) {
CNluciusa66c3972015-09-06 20:31:29 +08001397 continue;
1398 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001399 ovsdbPorts.add(new OvsdbPort(new OvsdbPortNumber(ofPort),
1400 new OvsdbPortName(portName)));
CNluciusa66c3972015-09-06 20:31:29 +08001401 }
1402 return ovsdbPorts;
1403 }
1404
1405 private String getIfaceid(Interface intf) {
1406 OvsdbMap ovsdbMap = (OvsdbMap) intf.getExternalIdsColumn().data();
1407 @SuppressWarnings("unchecked")
1408 Map<String, String> externalIds = ovsdbMap.map();
1409 if (externalIds.isEmpty()) {
1410 log.warn("The external_ids is null");
1411 return null;
1412 }
Hyunsun Moon1251e192016-06-07 16:57:05 -07001413 String ifaceid = externalIds.get(EXTERNAL_ID_INTERFACE_ID);
CNluciusa66c3972015-09-06 20:31:29 +08001414 if (ifaceid == null) {
1415 log.warn("The ifaceid is null");
1416 return null;
1417 }
1418 return ifaceid;
1419 }
Hyunsun Moon5fb20a52015-09-25 17:02:33 -07001420
1421 @Override
1422 public void disconnect() {
1423 channel.disconnect();
1424 this.agent.removeConnectedNode(nodeId);
1425 }
Sho SHIMIZUe4efe452015-08-26 15:06:55 -07001426}