use of org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.mapping.record.container.MappingRecord.Action in project netvirt by opendaylight.
the class ElanUtils method buildLocalDmacFlowEntry.
/**
* Builds the flow to be programmed in the DMAC table of the local DPN (that
* is, where the MAC is attached to). This flow consists in:
*
* <p>Match: + elanTag in metadata + packet goes to a MAC locally attached
* Actions: + optionally, pop-vlan + set-vlan-id + output to ifName's
* portNumber
*
* @param elanTag
* the elan tag
* @param dpId
* the dp id
* @param ifName
* the if name
* @param macAddress
* the mac address
* @param elanInfo
* the elan info
* @param ifTag
* the if tag
* @return the flow
*/
public Flow buildLocalDmacFlowEntry(long elanTag, BigInteger dpId, String ifName, String macAddress, ElanInstance elanInfo, long ifTag) {
List<MatchInfo> mkMatches = new ArrayList<>();
mkMatches.add(new MatchMetadata(ElanHelper.getElanMetadataLabel(elanTag), MetaDataUtil.METADATA_MASK_SERVICE));
mkMatches.add(new MatchEthernetDestination(new MacAddress(macAddress)));
List<Instruction> mkInstructions = new ArrayList<>();
List<Action> actions = getEgressActionsForInterface(ifName, /* tunnelKey */
null);
mkInstructions.add(MDSALUtil.buildApplyActionsInstruction(actions));
Flow flow = MDSALUtil.buildFlowNew(NwConstants.ELAN_DMAC_TABLE, getKnownDynamicmacFlowRef(NwConstants.ELAN_DMAC_TABLE, dpId, ifTag, macAddress, elanTag), 20, elanInfo.getElanInstanceName(), 0, 0, ElanConstants.COOKIE_ELAN_KNOWN_DMAC.add(BigInteger.valueOf(elanTag)), mkMatches, mkInstructions);
return flow;
}
use of org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.mapping.record.container.MappingRecord.Action in project netvirt by opendaylight.
the class VrfEntryListener method manageRemoteRouteOnDPN.
public void manageRemoteRouteOnDPN(final boolean action, final BigInteger localDpnId, final long vpnId, final String rd, final String destPrefix, final String destTepIp, final long label) {
final VpnInstanceOpDataEntry vpnInstance = fibUtil.getVpnInstance(rd);
if (vpnInstance == null) {
LOG.error("VpnInstance for rd {} not present for prefix {}", rd, destPrefix);
return;
}
jobCoordinator.enqueueJob(FibUtil.getJobKeyForVpnIdDpnId(vpnId, localDpnId), () -> Collections.singletonList(txRunner.callWithNewWriteOnlyTransactionAndSubmit(tx -> {
synchronized (vpnInstance.getVpnInstanceName().intern()) {
VrfTablesKey vrfTablesKey = new VrfTablesKey(rd);
VrfEntry vrfEntry = getVrfEntry(dataBroker, rd, destPrefix);
if (vrfEntry == null) {
return;
}
LOG.trace("manageRemoteRouteOnDPN :: action {}, DpnId {}, vpnId {}, rd {}, destPfx {}", action, localDpnId, vpnId, rd, destPrefix);
List<RoutePaths> routePathList = vrfEntry.getRoutePaths();
VrfEntry modVrfEntry;
if (routePathList == null || routePathList.isEmpty()) {
modVrfEntry = FibHelper.getVrfEntryBuilder(vrfEntry, label, Collections.singletonList(destTepIp), RouteOrigin.value(vrfEntry.getOrigin()), null).build();
} else {
modVrfEntry = vrfEntry;
}
if (action) {
LOG.trace("manageRemoteRouteOnDPN updated(add) vrfEntry :: {}", modVrfEntry);
createRemoteFibEntry(localDpnId, vpnId, vrfTablesKey.getRouteDistinguisher(), modVrfEntry, tx);
} else {
LOG.trace("manageRemoteRouteOnDPN updated(remove) vrfEntry :: {}", modVrfEntry);
List<String> usedRds = VpnExtraRouteHelper.getUsedRds(dataBroker, vpnInstance.getVpnId(), vrfEntry.getDestPrefix());
if (usedRds.size() > 1) {
LOG.debug("The extra route prefix is still present in some DPNs");
return;
}
// Is this fib route an extra route? If yes, get the nexthop which would be
// an adjacency in the vpn
Optional<Routes> extraRouteOptional = Optional.absent();
if (usedRds.size() != 0) {
extraRouteOptional = VpnExtraRouteHelper.getVpnExtraroutes(dataBroker, fibUtil.getVpnNameFromId(vpnInstance.getVpnId()), usedRds.get(0), vrfEntry.getDestPrefix());
}
baseVrfEntryHandler.deleteRemoteRoute(null, localDpnId, vpnId, vrfTablesKey, modVrfEntry, extraRouteOptional, tx);
}
}
})));
}
use of org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.mapping.record.container.MappingRecord.Action in project netvirt by opendaylight.
the class BaseVrfEntryHandler method addTunnelInterfaceActions.
protected void addTunnelInterfaceActions(AdjacencyResult adjacencyResult, long vpnId, VrfEntry vrfEntry, List<ActionInfo> actionInfos, String rd) {
Class<? extends TunnelTypeBase> tunnelType = VpnExtraRouteHelper.getTunnelType(nextHopManager.getInterfaceManager(), adjacencyResult.getInterfaceName());
if (tunnelType == null) {
LOG.debug("Tunnel type not found for vrfEntry {}", vrfEntry);
return;
}
// TODO - For now have added routePath into adjacencyResult so that we know for which
// routePath this result is built for. If this is not possible construct a map which does
// the same.
String nextHopIp = adjacencyResult.getNextHopIp();
java.util.Optional<Long> optionalLabel = FibUtil.getLabelForNextHop(vrfEntry, nextHopIp);
if (!optionalLabel.isPresent()) {
LOG.warn("NextHopIp {} not found in vrfEntry {}", nextHopIp, vrfEntry);
return;
}
long label = optionalLabel.get();
BigInteger tunnelId = null;
Prefixes prefixInfo = null;
// revisit
if (tunnelType.equals(TunnelTypeVxlan.class)) {
prefixInfo = fibUtil.getPrefixToInterface(vpnId, vrfEntry.getDestPrefix());
// For extra route, the prefixInfo is fetched from the primary adjacency
if (prefixInfo == null) {
prefixInfo = fibUtil.getPrefixToInterface(vpnId, adjacencyResult.getPrefix());
}
// Internet VPN VNI will be used as tun_id for NAT use-cases
if (Prefixes.PrefixCue.Nat.equals(prefixInfo.getPrefixCue())) {
if (vrfEntry.getL3vni() != null && vrfEntry.getL3vni() != 0) {
tunnelId = BigInteger.valueOf(vrfEntry.getL3vni());
}
} else {
if (fibUtil.enforceVxlanDatapathSemanticsforInternalRouterVpn(prefixInfo.getSubnetId(), vpnId, rd)) {
java.util.Optional<Long> optionalVni = fibUtil.getVniForVxlanNetwork(prefixInfo.getSubnetId());
if (!optionalVni.isPresent()) {
LOG.error("VNI not found for nexthop {} vrfEntry {} with subnetId {}", nextHopIp, vrfEntry, prefixInfo.getSubnetId());
return;
}
tunnelId = BigInteger.valueOf(optionalVni.get());
} else {
tunnelId = BigInteger.valueOf(label);
}
}
} else {
tunnelId = BigInteger.valueOf(label);
}
LOG.debug("adding set tunnel id action for label {}", label);
actionInfos.add(new ActionSetFieldTunnelId(tunnelId));
addRewriteDstMacAction(vpnId, vrfEntry, prefixInfo, actionInfos);
}
use of org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.mapping.record.container.MappingRecord.Action in project netvirt by opendaylight.
the class EvpnVrfEntryHandler method createRemoteFibEntry.
private void createRemoteFibEntry(final BigInteger remoteDpnId, final long vpnId, final VrfTablesKey vrfTableKey, final VrfEntry vrfEntry, boolean isNatPrefix, WriteTransaction tx) {
String rd = vrfTableKey.getRouteDistinguisher();
List<SubTransaction> subTxns = new ArrayList<>();
LOG.debug("createremotefibentry: adding route {} for rd {} with transaction {}", vrfEntry.getDestPrefix(), rd, tx);
List<NexthopManager.AdjacencyResult> tunnelInterfaceList = resolveAdjacency(remoteDpnId, vpnId, vrfEntry, rd);
if (tunnelInterfaceList.isEmpty()) {
LOG.error("Could not get interface for route-paths: {} in vpn {}", vrfEntry.getRoutePaths(), rd);
LOG.warn("Failed to add Route: {} in vpn: {}", vrfEntry.getDestPrefix(), rd);
return;
}
for (NexthopManager.AdjacencyResult adjacencyResult : tunnelInterfaceList) {
List<ActionInfo> actionInfos = new ArrayList<>();
BigInteger tunnelId;
String prefix = adjacencyResult.getPrefix();
Prefixes prefixInfo = getFibUtil().getPrefixToInterface(vpnId, prefix);
String interfaceName = prefixInfo.getVpnInterfaceName();
if (vrfEntry.getOrigin().equals(RouteOrigin.BGP.getValue()) || isNatPrefix) {
tunnelId = BigInteger.valueOf(vrfEntry.getL3vni());
} else if (elanManager.isOpenStackVniSemanticsEnforced()) {
tunnelId = BigInteger.valueOf(getFibUtil().getVniForVxlanNetwork(prefixInfo.getSubnetId()).get());
} else {
Interface interfaceState = getFibUtil().getInterfaceStateFromOperDS(interfaceName);
tunnelId = BigInteger.valueOf(interfaceState.getIfIndex());
}
LOG.debug("adding set tunnel id action for label {}", tunnelId);
String macAddress = null;
String vpnName = getFibUtil().getVpnNameFromId(vpnId);
if (vpnName == null) {
LOG.debug("Failed to get VPN name for vpnId {}", vpnId);
return;
}
if (interfaceName != null) {
macAddress = getFibUtil().getMacAddressFromPrefix(interfaceName, vpnName, prefix);
actionInfos.add(new ActionSetFieldEthernetDestination(new MacAddress(macAddress)));
}
actionInfos.add(new ActionSetFieldTunnelId(tunnelId));
List<ActionInfo> egressActions = nexthopManager.getEgressActionsForInterface(adjacencyResult.getInterfaceName(), actionInfos.size());
if (egressActions.isEmpty()) {
LOG.error("Failed to retrieve egress action for prefix {} route-paths {} interface {}." + " Aborting remote FIB entry creation..", vrfEntry.getDestPrefix(), vrfEntry.getRoutePaths(), adjacencyResult.getInterfaceName());
return;
}
actionInfos.addAll(egressActions);
List<InstructionInfo> instructions = new ArrayList<>();
instructions.add(new InstructionApplyActions(actionInfos));
makeConnectedRoute(remoteDpnId, vpnId, vrfEntry, rd, instructions, NwConstants.ADD_FLOW, tx, subTxns);
}
LOG.debug("Successfully added FIB entry for prefix {} in rd {}", vrfEntry.getDestPrefix(), rd);
}
use of org.opendaylight.yang.gen.v1.urn.opendaylight.lfm.lisp.proto.rev151105.mapping.record.container.MappingRecord.Action in project netvirt by opendaylight.
the class ElanServiceTestBase method sortActions.
org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.Instruction sortActions(org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.Instruction input) {
if (input instanceof ApplyActionsCase) {
List<Action> action = new ArrayList<>(((ApplyActionsCase) input).getApplyActions().getAction());
Collections.sort(action, (o1, o2) -> o1.getOrder().compareTo(o2.getOrder()));
ApplyActions actions = new ApplyActionsBuilder().setAction(action).build();
return new ApplyActionsCaseBuilder().setApplyActions(actions).build();
}
return null;
}
Aggregations