<project.translate.groupId>io.fd.honeycomb</project.translate.groupId>
</properties>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>org.opendaylight.mdsal.model</groupId>
/*
- * Copyright (c) 2015 Cisco and/or its affiliates.
+ * Copyright (c) 2016 Cisco and/or its affiliates.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package lisp;
+package org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.lisp.address.types.rev151105;
import java.util.List;
import java.util.regex.Pattern;
/**
- * Class that checks whether {@link String} can represent Ipv4Address
+ * Class that checks whether {@link String} can represent Ipv4Address.
*/
public final class Ipv4Matcher {
/*
- * Copyright (c) 2015 Cisco and/or its affiliates.
+ * Copyright (c) 2016 Cisco and/or its affiliates.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package lisp;
+package org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.lisp.address.types.rev151105;
import java.util.List;
import java.util.regex.Pattern;
/*
- * Copyright (c) 2015 Cisco and/or its affiliates.
+ * Copyright (c) 2016 Cisco and/or its affiliates.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package lisp;
+package org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.lisp.address.types.rev151105;
import java.util.List;
import java.util.regex.Pattern;
import static com.google.common.base.Preconditions.checkNotNull;
-import lisp.Ipv4Matcher;
-import lisp.Ipv6Matcher;
-import lisp.MacMatcher;
import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv4Address;
import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv6Address;
/**
* The purpose of generated class in src/main/java for Union types is to create new instances of unions from a string representation.
* In some cases it is very difficult to automate it since there can be unions such as (uint32 - uint16), or (string - uint32).
- *
+ * <p/>
* The reason behind putting it under src/main/java is:
* This class is generated in form of a stub and needs to be finished by the user. This class is generated only once to prevent
* loss of user code.
- *
*/
-public class SimpleAddressBuilder {
+public final class SimpleAddressBuilder {
public static SimpleAddress getDefaultInstance(String defaultValue) {
checkNotNull(defaultValue, "Cannot convert null address");
} else if (MacMatcher.matches(defaultValue)) {
return new SimpleAddress(new MacAddress(defaultValue));
} else {
- //TODO - implement other conversions
throw new IllegalArgumentException("Unknown type");
}
}
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://maven.apache.org/POM/4.0.0"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
- <groupId>io.fd.honeycomb.common</groupId>
- <artifactId>impl-parent</artifactId>
+ <groupId>io.fd.honeycomb.vpp</groupId>
+ <artifactId>vpp-impl-parent</artifactId>
<version>1.16.12-SNAPSHOT</version>
- <relativePath>../../common/impl-parent</relativePath>
+ <relativePath>../../vpp-common/vpp-impl-parent</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-core</artifactId>
- <version>16.12-SNAPSHOT</version>
</dependency>
<!-- DI -->
<dependency>
<groupId>com.google.inject</groupId>
<artifactId>guice</artifactId>
- <version>${guice.version}</version>
</dependency>
<dependency>
<groupId>net.jmob</groupId>
<artifactId>guice.conf</artifactId>
- <version>${guice.config.version}</version>
</dependency>
<dependency>
<groupId>com.google.inject.extensions</groupId>
<artifactId>guice-multibindings</artifactId>
- <version>${guice.version}</version>
</dependency>
<!-- Testing Dependencies -->
/**
* Class containing static configuration for Lisp module,<br>
- * either loaded from property file or statically typed
+ * either loaded from property file or statically typed.
*/
@BindConfig(value = "lisp", syntax = Syntax.JSON)
public class LispConfiguration {
- //TODO - this constant should be part of V3po plugin
+ //TODO HONEYCOMB-176 - this constant should be part of V3po plugin
/**
- * Interface index to name mapping
+ * Interface index to name mapping.
*/
public static final String INTERFACE_CONTEXT = "interface-context";
/**
- * Locator set index to name mapping
+ * Locator set index to name mapping.
*/
public static final String LOCATOR_SET_CONTEXT = "locator-set-context";
/**
- * Local mappings's eid to name mapping
+ * Local mappings's eid to name mapping.
*/
public static final String LOCAL_MAPPING_CONTEXT = "local-mapping-context";
/**
- * Remote mappings's eid to name mapping
+ * Remote mappings's eid to name mapping.
*/
public static final String REMOTE_MAPPING_CONTEXT = "remote-mapping-context";
/**
- * Central honeycomb initializer
+ * Central honeycomb initializer.
*/
public static final String HONEYCOMB_INITIALIZER = "honeycomb-initializer";
/**
- * Unique prefix for naming context of interfaces
+ * Unique prefix for naming context of interfaces.
**/
public static final String INTERFACE_CONTEXT_PREFIX = "interface-";
/**
- * Unique prefix for naming context of locator sets
+ * Unique prefix for naming context of locator sets.
**/
public static final String LOCATOR_SET_CONTEXT_PREFIX = "locator-set-";
}
public void readCurrentAttributes(@Nonnull final InstanceIdentifier<Adjacency> id,
@Nonnull final AdjacencyBuilder builder, @Nonnull final ReadContext ctx)
throws ReadFailedException {
- //TODO - finish after https://jira.fd.io/browse/VPP-362
+ // TODO - finish after https://jira.fd.io/browse/VPP-362
throw new ReadFailedException(id, new OperationNotSupportedException("Operation not supported"));
}
}
/**
- * Produces reader for {@link LocatorSets} <br> and all its inhired child readers
+ * Produces reader for {@link LocatorSets} <br> and all its inhired child readers.
*/
public class LocatorSetsReaderFactory extends AbstractLispReaderFactoryBase implements ReaderFactory {
private LocatorSetsReaderFactory(final InstanceIdentifier<LispState> lispStateId,
final FutureJVppCore vppApi,
final NamingContext interfaceContext,
- final NamingContext locatorSetContext
- ) {
+ final NamingContext locatorSetContext) {
super(lispStateId, vppApi);
this.interfaceContext = interfaceContext;
this.locatorSetContext = locatorSetContext;
} else if (address instanceof Mac) {
return MAC;
} else {
- //TODO - other types
throw new IllegalStateException("Unknown type detected");
}
}
case MAC:
return TranslateUtils.parseMac(((Mac) address).getMac().getValue());
default:
- //TODO - other types
throw new IllegalArgumentException("Unsupported type");
}
}
/**
- * Customizer for {@link LocatorSet} entity
+ * Customizer for {@link LocatorSet} entity.
*
* @see LocatorSet
*/
final String locatorSetName = dataAfter.getName();
checkNotNull(locatorSetName, "LocatorSet name is null");
- //TODO check and fill mapping when api returns index of created locator set
+ // TODO VPP-323 check and fill mapping when api returns index of created locator set
// checkState(!locatorSetContext.containsIndex(locatorSetName, writeContext.getMappingContext()),
// "Locator set with name %s allready defined", locatorSetName);
public void updateCurrentAttributes(@Nonnull InstanceIdentifier<LocatorSet> id,
@Nonnull LocatorSet dataBefore,
@Nonnull LocatorSet dataAfter,
- WriteContext writeContext) throws WriteFailedException {
+ @Nonnull WriteContext writeContext) throws WriteFailedException {
throw new UnsupportedOperationException("Operation not supported");
}
new MacAddress("aa:bb:cc:dd:ee:ff"))
.build())
.build()));
-
- //TODO testing of other types when they are implemented
}
}
<prerequisites>
<maven>3.1.1</maven>
</prerequisites>
+
<modules>
<module>api</module>
<module>lisp2vpp</module>
<version>1.16.12-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>org.opendaylight.mdsal.model</groupId>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
- <groupId>io.fd.honeycomb.common</groupId>
- <artifactId>impl-parent</artifactId>
+ <groupId>io.fd.honeycomb.vpp</groupId>
+ <artifactId>vpp-impl-parent</artifactId>
<version>1.16.12-SNAPSHOT</version>
- <relativePath>../../common/impl-parent</relativePath>
+ <relativePath>../../vpp-common/vpp-impl-parent</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>nsh-api</artifactId>
<version>${project.version}</version>
</dependency>
+
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
== Notifications
A sample notification was added to the models to showcase notification capabilities
-
-// TODO provide a groovy version, will be more compact
\ No newline at end of file
<dependency>
<groupId>com.google.inject</groupId>
<artifactId>guice</artifactId>
- <version>${guice.version}</version>
</dependency>
<dependency>
<groupId>net.jmob</groupId>
<artifactId>guice.conf</artifactId>
- <version>${guice.config.version}</version>
</dependency>
<dependency>
<groupId>com.google.inject.extensions</groupId>
<artifactId>guice-multibindings</artifactId>
- <version>${guice.version}</version>
</dependency>
<dependency>
<version>1.16.12-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<!-- Uncomment if iana-if-type model is imported -->
<!--<dependency>-->
<version>1.16.12-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>org.opendaylight.mdsal.model</groupId>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
- <groupId>io.fd.honeycomb.common</groupId>
- <artifactId>impl-parent</artifactId>
+ <groupId>io.fd.honeycomb.vpp</groupId>
+ <artifactId>vpp-impl-parent</artifactId>
<version>1.16.12-SNAPSHOT</version>
- <relativePath>../../common/impl-parent</relativePath>
+ <relativePath>../../vpp-common/vpp-impl-parent</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-core</artifactId>
- <version>16.12-SNAPSHOT</version>
</dependency>
<!-- DI -->
<dependency>
<groupId>com.google.inject</groupId>
<artifactId>guice</artifactId>
- <version>${guice.version}</version>
</dependency>
<dependency>
<groupId>net.jmob</groupId>
<artifactId>guice.conf</artifactId>
- <version>${guice.config.version}</version>
</dependency>
<dependency>
<groupId>com.google.inject.extensions</groupId>
<artifactId>guice-multibindings</artifactId>
- <version>${guice.version}</version>
</dependency>
<!-- Testing Dependencies -->
<version>1.0.8</version>
<scope>test</scope>
</dependency>
-
</dependencies>
</project>
final InstanceIdentifier<Interface2> ifc2AugId = ifcId.augmentation(Interface2.class);
registry.addStructuralReader(ifc2AugId, Interface2Builder.class);
// Ipv4
- // TODO unfinished customizer
final InstanceIdentifier<Ipv4> ipv4Id = ifc2AugId.child(Ipv4.class);
registry.add(new GenericReader<>(ipv4Id, new Ipv4Customizer(jvpp)));
// Address
final InstanceIdentifier<Neighbor> neighborId = ipv4Id.child(Neighbor.class);
registry.add(new GenericListReader<>(neighborId, new Ipv4NeighbourCustomizer(jvpp)));
// Ipv6
- // TODO unfinished customizer
final InstanceIdentifier<Ipv6> ipv6Id = ifc2AugId.child(Ipv6.class);
registry.add(new GenericReader<>(ipv6Id, new Ipv6Customizer(jvpp, ifcCtx)));
}
addVppInterfaceAgmentationWriters(IFC_ID, registry);
// Interface1 (ietf-ip augmentation)
addInterface1AugmentationWriters(IFC_ID, registry);
- // SubinterfaceAugmentation TODO make dedicated module for subIfc writer factory
+ // SubinterfaceAugmentation
new SubinterfaceAugmentationWriterFactory(jvpp, aclWriter, ifcContext, bdContext, classifyTableContext).init(registry);
}
private void addInterface1AugmentationWriters(final InstanceIdentifier<Interface> ifcId,
final ModifiableWriterRegistryBuilder registry) {
final InstanceIdentifier<Interface1> ifc1AugId = ifcId.augmentation(Interface1.class);
- // Ipv6(after interface) TODO unfinished customizer =
+ // Ipv6(after interface) =
registry.addAfter(new GenericWriter<>(ifc1AugId.child(Ipv6.class), new Ipv6Customizer(jvpp)),
ifcId);
// Ipv4(after interface)
final Set<InstanceIdentifier<?>> specificIfcTypes = Sets.newHashSet(vhostId, vxlanGpeId, vxlanGpeId, tapId);
- // Ethernet(No dependency, customizer not finished TODO) =
+ // Ethernet =
registry.add(new GenericWriter<>(VPP_IFC_AUG_ID.child(Ethernet.class), new EthernetCustomizer(jvpp)));
// Routing(Execute only after specific interface customizers) =
registry.addAfter(
// Subinterfaces
// Subinterface(Handle only after all interface related stuff gets processed) =
registry.subtreeAddAfter(
- // TODO this customizer covers quite a lot of complex child nodes (maybe refactor ?)
+ // TODO HONEYCOMB-188 this customizer covers quite a lot of complex child nodes (maybe refactor ?)
Sets.newHashSet(
InstanceIdentifier.create(SubInterface.class).child(Tags.class),
InstanceIdentifier.create(SubInterface.class).child(Tags.class).child(Tag.class),
install(ConfigurationModule.create());
requestInjection(V3poConfiguration.class);
+ // TODO HONEYCOMB-173 put into constants
// Naming contexts
bind(NamingContext.class)
.annotatedWith(Names.named("interface-context"))
registry.addStructuralReader(vppStateId, VppStateBuilder.class);
// Version
// Wrap with keepalive reader to detect connection issues
- // TODO keepalive reader wrapper relies on VersionReaderCustomizer (to perform timeout on reads)
- // Once readers+customizers are asynchronous, pull the timeout to keepalive executor so that keepalive wrapper
- // is truly generic
+ // Relying on VersionCustomizer to provide a "timing out read"
registry.add(new KeepaliveReaderWrapper<>(
new GenericReader<>(vppStateId.child(Version.class), new VersionCustomizer(jVpp)),
keepaliveExecutor, ReadTimeoutException.class, 30,
- // FIXME-minimal trigger jvpp reinitialization here
+ // FIXME HONEYCOMB-78 trigger jvpp reinitialization here
() -> LOG.error("Keepalive failed. VPP is probably DOWN!")));
// BridgeDomains(Structural)
final InstanceIdentifier<BridgeDomains> bridgeDomainsId = vppStateId.child(BridgeDomains.class);
return interfacesBuilder.build();
}
- // FIXME https://jira.fd.io/browse/HONEYCOMB-73 this kind of initialization/transformation is bad
+ // TODO https://jira.fd.io/browse/HONEYCOMB-73 this kind of initialization/transformation is bad
// There is no relation to readers, it cannot be extended (readers can) and its hard to keep in sync with readers
- // TODO add IP v4/ v6 initializer
-
private static Interface initialize(
final org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface input) {
InterfaceBuilder builder = new InterfaceBuilder();
builder.setName(input.getName());
builder.setType(input.getType());
builder.setEnabled(AdminStatus.Up.equals(input.getAdminStatus()));
- // builder.setLinkUpDownTrapEnable(); TODO not present in interfaces-state
+ // Not present in interfaces-state
+ // builder.setLinkUpDownTrapEnable();
initializeVppInterfaceStateAugmentation(input, builder);
SubInterfaceInitializationUtils.initializeSubinterfaceStateAugmentation(input, builder);
setAcl(augmentBuilder, acl);
}
- // TODO set routing, not present in interface-state
+ // Routing is not present in interface-state. Doing nothing for it
builder.addAugmentation(VppInterfaceAugmentation.class, augmentBuilder.build());
}
augmentBuilder.setIpv4(new Ipv4Builder().setAddress(collect).setNeighbor(neighbors).build());
}
- // TODO ipv6
-
builder.addAugmentation(Interface1.class, augmentBuilder.build());
}
}
final org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.ip.rev140616.interfaces.state._interface.ipv4.address.Subnet
subnet = address.getSubnet();
- // TODO only prefix length supported
+ // Only prefix length supported
Preconditions.checkArgument(
subnet instanceof org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.ip.rev140616.interfaces.state._interface.ipv4.address.subnet.PrefixLength);
super(bindingDataBroker, InstanceIdentifier.create(VppState.class), InstanceIdentifier.create(Vpp.class));
}
- // TODO move to v3po2vpp
-
@Override
protected Vpp convert(final VppState operationalData) {
LOG.debug("VppInitializer.convert()");
public void writeCurrentAttributes(@Nonnull final InstanceIdentifier<Ethernet> id,
@Nonnull final Ethernet dataAfter, @Nonnull final WriteContext writeContext)
throws WriteFailedException {
- // TODO
LOG.warn("Unsupported, ignoring configuration {}", dataAfter);
// VPP API does not support setting MTU
}
public void updateCurrentAttributes(@Nonnull final InstanceIdentifier<Ethernet> id,
@Nonnull final Ethernet dataBefore, @Nonnull final Ethernet dataAfter,
@Nonnull final WriteContext writeContext) {
- // TODO
LOG.warn("Unsupported, ignoring configuration {}", dataAfter);
}
@Override
public void deleteCurrentAttributes(@Nonnull final InstanceIdentifier<Ethernet> id,
@Nonnull final Ethernet dataBefore, @Nonnull final WriteContext writeContext) {
- // TODO
LOG.warn("Unsupported, ignoring configuration delete {}", id);
}
}
} else if (ic instanceof BridgeBased) {
setBridgeBasedL2(id, swIfIndex, ifcName, (BridgeBased) ic, writeContext, (byte) 1 /*enable*/);
} else {
- // FIXME how does choice extensibility work
- // FIXME it is not even possible to create a dedicated customizer for Interconnection, since it's not a DataObject
- // FIXME we might need a choice customizer
- // THis choice is already from augment, so its probably not possible to augment augmented choice
+ // Choices&cases are not data objects, so they cannot have a dedicated Reader/Writer
+ // This choice is already from augment, so its not possible to augment augmented choice
LOG.error("Unable to handle Interconnection of type {}", ic.getClass());
throw new WriteFailedException(id, "Unable to handle Interconnection of type " + ic.getClass());
}
public void deleteCurrentAttributes(@Nonnull final InstanceIdentifier<Interface> id,
@Nonnull final Interface dataBefore,
@Nonnull final WriteContext writeContext) {
-
- // TODO Handle deletes
+ // Nothing to be done here, customizers for specific interface types e.g. vxlan handle the delete
}
private void setInterface(final InstanceIdentifier<Interface> id, final Interface swIf,
final String ifcName = id.firstKeyOf(Interface.class).getName();
final int swIfc = interfaceContext.getIndex(ifcName, writeContext.getMappingContext());
- // TODO handle update properly (if possible)
+ // No update, again calling set
setL2(id, swIfc, ifcName, dataAfter, writeContext);
}
final String ifName = id.firstKeyOf(Interface.class).getName();
try {
- // TODO handle updates properly
setRouting(id, ifName, dataAfter, writeContext);
} catch (VppBaseCallException e) {
LOG.warn("Failed to update routing for interface: {}, {}, vxlan: {}", ifName, writeContext, dataAfter);
@Override
public void deleteCurrentAttributes(@Nonnull final InstanceIdentifier<Routing> id,
@Nonnull final Routing dataBefore, @Nonnull final WriteContext writeContext) {
- // TODO implement delete
+ // TODO HONEYCOMB-176 implement delete
}
private void setRouting(final InstanceIdentifier<Routing> id, final String name, final Routing rt,
import io.fd.honeycomb.translate.v3po.util.WriteTimeoutException;
import io.fd.honeycomb.translate.write.WriteContext;
import io.fd.honeycomb.translate.write.WriteFailedException;
-import java.util.Objects;
+import java.util.List;
import java.util.concurrent.CompletionStage;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
}
private CreateSubif getCreateSubifRequest(@Nonnull final SubInterface subInterface, final int swIfIndex) {
- // TODO add validation
+ // TODO HONEYCOMB-183 add validation
CreateSubif request = new CreateSubif();
request.subId = Math.toIntExact(subInterface.getIdentifier().intValue());
request.swIfIndex = swIfIndex;
}
request.dot1Ad = booleanToByte(_802dot1ad.class == subInterface.getVlanType());
- final MatchType matchType = subInterface.getMatch().getMatchType(); // todo match should be mandatory
+ // TODO HONEYCOMB-183 match should be mandatory
+ final MatchType matchType = subInterface.getMatch().getMatchType();
request.exactMatch =
booleanToByte(matchType instanceof VlanTagged && ((VlanTagged) matchType).isMatchExactTags());
request.defaultSub = booleanToByte(matchType instanceof Default);
@Nonnull final SubInterface dataBefore, @Nonnull final SubInterface dataAfter,
@Nonnull final WriteContext writeContext)
throws WriteFailedException {
- if (Objects.equals(dataBefore.isEnabled(), dataAfter.isEnabled())) {
- LOG.debug("No state update will be performed. Ignoring config");
- return; // TODO shouldn't we throw exception here (if there will be dedicated L2 customizer)?
- }
final String subIfaceName = getSubInterfaceName(id.firstKeyOf(Interface.class).getName(),
Math.toIntExact(dataAfter.getIdentifier()));
try {
final String subInterfaceName = getSubInterfaceName(id);
final int subInterfaceIndex = interfaceContext.getIndex(subInterfaceName, writeContext.getMappingContext());
- // TODO handle update properly (if possible)
+ // Setting L2 to new values
setL2(id, subInterfaceIndex, subInterfaceName, dataAfter, writeContext);
}
CreateVhostUserIf request = new CreateVhostUserIf();
request.isServer = TranslateUtils.booleanToByte(VhostUserRole.Server.equals(vhostUser.getRole()));
request.sockFilename = vhostUser.getSocket().getBytes();
- request.renumber = 0; // TODO
- request.customDevInstance = 0; // TODO
+ // TODO HONEYCOMB-177 expose device instance attribute just like for TAP
+ request.renumber = 0;
+ request.customDevInstance = 0;
request.useCustomMac = 0;
request.macAddress = new byte[]{};
return request;
ModifyVhostUserIf request = new ModifyVhostUserIf();
request.isServer = TranslateUtils.booleanToByte(VhostUserRole.Server.equals(vhostUser.getRole()));
request.sockFilename = vhostUser.getSocket().getBytes();
- request.renumber = 0; // TODO
- request.customDevInstance = 0; // TODO
+ // TODO HONEYCOMB-177
+ request.renumber = 0;
+ request.customDevInstance = 0;
request.swIfIndex = swIfIndex;
return request;
}
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-// TODO extract common code from all Interface type specific writer customizers into a superclass
public class VxlanCustomizer extends AbstractInterfaceTypeCustomizer<Vxlan> {
private static final Logger LOG = LoggerFactory.getLogger(VxlanCustomizer.class);
/**
* Base writer for translation of ietf-acl model ACEs to VPP's classify tables and sessions.
- *
+ * <p/>
* Creates one classify table with single session per ACE.
*
* @param <T> type of access control list entry
*/
abstract class AbstractAceWriter<T extends AceType> implements AceWriter {
- // TODO: minimise memory used by classify tables (we create a lot of them to make ietf-acl model
+ // TODO: HONEYCOMB-181 minimise memory used by classify tables (we create a lot of them to make ietf-acl model
// mapping more convenient):
// according to https://wiki.fd.io/view/VPP/Introduction_To_N-tuple_Classifiers#Creating_a_classifier_table,
// classify table needs 16*(1 + match_n_vectors) bytes, but this does not quite work, so setting 8K for now
// filter ACE entries and group by AceType
final Map<AclType, List<Ace>> acesByType = acls.stream()
.flatMap(acl -> aclToAceStream(acl, writeContext))
- // TODO we should not tolerate nulls, but throw some meaningful exceptions instead
- .filter(ace -> ace != null && ace.getMatches() != null && ace.getMatches().getAceType() != null &&
- ace.getActions() != null && ace.getActions().getPacketHandling() != null)
.collect(Collectors.groupingBy(AclType::fromAce));
final InputAclSetInterface request = new InputAclSetInterface();
@Nonnull
private static AclType fromAce(final Ace ace) {
AclType result = null;
- final AceType aceType = ace.getMatches().getAceType();
- if (aceType instanceof AceEth) {
- result = ETH;
- } else if (aceType instanceof AceIp) {
- final AceIpVersion aceIpVersion = ((AceIp) aceType).getAceIpVersion();
- if (aceIpVersion instanceof AceIpv4) {
- result = IP4;
- } else {
- result = IP6;
+ final AceType aceType;
+ try {
+ aceType = ace.getMatches().getAceType();
+ if (aceType instanceof AceEth) {
+ result = ETH;
+ } else if (aceType instanceof AceIp) {
+ final AceIpVersion aceIpVersion = ((AceIp) aceType).getAceIpVersion();
+ if (aceIpVersion instanceof AceIpv4) {
+ result = IP4;
+ } else {
+ result = IP6;
+ }
}
+ } catch (NullPointerException e) {
+ throw new IllegalArgumentException("Incomplete ACE: " + ace, e);
}
if (result == null) {
throw new IllegalArgumentException(String.format("Not supported ace type %s", aceType));
} else if (subnet instanceof Netmask) {
setNetmaskSubnet(add, id, interfaceName, interfaceIndex, address, (Netmask) subnet);
} else {
- // FIXME how does choice extensibility work
- // FIXME it is not even possible to create a dedicated
- // customizer for Interconnection, since it's not a DataObject
- // FIXME we might need a choice customizer
- // THis choice is already from augment, so its probably not
- // possible to augment augmented choice
LOG.error("Unable to handle subnet of type {}", subnet.getClass());
throw new WriteFailedException(id, "Unable to handle subnet of type " + subnet.getClass());
}
throws WriteFailedException {
final String ifcName = id.firstKeyOf(Interface.class).getName();
- // TODO handle update in a better way
+ // TODO HONEYCOMB-180 handle update in a better way
setIpv4(id, ifcName, dataAfter, writeContext);
}
@Override
public void deleteCurrentAttributes(@Nonnull final InstanceIdentifier<Ipv4> id,
@Nonnull final Ipv4 dataBefore, @Nonnull final WriteContext writeContext) {
- // TODO implement delete
+ // TODO HONEYCOMB-180 implement delete
}
private void setIpv4(final InstanceIdentifier<Ipv4> id, final String name, final Ipv4 ipv4,
final int swIfc = interfaceContext.getIndex(name, writeContext.getMappingContext());
LOG.warn("Ignoring Ipv4 leaf nodes (create/update is not supported)");
- // TODO add support for enabled leaf
- // TODO add support for forwarding leaf
- // TODO add support for mtu leaf
+ // TODO HONEYCOMB-180 add support for:
+ // enabled leaf
+ // forwarding leaf
+ // mtu leaf
}
}
/**
- * Customizer for writing {@link Neighbor} for {@link Ipv4}
+ * Customizer for writing {@link Neighbor} for {@link Ipv4}.
*/
public class Ipv4NeighbourCustomizer extends FutureJVppCustomizer
implements ListWriterCustomizer<Neighbor, NeighborKey> {
request.macAddress = TranslateUtils.parseMac(data.getLinkLayerAddress().getValue());
request.swIfIndex = parentInterfaceIndex;
- //TODO if it is necessary for future use ,make adjustments to be able to set vrfid
+ //TODO HONEYCOMB-182 if it is necessary for future use ,make adjustments to be able to set vrfid
//request.vrfId
TranslateUtils.getReplyForWrite(getFutureJVpp().ipNeighborAddDel(request).toCompletableFuture(), id);
}
/**
* Utility class providing Ipv4 CUD support.
*/
-// TODO replace with interface with default methods or abstract class
+// TODO HONEYCOMB-175 replace with interface with default methods or abstract class
final class Ipv4WriteUtils {
private static final int DOTTED_QUAD_MASK_LENGTH = 4;
@Override
public void writeCurrentAttributes(@Nonnull final InstanceIdentifier<Ipv6> id,
@Nonnull final Ipv6 dataAfter, @Nonnull final WriteContext writeContext) {
- // TODO
LOG.warn("Unsupported, ignoring configuration {}", dataAfter);
}
public void deleteCurrentAttributes(@Nonnull final InstanceIdentifier<Ipv6> id,
@Nonnull final Ipv6 dataBefore, @Nonnull final WriteContext writeContext) {
LOG.warn("Unsupported, ignoring configuration delete {}", id);
- // TODO
}
}
} else if (subnet instanceof Netmask) {
setNetmaskSubnet(add, id, interfaceName, subInterfaceIndex, address, (Netmask) subnet);
} else {
- // FIXME how does choice extensibility work
- // FIXME it is not even possible to create a dedicated
- // customizer for Interconnection, since it's not a DataObject
- // FIXME we might need a choice customizer
- // THis choice is already from augment, so its probably not
- // possible to augment augmented choice
LOG.error("Unable to handle subnet of type {}", subnet.getClass());
throw new WriteFailedException(id, "Unable to handle subnet of type " + subnet.getClass());
}
/**
* Utility class providing Interconnection read support.
*/
-// FIXME this should be customizer, but it is not possible because Interconnection is not a DataObject
final class InterconnectionReadUtils {
private static final Logger LOG = LoggerFactory.getLogger(InterconnectionReadUtils.class);
}
return bbBuilder.build();
}
- // TODO is there a way to check if interconnection is XconnectBased?
+ // TODO HONEYCOMB-190 is there a way to check if interconnection is XconnectBased?
return null;
}
throws ReadFailedException {
try {
// We need to perform full bd dump, because there is no way
- // to ask VPP for BD details given interface id/name (TODO add it to vpp.api?)
- // TODO cache dump result
+ // to ask VPP for BD details given interface id/name (TODO HONEYCOMB-190 add it to vpp.api?)
+ // TODO HONEYCOMB-190 cache dump result
final BridgeDomainDump request = new BridgeDomainDump();
request.bdId = -1;
sb.append(HEX_CHARS[v & 15]);
}
- // TODO rename and move to V3poUtils
-
/**
* Reads first 6 bytes of supplied byte array and converts to string as Yang dictates <p> Replace later with
* https://git.opendaylight.org/gerrit/#/c/34869/10/model/ietf/ietf-type- util/src/main/
public class ProxyArpCustomizer extends FutureJVppCustomizer
implements ReaderCustomizer<ProxyArp,
- org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.interfaces.
- state._interface.ProxyArpBuilder> {
+ org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.interfaces.state._interface.ProxyArpBuilder> {
private static final Logger LOG = LoggerFactory.getLogger(ProxyArpCustomizer.class);
private final NamingContext interfaceContext;
.rev150105.interfaces.state._interface.ProxyArpBuilder builder,
@Nonnull ReadContext ctx) throws ReadFailedException {
- //TODO: Implement fully when VPP Proxy ARP read API is available
- // https://jira.fd.io/browse/VPP-225
+ //TODO: VPP-225 Implement fully when VPP Proxy ARP read API is available
final InterfaceKey key = id.firstKeyOf(Interface.class);
final int index = interfaceContext.getIndex(key.getName(), ctx.getMappingContext());
LOG.warn("Reading of ARP data not (yet) supported by VPP API");
final String ifaceName = key.getName();
final int ifaceId = interfaceContext.getIndex(ifaceName, context.getMappingContext());
- // TODO if we know that full dump was already performed we could use cache
+ // TODO HONEYCOMB-189 if we know that full dump was already performed we could use cache
// (checking if getCachedInterfaceDump() returns non empty map is not enough, because
// we could be part of particular iface state read
final SwInterfaceDump request = new SwInterfaceDump();
@Override
public void readCurrentAttributes(@Nonnull final InstanceIdentifier<Ipv4> id, @Nonnull final Ipv4Builder builder,
@Nonnull final ReadContext ctx) throws ReadFailedException {
- //TODO add reading of isForwarding flag when there is dump for it
+ //TODO HONEYCOMB-180 add reading of isForwarding flag when there is dump for it
LOG.warn("Operation not supported");
}
// Many VPP APIs do not provide get operation for single item. Dump requests for all items are used instead.
// To improve HC performance, caching dump requests is a common pattern.
- // TODO: use more generic caching implementation, once provided
+ // TODO: HONEYCOMB-102 use more generic caching implementation, once provided
static Optional<IpAddressDetailsReplyDump> dumpAddresses(@Nonnull final FutureJVppCore futureJVppCore,
@Nonnull final InstanceIdentifier<?> id,
@Nonnull final String interfaceName,
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+
package io.fd.honeycomb.translate.v3po.interfacesstate.ip;
import io.fd.honeycomb.translate.read.ReadContext;
@Override
public void readCurrentAttributes(@Nonnull final InstanceIdentifier<Ipv6> id, @Nonnull final Ipv6Builder builder,
@Nonnull final ReadContext ctx) throws ReadFailedException {
- // TODO implement
+ // TODO HONEYCOMB-102 implement
// final IpAddressDump dumpRequest = new IpAddressDump();
// dumpRequest.isIpv6 = 1;
-// dumpRequest.swIfIndex = interfaceContext.getIndex(id.firstKeyOf(Interface.class).getName(), ctx.getMappingContext());
-// final CompletionStage<IpAddressDetailsReplyDump> addressDumpFuture = getFutureJVpp().ipAddressDump(dumpRequest);
- // TODO consider extracting customizer for address
+// dumpRequest.swIfIndex = interfaceContext.getIndex(id.firstKeyOf(Interface.class).getName(),
+// ctx.getMappingContext());
+// final CompletionStage<IpAddressDetailsReplyDump> addressDumpFuture = getFutureJVpp().
+// ipAddressDump(dumpRequest);
// final IpAddressDetailsReplyDump reply = TranslateUtils.getReply(addressDumpFuture.toCompletableFuture());
}
notificationListenerReg = jvpp.getNotificationRegistry().registerSwInterfaceSetFlagsNotificationCallback(
swInterfaceSetFlagsNotification -> {
LOG.trace("Interface notification received: {}", swInterfaceSetFlagsNotification);
- // TODO this should be lazy
+ // TODO HONEYCOMB-166 this should be lazy
collector.onNotification(transformNotification(swInterfaceSetFlagsNotification));
}
);
* data tree (write transaction is still in progress and context changes have not been committed yet, or
* VPP sends the notification before it returns create request(that would store mapping)).
* <p/>
- * In case mapping is not available, index is used as name. TODO inconsistent behavior, maybe just use indices ?
+ * In case mapping is not available, index is used as name.
*/
private InterfaceNameOrIndex getIfcName(final SwInterfaceSetFlagsNotification swInterfaceSetFlagsNotification) {
final Optional<String> optionalName =
final IpAddress ipAddress = entry.getIpAddress();
if (ipAddress.getIpv6Address() != null) {
- // FIXME: vpp does not support ipv6 in arp-termination table (based on analysis of l2_bd.c)
+ // FIXME: HONEYCOMB-187 vpp does not support ipv6 in arp-termination table (based on analysis of l2_bd.c)
throw new UnsupportedOperationException("IPv6 address for ARP termination table is not supported yet");
}
import com.google.common.base.Preconditions;
import io.fd.honeycomb.translate.spi.write.ListWriterCustomizer;
import io.fd.honeycomb.translate.v3po.util.FutureJVppCustomizer;
-import io.fd.honeycomb.translate.v3po.util.WriteTimeoutException;
-import io.fd.honeycomb.translate.write.WriteContext;
import io.fd.honeycomb.translate.v3po.util.NamingContext;
import io.fd.honeycomb.translate.v3po.util.TranslateUtils;
+import io.fd.honeycomb.translate.v3po.util.WriteTimeoutException;
+import io.fd.honeycomb.translate.write.WriteContext;
import io.fd.honeycomb.translate.write.WriteFailedException;
import javax.annotation.Nonnull;
+import javax.annotation.concurrent.GuardedBy;
import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.vpp.bridge.domains.BridgeDomain;
import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.vpp.bridge.domains.BridgeDomainKey;
import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
private static final byte ADD_OR_UPDATE_BD = (byte) 1;
private final NamingContext bdContext;
+ @GuardedBy("this")
+ private int bridgeDomainIndexCounter = 1;
public BridgeDomainCustomizer(@Nonnull final FutureJVppCore futureJVppCore, @Nonnull final NamingContext bdContext) {
super(futureJVppCore);
LOG.debug("writeCurrentAttributes: id={}, current={}, ctx={}", id, dataBefore, ctx);
final String bdName = dataBefore.getName();
- try {
- int index;
- if (bdContext.containsIndex(bdName, ctx.getMappingContext())) {
- index = bdContext.getIndex(bdName, ctx.getMappingContext());
- } else {
- // FIXME we need the bd index to be returned by VPP or we should have a counter field
- // (maybe in context similar to artificial name)
- // Here we assign the next available ID from bdContext's perspective
- index = 1;
- while (bdContext.containsName(index, ctx.getMappingContext())) {
- index++;
+ // Invoke 1. check index, 2. increase index 3. create ND 4. store mapping in a synchronized block to prevent
+ // race conditions in case of concurrent invocation
+ synchronized (this) {
+ try {
+ int index;
+ if (bdContext.containsIndex(bdName, ctx.getMappingContext())) {
+ index = bdContext.getIndex(bdName, ctx.getMappingContext());
+ } else {
+ // Critical section due to bridgeDomainIndexCounter read and write access
+ // TODO HONEYCOMB-199 move this "get next available index" into naming context or an adapter
+ // or a dedicated object
+
+ // Use counter to assign bridge domain index, but still check naming context if it's not taken there
+ while (bdContext.containsName(bridgeDomainIndexCounter, ctx.getMappingContext())) {
+ bridgeDomainIndexCounter++;
+ }
+ index = bridgeDomainIndexCounter;
}
+ addOrUpdateBridgeDomain(id, index, dataBefore);
+ bdContext.addName(index, bdName, ctx.getMappingContext());
+ } catch (VppBaseCallException e) {
+ LOG.warn("Failed to create bridge domain", e);
+ throw new WriteFailedException.CreateFailedException(id, dataBefore, e);
}
- addOrUpdateBridgeDomain(id, index, dataBefore);
- bdContext.addName(index, bdName, ctx.getMappingContext());
- } catch (VppBaseCallException e) {
- LOG.warn("Failed to create bridge domain", e);
- throw new WriteFailedException.CreateFailedException(id, dataBefore, e);
}
}
private OpaqueIndex readOpaqueIndex(final int opaqueIndex) {
// We first try to map the value to a vpp node, if that fails, simply wrap the u32 value
- // FIXME: the approach might fail if the opaqueIndex contains small value that collides
+ // TODO: HONEYCOMB-118 the approach might fail if the opaqueIndex contains small value that collides
// with some of the adjacent nodes
final VppNode node = readVppNode(opaqueIndex, LOG);
if (node != null) {
@Nonnull
@Override
public List<BridgeDomainKey> getAllIds(@Nonnull final InstanceIdentifier<BridgeDomain> id,
- @Nonnull final ReadContext context) {
+ @Nonnull final ReadContext context) throws ReadFailedException {
final BridgeDomainDump request = new BridgeDomainDump();
request.bdId = -1; // dump call
try {
reply = getFutureJVpp().bridgeDomainDump(request).toCompletableFuture().get();
} catch (Exception e) {
- throw new IllegalStateException("Bridge domain dump failed", e); // TODO ReadFailedException?
+ throw new ReadFailedException(id, e);
}
if (reply == null || reply.bridgeDomainDetails == null) {
LOG.debug("Reading L2 FIB entry: key={}. bridgeDomainKey={}, bdId={}", key, bridgeDomainKey, bdId);
try {
- // TODO use cached l2FibTable
+ // TODO HONEYCOMB-186 use cached l2FibTable
final L2FibTableEntry entry = dumpL2Fibs(id, bdId).stream().filter(e -> key.getPhysAddress()
.equals(new PhysAddress(vppPhysAddrToYang(Longs.toByteArray(e.mac), 2))))
.collect(SINGLE_ITEM_COLLECTOR);
initMocks(this);
InterfaceTypeTestUtils.setupWriteContext(writeContext,
org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.GreTunnel.class);
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
NamingContext namingContext = new NamingContext("generateInterfaceNAme", "test-instance");
final ModificationCache toBeReturned = new ModificationCache();
doReturn(toBeReturned).when(writeContext).getModificationCache();
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.doReturn;
-import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.MockitoAnnotations.initMocks;
import com.google.common.base.Optional;
-import io.fd.honeycomb.translate.v3po.test.ContextTestUtils;
-import io.fd.honeycomb.translate.write.WriteContext;
import io.fd.honeycomb.translate.MappingContext;
+import io.fd.honeycomb.translate.v3po.test.ContextTestUtils;
import io.fd.honeycomb.translate.v3po.test.TestHelperUtils;
import io.fd.honeycomb.translate.v3po.util.NamingContext;
+import io.fd.honeycomb.translate.write.WriteContext;
import io.fd.honeycomb.translate.write.WriteFailedException;
import java.util.Arrays;
import java.util.List;
initMocks(this);
namingContext = new NamingContext("generatedSubInterfaceName", "test-instance");
doReturn(mappingContext).when(writeContext).getMappingContext();
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
customizer = new SubInterfaceCustomizer(api, namingContext);
doReturn(ContextTestUtils.getMapping(SUPER_IF_NAME, SUPER_IF_ID)).when(mappingContext)
.read(ContextTestUtils.getMappingIid(SUPER_IF_NAME, "test-instance"));
verifySwInterfaceSetFlagsWasInvoked(generateSwInterfaceEnableRequest(SUBIF_INDEX));
}
- @Test
- public void testUpdateNoStateChange() throws Exception {
- final List<Tag> tags = Arrays.asList(STAG_100, CTAG_200);
- final SubInterface before = generateSubInterface(false, tags);
- final SubInterface after = generateSubInterface(false, tags);
- customizer.updateCurrentAttributes(null, before, after, writeContext);
-
- verify(api, never()).swInterfaceSetFlags(any());
- }
-
@Test(expected = UnsupportedOperationException.class)
public void testDelete() throws Exception {
final SubInterface subInterface = generateSubInterface(false, Arrays.asList(STAG_100, CTAG_200));
doReturn(toBeReturned).when(writeContext).getModificationCache();
doReturn(mappingContext).when(writeContext).getMappingContext();
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
customizer = new VhostUserCustomizer(api, namingContext);
}
initMocks(this);
InterfaceTypeTestUtils.setupWriteContext(writeContext,
org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.VxlanTunnel.class);
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
NamingContext namingContext = new NamingContext("generateInterfaceNAme", "test-instance");
final ModificationCache toBeReturned = new ModificationCache();
doReturn(toBeReturned).when(writeContext).getModificationCache();
initMocks(this);
InterfaceTypeTestUtils.setupWriteContext(writeContext,
org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.v3po.rev150105.VxlanGpeTunnel.class);
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
NamingContext namingContext = new NamingContext("generateInterfaceNAme", "test-instance");
final ModificationCache toBeReturned = new ModificationCache();
doReturn(toBeReturned).when(writeContext).getModificationCache();
return new InterfaceCustomizer(api, interfacesContext);
}
- // TODO use reflexion and move to ListReaderCustomizerTest
@Test
public void testMerge() throws Exception {
final InterfacesStateBuilder builder = mock(InterfacesStateBuilder.class);
private void verifySwInterfaceDumpWasInvoked(final int nameFilterValid, final String ifaceName,
final int dumpIfcsInvocationCount)
throws VppInvocationException {
- // TODO adding equals methods for jvpp DTOs would make ArgumentCaptor usage obsolete
+ // TODO HONEYCOMB-185 adding equals methods for jvpp DTOs would make ArgumentCaptor usage obsolete
ArgumentCaptor<SwInterfaceDump> argumentCaptor = ArgumentCaptor.forClass(SwInterfaceDump.class);
verify(api, times(dumpIfcsInvocationCount)).swInterfaceDump(argumentCaptor.capture());
final SwInterfaceDump actual = argumentCaptor.getValue();
@Before
public void setUp() throws Exception {
initMocks(this);
- // TODO create base class for tests using vppApi
+ // TODO HONEYCOMB-116 create base class for tests using vppApi
NamingContext namingContext = new NamingContext("generatedBDName", "test-instance");
final ModificationCache toBeReturned = new ModificationCache();
doReturn(toBeReturned).when(ctx).getModificationCache();
final byte learn = BridgeDomainTestUtils.booleanToByte(bd.isLearn());
final byte uuf = BridgeDomainTestUtils.booleanToByte(bd.isUnknownUnicastFlood());
- // TODO adding equals methods for jvpp DTOs would make ArgumentCaptor usage obsolete
+ // TODO HONEYCOMB-185 adding equals methods for jvpp DTOs would make ArgumentCaptor usage obsolete
ArgumentCaptor<BridgeDomainAddDel> argumentCaptor = ArgumentCaptor.forClass(BridgeDomainAddDel.class);
verify(api).bridgeDomainAddDel(argumentCaptor.capture());
final BridgeDomainAddDel actual = argumentCaptor.getValue();
import com.google.common.base.Optional;
import com.google.common.collect.Iterables;
import com.google.common.collect.Multimap;
+import io.fd.honeycomb.translate.MappingContext;
import io.fd.honeycomb.translate.ModificationCache;
import io.fd.honeycomb.translate.impl.read.GenericListReader;
import io.fd.honeycomb.translate.read.ReadContext;
-import io.fd.honeycomb.translate.v3po.test.ContextTestUtils;
-import io.fd.honeycomb.translate.MappingContext;
+import io.fd.honeycomb.translate.read.ReadFailedException;
import io.fd.honeycomb.translate.read.registry.ReaderRegistry;
+import io.fd.honeycomb.translate.v3po.test.ContextTestUtils;
import io.fd.honeycomb.translate.v3po.util.NamingContext;
import java.util.Arrays;
import java.util.Collections;
read.get());
}
- @Test(expected = IllegalArgumentException.class)
+ @Test(expected = ReadFailedException.class)
public void testReadBridgeDomainNotExisting() throws Exception {
doReturn(Optional.absent()).when(mappingContext).read(
ContextTestUtils.getMappingIid("NOT EXISTING", "bd-test-instance"));
final InstanceIdentifier<VppState> vppStateId = InstanceIdentifier.create(VppState.class);
registry.addStructuralReader(vppStateId, VppStateBuilder.class);
// Version
- // Wrap with keepalive reader to detect connection issues
- // TODO keepalive reader wrapper relies on VersionReaderCustomizer (to perform timeout on reads)
- // Once readers+customizers are asynchronous, pull the timeout to keepalive executor so that keepalive wrapper
- // is truly generic
registry.add(new GenericReader<>(vppStateId.child(Version.class), new VersionCustomizer(jVpp)));
// BridgeDomains(Structural)
bridgeDomainsId = vppStateId.child(BridgeDomains.class);
<properties>
<main.class>io.fd.honeycomb.vpp.distro.Main</main.class>
<honeycomb.min.distro.version>1.16.12-SNAPSHOT</honeycomb.min.distro.version>
+ <jvpp.version>16.12-SNAPSHOT</jvpp.version>
</properties>
<build>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-registry</artifactId>
- <version>16.12-SNAPSHOT</version>
+ <version>${jvpp.version}</version>
</dependency>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-core</artifactId>
- <version>16.12-SNAPSHOT</version>
+ <version>${jvpp.version}</version>
</dependency>
<dependency>
<groupId>${project.groupId}</groupId>
<version>1.16.12-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
</project>
<groupId>io.fd.honeycomb.vpp</groupId>
<artifactId>naming-context-impl</artifactId>
<version>1.16.12-SNAPSHOT</version>
+ <packaging>bundle</packaging>
<dependencies>
<dependency>
<version>${project.version}</version>
</dependency>
</dependencies>
-
- <packaging>bundle</packaging>
-
-
-
</project>
<module>naming-context-api</module>
<module>naming-context-impl</module>
<module>minimal-distribution</module>
+ <module>vpp-impl-parent</module>
</modules>
<!-- DO NOT install or deploy the repo root pom as it's only needed to initiate a build -->
<build>
--- /dev/null
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- vi: set et smarttab sw=4 tabstop=4: -->
+<!--
+ Copyright (c) 2015 Cisco and/or its affiliates.
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at:
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <parent>
+ <groupId>io.fd.honeycomb.common</groupId>
+ <artifactId>impl-parent</artifactId>
+ <version>1.16.12-SNAPSHOT</version>
+ <relativePath>../../common/impl-parent</relativePath>
+ </parent>
+
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>io.fd.honeycomb.vpp</groupId>
+ <artifactId>vpp-impl-parent</artifactId>
+ <version>1.16.12-SNAPSHOT</version>
+ <properties>
+ <jvpp.version>16.12-SNAPSHOT</jvpp.version>
+ </properties>
+ <packaging>pom</packaging>
+
+ <dependencyManagement>
+ <dependencies>
+ <dependency>
+ <groupId>io.fd.vpp</groupId>
+ <artifactId>jvpp-core</artifactId>
+ <version>${jvpp.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>io.fd.vpp</groupId>
+ <artifactId>jvpp-registry</artifactId>
+ <version>${jvpp.version}</version>
+ </dependency>
+ </dependencies>
+ </dependencyManagement>
+</project>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
- <groupId>io.fd.honeycomb.common</groupId>
- <artifactId>impl-parent</artifactId>
+ <groupId>io.fd.honeycomb.vpp</groupId>
+ <artifactId>vpp-impl-parent</artifactId>
<version>1.16.12-SNAPSHOT</version>
- <relativePath>../../common/impl-parent</relativePath>
+ <relativePath>../../vpp-common/vpp-impl-parent</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<version>1.16.12-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>0.8.2-Beryllium-SR2</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
+ <properties>
+ <commons.codec.version>1.9</commons.codec.version>
+ </properties>
<dependencies>
<dependency>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-registry</artifactId>
- <version>16.12-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>io.fd.vpp</groupId>
<artifactId>jvpp-core</artifactId>
- <version>16.12-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.opendaylight.mdsal.model</groupId>
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
- <version>1.9</version>
+ <version>${commons.codec.version}</version>
</dependency>
- <!-- Testing Dependencies -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<artifactId>mockito-all</artifactId>
<scope>test</scope>
</dependency>
-
</dependencies>
-
</project>
/**
* Validation WriteCustomizers for Interface subnodes.
* Validates the type of interface.
- *
- * TODO this should be validated on model/DataTree level. However DataTree does not enforce When conditions
- * Delete this class when DataTree handles when constraints properly
*/
public abstract class AbstractInterfaceTypeCustomizer<D extends DataObject>
extends FutureJVppCustomizer implements WriterCustomizer<D> {
import javax.annotation.Nullable;
/**
- * Defines vlan tag rewrite config options for VPP
- *
- * TODO corresponding enum (defined in l2_vtr.h) should be defined in vpe.api
+ * Defines vlan tag rewrite config options for VPP.
+ * <p/>
+ * TODO HONEYCOMB-184 corresponding enum (defined in l2_vtr.h) should be defined in vpe.api
* (does vpp's IDL support enum type definition?)
* which would allow to generate this class in jvpp
*/
translate_2_to_1(2),
translate_2_to_2(2);
- private final static int MAX_INDEX = 3;
+ private static final int MAX_INDEX = 3;
private final int code;
private final byte popTags;
@Nullable
public static TagRewriteOperation get(@Nonnegative final int code) {
for (TagRewriteOperation operation : TagRewriteOperation.values()) {
- if (code == operation.code){
+ if (code == operation.code) {
return operation;
}
}
<prerequisites>
<maven>3.1.1</maven>
</prerequisites>
+
<modules>
<module>minimal-distribution</module>
</modules>
+
<!-- DO NOT install or deploy the repo root pom as it's only needed to initiate a build -->
<build>
<plugins>