2 * Copyright (c) 2016 Cisco and/or its affiliates.
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:
8 * http://www.apache.org/licenses/LICENSE-2.0
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.
17 package io.fd.honeycomb.translate.v3po.interfaces;
19 import static com.google.common.base.Preconditions.checkArgument;
20 import static java.util.Objects.requireNonNull;
22 import io.fd.honeycomb.translate.vpp.util.JvppReplyConsumer;
23 import io.fd.honeycomb.translate.vpp.util.NamingContext;
24 import io.fd.honeycomb.translate.vpp.util.WriteTimeoutException;
25 import io.fd.honeycomb.translate.write.WriteContext;
26 import io.fd.honeycomb.translate.write.WriteFailedException;
27 import java.util.concurrent.CompletionStage;
28 import javax.annotation.Nonnull;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.l2.base.attributes.Interconnection;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.l2.base.attributes.interconnection.BridgeBased;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.l2.base.attributes.interconnection.XconnectBased;
32 import org.opendaylight.yangtools.yang.binding.DataObject;
33 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
34 import org.openvpp.jvpp.VppBaseCallException;
35 import org.openvpp.jvpp.core.dto.SwInterfaceSetL2Bridge;
36 import org.openvpp.jvpp.core.dto.SwInterfaceSetL2BridgeReply;
37 import org.openvpp.jvpp.core.dto.SwInterfaceSetL2Xconnect;
38 import org.openvpp.jvpp.core.dto.SwInterfaceSetL2XconnectReply;
39 import org.openvpp.jvpp.core.future.FutureJVppCore;
40 import org.slf4j.Logger;
41 import org.slf4j.LoggerFactory;
44 * Utility class providing Interconnection CUD support.
46 final class InterconnectionWriteUtils implements JvppReplyConsumer {
48 private static final Logger LOG = LoggerFactory.getLogger(InterconnectionWriteUtils.class);
50 private final FutureJVppCore futureJVppCore;
51 private final NamingContext interfaceContext;
52 private final NamingContext bridgeDomainContext;
54 InterconnectionWriteUtils(@Nonnull final FutureJVppCore futureJVppCore,
55 @Nonnull final NamingContext interfaceContext,
56 @Nonnull final NamingContext bridgeDomainContext) {
57 this.futureJVppCore = requireNonNull(futureJVppCore, "futureJVppCore should not be null");
58 this.interfaceContext = requireNonNull(interfaceContext, "interfaceContext should not be null");
59 this.bridgeDomainContext = requireNonNull(bridgeDomainContext, "bridgeDomainContext should not be null");
62 void setInterconnection(final InstanceIdentifier<? extends DataObject> id, final int swIfIndex,
63 final String ifcName, final Interconnection ic, final WriteContext writeContext)
64 throws WriteFailedException {
66 if (ic == null) { // TODO in case of update we should delete interconnection
67 LOG.trace("Interconnection is not set. Skipping");
68 } else if (ic instanceof XconnectBased) {
69 setXconnectBasedL2(id, swIfIndex, ifcName, (XconnectBased) ic, writeContext, (byte) 1 /*enable*/);
70 } else if (ic instanceof BridgeBased) {
71 setBridgeBasedL2(id, swIfIndex, ifcName, (BridgeBased) ic, writeContext, (byte) 1 /*enable*/);
73 // Choices&cases are not data objects, so they cannot have a dedicated Reader/Writer
74 // This choice is already from augment, so its not possible to augment augmented choice
75 LOG.error("Unable to handle Interconnection of type {}", ic.getClass());
76 throw new WriteFailedException(id, "Unable to handle Interconnection of type " + ic.getClass());
78 } catch (VppBaseCallException e) {
79 LOG.warn("Failed to update bridge/xconnect based interconnection flags for: {}, interconnection: {}",
81 throw new WriteFailedException(id, "Unable to handle Interconnection of type " + ic.getClass(), e);
85 void deleteInterconnection(final InstanceIdentifier<? extends DataObject> id, final int swIfIndex,
86 final String ifcName, final Interconnection ic, final WriteContext writeContext)
87 throws WriteFailedException {
89 if (ic == null) { // TODO in case of update we should delete interconnection
90 LOG.trace("Interconnection is not set. Skipping");
91 } else if (ic instanceof XconnectBased) {
92 setXconnectBasedL2(id, swIfIndex, ifcName, (XconnectBased) ic, writeContext, (byte) 0 /*disable*/);
93 } else if (ic instanceof BridgeBased) {
94 setBridgeBasedL2(id, swIfIndex, ifcName, (BridgeBased) ic, writeContext, (byte) 0 /*disable*/);
96 LOG.error("Unable to delete Interconnection of type {}", ic.getClass());
97 throw new WriteFailedException(id, "Unable to delete Interconnection of type " + ic.getClass());
99 } catch (VppBaseCallException e) {
100 LOG.warn("Failed to delete bridge/xconnect based interconnection flags for: {}, interconnection: {}",
102 throw new WriteFailedException(id, "Unable to delete Interconnection of type " + ic.getClass(), e);
106 private void setBridgeBasedL2(final InstanceIdentifier<? extends DataObject> id, final int swIfIndex,
107 final String ifcName, final BridgeBased bb,
108 final WriteContext writeContext, final byte enabled)
109 throws VppBaseCallException, WriteTimeoutException {
110 LOG.debug("Setting bridge based interconnection(bridge-domain={}) for interface: {}", bb.getBridgeDomain(),
113 String bdName = bb.getBridgeDomain();
115 int bdId = bridgeDomainContext.getIndex(bdName, writeContext.getMappingContext());
116 checkArgument(bdId > 0, "Unable to set Interconnection for Interface: %s, bridge domain: %s does not exist",
119 byte bvi = bb.isBridgedVirtualInterface()
123 if (bb.getSplitHorizonGroup() != null) {
124 shg = bb.getSplitHorizonGroup().byteValue();
127 final CompletionStage<SwInterfaceSetL2BridgeReply> swInterfaceSetL2BridgeReplyCompletionStage = futureJVppCore
128 .swInterfaceSetL2Bridge(getL2BridgeRequest(swIfIndex, bdId, shg, bvi, enabled));
129 getReplyForWrite(swInterfaceSetL2BridgeReplyCompletionStage.toCompletableFuture(), id);
131 LOG.debug("Bridge based interconnection updated successfully for: {}, interconnection: {}", ifcName, bb);
134 private SwInterfaceSetL2Bridge getL2BridgeRequest(final int swIfIndex, final int bdId, final byte shg,
135 final byte bvi, final byte enabled) {
136 final SwInterfaceSetL2Bridge swInterfaceSetL2Bridge = new SwInterfaceSetL2Bridge();
137 swInterfaceSetL2Bridge.rxSwIfIndex = swIfIndex;
138 swInterfaceSetL2Bridge.bdId = bdId;
139 swInterfaceSetL2Bridge.shg = shg;
140 swInterfaceSetL2Bridge.bvi = bvi;
141 swInterfaceSetL2Bridge.enable = enabled;
142 return swInterfaceSetL2Bridge;
145 private void setXconnectBasedL2(final InstanceIdentifier<? extends DataObject> id, final int swIfIndex,
146 final String ifcName, final XconnectBased ic,
147 final WriteContext writeContext, final byte enabled)
148 throws VppBaseCallException, WriteTimeoutException {
149 String outSwIfName = ic.getXconnectOutgoingInterface();
150 LOG.debug("Setting xconnect based interconnection(outgoing ifc={}) for interface: {}", outSwIfName, ifcName);
152 int outSwIfIndex = interfaceContext.getIndex(outSwIfName, writeContext.getMappingContext());
153 checkArgument(outSwIfIndex > 0,
154 "Unable to set Interconnection for Interface: %s, outgoing interface: %s does not exist",
155 ifcName, outSwIfIndex);
157 final CompletionStage<SwInterfaceSetL2XconnectReply> swInterfaceSetL2XconnectReplyCompletionStage =
159 .swInterfaceSetL2Xconnect(getL2XConnectRequest(swIfIndex, outSwIfIndex, enabled));
160 getReplyForWrite(swInterfaceSetL2XconnectReplyCompletionStage.toCompletableFuture(), id);
161 LOG.debug("Xconnect based interconnection updated successfully for: {}, interconnection: {}", ifcName, ic);
164 private SwInterfaceSetL2Xconnect getL2XConnectRequest(final int rxIfc, final int txIfc,
165 final byte enabled) {
167 final SwInterfaceSetL2Xconnect swInterfaceSetL2Xconnect = new SwInterfaceSetL2Xconnect();
168 swInterfaceSetL2Xconnect.enable = enabled;
169 swInterfaceSetL2Xconnect.rxSwIfIndex = rxIfc;
170 swInterfaceSetL2Xconnect.txSwIfIndex = txIfc;
171 return swInterfaceSetL2Xconnect;