.tox/
nbactions.xml
nb-configuration.xml
+.fbExcludeFilterFile
+.factorypath
<build>
<plugins>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
@Override
public void run() {
- readFlowsX(dpnCount, flowsPerDpn, verbose);
+ readFlowsX();
}
- private void readFlowsX(Integer dpnCount, Integer flowsPerDPN, boolean verbose) {
+ private void readFlowsX() {
readOpStatus.set(FlowCounter.OperationStatus.IN_PROGRESS.status());
for (int i = 1; i <= dpnCount; i++) {
String dpId = BulkOMaticUtils.DEVICE_TYPE_PREFIX + i;
- for (int j = 0; j < flowsPerDPN; j++) {
+ for (int j = 0; j < flowsPerDpn; j++) {
short tableRollover = (short) (endTableId - startTableId + 1);
short tableId = (short) (j % tableRollover + startTableId);
LOG.info("Using Sequential implementation of Flow Writer.");
}
- public void addFlows(Integer dpnCount, Integer flowsPerDPN, int batchSize, int sleepMillis, short startTableId,
+ public void addFlows(Integer count, Integer flowsPerDPN, int batchSize, int sleepMillis, short startTableId,
short endTableId, boolean isCreateParents) {
LOG.info("Using Sequential implementation of Flow Writer.");
- this.dpnCount = dpnCount;
- countDpnWriteCompletion.set(dpnCount);
+ this.dpnCount = count;
+ countDpnWriteCompletion.set(count);
startTime = System.nanoTime();
- for (int i = 1; i <= dpnCount; i++) {
+ for (int i = 1; i <= count; i++) {
FlowHandlerTask task = new FlowHandlerTask(Integer.toString(i), flowsPerDPN, true, batchSize, sleepMillis,
startTableId, endTableId, isCreateParents);
flowPusher.execute(task);
}
}
- public void deleteFlows(Integer dpnCount, Integer flowsPerDPN, int batchSize, short startTableId,
+ public void deleteFlows(Integer count, Integer flowsPerDPN, int batchSize, short startTableId,
short endTableId) {
LOG.info("Using Sequential implementation of Flow Writer.");
- countDpnWriteCompletion.set(dpnCount);
- for (int i = 1; i <= dpnCount; i++) {
+ countDpnWriteCompletion.set(count);
+ for (int i = 1; i <= count; i++) {
FlowHandlerTask task = new FlowHandlerTask(Integer.toString(i), flowsPerDPN, false, batchSize, 0,
startTableId, endTableId, false);
flowPusher.execute(task);
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.concurrent.Future;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
public void onFailure(Throwable throwable) {
LOG.error("Stale Flow creation failed {}", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.Collection;
.listenInPoolThread(salBundleService.addBundleMessages(addBundleMessagesInput));
}
return Futures.immediateFuture(null);
- });
+ }, MoreExecutors.directExecutor());
ListenableFuture<RpcResult<Void>> commitBundleFuture = Futures.transformAsync(addBundleMessagesFuture,
rpcResult -> {
if (rpcResult.isSuccessful()) {
.listenInPoolThread(salBundleService.controlBundle(commitBundleInput));
}
return Futures.immediateFuture(null);
- });
+ }, MoreExecutors.directExecutor());
/* Bundles not supported for meters */
List<Meter> meters = flowNode.get().getMeter() != null ? flowNode.get().getMeter()
}
}
return Futures.immediateFuture(null);
- });
+ }, MoreExecutors.directExecutor());
trans.close();
try {
+ ", id=" + groupId;
LOG.debug(msg, cause);
}
- });
+ }, MoreExecutors.directExecutor());
map.put(groupId, future);
}
public void onFailure(Throwable throwable) {
LOG.debug("Stale entity removal failed {}", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
}
private Flow getDeleteAllFlow() {
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.concurrent.Future;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.DataTreeIdentifier;
public void onFailure(Throwable throwable) {
LOG.error("Stale Group creation failed {}", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
}
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.concurrent.Future;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.DataTreeIdentifier;
public void onFailure(Throwable throwable) {
LOG.error("Stale Meter creation failed {}", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
}
private InstanceIdentifier<org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819
</dependency>
<dependency>
- <groupId>org.codehaus.sonar-plugins.java</groupId>
+ <groupId>org.sonarsource.java</groupId>
<artifactId>sonar-jacoco-listeners</artifactId>
<version>${sonar-jacoco-listeners.version}</version>
<scope>test</scope>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.Objects;
import java.util.concurrent.Semaphore;
import java.util.concurrent.TimeUnit;
LOG.debug("Syncup guard acquired and running for {} ", nodeId.getValue());
}
final ListenableFuture<Boolean> endResult = delegate.syncup(flowcapableNodePath, syncupEntry);
- Futures.addCallback(endResult, createSyncupCallback(guard, stampBeforeGuard, stampAfterGuard, nodeId));
+ Futures.addCallback(endResult, createSyncupCallback(guard, stampBeforeGuard, stampAfterGuard, nodeId),
+ MoreExecutors.directExecutor());
return endResult;
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
if (LOG.isDebugEnabled()) {
Futures.addCallback(JdkFutureAdapters.listenInPoolThread(rpcResultFuture),
- createCounterCallback(batchBag, batchOrder, counters));
+ createCounterCallback(batchBag, batchOrder, counters), MoreExecutors.directExecutor());
}
return Futures.transform(JdkFutureAdapters.listenInPoolThread(rpcResultFuture),
ReconcileUtil.<ProcessFlatBatchOutput>createRpcResultToVoidFunction("flat-batch"));
}
- });
+ }, MoreExecutors.directExecutor());
return resultVehicle;
}
import com.google.common.util.concurrent.AsyncFunction;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.ListenableFuture;
import java.util.ArrayList;
import java.util.Collections;
}
return addMissingGroups(nodeId, nodeIdent, diffInput.getGroupsToAddOrUpdate(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingGroups"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingGroups"),
+ MoreExecutors.directExecutor());
resultVehicle = Futures.transformAsync(resultVehicle, new AsyncFunction<RpcResult<Void>, RpcResult<Void>>() {
@Override
public ListenableFuture<RpcResult<Void>> apply(final RpcResult<Void> input) throws Exception {
}
return addMissingMeters(nodeId, nodeIdent, diffInput.getMetersToAddOrUpdate(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingMeters"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingMeters"),
+ MoreExecutors.directExecutor());
resultVehicle = Futures.transformAsync(resultVehicle, new AsyncFunction<RpcResult<Void>, RpcResult<Void>>() {
@Override
public ListenableFuture<RpcResult<Void>> apply(final RpcResult<Void> input) throws Exception {
}
return addMissingFlows(nodeId, nodeIdent, diffInput.getFlowsToAddOrUpdate(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingFlows"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "addMissingFlows"),
+ MoreExecutors.directExecutor());
resultVehicle = Futures.transformAsync(resultVehicle, new AsyncFunction<RpcResult<Void>, RpcResult<Void>>() {
}
return removeRedundantFlows(nodeId, nodeIdent, diffInput.getFlowsToRemove(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantFlows"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantFlows"),
+ MoreExecutors.directExecutor());
resultVehicle = Futures.transformAsync(resultVehicle, new AsyncFunction<RpcResult<Void>, RpcResult<Void>>() {
@Override
public ListenableFuture<RpcResult<Void>> apply(final RpcResult<Void> input) throws Exception {
}
return removeRedundantMeters(nodeId, nodeIdent, diffInput.getMetersToRemove(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantMeters"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantMeters"),
+ MoreExecutors.directExecutor());
resultVehicle = Futures.transformAsync(resultVehicle, new AsyncFunction<RpcResult<Void>, RpcResult<Void>>() {
@Override
public ListenableFuture<RpcResult<Void>> apply(final RpcResult<Void> input) throws Exception {
}
return removeRedundantGroups(nodeId, nodeIdent, diffInput.getGroupsToRemove(), counters);
}
- });
- Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantGroups"));
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(resultVehicle, FxChainUtil.logResultCallback(nodeId, "removeRedundantGroups"),
+ MoreExecutors.directExecutor());
return resultVehicle;
}
final ListenableFuture<RpcResult<Void>> singleVoidResult = Futures.transform(
Futures.allAsList(allResults), ReconcileUtil.<RemoveFlowOutput>createRpcResultCondenser("flow remove"));
return Futures.transformAsync(singleVoidResult,
- ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService));
+ ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService),
+ MoreExecutors.directExecutor());
}
return result;
}
- });
+ }, MoreExecutors.directExecutor());
}
} catch (IllegalStateException e) {
chainedResult = RpcResultBuilder.<Void>failed()
ReconcileUtil.<RemoveGroupOutput>createRpcResultCondenser("group remove"));
return Futures.transformAsync(singleVoidResult,
- ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService));
+ ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService),
+ MoreExecutors.directExecutor());
}
ListenableFuture<RpcResult<Void>> updateTableFeatures(final InstanceIdentifier<FlowCapableNode> nodeIdent,
ReconcileUtil.<UpdateTableOutput>createRpcResultCondenser("table update"));
return Futures.transformAsync(singleVoidResult,
- ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService));
+ ReconcileUtil.chainBarrierFlush(PathUtil.digNodePath(nodeIdent), transactionService),
+ MoreExecutors.directExecutor());
}
private ListenableFuture<RpcResult<Void>> flushAddGroupPortionAndBarrier(
return Futures.transformAsync(summaryResult, ReconcileUtil.chainBarrierFlush(
- PathUtil.digNodePath(nodeIdent), transactionService));
+ PathUtil.digNodePath(nodeIdent), transactionService), MoreExecutors.directExecutor());
}
ListenableFuture<RpcResult<Void>> addMissingMeters(final NodeId nodeId,
return result;
}
- });
+ }, MoreExecutors.directExecutor());
}
} else {
chainedResult = RpcResultBuilder.<Void>success().buildFuture();
import com.google.common.base.Splitter;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.ArrayList;
import java.util.Arrays;
public void testChainBarrierFlush() throws Exception {
SettableFuture<RpcResult<Void>> testRabbit = SettableFuture.create();
final ListenableFuture<RpcResult<Void>> vehicle =
- Futures.transformAsync(testRabbit, ReconcileUtil.chainBarrierFlush(NODE_IDENT, flowCapableService));
+ Futures.transformAsync(testRabbit, ReconcileUtil.chainBarrierFlush(NODE_IDENT, flowCapableService),
+ MoreExecutors.directExecutor());
Mockito.when(flowCapableService.sendBarrier(barrierInputCaptor.capture()))
.thenReturn(RpcResultBuilder.<Void>success().buildFuture());
<propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
</project>
}
}
- /**
- * {@inheritDoc}
- */
@Override
public void nodeConnectorAdded(final InstanceIdentifier<NodeConnector> nodeConnectorInstanceId,
final FlowCapableNodeConnector flowConnector) {
packetProcessingService.transmitPacket(packet);
}
- /**
- * {@inheritDoc}
- */
@Override
public void nodeConnectorRemoved(final InstanceIdentifier<NodeConnector> nodeConnectorInstanceId) {
nodeConnectorMap.remove(nodeConnectorInstanceId);
private static final Logger LOG = LoggerFactory.getLogger(LLDPUtil.class);
private static final String OF_URI_PREFIX = "openflow:";
+ private LLDPUtil() {
+ }
+
static byte[] buildLldpFrame(final NodeId nodeId, final NodeConnectorId nodeConnectorId, final MacAddress src,
final Long outPortNo, final MacAddress destinationAddress) {
// Create discovery pkt
/**
* Helper methods that are used by multiple tests.
*/
-public class TestUtils {
+public final class TestUtils {
+ private TestUtils() {
+ }
+
static InstanceIdentifier<NodeConnector> createNodeConnectorId(String nodeKey, String nodeConnectorKey) {
return InstanceIdentifier.builder(Nodes.class)
.child(Node.class, new NodeKey(new NodeId(nodeKey)))
<propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
</project>
/**
* Method to initialize NotificationProviderConfig.
*/
- private NotificationProviderConfig initializeNotificationProviderConfig(boolean flowSupp, boolean meterSupp,
- boolean groupSupp,
- boolean connectorStatSupp,
- boolean flowStatSupp,
- boolean flowTableStatSupp,
- boolean meterStatSupp,
- boolean groupStatSupp,
- boolean queueStatSupp) {
+ private NotificationProviderConfig initializeNotificationProviderConfig(boolean hasFlowSupp,
+ boolean hasMeterSupp,
+ boolean hasGroupSupp,
+ boolean hasConnectorStatSupp,
+ boolean hasFlowStatSupp,
+ boolean hasFlowTableStatSupp,
+ boolean hasMeterStatSupp,
+ boolean hasGroupStatSupp,
+ boolean hasQueueStatSupp) {
NotificationProviderConfig.NotificationProviderConfigBuilder notif
= new NotificationProviderConfig.NotificationProviderConfigBuilder();
- notif.setFlowSupport(flowSupp);
- notif.setMeterSupport(meterSupp);
- notif.setGroupSupport(groupSupp);
- notif.setNodeConnectorStatSupport(connectorStatSupp);
- notif.setFlowStatSupport(flowStatSupp);
- notif.setFlowTableStatSupport(flowTableStatSupp);
- notif.setMeterStatSupport(meterStatSupp);
- notif.setGroupStatSupport(groupStatSupp);
- notif.setQueueStatSupport(queueStatSupp);
+ notif.setFlowSupport(hasFlowSupp);
+ notif.setMeterSupport(hasMeterSupp);
+ notif.setGroupSupport(hasGroupSupp);
+ notif.setNodeConnectorStatSupport(hasConnectorStatSupp);
+ notif.setFlowStatSupport(hasFlowStatSupp);
+ notif.setFlowTableStatSupport(hasFlowTableStatSupp);
+ notif.setMeterStatSupport(hasMeterStatSupp);
+ notif.setGroupStatSupport(hasGroupStatSupp);
+ notif.setQueueStatSupport(hasQueueStatSupp);
return notif.build();
}
/**
* Class is designed as ConfigSubsystem settings holder.
*/
-public class NotificationProviderConfig {
+public final class NotificationProviderConfig {
private final boolean flowSupport;
private final boolean meterSupport;
public class NotificationProviderTest {
private NotificationProviderService notificationProviderService;
- private NotificationProviderConfig config;
private DataBroker dataBroker;
@Before
}
@Test
- public void testCreateAllSuppliers() {
+ public void testCreateAllSuppliers() throws Exception {
final NotificationProviderConfig config = createAllConfigSupplier();
- final NotificationProvider provider = new NotificationProvider(notificationProviderService, dataBroker,
- config.isFlowSupport(), config.isMeterSupport(),
- config.isGroupSupport(),
- config.isNodeConnectorStatSupport(),
- config.isFlowStatSupport(),
- config.isFlowTableStatSupport(),
- config.isMeterStatSupport(),
- config.isGroupStatSupport(),
- config.isQueueStatSupport());
- provider.start();
- final List<NotificationSupplierDefinition<?>> listSuppliers = provider.getSupplierList();
- int nrOfSuppliers = 0;
- for (final NotificationSupplierDefinition<?> supplier : listSuppliers) {
- if (supplier != null) {
- nrOfSuppliers++;
+ try (NotificationProvider provider = new NotificationProvider(notificationProviderService, dataBroker,
+ config.isFlowSupport(), config.isMeterSupport(), config.isGroupSupport(),
+ config.isNodeConnectorStatSupport(), config.isFlowStatSupport(), config.isFlowTableStatSupport(),
+ config.isMeterStatSupport(), config.isGroupStatSupport(), config.isQueueStatSupport())) {
+ provider.start();
+ final List<NotificationSupplierDefinition<?>> listSuppliers = provider.getSupplierList();
+ int nrOfSuppliers = 0;
+ for (final NotificationSupplierDefinition<?> supplier : listSuppliers) {
+ if (supplier != null) {
+ nrOfSuppliers++;
+ }
}
+ assertEquals(11, nrOfSuppliers);
}
- assertEquals(11, nrOfSuppliers);
}
@Test
import java.util.Collection;
import java.util.Collections;
-public class TestChangeEventBuildHelper {
+public final class TestChangeEventBuildHelper {
private TestChangeEventBuildHelper() {
throw new UnsupportedOperationException("Test utility class");
import org.opendaylight.controller.md.sal.binding.api.DataTreeChangeListener;
import org.opendaylight.controller.md.sal.binding.api.DataTreeIdentifier;
-public class TestSupplierVerifyHelper {
+public final class TestSupplierVerifyHelper {
private TestSupplierVerifyHelper() {
throw new UnsupportedOperationException("Test utility class");
<scope>test</scope>
</dependency>
</dependencies>
-
- <build>
- <plugins>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
- </plugins>
- </build>
</project>
<packaging>pom</packaging>
<build>
- <pluginManagement>
- <plugins>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
- </plugins>
- </pluginManagement>
<plugins>
<plugin>
<groupId>org.apache.felix</groupId>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
*/
public class GetRegisteredServices extends OsgiCommandSupport {
private static final Logger LOG = LoggerFactory.getLogger(GetRegisteredServices.class);
- public static final String CLI_FORMAT = "%d %-20s ";
+ private static final String CLI_FORMAT = "%d %-20s ";
private ReconciliationManager reconciliationManager;
import com.google.common.collect.ImmutableMap;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
public class ReconciliationManagerImpl implements ReconciliationManager, ReconciliationFrameworkEvent {
private static final Logger LOG = LoggerFactory.getLogger(ReconciliationManagerImpl.class);
- private MastershipChangeServiceManager mastershipChangeServiceManager;
- private Map<Integer, List<ReconciliationNotificationListener>> registeredServices = new ConcurrentSkipListMap<>();
- private Map<DeviceInfo, ListenableFuture<ResultState>> futureMap = new ConcurrentHashMap<>();
- private Map<ResultState, Integer> resultStateMap = new ConcurrentHashMap<>();
- private AtomicReference<ResultState> decidedResultState = new AtomicReference<>(ResultState.DONOTHING);
+ private final MastershipChangeServiceManager mastershipChangeServiceManager;
+ private final Map<Integer, List<ReconciliationNotificationListener>> registeredServices =
+ new ConcurrentSkipListMap<>();
+ private final Map<DeviceInfo, ListenableFuture<ResultState>> futureMap = new ConcurrentHashMap<>();
+ private final Map<ResultState, Integer> resultStateMap = new ConcurrentHashMap<>();
+ private final AtomicReference<ResultState> decidedResultState = new AtomicReference<>(ResultState.DONOTHING);
public ReconciliationManagerImpl(MastershipChangeServiceManager mastershipChangeServiceManager) {
this.mastershipChangeServiceManager = Preconditions
List<ReconciliationNotificationListener>
servicesForPriority,
DeviceInfo node) {
- return Futures.transformAsync(prevFuture, prevResult -> {
- return Futures.transform(Futures.allAsList(
- servicesForPriority.stream().map(service -> service.startReconciliation(node))
- .collect(Collectors.toList())), results -> decidedResultState.get());
- });
+ return Futures.transformAsync(prevFuture, prevResult -> Futures.transform(Futures.allAsList(
+ servicesForPriority.stream().map(service -> service.startReconciliation(node))
+ .collect(Collectors.toList())), results -> decidedResultState.get(),
+ MoreExecutors.directExecutor()),
+ MoreExecutors.directExecutor());
}
private ListenableFuture<Void> cancelNodeReconciliation(DeviceInfo node) {
List<ReconciliationNotificationListener>
servicesForPriority,
DeviceInfo node) {
- return Futures.transformAsync(prevFuture, prevResult -> {
- return Futures.transform(Futures.allAsList(
- servicesForPriority.stream().map(service -> service.endReconciliation(node))
- .collect(Collectors.toList())), results -> null);
- });
+ return Futures.transformAsync(prevFuture, prevResult -> Futures.transform(Futures.allAsList(
+ servicesForPriority.stream().map(service -> service.endReconciliation(node))
+ .collect(Collectors.toList())), results -> null, MoreExecutors.directExecutor()),
+ MoreExecutors.directExecutor());
}
}
\ No newline at end of file
public class ReconciliationServiceDelegate implements NotificationRegistration {
- private ReconciliationNotificationListener reconciliationNotificationListener;
- private AutoCloseable unregisterService;
+ private final ReconciliationNotificationListener reconciliationNotificationListener;
+ private final AutoCloseable unregisterService;
public ReconciliationServiceDelegate(ReconciliationNotificationListener reconciliationNotificationListener,
AutoCloseable unregisterService) {
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-public class ShellUtil {
+public final class ShellUtil {
private static final Logger LOG = LoggerFactory.getLogger(ShellUtil.class);
public static final String NODE_PREFIX = "openflow:";
+ private ShellUtil() {
+ }
+
public static List<OFNode> getAllNodes(final DataBroker broker) {
List<Node> nodes = null;
ReadOnlyTransaction tx = broker.newReadOnlyTransaction();
}
return ofNode;
}
-}
\ No newline at end of file
+}
<propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
</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">
<modelVersion>4.0.0</modelVersion>
<parent>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>binding-parent</artifactId>
- <version>0.12.0-SNAPSHOT</version>
- <relativePath/>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-parent</artifactId>
+ <version>0.6.0-SNAPSHOT</version>
+ <relativePath>../../parent</relativePath>
</parent>
<groupId>org.opendaylight.openflowplugin.applications</groupId>
<artifactId>topology-lldp-discovery</artifactId>
<version>0.6.0-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.openflowplugin</groupId>
- <artifactId>openflowplugin-artifacts</artifactId>
- <version>${project.version}</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>mdsal-artifacts</artifactId>
- <version>1.7.0-SNAPSHOT</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>liblldp</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
+ <dependency>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-api</artifactId>
+ </dependency>
<dependency>
<groupId>org.opendaylight.openflowplugin.model</groupId>
<artifactId>model-flow-base</artifactId>
package org.opendaylight.openflowplugin.applications.topology.lldp;
import org.opendaylight.controller.sal.binding.api.NotificationProviderService;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfig;
import org.opendaylight.yangtools.concepts.ListenerRegistration;
import org.opendaylight.yangtools.yang.binding.NotificationListener;
import org.slf4j.Logger;
private final ListenerRegistration<NotificationListener> lldpNotificationRegistration;
public LLDPActivator(NotificationProviderService notificationService, LLDPDiscoveryListener lldpDiscoveryListener,
- String secureKey) {
- lldpSecureKey = secureKey;
+ TopologyLldpDiscoveryConfig topologyLldpDiscoveryConfig) {
+ lldpSecureKey = topologyLldpDiscoveryConfig.getLldpSecureKey();
LOG.info("Starting LLDPActivator with lldpSecureKey: {}", lldpSecureKey);
import java.util.Date;
import java.util.Map;
import java.util.Map.Entry;
+import java.util.Optional;
import java.util.Timer;
import java.util.TimerTask;
import java.util.concurrent.ConcurrentHashMap;
+import javax.annotation.Nonnull;
import org.opendaylight.controller.sal.binding.api.NotificationProviderService;
+import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationListener;
+import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.topology.discovery.rev130819.LinkDiscovered;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.topology.discovery.rev130819.LinkRemovedBuilder;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfig;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
-
-public class LLDPLinkAger implements AutoCloseable {
+public class LLDPLinkAger implements ConfigurationListener, AutoCloseable {
+ private static final Logger LOG = LoggerFactory.getLogger(LLDPLinkAger.class);
private final long linkExpirationTime;
private final Map<LinkDiscovered, Date> linkToDate;
private final Timer timer;
private final NotificationProviderService notificationService;
+ private final AutoCloseable configurationServiceRegistration;
/**
* default ctor - start timer
*/
- public LLDPLinkAger(final long lldpInterval, final long linkExpirationTime,
- final NotificationProviderService notificationService) {
- this.linkExpirationTime = linkExpirationTime;
+ public LLDPLinkAger(final TopologyLldpDiscoveryConfig topologyLldpDiscoveryConfig,
+ final NotificationProviderService notificationService,
+ final ConfigurationService configurationService) {
+ this.linkExpirationTime = topologyLldpDiscoveryConfig.getTopologyLldpExpirationInterval().getValue();
this.notificationService = notificationService;
+ this.configurationServiceRegistration = configurationService.registerListener(this);
linkToDate = new ConcurrentHashMap<>();
timer = new Timer();
- timer.schedule(new LLDPAgingTask(), 0, lldpInterval);
+ timer.schedule(new LLDPAgingTask(), 0, topologyLldpDiscoveryConfig.getTopologyLldpInterval().getValue());
}
public void put(LinkDiscovered link) {
}
@Override
- public void close() {
+ public void close() throws Exception {
timer.cancel();
linkToDate.clear();
+ configurationServiceRegistration.close();
}
private class LLDPAgingTask extends TimerTask {
return linkToDate.isEmpty();
}
-}
-
+ @Override
+ public void onPropertyChanged(@Nonnull final String propertyName, @Nonnull final String propertyValue) {
+ Optional.ofNullable(TopologyLLDPDiscoveryProperty.forValue(propertyName)).ifPresent(lldpDiscoveryProperty -> {
+ switch (lldpDiscoveryProperty) {
+ case LLDP_SECURE_KEY:
+ LOG.warn("Runtime update not supported for property {}", lldpDiscoveryProperty);
+ break;
+ case TOPOLOGY_LLDP_INTERVAL:
+ LOG.warn("Runtime update not supported for property {}", lldpDiscoveryProperty);
+ break;
+ case TOPOLOGY_LLDP_EXPIRATION_INTERVAL:
+ LOG.warn("Runtime update not supported for property {}", lldpDiscoveryProperty);
+ break;
+ default:
+ LOG.warn("No topology lldp discovery property found.");
+ break;
+ }
+ });
+ }
+}
\ No newline at end of file
--- /dev/null
+/**
+ * Copyright (c) 2017 Ericsson India Global Services Pvt Ltd. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.applications.topology.lldp;
+
+import com.google.common.collect.ImmutableMap;
+
+import java.util.Map;
+
+public enum TopologyLLDPDiscoveryProperty {
+ LLDP_SECURE_KEY,
+ TOPOLOGY_LLDP_INTERVAL,
+ TOPOLOGY_LLDP_EXPIRATION_INTERVAL;
+
+ private static final Map<String, TopologyLLDPDiscoveryProperty> KEY_VALUE_MAP;
+
+ /**
+ * Get property type from property key.
+ *
+ * @param key the property key
+ * @return the property type
+ */
+ public static TopologyLLDPDiscoveryProperty forValue(final String key) {
+ return KEY_VALUE_MAP.get(key);
+ }
+
+ static {
+ final TopologyLLDPDiscoveryProperty[] values = values();
+ final ImmutableMap.Builder<String, TopologyLLDPDiscoveryProperty> builder = ImmutableMap.builder();
+
+ for (final TopologyLLDPDiscoveryProperty value : values) {
+ builder.put(value.toString(), value);
+ }
+
+ KEY_VALUE_MAP = builder.build();
+ }
+
+ /**
+ * Converts enum name to property key.
+ *
+ * @return the property key
+ */
+ @Override
+ public String toString() {
+ return this.name().toLowerCase().replace('_', '-');
+ }
+}
odl:use-default-for-reference-types="true">
<reference id="notificationService" interface="org.opendaylight.controller.sal.binding.api.NotificationProviderService"/>
+ <reference id="configurationService" interface="org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService"/>
+
<odl:clustered-app-config id="topologyLLDPConfig"
- binding-class="org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfig">
- <odl:default-config><![CDATA[
+ binding-class="org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfig">
+ <odl:default-config><![CDATA[
<topology-lldp-discovery-config xmlns="urn:opendaylight:params:xml:ns:yang:topology-lldp-discovery:config">
<lldp-secure-key>aa9251f8-c7c0-4322-b8d6-c3a84593bda3</lldp-secure-key>
</topology-lldp-discovery-config>
]]></odl:default-config>
</odl:clustered-app-config>
- <cm:property-placeholder persistent-id="org.opendaylight.openflowplugin"
- update-strategy="none">
- <cm:default-properties>
- <!-- Interval to check LLDP links -->
- <cm:property name="topology-lldp-interval" value="5000"/>
- <!-- Expiration interval for aging out links -->
- <cm:property name="topology-lldp-expiration-interval" value="60000"/>
- </cm:default-properties>
- </cm:property-placeholder>
-
<bean id="lldpLinkAger" class="org.opendaylight.openflowplugin.applications.topology.lldp.LLDPLinkAger"
destroy-method="close">
- <argument value="${topology-lldp-interval}"/>
- <argument value="${topology-lldp-expiration-interval}"/>
+ <argument ref="topologyLLDPConfig"/>
<argument ref="notificationService"/>
+ <argument ref="configurationService"/>
</bean>
<bean id="lldpDiscoveryListener" class="org.opendaylight.openflowplugin.applications.topology.lldp.LLDPDiscoveryListener">
destroy-method="close">
<argument ref="notificationService"/>
<argument ref="lldpDiscoveryListener"/>
- <argument>
- <bean factory-ref="topologyLLDPConfig" factory-method="getLldpSecureKey"/>
- </argument>
+ <argument ref="topologyLLDPConfig"/>
</bean>
</blueprint>
\ No newline at end of file
import static org.junit.Assert.assertTrue;
import static org.mockito.Mockito.verify;
-import java.util.Date;
-import java.util.Map;
-import java.util.Timer;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Matchers;
import org.mockito.Mock;
+import org.mockito.Mockito;
import org.mockito.runners.MockitoJUnitRunner;
import org.opendaylight.controller.sal.binding.api.NotificationProviderService;
+import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.topology.discovery.rev130819.LinkDiscovered;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.topology.discovery.rev130819.LinkRemoved;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.NonZeroUint32Type;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfig;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.topology.lldp.discovery.config.rev160511.TopologyLldpDiscoveryConfigBuilder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
private final long LLDP_INTERVAL = 5L;
private final long LINK_EXPIRATION_TIME = 10L;
/**
- * We need to w8 while other tasks are finished before we can check anything
+ * We need to wait while other tasks are finished before we can check anything
* in LLDPAgingTask
*/
private final int SLEEP = 100;
-
@Mock
private LinkDiscovered link;
@Mock
- private Map<LinkDiscovered, Date> linkToDate;
- @Mock
- private Timer timer;
- @Mock
private NotificationProviderService notificationService;
- @Mock
- private LinkRemoved linkRemoved;
@Before
public void setUp() throws Exception {
- lldpLinkAger = new LLDPLinkAger(LLDP_INTERVAL, LINK_EXPIRATION_TIME, notificationService);
+ lldpLinkAger = new LLDPLinkAger(getConfig(), notificationService, getConfigurationService());
}
@Test
}
@Test
- public void testClose() {
+ public void testClose() throws Exception {
lldpLinkAger.close();
assertTrue(lldpLinkAger.isLinkToDateEmpty());
}
Thread.sleep(SLEEP);
verify(notificationService).publish(Matchers.any(LinkRemoved.class));
}
+
+ private TopologyLldpDiscoveryConfig getConfig() {
+ TopologyLldpDiscoveryConfigBuilder cfgBuilder = new TopologyLldpDiscoveryConfigBuilder();
+ cfgBuilder.setTopologyLldpInterval(new NonZeroUint32Type(LLDP_INTERVAL));
+ cfgBuilder.setTopologyLldpExpirationInterval(new NonZeroUint32Type(LINK_EXPIRATION_TIME));
+ return cfgBuilder.build();
+ }
+
+ private ConfigurationService getConfigurationService() {
+ final ConfigurationService configurationService = Mockito.mock(ConfigurationService.class);
+ final TopologyLldpDiscoveryConfig config = getConfig();
+
+ Mockito.when(configurationService.registerListener(Mockito.any())).thenReturn(() -> {
+ });
+
+ Mockito.when(configurationService.getProperty(Mockito.eq("topology-lldp-interval"), Mockito.any()))
+ .thenReturn(config.getTopologyLldpInterval());
+
+ Mockito.when(configurationService.getProperty(Mockito.eq("topology-lldp-expiration-interval"), Mockito.any()))
+ .thenReturn(config.getTopologyLldpExpirationInterval());
+
+ return configurationService;
+ }
}
\ No newline at end of file
<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">
<modelVersion>4.0.0</modelVersion>
<parent>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>binding-parent</artifactId>
- <version>0.12.0-SNAPSHOT</version>
- <relativePath/>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-parent</artifactId>
+ <version>0.6.0-SNAPSHOT</version>
+ <relativePath>../../parent</relativePath>
</parent>
<groupId>org.opendaylight.openflowplugin.applications</groupId>
<artifactId>topology-manager</artifactId>
<version>0.6.0-SNAPSHOT</version>
<packaging>bundle</packaging>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.openflowplugin</groupId>
- <artifactId>openflowplugin-artifacts</artifactId>
- <version>${project.version}</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>mdsal-artifacts</artifactId>
- <version>1.7.0-SNAPSHOT</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>com.google.guava</groupId>
<propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- </plugin>
</plugins>
</build>
LOG.debug("Error occurred when trying to read Link.. ", e);
}
if (linkOptional.isPresent()) {
- manager.addDeleteOperationTotTxChain(LogicalDatastoreType.OPERATIONAL,
+ manager.addDeleteOperationToTxChain(LogicalDatastoreType.OPERATIONAL,
TopologyManagerUtil.linkPath(toTopologyLink(notification), iiToTopology));
}
}
iiToTopologyRemovedNode = provideIIToTopologyNode(nodeId);
if (iiToTopologyRemovedNode != null) {
operationProcessor.enqueueOperation(manager -> {
- manager.addDeleteOperationTotTxChain(LogicalDatastoreType.OPERATIONAL, iiToTopologyRemovedNode);
+ manager.addDeleteOperationToTxChain(LogicalDatastoreType.OPERATIONAL, iiToTopologyRemovedNode);
TopologyManagerUtil.removeAffectedLinks(nodeId, manager, II_TO_TOPOLOGY);
});
} else {
}
if (nodeOptional.isPresent()) {
TopologyManagerUtil.removeAffectedLinks(terminationPointId, manager, II_TO_TOPOLOGY);
- manager.addDeleteOperationTotTxChain(LogicalDatastoreType.OPERATIONAL,
+ manager.addDeleteOperationToTxChain(LogicalDatastoreType.OPERATIONAL,
iiToTopologyTerminationPoint);
}
});
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-class TopologyManagerUtil {
+final class TopologyManagerUtil {
private static final Logger LOG = LoggerFactory.getLogger(TopologyManagerUtil.class);
topologyOptional.get().getLink() != null ? topologyOptional.get().getLink() : Collections.emptyList();
for (Link link : linkList) {
if (id.equals(link.getSource().getSourceNode()) || id.equals(link.getDestination().getDestNode())) {
- manager.addDeleteOperationTotTxChain(LogicalDatastoreType.OPERATIONAL, linkPath(link, topology));
+ manager.addDeleteOperationToTxChain(LogicalDatastoreType.OPERATIONAL, linkPath(link, topology));
}
}
}
.getLink() : Collections.<Link>emptyList();
for (Link link : linkList) {
if (id.equals(link.getSource().getSourceTp()) || id.equals(link.getDestination().getDestTp())) {
- manager.addDeleteOperationTotTxChain(LogicalDatastoreType.OPERATIONAL, linkPath(link, topology));
+ manager.addDeleteOperationToTxChain(LogicalDatastoreType.OPERATIONAL, linkPath(link, topology));
}
}
}
import static org.mockito.Mockito.never;
import com.google.common.base.Optional;
-import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.SettableFuture;
import com.google.common.util.concurrent.Uninterruptibles;
import java.util.concurrent.TimeUnit;
import org.mockito.ArgumentCaptor;
import org.mockito.InOrder;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
-import org.opendaylight.controller.md.sal.common.api.data.TransactionCommitFailedException;
import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes;
import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.node.NodeConnector;
import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.node.NodeConnectorKey;
import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
-public class TestUtils {
+public final class TestUtils {
+ private TestUtils() {
+ }
+
static void verifyMockTx(ReadWriteTransaction mockTx) {
InOrder inOrder = inOrder(mockTx);
inOrder.verify(mockTx, atLeast(0)).submit();
static CountDownLatch setupStubbedSubmit(ReadWriteTransaction mockTx) {
final CountDownLatch latch = new CountDownLatch(1);
- doAnswer(new Answer<CheckedFuture<Void, TransactionCommitFailedException>>() {
- @Override
- public CheckedFuture<Void, TransactionCommitFailedException> answer(InvocationOnMock invocation) {
- latch.countDown();
- return Futures.immediateCheckedFuture(null);
- }
+ doAnswer(invocation -> {
+ latch.countDown();
+ return Futures.immediateCheckedFuture(null);
}).when(mockTx).submit();
return latch;
@SuppressWarnings("rawtypes")
static void setupStubbedDeletes(ReadWriteTransaction mockTx, ArgumentCaptor<InstanceIdentifier> deletedLinkIDs,
final CountDownLatch latch) {
- doAnswer(new Answer<Void>() {
- @Override
- public Void answer(InvocationOnMock invocation) {
- latch.countDown();
- return null;
- }
+ doAnswer(invocation -> {
+ latch.countDown();
+ return null;
}).when(mockTx).delete(eq(LogicalDatastoreType.OPERATIONAL), deletedLinkIDs.capture());
}
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odlparent-lite</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>karaf4-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
</parent>
<groupId>org.opendaylight.openflowplugin</groupId>
<artifactId>openflowplugin-karaf</artifactId>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>feature-repo-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odlparent-lite</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
-
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
</plugins>
</build>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
-
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
</plugins>
</build>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
-
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
</plugins>
</build>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
</plugin>
-
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
</plugins>
</build>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>feature-repo-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<groupId>org.opendaylight.openflowplugin</groupId>
<artifactId>openflowplugin-extension-api</artifactId>
</dependency>
+ <dependency>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-extension-onf</artifactId>
+ </dependency>
<dependency>
<groupId>org.opendaylight.controller</groupId>
<artifactId>liblldp</artifactId>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odlparent-lite</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
--- /dev/null
+<?xml version="1.0" encoding="UTF-8"?>
+<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">
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>libraries</artifactId>
+ <version>0.6.0-SNAPSHOT</version>
+ </parent>
+
+ <groupId>org.opendaylight.openflowplugin.libraries</groupId>
+ <artifactId>liblldp</artifactId>
+ <packaging>bundle</packaging>
+
+ <dependencies>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.commons</groupId>
+ <artifactId>commons-lang3</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-log4j12</artifactId>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>com.google.guava</groupId>
+ <artifactId>guava</artifactId>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <configuration>
+ <instructions>
+ <Export-Package>
+ org.opendaylight.openflowplugin.libraries.liblldp</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+
+ <scm>
+ <connection>scm:git:ssh://git.opendaylight.org:29418/openflowplugin.git</connection>
+ <developerConnection>scm:git:ssh://git.opendaylight.org:29418/openflowplugin.git</developerConnection>
+ <url>https://wiki.opendaylight.org/view/OpenDaylight_OpenFlow_Plugin:Main</url>
+ <tag>HEAD</tag>
+ </scm>
+</project>
\ No newline at end of file
--- /dev/null
+/*
+ * Copyright (c) 2013, 2017 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+/**
+ *
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.util.Arrays;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * BitBufferHelper class that provides utility methods to - fetch specific bits
+ * from a serialized stream of bits - convert bits to primitive data type - like
+ * short, int, long - store bits in specified location in stream of bits -
+ * convert primitive data types to stream of bits.
+ */
+public abstract class BitBufferHelper {
+ protected static final Logger LOG = LoggerFactory.getLogger(BitBufferHelper.class);
+
+ public static final long ByteMask = 0xFF;
+
+ // Getters
+ // data: array where data are stored
+ // startOffset: bit from where to start reading
+ // numBits: number of bits to read
+ // All this function return an exception if overflow or underflow
+
+ /**
+ * Returns the first byte from the byte array.
+ *
+ * @return byte value
+ */
+ public static byte getByte(final byte[] data) {
+ if (data.length * NetUtils.NumBitsInAByte > Byte.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ return data[0];
+ }
+
+ /**
+ * Returns the short value for the byte array passed. Size of byte array is
+ * restricted to Short.SIZE
+ *
+ * @return short value
+ */
+ public static short getShort(final byte[] data) {
+ if (data.length > Short.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ return (short) toNumber(data);
+ }
+
+ /**
+ * Returns the int value for the byte array passed. Size of byte array is
+ * restricted to Integer.SIZE
+ *
+ * @return int - the integer value of byte array
+ */
+ public static int getInt(final byte[] data) {
+ if (data.length > Integer.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ return (int) toNumber(data);
+ }
+
+ /**
+ * Returns the long value for the byte array passed. Size of byte array is
+ * restricted to Long.SIZE
+ *
+ * @return long - the integer value of byte array
+ */
+ public static long getLong(final byte[] data) {
+ if (data.length > Long.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final Exception e) {
+ LOG.error("", e);
+ }
+ }
+ return toNumber(data);
+ }
+
+ /**
+ * Returns the short value for the last numBits of the byte array passed.
+ * Size of numBits is restricted to Short.SIZE
+ *
+ * @return short - the short value of byte array
+ */
+ public static short getShort(final byte[] data, final int numBits) {
+ if (numBits > Short.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ int startOffset = data.length * NetUtils.NumBitsInAByte - numBits;
+ byte[] bits = null;
+ try {
+ bits = BitBufferHelper.getBits(data, startOffset, numBits);
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ return (short) toNumber(bits, numBits);
+ }
+
+ /**
+ * Returns the int value for the last numBits of the byte array passed. Size
+ * of numBits is restricted to Integer.SIZE
+ *
+ * @return int - the integer value of byte array
+ */
+ public static int getInt(final byte[] data, final int numBits) {
+ if (numBits > Integer.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ int startOffset = data.length * NetUtils.NumBitsInAByte - numBits;
+ byte[] bits = null;
+ try {
+ bits = BitBufferHelper.getBits(data, startOffset, numBits);
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ return (int) toNumber(bits, numBits);
+ }
+
+ /**
+ * Returns the long value for the last numBits of the byte array passed.
+ * Size of numBits is restricted to Long.SIZE
+ *
+ * @return long - the integer value of byte array
+ */
+ public static long getLong(final byte[] data, final int numBits) {
+ if (numBits > Long.SIZE) {
+ try {
+ throw new BufferException("Container is too small for the number of requested bits");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ if (numBits > data.length * NetUtils.NumBitsInAByte) {
+ try {
+ throw new BufferException("Trying to read more bits than contained in the data buffer");
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ }
+ int startOffset = data.length * NetUtils.NumBitsInAByte - numBits;
+ byte[] bits = null;
+ try {
+ bits = BitBufferHelper.getBits(data, startOffset, numBits);
+ } catch (final BufferException e) {
+ LOG.error("", e);
+ }
+ return toNumber(bits, numBits);
+ }
+
+ /**
+ * Reads the specified number of bits from the passed byte array starting to
+ * read from the specified offset The bits read are stored in a byte array
+ * which size is dictated by the number of bits to be stored. The bits are
+ * stored in the byte array LSB aligned.
+ *
+ * Ex. Read 7 bits at offset 10 0 9 10 16 17 0101000010 | 0000101 |
+ * 1111001010010101011 will be returned as {0,0,0,0,0,1,0,1}
+ *
+ * @param startOffset
+ * - offset to start fetching bits from data from
+ * @param numBits
+ * - number of bits to be fetched from data
+ * @return byte [] - LSB aligned bits
+ *
+ * @throws BufferException
+ * when the startOffset and numBits parameters are not congruent
+ * with the data buffer size
+ */
+ public static byte[] getBits(final byte[] data, final int startOffset, final int numBits) throws BufferException {
+ int startByteOffset = 0;
+ int valfromcurr, valfromnext;
+ int extranumBits = numBits % NetUtils.NumBitsInAByte;
+ int extraOffsetBits = startOffset % NetUtils.NumBitsInAByte;
+ int numBytes = numBits % NetUtils.NumBitsInAByte != 0 ? 1 + numBits / NetUtils.NumBitsInAByte
+ : numBits / NetUtils.NumBitsInAByte;
+ byte[] shiftedBytes = new byte[numBytes];
+ startByteOffset = startOffset / NetUtils.NumBitsInAByte;
+ byte[] bytes = new byte[numBytes];
+ if (numBits == 0) {
+ return bytes;
+ }
+
+ checkExceptions(data, startOffset, numBits);
+
+ if (extraOffsetBits == 0) {
+ if (extranumBits == 0) {
+ System.arraycopy(data, startByteOffset, bytes, 0, numBytes);
+ return bytes;
+ } else {
+ System.arraycopy(data, startByteOffset, bytes, 0, numBytes - 1);
+ bytes[numBytes - 1] = (byte) (data[startByteOffset + numBytes - 1] & getMSBMask(extranumBits));
+ }
+ } else {
+ int i;
+ for (i = 0; i < numBits / NetUtils.NumBitsInAByte; i++) {
+ // Reading numBytes starting from offset
+ valfromcurr = data[startByteOffset + i] & getLSBMask(NetUtils.NumBitsInAByte - extraOffsetBits);
+ valfromnext = data[startByteOffset + i + 1] & getMSBMask(extraOffsetBits);
+ bytes[i] = (byte) (valfromcurr << extraOffsetBits
+ | valfromnext >> NetUtils.NumBitsInAByte - extraOffsetBits);
+ }
+ // Now adding the rest of the bits if any
+ if (extranumBits != 0) {
+ if (extranumBits < NetUtils.NumBitsInAByte - extraOffsetBits) {
+ valfromnext = (byte) (data[startByteOffset + i] & getMSBMask(extranumBits) >> extraOffsetBits);
+ bytes[i] = (byte) (valfromnext << extraOffsetBits);
+ } else if (extranumBits == NetUtils.NumBitsInAByte - extraOffsetBits) {
+ valfromcurr = data[startByteOffset + i] & getLSBMask(NetUtils.NumBitsInAByte - extraOffsetBits);
+ bytes[i] = (byte) (valfromcurr << extraOffsetBits);
+ } else {
+ valfromcurr = data[startByteOffset + i] & getLSBMask(NetUtils.NumBitsInAByte - extraOffsetBits);
+ valfromnext = data[startByteOffset + i + 1]
+ & getMSBMask(extranumBits - (NetUtils.NumBitsInAByte - extraOffsetBits));
+ bytes[i] = (byte) (valfromcurr << extraOffsetBits
+ | valfromnext >> NetUtils.NumBitsInAByte - extraOffsetBits);
+ }
+
+ }
+ }
+ // Aligns the bits to LSB
+ shiftedBytes = shiftBitsToLSB(bytes, numBits);
+ return shiftedBytes;
+ }
+
+ // Setters
+ // data: array where data will be stored
+ // input: the data that need to be stored in the data array
+ // startOffset: bit from where to start writing
+ // numBits: number of bits to read
+
+ /**
+ * Bits are expected to be stored in the input byte array from LSB
+ *
+ * @param data
+ * to set the input byte
+ * @param input
+ * byte to be inserted
+ * @param startOffset
+ * offset of data[] to start inserting byte from
+ * @param numBits
+ * number of bits of input to be inserted into data[]
+ *
+ * @throws BufferException
+ * when the input, startOffset and numBits are not congruent
+ * with the data buffer size
+ */
+ public static void setByte(final byte[] data, final byte input, final int startOffset, final int numBits)
+ throws BufferException {
+ byte[] inputByteArray = new byte[1];
+ Arrays.fill(inputByteArray, 0, 1, input);
+ setBytes(data, inputByteArray, startOffset, numBits);
+ }
+
+ /**
+ * Bits are expected to be stored in the input byte array from LSB
+ *
+ * @param data
+ * to set the input byte
+ * @param input
+ * bytes to be inserted
+ * @param startOffset
+ * offset of data[] to start inserting byte from
+ * @param numBits
+ * number of bits of input to be inserted into data[]
+ * @throws BufferException
+ * when the startOffset and numBits parameters are not congruent
+ * with data and input buffers' size
+ */
+ public static void setBytes(final byte[] data, final byte[] input, final int startOffset, final int numBits)
+ throws BufferException {
+ checkExceptions(data, startOffset, numBits);
+ insertBits(data, input, startOffset, numBits);
+ }
+
+ /**
+ * Returns numBits 1's in the MSB position
+ */
+ public static int getMSBMask(final int numBits) {
+ int mask = 0;
+ for (int i = 0; i < numBits; i++) {
+ mask = mask | 1 << 7 - i;
+ }
+ return mask;
+ }
+
+ /**
+ * Returns numBits 1's in the LSB position
+ */
+ public static int getLSBMask(final int numBits) {
+ int mask = 0;
+ for (int i = 0; i < numBits; i++) {
+ mask = mask | 1 << i;
+ }
+ return mask;
+ }
+
+ /**
+ * Returns the numerical value of the byte array passed
+ *
+ * @return long - numerical value of byte array passed
+ */
+ static public long toNumber(final byte[] array) {
+ long ret = 0;
+ long length = array.length;
+ int value = 0;
+ for (int i = 0; i < length; i++) {
+ value = array[i];
+ if (value < 0) {
+ value += 256;
+ }
+ ret = ret | (long) value << (length - i - 1) * NetUtils.NumBitsInAByte;
+ }
+ return ret;
+ }
+
+ /**
+ * Returns the numerical value of the last numBits (LSB bits) of the byte
+ * array passed
+ *
+ * @return long - numerical value of byte array passed
+ */
+ static public long toNumber(final byte[] array, final int numBits) {
+ int length = numBits / NetUtils.NumBitsInAByte;
+ int bitsRest = numBits % NetUtils.NumBitsInAByte;
+ int startOffset = array.length - length;
+ long ret = 0;
+ int value = 0;
+
+ value = array[startOffset - 1] & getLSBMask(bitsRest);
+ value = array[startOffset - 1] < 0 ? array[startOffset - 1] + 256 : array[startOffset - 1];
+ ret = ret | value << (array.length - startOffset) * NetUtils.NumBitsInAByte;
+
+ for (int i = startOffset; i < array.length; i++) {
+ value = array[i];
+ if (value < 0) {
+ value += 256;
+ }
+ ret = ret | (long) value << (array.length - i - 1) * NetUtils.NumBitsInAByte;
+ }
+
+ return ret;
+ }
+
+ /**
+ * Accepts a number as input and returns its value in byte form in LSB
+ * aligned form example: input = 5000 [1001110001000] bytes = 19, -120
+ * [00010011] [10001000]
+ */
+ public static byte[] toByteArray(final Number input) {
+ Class<? extends Number> dataType = input.getClass();
+ short size = 0;
+ long longValue = input.longValue();
+
+ if (dataType == Byte.class || dataType == byte.class) {
+ size = Byte.SIZE;
+ } else if (dataType == Short.class || dataType == short.class) {
+ size = Short.SIZE;
+ } else if (dataType == Integer.class || dataType == int.class) {
+ size = Integer.SIZE;
+ } else if (dataType == Long.class || dataType == long.class) {
+ size = Long.SIZE;
+ } else {
+ throw new IllegalArgumentException("Parameter must one of the following: Short/Int/Long\n");
+ }
+
+ int length = size / NetUtils.NumBitsInAByte;
+ byte bytes[] = new byte[length];
+
+ // Getting the bytes from input value
+ for (int i = 0; i < length; i++) {
+ bytes[i] = (byte) (longValue >> NetUtils.NumBitsInAByte * (length - i - 1) & ByteMask);
+ }
+ return bytes;
+ }
+
+ /**
+ * Accepts a number as input and returns its value in byte form in MSB
+ * aligned form example: input = 5000 [1001110001000] bytes = -114, 64
+ * [10011100] [01000000]
+ *
+ * @param numBits
+ * - the number of bits to be returned
+ * @return byte[]
+ *
+ */
+ public static byte[] toByteArray(final Number input, final int numBits) {
+ Class<? extends Number> dataType = input.getClass();
+ short size = 0;
+ long longValue = input.longValue();
+
+ if (dataType == Short.class) {
+ size = Short.SIZE;
+ } else if (dataType == Integer.class) {
+ size = Integer.SIZE;
+ } else if (dataType == Long.class) {
+ size = Long.SIZE;
+ } else {
+ throw new IllegalArgumentException("Parameter must one of the following: Short/Int/Long\n");
+ }
+
+ int length = size / NetUtils.NumBitsInAByte;
+ byte bytes[] = new byte[length];
+ byte[] inputbytes = new byte[length];
+ byte shiftedBytes[];
+
+ // Getting the bytes from input value
+ for (int i = 0; i < length; i++) {
+ bytes[i] = (byte) (longValue >> NetUtils.NumBitsInAByte * (length - i - 1) & ByteMask);
+ }
+
+ if (bytes[0] == 0 && dataType == Long.class || bytes[0] == 0 && dataType == Integer.class) {
+ int index = 0;
+ for (index = 0; index < length; ++index) {
+ if (bytes[index] != 0) {
+ bytes[0] = bytes[index];
+ break;
+ }
+ }
+ System.arraycopy(bytes, index, inputbytes, 0, length - index);
+ Arrays.fill(bytes, length - index + 1, length - 1, (byte) 0);
+ } else {
+ System.arraycopy(bytes, 0, inputbytes, 0, length);
+ }
+
+ shiftedBytes = shiftBitsToMSB(inputbytes, numBits);
+
+ return shiftedBytes;
+ }
+
+ /**
+ * Takes an LSB aligned byte array and returned the LSB numBits in a MSB
+ * aligned byte array.
+ * <p>
+ * It aligns the last numBits bits to the head of the byte array following
+ * them with numBits % 8 zero bits.
+ *
+ * Example: For inputbytes = [00000111][01110001] and numBits = 12 it
+ * returns: shiftedBytes = [01110111][00010000]
+ *
+ * @param numBits
+ * - number of bits to be left aligned
+ * @return byte[]
+ */
+ public static byte[] shiftBitsToMSB(final byte[] inputBytes, final int numBits) {
+ int numBitstoShiftBy = 0, leadZeroesMSB = 8, numEndRestBits = 0;
+ int size = inputBytes.length;
+ byte[] shiftedBytes = new byte[size];
+ int i;
+
+ for (i = 0; i < Byte.SIZE; i++) {
+ if ((byte) (inputBytes[0] & getMSBMask(i + 1)) != 0) {
+ leadZeroesMSB = i;
+ break;
+ }
+ }
+
+ if (numBits % NetUtils.NumBitsInAByte == 0) {
+ numBitstoShiftBy = 0;
+ } else {
+ numBitstoShiftBy = NetUtils.NumBitsInAByte - numBits % NetUtils.NumBitsInAByte < leadZeroesMSB
+ ? NetUtils.NumBitsInAByte - numBits % NetUtils.NumBitsInAByte : leadZeroesMSB;
+ }
+ if (numBitstoShiftBy == 0) {
+ return inputBytes;
+ }
+
+ if (numBits < NetUtils.NumBitsInAByte) {
+ // inputbytes.length = 1 OR read less than a byte
+ shiftedBytes[0] = (byte) ((inputBytes[0] & getLSBMask(numBits)) << numBitstoShiftBy);
+ } else {
+ // # of bits to read from last byte
+ numEndRestBits = NetUtils.NumBitsInAByte
+ - (inputBytes.length * NetUtils.NumBitsInAByte - numBits - numBitstoShiftBy);
+
+ for (i = 0; i < size - 1; i++) {
+ if (i + 1 == size - 1) {
+ if (numEndRestBits > numBitstoShiftBy) {
+ shiftedBytes[i] = (byte) (inputBytes[i] << numBitstoShiftBy
+ | (inputBytes[i + 1] & getMSBMask(numBitstoShiftBy)) >> numEndRestBits
+ - numBitstoShiftBy);
+ shiftedBytes[i + 1] = (byte) ((inputBytes[i + 1]
+ & getLSBMask(numEndRestBits - numBitstoShiftBy)) << numBitstoShiftBy);
+ } else {
+ shiftedBytes[i] = (byte) (inputBytes[i] << numBitstoShiftBy
+ | (inputBytes[i + 1] & getMSBMask(numEndRestBits)) >> NetUtils.NumBitsInAByte
+ - numEndRestBits);
+ }
+ }
+ shiftedBytes[i] = (byte) (inputBytes[i] << numBitstoShiftBy
+ | (inputBytes[i + 1] & getMSBMask(numBitstoShiftBy)) >> NetUtils.NumBitsInAByte
+ - numBitstoShiftBy);
+ }
+
+ }
+ return shiftedBytes;
+ }
+
+ /**
+ * It aligns the first numBits bits to the right end of the byte array
+ * preceding them with numBits % 8 zero bits.
+ *
+ * Example: For inputbytes = [01110111][00010000] and numBits = 12 it
+ * returns: shiftedBytes = [00000111][01110001]
+ *
+ * @param inputBytes
+ * @param numBits
+ * - number of bits to be right aligned
+ * @return byte[]
+ */
+ public static byte[] shiftBitsToLSB(final byte[] inputBytes, final int numBits) {
+ int numBytes = inputBytes.length;
+ int numBitstoShift = numBits % NetUtils.NumBitsInAByte;
+ byte[] shiftedBytes = new byte[numBytes];
+ int inputLsb = 0, inputMsb = 0;
+
+ if (numBitstoShift == 0) {
+ return inputBytes;
+ }
+
+ for (int i = 1; i < numBytes; i++) {
+ inputLsb = inputBytes[i - 1] & getLSBMask(NetUtils.NumBitsInAByte - numBitstoShift);
+ inputLsb = inputLsb < 0 ? inputLsb + 256 : inputLsb;
+ inputMsb = inputBytes[i] & getMSBMask(numBitstoShift);
+ inputMsb = inputBytes[i] < 0 ? inputBytes[i] + 256 : inputBytes[i];
+ shiftedBytes[i] = (byte) (inputLsb << numBitstoShift
+ | inputMsb >> NetUtils.NumBitsInAByte - numBitstoShift);
+ }
+ inputMsb = inputBytes[0] & getMSBMask(numBitstoShift);
+ inputMsb = inputMsb < 0 ? inputMsb + 256 : inputMsb;
+ shiftedBytes[0] = (byte) (inputMsb >> NetUtils.NumBitsInAByte - numBitstoShift);
+ return shiftedBytes;
+ }
+
+ /**
+ * Insert in the data buffer at position dictated by the offset the number
+ * of bits specified from the input data byte array. The input byte array
+ * has the bits stored starting from the LSB
+ */
+ public static void insertBits(final byte[] data, final byte[] inputdataLSB, final int startOffset,
+ final int numBits) {
+ byte[] inputdata = shiftBitsToMSB(inputdataLSB, numBits); // Align to
+ // MSB the
+ // passed
+ // byte
+ // array
+ int numBytes = numBits / NetUtils.NumBitsInAByte;
+ int startByteOffset = startOffset / NetUtils.NumBitsInAByte;
+ int extraOffsetBits = startOffset % NetUtils.NumBitsInAByte;
+ int extranumBits = numBits % NetUtils.NumBitsInAByte;
+ int RestBits = numBits % NetUtils.NumBitsInAByte;
+ int InputMSBbits = 0, InputLSBbits = 0;
+ int i;
+
+ if (numBits == 0) {
+ return;
+ }
+
+ if (extraOffsetBits == 0) {
+ if (extranumBits == 0) {
+ numBytes = numBits / NetUtils.NumBitsInAByte;
+ System.arraycopy(inputdata, 0, data, startByteOffset, numBytes);
+ } else {
+ System.arraycopy(inputdata, 0, data, startByteOffset, numBytes);
+ data[startByteOffset + numBytes] = (byte) (data[startByteOffset + numBytes]
+ | inputdata[numBytes] & getMSBMask(extranumBits));
+ }
+ } else {
+ for (i = 0; i < numBytes; i++) {
+ if (i != 0) {
+ InputLSBbits = inputdata[i - 1] & getLSBMask(extraOffsetBits);
+ }
+ InputMSBbits = (byte) (inputdata[i] & getMSBMask(NetUtils.NumBitsInAByte - extraOffsetBits));
+ InputMSBbits = InputMSBbits >= 0 ? InputMSBbits : InputMSBbits + 256;
+ data[startByteOffset + i] = (byte) (data[startByteOffset + i]
+ | InputLSBbits << NetUtils.NumBitsInAByte - extraOffsetBits | InputMSBbits >> extraOffsetBits);
+ InputMSBbits = InputLSBbits = 0;
+ }
+ if (RestBits < NetUtils.NumBitsInAByte - extraOffsetBits) {
+ if (numBytes != 0) {
+ InputLSBbits = inputdata[i - 1] & getLSBMask(extraOffsetBits);
+ }
+ InputMSBbits = (byte) (inputdata[i] & getMSBMask(RestBits));
+ InputMSBbits = InputMSBbits >= 0 ? InputMSBbits : InputMSBbits + 256;
+ data[startByteOffset + i] = (byte) (data[startByteOffset + i]
+ | InputLSBbits << NetUtils.NumBitsInAByte - extraOffsetBits | InputMSBbits >> extraOffsetBits);
+ } else if (RestBits == NetUtils.NumBitsInAByte - extraOffsetBits) {
+ if (numBytes != 0) {
+ InputLSBbits = inputdata[i - 1] & getLSBMask(extraOffsetBits);
+ }
+ InputMSBbits = (byte) (inputdata[i] & getMSBMask(NetUtils.NumBitsInAByte - extraOffsetBits));
+ InputMSBbits = InputMSBbits >= 0 ? InputMSBbits : InputMSBbits + 256;
+ data[startByteOffset + i] = (byte) (data[startByteOffset + i]
+ | InputLSBbits << NetUtils.NumBitsInAByte - extraOffsetBits | InputMSBbits >> extraOffsetBits);
+ } else {
+ if (numBytes != 0) {
+ InputLSBbits = inputdata[i - 1] & getLSBMask(extraOffsetBits);
+ }
+ InputMSBbits = (byte) (inputdata[i] & getMSBMask(NetUtils.NumBitsInAByte - extraOffsetBits));
+ InputMSBbits = InputMSBbits >= 0 ? InputMSBbits : InputMSBbits + 256;
+ data[startByteOffset + i] = (byte) (data[startByteOffset + i]
+ | InputLSBbits << NetUtils.NumBitsInAByte - extraOffsetBits | InputMSBbits >> extraOffsetBits);
+
+ InputLSBbits = inputdata[i]
+ & getLSBMask(RestBits - (NetUtils.NumBitsInAByte - extraOffsetBits)) << NetUtils.NumBitsInAByte
+ - RestBits;
+ data[startByteOffset + i + 1] = (byte) (data[startByteOffset + i + 1]
+ | InputLSBbits << NetUtils.NumBitsInAByte - extraOffsetBits);
+ }
+ }
+ }
+
+ /**
+ * Checks for overflow and underflow exceptions
+ *
+ * @throws BufferException
+ * when the startOffset and numBits parameters are not congruent
+ * with the data buffer's size
+ */
+ public static void checkExceptions(final byte[] data, final int startOffset, final int numBits)
+ throws BufferException {
+ int endOffsetByte;
+ int startByteOffset;
+ endOffsetByte = startOffset / NetUtils.NumBitsInAByte + numBits / NetUtils.NumBitsInAByte
+ + (numBits % NetUtils.NumBitsInAByte != 0 ? 1 : startOffset % NetUtils.NumBitsInAByte != 0 ? 1 : 0);
+ startByteOffset = startOffset / NetUtils.NumBitsInAByte;
+
+ if (data == null) {
+ throw new BufferException("data[] is null\n");
+ }
+
+ if (startOffset < 0 || startByteOffset >= data.length || endOffsetByte > data.length || numBits < 0
+ || numBits > NetUtils.NumBitsInAByte * data.length) {
+ throw new BufferException("Illegal arguement/out of bound exception - data.length = " + data.length
+ + " startOffset = " + startOffset + " numBits " + numBits);
+ }
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+/**
+ * Describes an exception that is raised during BitBufferHelper operations.
+ */
+public class BufferException extends Exception {
+ private static final long serialVersionUID = 1L;
+
+ public BufferException(final String message) {
+ super(message);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+/**
+ * @file ConstructionException.java
+ *
+ *
+ * @brief Describe an exception that is raised when a construction
+ * for a Node/NodeConnector/Edge or any of the SAL basic object fails
+ * because input passed are not valid or compatible
+ *
+ *
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+public class ConstructionException extends Exception {
+ private static final long serialVersionUID = 1L;
+
+ public ConstructionException(final String message) {
+ super(message);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+public class CustomTLVKey {
+
+ private int oui;
+ private byte subtype;
+
+ /**
+ * @param oui
+ * @param subtype
+ */
+ public CustomTLVKey(final int oui, final byte subtype) {
+ this.oui = oui;
+ this.subtype = subtype;
+ }
+
+ /**
+ * @return the oui
+ */
+ public int getOui() {
+ return oui;
+ }
+
+ /**
+ * @return the subtype
+ */
+ public byte getSubtype() {
+ return subtype;
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + oui;
+ result = prime * result + subtype;
+ return result;
+ }
+
+ @Override
+ public boolean equals(final Object obj) {
+ if (this == obj) {
+ return true;
+ }
+
+ if (obj == null) {
+ return false;
+ }
+
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+
+ CustomTLVKey other = (CustomTLVKey) obj;
+ if (oui != other.oui) {
+ return false;
+ }
+
+ if (subtype != other.subtype) {
+ return false;
+ }
+
+ return true;
+ }
+
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.io.Serializable;
+
+import javax.xml.bind.annotation.XmlRootElement;
+
+/**
+ * @file DataLinkAddress.java
+ *
+ * @brief Abstract base class for a Datalink Address
+ *
+ */
+
+/**
+ * Abstract base class for a Datalink Address
+ *
+ */
+@XmlRootElement
+abstract public class DataLinkAddress implements Serializable {
+ private static final long serialVersionUID = 1L;
+ private String name;
+
+ public DataLinkAddress() {
+
+ }
+
+ /**
+ * Constructor of super class
+ *
+ * @param name Create a new DataLink, not for general use but
+ * available only for sub classes
+ */
+ protected DataLinkAddress(final String name) {
+ this.name = name;
+ }
+
+ /**
+ * Used to copy the DataLinkAddress in a polymorphic way
+ *
+ *
+ * @return A clone of this DataLinkAddress
+ */
+ @Override
+ abstract public DataLinkAddress clone();
+
+ /**
+ * Allow to distinguish among different data link addresses
+ *
+ *
+ * @return Name of the DataLinkAdress we are working on
+ */
+ public String getName() {
+ return this.name;
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + ((name == null) ? 0 : name.hashCode());
+ return result;
+ }
+
+ @Override
+ public boolean equals(final Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (obj == null) {
+ return false;
+ }
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+ DataLinkAddress other = (DataLinkAddress) obj;
+ if (name == null) {
+ if (other.name != null) {
+ return false;
+ }
+ } else if (!name.equals(other.name)) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public String toString() {
+ return "DataLinkAddress [name=" + name + "]";
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * The enum contains the most common 802.3 ethernet types and 802.2 + SNAP protocol ids
+ *
+ *
+ *
+ */
+public enum EtherTypes {
+ PVSTP("PVSTP", 0x010B), // 802.2 + SNAP (Spanning Tree)
+ CDP("CDP", 0x2000), // 802.2 + SNAP
+ VTP("VTP", 0x2003), // 802.2 + SNAP
+ IPv4("IPv4", 0x800), ARP("ARP", 0x806), RARP("Reverse ARP", 0x8035), VLANTAGGED(
+ "VLAN Tagged", 0x8100), // 802.1Q
+ IPv6("IPv6", 0x86DD), MPLSUCAST("MPLS Unicast", 0x8847), MPLSMCAST(
+ "MPLS Multicast", 0x8848), QINQ("QINQ", 0x88A8), // Standard 802.1ad QinQ
+ LLDP("LLDP", 0x88CC), OLDQINQ("Old QINQ", 0x9100), // Old non-standard QinQ
+ CISCOQINQ("Cisco QINQ", 0x9200); // Cisco non-standard QinQ
+
+ private static final String regexNumberString = "^[0-9]+$";
+ private String description;
+ private int number;
+
+ EtherTypes(final String description, final int number) {
+ this.description = description;
+ this.number = number;
+ }
+
+ public String toString() {
+ return description;
+ }
+
+ public int intValue() {
+ return number;
+ }
+
+ public short shortValue() {
+ return ((Integer) number).shortValue();
+ }
+
+ public static String getEtherTypeName(final int number) {
+ return getEtherTypeInternal(number);
+ }
+
+ public static String getEtherTypeName(final short number) {
+ return getEtherTypeInternal(number & 0xffff);
+ }
+
+ public static String getEtherTypeName(final byte number) {
+ return getEtherTypeInternal(number & 0xff);
+ }
+
+ private static String getEtherTypeInternal(final int number) {
+ for (EtherTypes type : EtherTypes.values()) {
+ if (type.number == number) {
+ return type.toString();
+ }
+ }
+ return "0x" + Integer.toHexString(number);
+ }
+
+ public static short getEtherTypeNumberShort(final String name) {
+ if (name.matches(regexNumberString)) {
+ return Short.valueOf(name);
+ }
+ for (EtherTypes type : EtherTypes.values()) {
+ if (type.description.equalsIgnoreCase(name)) {
+ return type.shortValue();
+ }
+ }
+ return 0;
+ }
+
+ public static int getEtherTypeNumberInt(final String name) {
+ if (name.matches(regexNumberString)) {
+ return Integer.valueOf(name);
+ }
+ for (EtherTypes type : EtherTypes.values()) {
+ if (type.description.equalsIgnoreCase(name)) {
+ return type.intValue();
+ }
+ }
+ return 0;
+ }
+
+ public static List<String> getEtherTypesNameList() {
+ List<String> ethertypesList = new ArrayList<>();
+ for (EtherTypes type : EtherTypes.values()) {
+ ethertypesList.add(type.toString());
+ }
+ return ethertypesList;
+ }
+
+ public static EtherTypes loadFromString(final String string) {
+ int intType = Integer.parseInt(string);
+
+ for (EtherTypes type : EtherTypes.values()) {
+ if (type.number == intType) {
+ return type;
+ }
+ }
+ return null;
+ }
+
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.util.HashMap;
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+import org.apache.commons.lang3.tuple.ImmutablePair;
+import org.apache.commons.lang3.tuple.Pair;
+
+/**
+ * Class that represents the Ethernet frame objects
+ */
+public class Ethernet extends Packet {
+ private static final String DMAC = "DestinationMACAddress";
+ private static final String SMAC = "SourceMACAddress";
+ private static final String ETHT = "EtherType";
+
+ // TODO: This has to be outside and it should be possible for osgi
+ // to add new coming packet classes
+ public static final Map<Short, Class<? extends Packet>> etherTypeClassMap;
+ static {
+ etherTypeClassMap = new HashMap<>();
+ etherTypeClassMap.put(EtherTypes.LLDP.shortValue(), LLDP.class);
+ }
+ private static Map<String, Pair<Integer, Integer>> fieldCoordinates = new LinkedHashMap<String, Pair<Integer, Integer>>() {
+ private static final long serialVersionUID = 1L;
+ {
+ put(DMAC, new ImmutablePair<>(0, 48));
+ put(SMAC, new ImmutablePair<>(48, 48));
+ put(ETHT, new ImmutablePair<>(96, 16));
+ }
+ };
+ private final Map<String, byte[]> fieldValues;
+
+ /**
+ * Default constructor that creates and sets the HashMap
+ */
+ public Ethernet() {
+ fieldValues = new HashMap<>();
+ hdrFieldCoordMap = fieldCoordinates;
+ hdrFieldsMap = fieldValues;
+ }
+
+ /**
+ * Constructor that sets the access level for the packet and
+ * creates and sets the HashMap
+ */
+ public Ethernet(final boolean writeAccess) {
+ super(writeAccess);
+ fieldValues = new HashMap<>();
+ hdrFieldCoordMap = fieldCoordinates;
+ hdrFieldsMap = fieldValues;
+ }
+
+ @Override
+ public void setHeaderField(final String headerField, final byte[] readValue) {
+ if (headerField.equals(ETHT)) {
+ payloadClass = etherTypeClassMap.get(BitBufferHelper
+ .getShort(readValue));
+ }
+ hdrFieldsMap.put(headerField, readValue);
+ }
+
+ /**
+ * Gets the destination MAC address stored
+ * @return byte[] - the destinationMACAddress
+ */
+ public byte[] getDestinationMACAddress() {
+ return fieldValues.get(DMAC);
+ }
+
+ /**
+ * Gets the source MAC address stored
+ * @return byte[] - the sourceMACAddress
+ */
+ public byte[] getSourceMACAddress() {
+ return fieldValues.get(SMAC);
+ }
+
+ /**
+ * Gets the etherType stored
+ * @return short - the etherType
+ */
+ public short getEtherType() {
+ return BitBufferHelper.getShort(fieldValues.get(ETHT));
+ }
+
+ public boolean isBroadcast(){
+ return NetUtils.isBroadcastMACAddr(getDestinationMACAddress());
+ }
+
+ public boolean isMulticast(){
+ return NetUtils.isMulticastMACAddr(getDestinationMACAddress());
+ }
+
+ /**
+ * Sets the destination MAC address for the current Ethernet object instance
+ * @param destinationMACAddress the destinationMACAddress to set
+ */
+ public Ethernet setDestinationMACAddress(final byte[] destinationMACAddress) {
+ fieldValues.put(DMAC, destinationMACAddress);
+ return this;
+ }
+
+ /**
+ * Sets the source MAC address for the current Ethernet object instance
+ * @param sourceMACAddress the sourceMACAddress to set
+ */
+ public Ethernet setSourceMACAddress(final byte[] sourceMACAddress) {
+ fieldValues.put(SMAC, sourceMACAddress);
+ return this;
+ }
+
+ /**
+ * Sets the etherType for the current Ethernet object instance
+ * @param etherType the etherType to set
+ */
+ public Ethernet setEtherType(final short etherType) {
+ byte[] ethType = BitBufferHelper.toByteArray(etherType);
+ fieldValues.put(ETHT, ethType);
+ return this;
+ }
+
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.util.Arrays;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+import javax.xml.bind.annotation.XmlTransient;
+
+@XmlRootElement
+@XmlAccessorType(XmlAccessType.NONE)
+public class EthernetAddress extends DataLinkAddress {
+ private static final long serialVersionUID = 1L;
+ @XmlTransient
+ private byte[] macAddress;
+
+ public static final EthernetAddress BROADCASTMAC = createWellKnownAddress(new byte[] {
+ (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff });
+
+ public static final EthernetAddress INVALIDHOST = BROADCASTMAC;
+
+ public static final String addressName = "Ethernet MAC Address";
+ public static final int SIZE = 6;
+
+ private static final EthernetAddress createWellKnownAddress(final byte[] mac) {
+ try {
+ return new EthernetAddress(mac);
+ } catch (final ConstructionException ce) {
+ return null;
+ }
+ }
+
+ /* Private constructor to satisfy JAXB */
+ @SuppressWarnings("unused")
+ private EthernetAddress() {
+ }
+
+ /**
+ * Public constructor for an Ethernet MAC address starting from
+ * the byte constituing the address, the constructor validate the
+ * size of the arrive to make sure it met the expected size
+ *
+ * @param macAddress A byte array in big endian format
+ * representing the Ethernet MAC Address
+ */
+ public EthernetAddress(final byte[] macAddress) throws ConstructionException {
+ super(addressName);
+
+ if (macAddress == null) {
+ throw new ConstructionException("Null input parameter passed");
+ }
+
+ if (macAddress.length != SIZE) {
+ throw new ConstructionException(
+ "Wrong size of passed byte array, expected:" + SIZE
+ + " got:" + macAddress.length);
+ }
+ this.macAddress = new byte[SIZE];
+ System.arraycopy(macAddress, 0, this.macAddress, 0, SIZE);
+ }
+
+ public EthernetAddress clone() {
+ try {
+ return new EthernetAddress(this.macAddress.clone());
+ } catch (final ConstructionException ce) {
+ return null;
+ }
+ }
+
+ /**
+ * Return the Ethernet Mac address in byte array format
+ *
+ * @return The Ethernet Mac address in byte array format
+ */
+ public byte[] getValue() {
+ return this.macAddress;
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = super.hashCode();
+ result = prime * result + Arrays.hashCode(macAddress);
+ return result;
+ }
+
+ @Override
+ public boolean equals(final Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (!super.equals(obj)) {
+ return false;
+ }
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+ EthernetAddress other = (EthernetAddress) obj;
+ if (!Arrays.equals(macAddress, other.macAddress)) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public String toString() {
+ return "EthernetAddress [macAddress=" + HexEncode.bytesToHexStringFormat(macAddress)
+ + "]";
+ }
+
+ @XmlElement(name = "macAddress")
+ public String getMacAddress() {
+ return HexEncode.bytesToHexStringFormat(macAddress);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.math.BigInteger;
+
+/**
+ * The class provides methods to convert hex encode strings
+ *
+ *
+ */
+public class HexEncode {
+ /**
+ * This method converts byte array into String format without ":" inserted.
+ *
+ * @param bytes
+ * The byte array to convert to string
+ * @return The hexadecimal representation of the byte array. If bytes is
+ * null, "null" string is returned
+ */
+ public static String bytesToHexString(final byte[] bytes) {
+
+ if (bytes == null) {
+ return "null";
+ }
+
+ StringBuilder buf = new StringBuilder();
+ for (int i = 0; i < bytes.length; i++) {
+ short u8byte = (short) (bytes[i] & 0xff);
+ String tmp = Integer.toHexString(u8byte);
+ if (tmp.length() == 1) {
+ buf.append("0");
+ }
+ buf.append(tmp);
+ }
+ return buf.toString();
+ }
+
+ public static String longToHexString(final long val) {
+ char arr[] = Long.toHexString(val).toCharArray();
+ StringBuilder buf = new StringBuilder();
+ // prepend the right number of leading zeros
+ int i = 0;
+ for (; i < (16 - arr.length); i++) {
+ buf.append("0");
+ if ((i & 0x01) == 1) {
+ buf.append(":");
+ }
+ }
+ for (int j = 0; j < arr.length; j++) {
+ buf.append(arr[j]);
+ if ((((i + j) & 0x01) == 1) && (j < (arr.length - 1))) {
+ buf.append(":");
+ }
+ }
+ return buf.toString();
+ }
+
+
+ public static byte[] bytesFromHexString(final String values) {
+ String target = "";
+ if (values != null) {
+ target = values;
+ }
+ String[] octets = target.split(":");
+
+ byte[] ret = new byte[octets.length];
+ for (int i = 0; i < octets.length; i++) {
+ ret[i] = Integer.valueOf(octets[i], 16).byteValue();
+ }
+ return ret;
+ }
+
+ public static long stringToLong(final String values) {
+ long value = new BigInteger(values.replaceAll(":", ""), 16).longValue();
+ return value;
+ }
+
+ /**
+ * This method converts byte array into HexString format with ":" inserted.
+ */
+ public static String bytesToHexStringFormat(final byte[] bytes) {
+ if (bytes == null) {
+ return "null";
+ }
+ StringBuilder buf = new StringBuilder();
+ for (int i = 0; i < bytes.length; i++) {
+ if (i > 0) {
+ buf.append(":");
+ }
+ short u8byte = (short) (bytes[i] & 0xff);
+ String tmp = Integer.toHexString(u8byte);
+ if (tmp.length() == 1) {
+ buf.append("0");
+ }
+ buf.append(tmp);
+ }
+ return buf.toString();
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import com.google.common.collect.Iterables;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Class that represents the LLDP frame objects
+ */
+
+public class LLDP extends Packet {
+ private static final String CHASSISID = "ChassisId";
+ private static final String SYSTEMNAMEID = "SystemNameID";
+ private static final String PORTID = "PortId";
+ private static final String TTL = "TTL";
+ private static final int LLDPDefaultTlvs = 3;
+ private static final LLDPTLV emptyTLV = new LLDPTLV().setLength((short) 0).setType((byte) 0);
+ public static final byte[] LLDPMulticastMac = { 1, (byte) 0x80, (byte) 0xc2, 0, 0, (byte) 0xe };
+
+ private Map<Byte, LLDPTLV> mandatoryTLVs;
+ private Map<Byte, LLDPTLV> optionalTLVs;
+ private Map<CustomTLVKey, LLDPTLV> customTLVs;
+
+ /**
+ * Default constructor that creates the tlvList LinkedHashMap
+ */
+ public LLDP() {
+ init();
+ }
+
+ /**
+ * Constructor that creates the tlvList LinkedHashMap and sets the write access for the same
+ */
+ public LLDP(final boolean writeAccess) {
+ super(writeAccess);
+ init();
+ }
+
+ private void init() {
+ mandatoryTLVs = new LinkedHashMap<>(LLDPDefaultTlvs);
+ optionalTLVs = new LinkedHashMap<>();
+ customTLVs = new LinkedHashMap<>();
+ }
+
+ /**
+ * @param String
+ * - description of the type of TLV
+ * @return byte - type of TLV
+ */
+ private byte getType(final String typeDesc) {
+ if (typeDesc.equals(CHASSISID)) {
+ return LLDPTLV.TLVType.ChassisID.getValue();
+ } else if (typeDesc.equals(PORTID)) {
+ return LLDPTLV.TLVType.PortID.getValue();
+ } else if (typeDesc.equals(TTL)) {
+ return LLDPTLV.TLVType.TTL.getValue();
+ } else if (typeDesc.equals(SYSTEMNAMEID)) {
+ return LLDPTLV.TLVType.SystemName.getValue();
+ } else {
+ return LLDPTLV.TLVType.Unknown.getValue();
+ }
+ }
+
+ private LLDPTLV getFromTLVs(final Byte type) {
+ LLDPTLV tlv = null;
+ tlv = mandatoryTLVs.get(type);
+ if (tlv == null) {
+ tlv = optionalTLVs.get(type);
+ }
+ return tlv;
+ }
+
+ private void putToTLVs(final Byte type, final LLDPTLV tlv) {
+ if (type == LLDPTLV.TLVType.ChassisID.getValue() || type == LLDPTLV.TLVType.PortID.getValue()
+ || type == LLDPTLV.TLVType.TTL.getValue()) {
+ mandatoryTLVs.put(type, tlv);
+ } else if (type != LLDPTLV.TLVType.Custom.getValue()) {
+ optionalTLVs.put(type, tlv);
+ }
+ }
+
+ /**
+ * @param type
+ * - description of the type of TLV
+ * @return LLDPTLV - full TLV
+ */
+ public LLDPTLV getTLV(final String type) {
+ return getFromTLVs(getType(type));
+ }
+
+ public LLDPTLV getCustomTLV(final CustomTLVKey key) {
+ return customTLVs.get(key);
+ }
+
+ /**
+ * @param type
+ * - description of the type of TLV
+ * @param tlv
+ * - tlv to set
+ */
+ public void setTLV(final String type, final LLDPTLV tlv) {
+ putToTLVs(getType(type), tlv);
+ }
+
+ /**
+ * @return the chassisId TLV
+ */
+ public LLDPTLV getChassisId() {
+ return getTLV(CHASSISID);
+ }
+
+ /**
+ * @param chassisId
+ * - the chassisId to set
+ */
+ public LLDP setChassisId(final LLDPTLV chassisId) {
+ setTLV(CHASSISID, chassisId);
+ return this;
+ }
+
+ /**
+ * @return the SystemName TLV
+ */
+ public LLDPTLV getSystemNameId() {
+ return getTLV(SYSTEMNAMEID);
+ }
+
+ /**
+ * @param systemNameId
+ * - the systemNameId to set
+ */
+ public LLDP setSystemNameId(final LLDPTLV systemNameId) {
+ setTLV(SYSTEMNAMEID, systemNameId);
+ return this;
+ }
+
+ /**
+ * @return LLDPTLV - the portId TLV
+ */
+ public LLDPTLV getPortId() {
+ return getTLV(PORTID);
+ }
+
+ /**
+ * @param portId
+ * - the portId to set
+ * @return LLDP
+ */
+ public LLDP setPortId(final LLDPTLV portId) {
+ setTLV(PORTID, portId);
+ return this;
+ }
+
+ /**
+ * @return LLDPTLV - the ttl TLV
+ */
+ public LLDPTLV getTtl() {
+ return getTLV(TTL);
+ }
+
+ /**
+ * @param ttl
+ * - the ttl to set
+ * @return LLDP
+ */
+ public LLDP setTtl(final LLDPTLV ttl) {
+ setTLV(TTL, ttl);
+ return this;
+ }
+
+ /**
+ * @return the optionalTLVList
+ */
+ public Iterable<LLDPTLV> getOptionalTLVList() {
+ return optionalTLVs.values();
+ }
+
+ /**
+ * @return the customTlvList
+ */
+ public Iterable<LLDPTLV> getCustomTlvList() {
+ return customTLVs.values();
+ }
+
+ /**
+ * @param optionalTLVList
+ * the optionalTLVList to set
+ * @return LLDP
+ */
+ public LLDP setOptionalTLVList(final List<LLDPTLV> optionalTLVList) {
+ for (LLDPTLV tlv : optionalTLVList) {
+ optionalTLVs.put(tlv.getType(), tlv);
+ }
+ return this;
+ }
+
+ /**
+ * @param customTLV
+ * the list of custom TLVs to set
+ * @return this LLDP
+ */
+ public LLDP addCustomTLV(final LLDPTLV customTLV) {
+ CustomTLVKey key = new CustomTLVKey(LLDPTLV.extractCustomOUI(customTLV),
+ LLDPTLV.extractCustomSubtype(customTLV));
+ customTLVs.put(key, customTLV);
+
+ return this;
+ }
+
+ @Override
+ public Packet deserialize(final byte[] data, final int bitOffset, final int size) throws PacketException {
+ int lldpOffset = bitOffset; // LLDP start
+ int lldpSize = size; // LLDP size
+
+ if (LOG.isTraceEnabled()) {
+ LOG.trace("LLDP: {} (offset {} bitsize {})", new Object[] { HexEncode.bytesToHexString(data),
+ lldpOffset, lldpSize });
+ }
+ /*
+ * Deserialize the TLVs until we reach the end of the packet
+ */
+ while (lldpSize > 0) {
+ LLDPTLV tlv = new LLDPTLV();
+ tlv.deserialize(data, lldpOffset, lldpSize);
+ if (tlv.getType() == 0 && tlv.getLength() == 0) {
+ break;
+ }
+ int tlvSize = tlv.getTLVSize(); // Size of current TLV in bits
+ lldpOffset += tlvSize;
+ lldpSize -= tlvSize;
+ if (tlv.getType() == LLDPTLV.TLVType.Custom.getValue()) {
+ addCustomTLV(tlv);
+ } else {
+ this.putToTLVs(tlv.getType(), tlv);
+ }
+ }
+ return this;
+ }
+
+ @Override
+ public byte[] serialize() throws PacketException {
+ int startOffset = 0;
+ byte[] serializedBytes = new byte[getLLDPPacketLength()];
+
+ final Iterable<LLDPTLV> allTlvs = Iterables.concat(mandatoryTLVs.values(), optionalTLVs.values(), customTLVs.values());
+ for (LLDPTLV tlv : allTlvs) {
+ int numBits = tlv.getTLVSize();
+ try {
+ BitBufferHelper.setBytes(serializedBytes, tlv.serialize(), startOffset, numBits);
+ } catch (final BufferException e) {
+ throw new PacketException(e.getMessage());
+ }
+ startOffset += numBits;
+ }
+ // Now add the empty LLDPTLV at the end
+ try {
+ BitBufferHelper.setBytes(serializedBytes, LLDP.emptyTLV.serialize(), startOffset,
+ LLDP.emptyTLV.getTLVSize());
+ } catch (final BufferException e) {
+ throw new PacketException(e.getMessage());
+ }
+
+ if (LOG.isTraceEnabled()) {
+ LOG.trace("LLDP: serialized: {}", HexEncode.bytesToHexString(serializedBytes));
+ }
+ return serializedBytes;
+ }
+
+ /**
+ * Returns the size of LLDP packet in bytes
+ *
+ * @return int - LLDP Packet size in bytes
+ */
+ private int getLLDPPacketLength() {
+ int len = 0;
+
+ for (LLDPTLV lldptlv : Iterables.concat(mandatoryTLVs.values(), optionalTLVs.values(), customTLVs.values())) {
+ len += lldptlv.getTLVSize();
+ }
+
+ len += LLDP.emptyTLV.getTLVSize();
+
+ return len / NetUtils.NumBitsInAByte;
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import org.apache.commons.lang3.ArrayUtils;
+import org.slf4j.LoggerFactory;
+
+import org.slf4j.Logger;
+import java.io.UnsupportedEncodingException;
+import java.nio.charset.Charset;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.LinkedHashMap;
+import java.util.Map;
+import org.apache.commons.lang3.tuple.MutablePair;
+import org.apache.commons.lang3.tuple.Pair;
+
+/**
+ * Class that represents the LLDPTLV objects
+ */
+
+public class LLDPTLV extends Packet {
+ private static final String TYPE = "Type";
+ private static final String LENGTH = "Length";
+ private static final String VALUE = "Value";
+ private static final int LLDPTLVFields = 3;
+
+ /** OpenFlow OUI */
+ public static final byte[] OFOUI = new byte[] { (byte) 0x00, (byte) 0x26,
+ (byte) 0xe1 };
+
+ /** Length of Organizationally defined subtype field of TLV in bytes */
+ private static final byte customTlvSubTypeLength = (byte)1;
+
+ /** OpenFlow subtype: nodeConnectorId of source */
+ public static final byte[] CUSTOM_TLV_SUB_TYPE_NODE_CONNECTOR_ID = new byte[] { 0 };
+
+ /** OpenFlow subtype: custom sec = hash code of verification of origin of LLDP */
+ public static final byte[] CUSTOM_TLV_SUB_TYPE_CUSTOM_SEC = new byte[] { 1 };
+
+ public static final int customTlvOffset = OFOUI.length + customTlvSubTypeLength;
+ public static final byte chassisIDSubType[] = new byte[] { 4 }; // MAC address for the system
+ public static final byte portIDSubType[] = new byte[] { 7 }; // locally assigned
+
+ private static final Logger LOG = LoggerFactory.getLogger(LLDPTLV.class);
+
+ public enum TLVType {
+ Unknown((byte) 0), ChassisID((byte) 1), PortID((byte) 2), TTL((byte) 3), PortDesc(
+ (byte) 4), SystemName((byte) 5), SystemDesc((byte) 6), Custom(
+ (byte) 127);
+
+ private byte value;
+
+ TLVType(final byte value) {
+ this.value = value;
+ }
+
+ public byte getValue() {
+ return value;
+ }
+ }
+
+ private static Map<String, Pair<Integer, Integer>> fieldCoordinates = new LinkedHashMap<String, Pair<Integer, Integer>>() {
+ private static final long serialVersionUID = 1L;
+
+ {
+ put(TYPE, new MutablePair<>(0, 7));
+ put(LENGTH, new MutablePair<>(7, 9));
+ put(VALUE, new MutablePair<>(16, 0));
+ }
+ };
+
+ protected Map<String, byte[]> fieldValues;
+
+ /**
+ * Default constructor that creates and sets the hash map values and sets
+ * the payload to null
+ */
+ public LLDPTLV() {
+ payload = null;
+ fieldValues = new HashMap<>(LLDPTLVFields);
+ hdrFieldCoordMap = fieldCoordinates;
+ hdrFieldsMap = fieldValues;
+ }
+
+ /**
+ * Constructor that writes the passed LLDPTLV values to the hdrFieldsMap
+ */
+ public LLDPTLV(final LLDPTLV other) {
+ for (Map.Entry<String, byte[]> entry : other.hdrFieldsMap.entrySet()) {
+ this.hdrFieldsMap.put(entry.getKey(), entry.getValue());
+ }
+ }
+
+ /**
+ * @return int - the length of TLV
+ */
+ public int getLength() {
+ return (int) BitBufferHelper.toNumber(fieldValues.get(LENGTH),
+ fieldCoordinates.get(LENGTH).getRight().intValue());
+ }
+
+ /**
+ * @return byte - the type of TLV
+ */
+ public byte getType() {
+ return BitBufferHelper.getByte(fieldValues.get(TYPE));
+ }
+
+ /**
+ * @return byte[] - the value field of TLV
+ */
+ public byte[] getValue() {
+ return fieldValues.get(VALUE);
+ }
+
+ /**
+ * @param type the type to set
+ * @return LLDPTLV
+ */
+ public LLDPTLV setType(final byte type) {
+ byte[] lldpTLVtype = { type };
+ fieldValues.put(TYPE, lldpTLVtype);
+ return this;
+ }
+
+ /**
+ * @param length the length to set
+ * @return LLDPTLV
+ */
+ public LLDPTLV setLength(final short length) {
+ fieldValues.put(LENGTH, BitBufferHelper.toByteArray(length));
+ return this;
+ }
+
+ /**
+ * @param value the value to set
+ * @return LLDPTLV
+ */
+ public LLDPTLV setValue(final byte[] value) {
+ fieldValues.put(VALUE, value);
+ return this;
+ }
+
+ @Override
+ public void setHeaderField(final String headerField, final byte[] readValue) {
+ hdrFieldsMap.put(headerField, readValue);
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = super.hashCode();
+ result = prime * result
+ + ((fieldValues == null) ? 0 : fieldValues.hashCode());
+ return result;
+ }
+
+ @Override
+ public boolean equals(final Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (!super.equals(obj)) {
+ return false;
+ }
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+ LLDPTLV other = (LLDPTLV) obj;
+ if (fieldValues == null) {
+ if (other.fieldValues != null) {
+ return false;
+ }
+ } else if (!fieldValues.equals(other.fieldValues)) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public int getfieldnumBits(final String fieldName) {
+ if (fieldName.equals(VALUE)) {
+ return (NetUtils.NumBitsInAByte * BitBufferHelper.getShort(
+ fieldValues.get(LENGTH), fieldCoordinates.get(LENGTH)
+ .getRight().intValue()));
+ }
+ return fieldCoordinates.get(fieldName).getRight();
+ }
+
+ /**
+ * Returns the size in bits of the whole TLV
+ *
+ * @return int - size in bits of full TLV
+ */
+ public int getTLVSize() {
+ return (LLDPTLV.fieldCoordinates.get(TYPE).getRight() + // static
+ LLDPTLV.fieldCoordinates.get(LENGTH).getRight() + // static
+ getfieldnumBits(VALUE)); // variable
+ }
+
+ /**
+ * Creates the SystemName TLV value
+ *
+ * @param nodeId
+ * node identifier string
+ * @return the SystemName TLV value in byte array
+ */
+ static public byte[] createSystemNameTLVValue(final String nodeId) {
+ byte[] nid = nodeId.getBytes();
+ return nid;
+ }
+
+ /**
+ * Creates the ChassisID TLV value including the subtype and ChassisID
+ * string
+ *
+ * @param nodeId
+ * node identifier string
+ * @return the ChassisID TLV value in byte array
+ */
+ static public byte[] createChassisIDTLVValue(final String nodeId) {
+ byte[] nid = HexEncode.bytesFromHexString(nodeId);
+ byte[] cid = new byte[6];
+ int srcPos = 0, dstPos = 0;
+
+ if (nid.length > cid.length) {
+ srcPos = nid.length - cid.length;
+ } else {
+ dstPos = cid.length - nid.length;
+ }
+ System.arraycopy(nid, srcPos, cid, dstPos, cid.length);
+
+ byte[] cidValue = new byte[cid.length + chassisIDSubType.length];
+
+ System.arraycopy(chassisIDSubType, 0, cidValue, 0,
+ chassisIDSubType.length);
+ System.arraycopy(cid, 0, cidValue, chassisIDSubType.length, cid.length);
+
+ return cidValue;
+ }
+
+ /**
+ * Creates the PortID TLV value including the subtype and PortID string
+ *
+ * @param portId
+ * port identifier string
+ * @return the PortID TLV value in byte array
+ */
+ static public byte[] createPortIDTLVValue(final String portId) {
+ byte[] pid = portId.getBytes(Charset.defaultCharset());
+ byte[] pidValue = new byte[pid.length + portIDSubType.length];
+
+ System.arraycopy(portIDSubType, 0, pidValue, 0, portIDSubType.length);
+ System.arraycopy(pid, 0, pidValue, portIDSubType.length, pid.length);
+
+ return pidValue;
+ }
+
+ /**
+ * Creates the custom TLV value including OUI, subtype and custom string
+ *
+ * @param customString
+ * port identifier string
+ * @return the custom TLV value in byte array
+ * @see #createCustomTLVValue(byte[],byte[])
+ */
+ static public byte[] createCustomTLVValue(final String customString) {
+ byte[] customByteArray = customString.getBytes(Charset.defaultCharset());
+ return createCustomTLVValue(CUSTOM_TLV_SUB_TYPE_NODE_CONNECTOR_ID, customByteArray);
+ }
+
+ /**
+ * Creates the custom TLV value including OUI, subtype and custom string
+ * @param subtype openflow subtype
+ * @param customByteArray
+ * port identifier string
+ * @return the custom TLV value in byte array
+ */
+ static public byte[] createCustomTLVValue(final byte[] subtype, final byte[] customByteArray) {
+ byte[] customValue = new byte[customTlvOffset + customByteArray.length];
+
+ System.arraycopy(OFOUI, 0, customValue, 0, OFOUI.length);
+ System.arraycopy(subtype, 0, customValue, OFOUI.length, 1);
+ System.arraycopy(customByteArray, 0, customValue, customTlvOffset,
+ customByteArray.length);
+
+ return customValue;
+ }
+
+ /**
+ * Retrieves the string from TLV value and returns it in HexString format
+ *
+ * @param tlvValue
+ * the TLV value
+ * @param tlvLen
+ * the TLV length
+ * @return the HexString
+ */
+ static public String getHexStringValue(final byte[] tlvValue, final int tlvLen) {
+ byte[] cidBytes = new byte[tlvLen - chassisIDSubType.length];
+ System.arraycopy(tlvValue, chassisIDSubType.length, cidBytes, 0,
+ cidBytes.length);
+ return HexEncode.bytesToHexStringFormat(cidBytes);
+ }
+
+ /**
+ * Retrieves the string from TLV value
+ *
+ * @param tlvValue
+ * the TLV value
+ * @param tlvLen
+ * the TLV length
+ * @return the string
+ */
+ static public String getStringValue(final byte[] tlvValue, final int tlvLen) {
+ byte[] pidSubType = new byte[portIDSubType.length];
+ byte[] pidBytes = new byte[tlvLen - portIDSubType.length];
+ System.arraycopy(tlvValue, 0, pidSubType, 0,
+ pidSubType.length);
+ System.arraycopy(tlvValue, portIDSubType.length, pidBytes, 0,
+ pidBytes.length);
+ if (pidSubType[0] == (byte) 0x3) {
+ return HexEncode.bytesToHexStringFormat(pidBytes);
+ } else {
+ return (new String(pidBytes, Charset.defaultCharset()));
+ }
+ }
+
+ /**
+ * Retrieves the custom string from the Custom TLV value which includes OUI,
+ * subtype and custom string
+ *
+ * @param customTlvValue
+ * the custom TLV value
+ * @param customTlvLen
+ * the custom TLV length
+ * @return the custom string
+ */
+ static public String getCustomString(final byte[] customTlvValue, final int customTlvLen) {
+ String customString = "";
+ byte[] vendor = new byte[3];
+ System.arraycopy(customTlvValue, 0, vendor, 0, vendor.length);
+ if (Arrays.equals(vendor, LLDPTLV.OFOUI)) {
+ int customArrayLength = customTlvLen - customTlvOffset;
+ byte[] customArray = new byte[customArrayLength];
+ System.arraycopy(customTlvValue, customTlvOffset, customArray, 0,
+ customArrayLength);
+ try {
+ customString = new String(customArray, "UTF-8");
+ } catch (final UnsupportedEncodingException e) {
+ }
+ }
+
+ return customString;
+ }
+
+ public static int extractCustomOUI(final LLDPTLV lldptlv) {
+ byte[] value = lldptlv.getValue();
+ return BitBufferHelper.getInt(ArrayUtils.subarray(value, 0, 3));
+ }
+
+ public static byte extractCustomSubtype(final LLDPTLV lldptlv) {
+ byte[] value = lldptlv.getValue();
+ return BitBufferHelper.getByte(ArrayUtils.subarray(value, 3, 4));
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013, 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.net.Inet4Address;
+import java.net.Inet6Address;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.util.Arrays;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Utility class containing the common utility functions needed for operating on
+ * networking data structures
+ */
+public abstract class NetUtils {
+ protected static final Logger LOG = LoggerFactory.getLogger(NetUtils.class);
+ /**
+ * Constant holding the number of bits in a byte
+ */
+ public static final int NumBitsInAByte = 8;
+
+ /**
+ * Constant holding the number of bytes in MAC Address
+ */
+ public static final int MACAddrLengthInBytes = 6;
+
+ /**
+ * Constant holding the number of words in MAC Address
+ */
+ public static final int MACAddrLengthInWords = 3;
+
+ /**
+ * Constant holding the broadcast MAC address
+ */
+ private static final byte[] BroadcastMACAddr = {-1, -1, -1, -1, -1, -1};
+
+ /**
+ * Converts a 4 bytes array into an integer number
+ *
+ * @param ba
+ * the 4 bytes long byte array
+ * @return the integer number
+ */
+ public static int byteArray4ToInt(final byte[] ba) {
+ if (ba == null || ba.length != 4) {
+ return 0;
+ }
+ return (0xff & ba[0]) << 24 | (0xff & ba[1]) << 16 | (0xff & ba[2]) << 8 | 0xff & ba[3];
+ }
+
+ /**
+ * Converts a 6 bytes array into a long number MAC addresses.
+ *
+ * @param ba
+ * The 6 bytes long byte array.
+ * @return The long number.
+ * Zero is returned if {@code ba} is {@code null} or
+ * the length of it is not six.
+ */
+ public static long byteArray6ToLong(final byte[] ba) {
+ if (ba == null || ba.length != MACAddrLengthInBytes) {
+ return 0L;
+ }
+ long num = 0L;
+ int i = 0;
+ do {
+ num <<= NumBitsInAByte;
+ num |= 0xff & ba[i];
+ i++;
+ } while (i < MACAddrLengthInBytes);
+ return num;
+ }
+
+ /**
+ * Converts a long number to a 6 bytes array for MAC addresses.
+ *
+ * @param addr
+ * The long number.
+ * @return The byte array.
+ */
+ public static byte[] longToByteArray6(long addr){
+ byte[] mac = new byte[MACAddrLengthInBytes];
+ int i = MACAddrLengthInBytes - 1;
+ do {
+ mac[i] = (byte) addr;
+ addr >>>= NumBitsInAByte;
+ i--;
+ } while (i >= 0);
+ return mac;
+ }
+
+ /**
+ * Converts an integer number into a 4 bytes array
+ *
+ * @param i
+ * the integer number
+ * @return the byte array
+ */
+ public static byte[] intToByteArray4(final int i) {
+ return new byte[] { (byte) (i >> 24 & 0xff), (byte) (i >> 16 & 0xff), (byte) (i >> 8 & 0xff),
+ (byte) (i & 0xff) };
+ }
+
+ /**
+ * Converts an IP address passed as integer value into the respective
+ * InetAddress object
+ *
+ * @param address
+ * the IP address in integer form
+ * @return the IP address in InetAddress form
+ */
+ public static InetAddress getInetAddress(final int address) {
+ InetAddress ip = null;
+ try {
+ ip = InetAddress.getByAddress(NetUtils.intToByteArray4(address));
+ } catch (final UnknownHostException e) {
+ LOG.error("", e);
+ }
+ return ip;
+ }
+
+ /**
+ * Return the InetAddress Network Mask given the length of the prefix bit
+ * mask. The prefix bit mask indicates the contiguous leading bits that are
+ * NOT masked out. Example: A prefix bit mask length of 8 will give an
+ * InetAddress Network Mask of 255.0.0.0
+ *
+ * @param prefixMaskLength
+ * integer representing the length of the prefix network mask
+ * @param isV6
+ * boolean representing the IP version of the returned address
+ * @return
+ */
+ public static InetAddress getInetNetworkMask(final int prefixMaskLength, final boolean isV6) {
+ if (prefixMaskLength < 0 || !isV6 && prefixMaskLength > 32 || isV6 && prefixMaskLength > 128) {
+ return null;
+ }
+ byte v4Address[] = { 0, 0, 0, 0 };
+ byte v6Address[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
+ byte address[] = isV6 ? v6Address : v4Address;
+ int numBytes = prefixMaskLength / 8;
+ int numBits = prefixMaskLength % 8;
+ int i = 0;
+ for (; i < numBytes; i++) {
+ address[i] = (byte) 0xff;
+ }
+ if (numBits > 0) {
+ int rem = 0;
+ for (int j = 0; j < numBits; j++) {
+ rem |= 1 << 7 - j;
+ }
+ address[i] = (byte) rem;
+ }
+
+ try {
+ return InetAddress.getByAddress(address);
+ } catch (final UnknownHostException e) {
+ LOG.error("", e);
+ }
+ return null;
+ }
+
+ /**
+ * Returns the prefix size in bits of the specified subnet mask. Example:
+ * For the subnet mask ff.ff.ff.e0 it returns 25 while for ff.00.00.00 it
+ * returns 8. If the passed subnetMask array is null, 0 is returned.
+ *
+ * @param subnetMask
+ * the subnet mask as byte array
+ * @return the prefix length as number of bits
+ */
+ public static int getSubnetMaskLength(final byte[] subnetMask) {
+ int maskLength = 0;
+ if (subnetMask != null && (subnetMask.length == 4 || subnetMask.length == 16)) {
+ int index = 0;
+ while (index < subnetMask.length && subnetMask[index] == (byte) 0xFF) {
+ maskLength += NetUtils.NumBitsInAByte;
+ index++;
+ }
+ if (index != subnetMask.length) {
+ int bits = NetUtils.NumBitsInAByte - 1;
+ while (bits >= 0 && (subnetMask[index] & 1 << bits) != 0) {
+ bits--;
+ maskLength++;
+ }
+ }
+ }
+ return maskLength;
+ }
+
+ /**
+ * Returns the prefix size in bits of the specified subnet mask. Example:
+ * For the subnet mask 255.255.255.128 it returns 25 while for 255.0.0.0 it
+ * returns 8. If the passed subnetMask object is null, 0 is returned
+ *
+ * @param subnetMask
+ * the subnet mask as InetAddress
+ * @return the prefix length as number of bits
+ */
+ public static int getSubnetMaskLength(final InetAddress subnetMask) {
+ return subnetMask == null ? 0 : NetUtils.getSubnetMaskLength(subnetMask.getAddress());
+ }
+
+ /**
+ * Given an IP address and a prefix network mask length, it returns the
+ * equivalent subnet prefix IP address Example: for ip = "172.28.30.254" and
+ * maskLen = 25 it will return "172.28.30.128"
+ *
+ * @param ip
+ * the IP address in InetAddress form
+ * @param maskLen
+ * the length of the prefix network mask
+ * @return the subnet prefix IP address in InetAddress form
+ */
+ public static InetAddress getSubnetPrefix(final InetAddress ip, final int maskLen) {
+ int bytes = maskLen / 8;
+ int bits = maskLen % 8;
+ byte modifiedByte;
+ byte[] sn = ip.getAddress();
+ if (bits > 0) {
+ modifiedByte = (byte) (sn[bytes] >> 8 - bits);
+ sn[bytes] = (byte) (modifiedByte << 8 - bits);
+ bytes++;
+ }
+ for (; bytes < sn.length; bytes++) {
+ sn[bytes] = (byte) 0;
+ }
+ try {
+ return InetAddress.getByAddress(sn);
+ } catch (final UnknownHostException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Checks if the test address and mask conflicts with the filter address and
+ * mask
+ *
+ * For example:
+ * testAddress: 172.28.2.23
+ * testMask: 255.255.255.0
+ * filterAddress: 172.28.1.10
+ * testMask: 255.255.255.0
+ * do conflict
+ *
+ * testAddress: 172.28.2.23
+ * testMask: 255.255.255.0
+ * filterAddress: 172.28.1.10
+ * testMask: 255.255.0.0
+ * do not conflict
+ *
+ * Null parameters are permitted
+ *
+ * @param testAddress
+ * @param filterAddress
+ * @param testMask
+ * @param filterMask
+ * @return
+ */
+ public static boolean inetAddressConflict(final InetAddress testAddress, final InetAddress filterAddress, final InetAddress testMask,
+ final InetAddress filterMask) {
+ // Sanity check
+ if (testAddress == null || filterAddress == null) {
+ return false;
+ }
+
+ // Presence check
+ if (isAny(testAddress) || isAny(filterAddress)) {
+ return false;
+ }
+
+ int testMaskLen = testMask == null ? testAddress instanceof Inet4Address ? 32 : 128 : NetUtils
+ .getSubnetMaskLength(testMask);
+ int filterMaskLen = filterMask == null ? testAddress instanceof Inet4Address ? 32 : 128 : NetUtils
+ .getSubnetMaskLength(filterMask);
+
+ // Mask length check. Test mask has to be more specific than filter one
+ if (testMaskLen < filterMaskLen) {
+ return true;
+ }
+
+ // Subnet Prefix on filter mask length must be the same
+ InetAddress prefix1 = getSubnetPrefix(testAddress, filterMaskLen);
+ InetAddress prefix2 = getSubnetPrefix(filterAddress, filterMaskLen);
+ return !prefix1.equals(prefix2);
+ }
+
+ /**
+ * Returns true if the passed MAC address is all zero
+ *
+ * @param mac
+ * the byte array representing the MAC address
+ * @return true if all MAC bytes are zero
+ */
+ public static boolean isZeroMAC(final byte[] mac) {
+ for (short i = 0; i < 6; i++) {
+ if (mac[i] != 0) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Returns true if the MAC address is the broadcast MAC address and false
+ * otherwise.
+ *
+ * @param MACAddress
+ * @return
+ */
+ public static boolean isBroadcastMACAddr(final byte[] MACAddress) {
+ if (MACAddress.length == MACAddrLengthInBytes) {
+ for (int i = 0; i < 6; i++) {
+ if (MACAddress[i] != BroadcastMACAddr[i]) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ return false;
+ }
+ /**
+ * Returns true if the MAC address is a unicast MAC address and false
+ * otherwise.
+ *
+ * @param MACAddress
+ * @return
+ */
+ public static boolean isUnicastMACAddr(final byte[] MACAddress) {
+ if (MACAddress.length == MACAddrLengthInBytes) {
+ return (MACAddress[0] & 1) == 0;
+ }
+ return false;
+ }
+
+ /**
+ * Returns true if the MAC address is a multicast MAC address and false
+ * otherwise. Note that this explicitly returns false for the broadcast MAC
+ * address.
+ *
+ * @param MACAddress
+ * @return
+ */
+ public static boolean isMulticastMACAddr(final byte[] MACAddress) {
+ if (MACAddress.length == MACAddrLengthInBytes && !isBroadcastMACAddr(MACAddress)) {
+ return (MACAddress[0] & 1) != 0;
+ }
+ return false;
+ }
+
+ /**
+ * Returns true if the passed InetAddress contains all zero
+ *
+ * @param ip
+ * the IP address to test
+ * @return true if the address is all zero
+ */
+ public static boolean isAny(final InetAddress ip) {
+ for (byte b : ip.getAddress()) {
+ if (b != 0) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ public static boolean fieldsConflict(final int field1, final int field2) {
+ if (field1 == 0 || field2 == 0 || field1 == field2) {
+ return false;
+ }
+ return true;
+ }
+
+ public static InetAddress parseInetAddress(final String addressString) {
+ InetAddress address = null;
+ try {
+ address = InetAddress.getByName(addressString);
+ } catch (final UnknownHostException e) {
+ LOG.error("", e);
+ }
+ return address;
+ }
+
+ /**
+ * Checks if the passed IP v4 address in string form is valid The address
+ * may specify a mask at the end as "/MM"
+ *
+ * @param cidr
+ * the v4 address as A.B.C.D/MM
+ * @return
+ */
+ public static boolean isIPv4AddressValid(final String cidr) {
+ if (cidr == null) {
+ return false;
+ }
+
+ String values[] = cidr.split("/");
+ Pattern ipv4Pattern = Pattern
+ .compile("(([01]?\\d\\d?|2[0-4]\\d|25[0-5])\\.){3}([01]?\\d\\d?|2[0-4]\\d|25[0-5])");
+ Matcher mm = ipv4Pattern.matcher(values[0]);
+ if (!mm.matches()) {
+ return false;
+ }
+ if (values.length >= 2) {
+ int prefix = Integer.valueOf(values[1]);
+ if (prefix < 0 || prefix > 32) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Checks if the passed IP v6 address in string form is valid The address
+ * may specify a mask at the end as "/MMM"
+ *
+ * @param cidr
+ * the v6 address as A::1/MMM
+ * @return
+ */
+ public static boolean isIPv6AddressValid(final String cidr) {
+ if (cidr == null) {
+ return false;
+ }
+
+ String values[] = cidr.split("/");
+ try {
+ // when given an IP address, InetAddress.getByName validates the ip
+ // address
+ InetAddress addr = InetAddress.getByName(values[0]);
+ if (!(addr instanceof Inet6Address)) {
+ return false;
+ }
+ } catch (final UnknownHostException ex) {
+ return false;
+ }
+
+ if (values.length >= 2) {
+ int prefix = Integer.valueOf(values[1]);
+ if (prefix < 0 || prefix > 128) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Checks if the passed IP address in string form is a valid v4 or v6
+ * address. The address may specify a mask at the end as "/MMM"
+ *
+ * @param cidr
+ * the v4 or v6 address as IP/MMM
+ * @return
+ */
+ public static boolean isIPAddressValid(final String cidr) {
+ return NetUtils.isIPv4AddressValid(cidr) || NetUtils.isIPv6AddressValid(cidr);
+ }
+
+ /*
+ * Following utilities are useful when you need to compare or bit shift java
+ * primitive type variable which are inherently signed
+ */
+ /**
+ * Returns the unsigned value of the passed byte variable
+ *
+ * @param b
+ * the byte value
+ * @return the int variable containing the unsigned byte value
+ */
+ public static int getUnsignedByte(final byte b) {
+ return b & 0xFF;
+ }
+
+ /**
+ * Return the unsigned value of the passed short variable
+ *
+ * @param s
+ * the short value
+ * @return the int variable containing the unsigned short value
+ */
+ public static int getUnsignedShort(final short s) {
+ return s & 0xFFFF;
+ }
+
+ /**
+ * Returns the highest v4 or v6 InetAddress
+ *
+ * @param v6
+ * true for IPv6, false for Ipv4
+ * @return The highest IPv4 or IPv6 address
+ */
+ public static InetAddress gethighestIP(final boolean v6) {
+ try {
+ return v6 ? InetAddress.getByName("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff") : InetAddress
+ .getByName("255.255.255.255");
+ } catch (final UnknownHostException e) {
+ return null;
+ }
+ }
+
+ /**
+ * Returns Broadcast MAC Address
+ *
+ * @return the byte array containing broadcast mac address
+ */
+ public static byte[] getBroadcastMACAddr() {
+ return Arrays.copyOf(BroadcastMACAddr, BroadcastMACAddr.length);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013, 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import java.util.Arrays;
+import java.util.Map;
+import java.util.Map.Entry;
+
+import org.apache.commons.lang3.tuple.Pair;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Abstract class which represents the generic network packet object It provides
+ * the basic methods which are common for all the packets, like serialize and
+ * deserialize
+ */
+
+public abstract class Packet {
+ protected static final Logger LOG = LoggerFactory.getLogger(Packet.class);
+ // Access level granted to this packet
+ protected boolean writeAccess;
+ // When deserialized from wire, packet could result corrupted
+ protected boolean corrupted;
+ // The packet that encapsulate this packet
+ protected Packet parent;
+ // The packet encapsulated by this packet
+ protected Packet payload;
+ // The unparsed raw payload carried by this packet
+ protected byte[] rawPayload;
+ // Bit coordinates of packet header fields
+ protected Map<String, Pair<Integer, Integer>> hdrFieldCoordMap;
+ // Header fields values: Map<FieldName,Value>
+ protected Map<String, byte[]> hdrFieldsMap;
+ // The class of the encapsulated packet object
+ protected Class<? extends Packet> payloadClass;
+
+ public Packet() {
+ writeAccess = false;
+ corrupted = false;
+ }
+
+ public Packet(final boolean writeAccess) {
+ this.writeAccess = writeAccess;
+ corrupted = false;
+ }
+
+ public Packet getParent() {
+ return parent;
+ }
+
+ public Packet getPayload() {
+ return payload;
+ }
+
+ public void setParent(final Packet parent) {
+ this.parent = parent;
+ }
+
+ public void setPayload(final Packet payload) {
+ this.payload = payload;
+ }
+
+ public void setHeaderField(final String headerField, final byte[] readValue) {
+ hdrFieldsMap.put(headerField, readValue);
+ }
+
+ /**
+ * This method deserializes the data bits obtained from the wire into the
+ * respective header and payload which are of type Packet
+ *
+ * @param data - data from wire to deserialize
+ * @param bitOffset bit position where packet header starts in data
+ * array
+ * @param size size of packet in bits
+ * @return Packet
+ * @throws PacketException
+ */
+ public Packet deserialize(final byte[] data, final int bitOffset, final int size)
+ throws PacketException {
+
+ // Deserialize the header fields one by one
+ int startOffset = 0, numBits = 0;
+ for (Entry<String, Pair<Integer, Integer>> pairs : hdrFieldCoordMap
+ .entrySet()) {
+ String hdrField = pairs.getKey();
+ startOffset = bitOffset + this.getfieldOffset(hdrField);
+ numBits = this.getfieldnumBits(hdrField);
+
+ byte[] hdrFieldBytes = null;
+ try {
+ hdrFieldBytes = BitBufferHelper.getBits(data, startOffset,
+ numBits);
+ } catch (final BufferException e) {
+ throw new PacketException(e.getMessage());
+ }
+
+ /*
+ * Store the raw read value, checks the payload type and set the
+ * payloadClass accordingly
+ */
+ this.setHeaderField(hdrField, hdrFieldBytes);
+
+ if (LOG.isTraceEnabled()) {
+ LOG.trace("{}: {}: {} (offset {} bitsize {})",
+ new Object[] { this.getClass().getSimpleName(), hdrField,
+ HexEncode.bytesToHexString(hdrFieldBytes),
+ startOffset, numBits });
+ }
+ }
+
+ // Deserialize the payload now
+ int payloadStart = startOffset + numBits;
+ int payloadSize = data.length * NetUtils.NumBitsInAByte - payloadStart;
+
+ if (payloadClass != null) {
+ try {
+ payload = payloadClass.newInstance();
+ } catch (final Exception e) {
+ throw new RuntimeException(
+ "Error parsing payload for Ethernet packet", e);
+ }
+ payload.deserialize(data, payloadStart, payloadSize);
+ payload.setParent(this);
+ } else {
+ /*
+ * The payload class was not set, it means no class for parsing
+ * this payload is present. Let's store the raw payload if any.
+ */
+ int start = payloadStart / NetUtils.NumBitsInAByte;
+ int stop = start + payloadSize / NetUtils.NumBitsInAByte;
+ rawPayload = Arrays.copyOfRange(data, start, stop);
+ }
+
+
+ // Take care of computation that can be done only after deserialization
+ postDeserializeCustomOperation(data, payloadStart - getHeaderSize());
+
+ return this;
+ }
+
+ /**
+ * This method serializes the header and payload from the respective
+ * packet class, into a single stream of bytes to be sent on the wire
+ *
+ * @return The byte array representing the serialized Packet
+ * @throws PacketException
+ */
+ public byte[] serialize() throws PacketException {
+
+ // Acquire or compute the serialized payload
+ byte[] payloadBytes = null;
+ if (payload != null) {
+ payloadBytes = payload.serialize();
+ } else if (rawPayload != null) {
+ payloadBytes = rawPayload;
+ }
+ int payloadSize = payloadBytes == null ? 0 : payloadBytes.length;
+
+ // Allocate the buffer to contain the full (header + payload) packet
+ int headerSize = this.getHeaderSize() / NetUtils.NumBitsInAByte;
+ byte packetBytes[] = new byte[headerSize + payloadSize];
+ if (payloadBytes != null) {
+ System.arraycopy(payloadBytes, 0, packetBytes, headerSize, payloadSize);
+ }
+
+ // Serialize this packet header, field by field
+ for (Map.Entry<String, Pair<Integer, Integer>> pairs : hdrFieldCoordMap
+ .entrySet()) {
+ String field = pairs.getKey();
+ byte[] fieldBytes = hdrFieldsMap.get(field);
+ // Let's skip optional fields when not set
+ if (fieldBytes != null) {
+ try {
+ BitBufferHelper.setBytes(packetBytes, fieldBytes,
+ getfieldOffset(field), getfieldnumBits(field));
+ } catch (final BufferException e) {
+ throw new PacketException(e.getMessage());
+ }
+ }
+ }
+
+ // Perform post serialize operations (like checksum computation)
+ postSerializeCustomOperation(packetBytes);
+
+ if (LOG.isTraceEnabled()) {
+ LOG.trace("{}: {}", this.getClass().getSimpleName(),
+ HexEncode.bytesToHexString(packetBytes));
+ }
+
+ return packetBytes;
+ }
+
+ /**
+ * This method gets called at the end of the serialization process It is
+ * intended for the child packets to insert some custom data into the output
+ * byte stream which cannot be done or cannot be done efficiently during the
+ * normal Packet.serialize() path. An example is the checksum computation
+ * for IPv4
+ *
+ * @param myBytes serialized bytes
+ * @throws PacketException
+ */
+ protected void postSerializeCustomOperation(byte[] myBytes)
+ throws PacketException {
+ // no op
+ }
+
+ /**
+ * This method re-computes the checksum of the bits received on the wire and
+ * validates it with the checksum in the bits received Since the computation
+ * of checksum varies based on the protocol, this method is overridden.
+ * Currently only IPv4 and ICMP do checksum computation and validation. TCP
+ * and UDP need to implement these if required.
+ *
+ * @param data The byte stream representing the Ethernet frame
+ * @param startBitOffset The bit offset from where the byte array corresponding to this Packet starts in the frame
+ * @throws PacketException
+ */
+ protected void postDeserializeCustomOperation(byte[] data, int startBitOffset)
+ throws PacketException {
+ // no op
+ }
+
+ /**
+ * Gets the header length in bits
+ *
+ * @return int the header length in bits
+ */
+ public int getHeaderSize() {
+ int size = 0;
+ /*
+ * We need to iterate over the fields that were read in the frame
+ * (hdrFieldsMap) not all the possible ones described in
+ * hdrFieldCoordMap. For ex, 802.1Q may or may not be there
+ */
+ for (Map.Entry<String, byte[]> fieldEntry : hdrFieldsMap.entrySet()) {
+ if (fieldEntry.getValue() != null) {
+ String field = fieldEntry.getKey();
+ size += getfieldnumBits(field);
+ }
+ }
+ return size;
+ }
+
+ /**
+ * This method fetches the start bit offset for header field specified by
+ * 'fieldname'. The offset is present in the hdrFieldCoordMap of the
+ * respective packet class
+ *
+ * @return Integer - startOffset of the requested field
+ */
+ public int getfieldOffset(final String fieldName) {
+ return hdrFieldCoordMap.get(fieldName).getLeft();
+ }
+
+ /**
+ * This method fetches the number of bits for header field specified by
+ * 'fieldname'. The numBits are present in the hdrFieldCoordMap of the
+ * respective packet class
+ *
+ * @return Integer - number of bits of the requested field
+ */
+ public int getfieldnumBits(final String fieldName) {
+ return hdrFieldCoordMap.get(fieldName).getRight();
+ }
+
+ @Override
+ public String toString() {
+ StringBuilder ret = new StringBuilder();
+ ret.append(this.getClass().getSimpleName());
+ ret.append(": [");
+ for (String field : hdrFieldCoordMap.keySet()) {
+ byte[] value = hdrFieldsMap.get(field);
+ ret.append(field);
+ ret.append(": ");
+ ret.append(HexEncode.bytesToHexString(value));
+ ret.append(", ");
+ }
+ ret.replace(ret.length()-2, ret.length()-1, "]");
+ return ret.toString();
+ }
+
+ /**
+ * Returns the raw payload carried by this packet in case payload was not
+ * parsed. Caller can call this function in case the getPaylod() returns null.
+ *
+ * @return The raw payload if not parsable as an array of bytes, null otherwise
+ */
+ public byte[] getRawPayload() {
+ return rawPayload;
+ }
+
+ /**
+ * Set a raw payload in the packet class
+ *
+ * @param payload The raw payload as byte array
+ */
+ public void setRawPayload(final byte[] payload) {
+ this.rawPayload = Arrays.copyOf(payload, payload.length);
+ }
+
+ /**
+ * Return whether the deserialized packet is to be considered corrupted.
+ * This is the case when the checksum computed after reconstructing the
+ * packet received from wire is not equal to the checksum read from the
+ * stream. For the Packet class which do not have a checksum field, this
+ * function will always return false.
+ *
+ *
+ * @return true if the deserialized packet's recomputed checksum is not
+ * equal to the packet carried checksum
+ */
+ public boolean isCorrupted() {
+ return corrupted;
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = super.hashCode();
+ result = prime * result
+ + (this.hdrFieldsMap == null ? 0 : hdrFieldsMap.hashCode());
+ return result;
+ }
+
+ @Override
+ public boolean equals(final Object obj) {
+ if (this == obj) {
+ return true;
+ }
+ if (getClass() != obj.getClass()) {
+ return false;
+ }
+ Packet other = (Packet) obj;
+ if (hdrFieldsMap == other.hdrFieldsMap) {
+ return true;
+ }
+ if (hdrFieldsMap == null || other.hdrFieldsMap == null) {
+ return false;
+ }
+ if (hdrFieldsMap != null && other.hdrFieldsMap != null) {
+ for (String field : hdrFieldsMap.keySet()) {
+ if (!Arrays.equals(hdrFieldsMap.get(field), other.hdrFieldsMap.get(field))) {
+ return false;
+ }
+ }
+ } else {
+ return false;
+ }
+ return true;
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+/**
+ * Describes an exception that is raised when the process of serializing or
+ * deserializing a network packet/stream fails. This generally happens when the
+ * packet/stream is malformed.
+ *
+ */
+public class PacketException extends Exception {
+ private static final long serialVersionUID = 1L;
+
+ public PacketException(final String message) {
+ super(message);
+ }
+
+ public PacketException(String message, Throwable cause) {
+ super(message, cause);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+public class HexEncodeTest {
+ @Test
+ public void testbytesToHexString() {
+ byte[] bytes1 = { (byte) 0x01, (byte) 0x02, (byte) 0x03 };
+ String str1 = HexEncode.bytesToHexString(bytes1);
+ Assert.assertTrue(str1.equals("010203"));
+
+ byte[] bytes2 = { (byte) 0x11, (byte) 0x22, (byte) 0x33 };
+ String str2 = HexEncode.bytesToHexString(bytes2);
+ Assert.assertFalse(str2.equals("010203"));
+
+ }
+
+ @Test
+ public void testLongToHexString() {
+ long value1 = 12345678L;
+ String str1 = HexEncode.longToHexString(value1);
+ Assert.assertTrue(str1.equals("00:00:00:00:00:bc:61:4e"));
+
+ long value2 = 98765432L;
+ String str2 = HexEncode.longToHexString(value2);
+ Assert.assertFalse(str2.equals("00:44:33:22:11:bc:61:4e"));
+
+ }
+
+ @Test
+ public void testBytesFromHexString() {
+ String byteStr1 = "00:11:22:33:44:55";
+ byte byteArray1[] = HexEncode.bytesFromHexString(byteStr1);
+
+ Assert.assertTrue(byteArray1[0] == (byte) 0x0);
+ Assert.assertTrue(byteArray1[1] == (byte) 0x11);
+ Assert.assertTrue(byteArray1[2] == (byte) 0x22);
+ Assert.assertTrue(byteArray1[3] == (byte) 0x33);
+ Assert.assertTrue(byteArray1[4] == (byte) 0x44);
+ Assert.assertTrue(byteArray1[5] == (byte) 0x55);
+
+ String byteStr2 = "00:11:22:33:44:55";
+ byte byteArray2[] = HexEncode.bytesFromHexString(byteStr2);
+
+ Assert.assertFalse(byteArray2[0] == (byte) 0x55);
+ Assert.assertFalse(byteArray2[1] == (byte) 0x44);
+ Assert.assertFalse(byteArray2[2] == (byte) 0x33);
+ Assert.assertFalse(byteArray2[3] == (byte) 0x22);
+ Assert.assertFalse(byteArray2[4] == (byte) 0x11);
+ Assert.assertFalse(byteArray2[5] == (byte) 0x0);
+
+ }
+}
--- /dev/null
+/**
+ * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import org.junit.Assert;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.google.common.io.BaseEncoding;
+import com.google.common.primitives.Bytes;
+
+/**
+ *
+ */
+public class LLDPTLVTest {
+
+ /** dummy custom tlv value */
+ private static final String CUSTOM_TLV_ULTIMATE = "What do you get when you multiply 6 by 9?";
+ /** dummy custom tlv value in binary form */
+ private static final byte[] CUSTOM_TLV_ULTIMATE_BIN = new byte[] {
+ 0x57, 0x68, 0x61, 0x74, 0x20, 0x64, 0x6f, 0x20, 0x79, 0x6f, 0x75, 0x20, 0x67, 0x65, 0x74,
+ 0x20, 0x77, 0x68, 0x65, 0x6e, 0x20, 0x79, 0x6f, 0x75, 0x20, 0x6d, 0x75, 0x6c, 0x74, 0x69,
+ 0x70, 0x6c, 0x79, 0x20, 0x36, 0x20, 0x62, 0x79, 0x20, 0x39, 0x3f
+ };
+
+ private static final Logger LOG = LoggerFactory.getLogger(LLDPTLVTest.class);
+
+ /**
+ * Test method for
+ * {@link org.opendaylight.openflowplugin.libraries.liblldp.LLDPTLV#createCustomTLVValue(java.lang.String)}
+ * .
+ */
+ @Test
+ public void testCreateCustomTLVValue() {
+ byte[] tlv = LLDPTLV.createCustomTLVValue(CUSTOM_TLV_ULTIMATE);
+
+ byte[] expectedCustomTlv = Bytes.concat(new byte[] {
+ // custom type (7b) + length (9b) = 16b = 2B (skipped)
+ // 0x7f, 24,
+ // openflow OUI
+ 0x00, 0x26, (byte) 0xe1,
+ // subtype
+ 0x00},
+ // custom value
+ CUSTOM_TLV_ULTIMATE_BIN);
+
+ BaseEncoding be = BaseEncoding.base16().withSeparator(" ", 2).lowerCase();
+ LOG.debug("expected: {}", be.encode(expectedCustomTlv));
+ LOG.debug("actual : {}", be.encode(tlv));
+ Assert.assertArrayEquals(expectedCustomTlv, tlv);
+ }
+
+ /**
+ * Test method for
+ * {@link org.opendaylight.openflowplugin.libraries.liblldp.LLDPTLV#getCustomString(byte[], int)}
+ * .
+ * @throws Exception
+ */
+ @Test
+ public void testGetCustomString() throws Exception {
+ byte[] inputCustomTlv = Bytes.concat(new byte[] {
+ // custom type (7b) + length (9b) = 16b = 2B (skipped)
+ // 0x7f, 24,
+ // openflow OUI
+ 0x00, 0x26, (byte) 0xe1,
+ // subtype
+ 0x00},
+ // custom value
+ CUSTOM_TLV_ULTIMATE_BIN);
+
+ String actual = LLDPTLV.getCustomString(inputCustomTlv, inputCustomTlv.length);
+ LOG.debug("actual custom TLV value as string: {}", actual);
+ Assert.assertEquals(CUSTOM_TLV_ULTIMATE, actual);
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.openflowplugin.libraries.liblldp;
+
+import static org.junit.Assert.assertArrayEquals;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
+import org.junit.Before;
+import java.util.Iterator;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.commons.lang3.ArrayUtils;
+import org.junit.Assert;
+import org.junit.Test;
+import org.junit.internal.ArrayComparisonFailure;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.google.common.primitives.Bytes;
+
+/**
+ * Test of {@link LLDP} serialization feature (TODO: and deserialization)
+ */
+public class LLDPTest {
+
+ private static final Logger LOG = LoggerFactory.getLogger(LLDPTest.class);
+
+ private static final byte[] CHASSIS_ID_VALUE = "chassis".getBytes();
+ private static final short CHASSIS_ID_LENGTH = (short) CHASSIS_ID_VALUE.length;
+
+ private static final byte[] TTL_VALUE = new byte[] { (byte) 0, (byte) 100 };
+ private static final short TTL_LENGTH = (short) TTL_VALUE.length;
+
+ private static final byte[] PORT_VALUE = "dummy port id".getBytes();
+ private static final short PORT_LENGTH = (short) PORT_VALUE.length;
+
+ private static final byte[] SYSTEM_NAME_VALUE = "dummy system name".getBytes();
+ private static final short SYSTEM_NAME_LENGTH = (short) SYSTEM_NAME_VALUE.length;
+
+ private static final byte SYSTEM_CAPABILITIES_TLV = 8;
+ private static final byte[] SYSTEM_CAPABILITIES_VALUE = "dummy system capabilities".getBytes();
+ private static final short SYSTEM_CAPABILITIES_LENGTH = (short) SYSTEM_CAPABILITIES_VALUE.length;
+
+ private static final byte[] OUI = LLDPTLV.OFOUI;
+
+ private static final byte[] OUI_SUBTYPE_A = new byte[] { (byte) 0 };
+ private static final byte[] CUSTOM_SUBTYPE_A_VALUE = "first custom value A".getBytes();
+ private static final short CUSTOM_SUBTYPE_A_LENGTH = (short) (OUI.length + OUI_SUBTYPE_A.length + CUSTOM_SUBTYPE_A_VALUE.length);
+
+ private static final byte[] OUI_SUBTYPE_B = new byte[] { (byte) 1 };
+ private static final byte[] CUSTOM_SUBTYPE_B_VALUE = "second custom value B".getBytes();
+ private static final short CUSTOM_SUBTYPE_B_LENGTH = (short) (OUI.length + OUI_SUBTYPE_B.length + CUSTOM_SUBTYPE_B_VALUE.length);
+
+ private static final byte[] BYTES_BEFORE_CUSTOM_A = new byte[] { 0x00, 0x26, (byte) 0xe1, OUI_SUBTYPE_A[0] };
+ private static final byte[] BYTES_BEFORE_CUSTOM_B = new byte[] { 0x00, 0x26, (byte) 0xe1, OUI_SUBTYPE_B[0] };
+ private LLDP lldpBuilder;
+
+ @Before
+ public void setup() {
+ lldpBuilder = new LLDP();
+ }
+
+ /**
+ * Tests whether serialization of LLDP packet is correct
+ *
+ * @see LLDP#serialize()
+ * @throws PacketException
+ */
+ @Test
+ public void testSerialize() throws PacketException {
+ lldpBuilder.setChassisId(dummyTlv(LLDPTLV.TLVType.ChassisID.getValue(), CHASSIS_ID_LENGTH, CHASSIS_ID_VALUE));
+ lldpBuilder.setTtl(dummyTlv(LLDPTLV.TLVType.TTL.getValue(), TTL_LENGTH, TTL_VALUE));
+ lldpBuilder.setPortId(dummyTlv(LLDPTLV.TLVType.PortID.getValue(), PORT_LENGTH, PORT_VALUE));
+ lldpBuilder.setSystemNameId(dummyTlv(LLDPTLV.TLVType.SystemName.getValue(), SYSTEM_NAME_LENGTH,
+ SYSTEM_NAME_VALUE));
+
+ // adding optional TLVs for which doesn't exist special set* methods in LLDP
+ final List<LLDPTLV> optionalTLVs = new ArrayList<>();
+ // System Capabilities TLV (type = 7)
+ optionalTLVs.add(dummyTlv(SYSTEM_CAPABILITIES_TLV, SYSTEM_CAPABILITIES_LENGTH, SYSTEM_CAPABILITIES_VALUE));
+ lldpBuilder.setOptionalTLVList(optionalTLVs);
+
+ // adding custom TLVs
+ lldpBuilder.addCustomTLV(dummyCustomTlv(LLDPTLV.TLVType.Custom.getValue(), OUI, OUI_SUBTYPE_A,
+ CUSTOM_SUBTYPE_A_LENGTH, CUSTOM_SUBTYPE_A_VALUE));
+ lldpBuilder.addCustomTLV(dummyCustomTlv(LLDPTLV.TLVType.Custom.getValue(), OUI, OUI_SUBTYPE_B,
+ CUSTOM_SUBTYPE_B_LENGTH, CUSTOM_SUBTYPE_B_VALUE));
+
+ byte[] serialized = lldpBuilder.serialize();
+
+ int offset = 0;
+ offset = checkTLV(serialized, offset, (byte) 0b00000010, "ChassisID", CHASSIS_ID_LENGTH, CHASSIS_ID_VALUE);
+ offset = checkTLV(serialized, offset, (byte) 0b00000110, "TTL", TTL_LENGTH, TTL_VALUE);
+ offset = checkTLV(serialized, offset, (byte) 0b00000100, "PortID", PORT_LENGTH, PORT_VALUE);
+ offset = checkTLV(serialized, offset, (byte) 0b00001010, "SystemName", SYSTEM_NAME_LENGTH, SYSTEM_NAME_VALUE);
+ offset = checkTLV(serialized, offset, (byte) 0b00010000, "System capabilities", SYSTEM_CAPABILITIES_LENGTH,
+ SYSTEM_CAPABILITIES_VALUE);
+ offset = checkTLV(serialized, offset, (byte) 0b11111110, "Custom subtype A", CUSTOM_SUBTYPE_A_LENGTH,
+ CUSTOM_SUBTYPE_A_VALUE, OUI[0], OUI[1], OUI[2], OUI_SUBTYPE_A[0]);
+ offset = checkTLV(serialized, offset, (byte) 0b11111110, "Custom subtype B", CUSTOM_SUBTYPE_B_LENGTH,
+ CUSTOM_SUBTYPE_B_VALUE, OUI[0], OUI[1], OUI[2], OUI_SUBTYPE_B[0]);
+
+ }
+
+ /**
+ * Tests whether serialization of LLDP packet is correct
+ *
+ * @see LLDP#deserialize(byte[], int, int)
+ * @throws Exception
+ */
+ @Test
+ public void testDeserialize() throws Exception {
+
+ byte[] rawLldpTlv = Bytes
+ .concat(awaitedBytes((byte) 0b00000010, CHASSIS_ID_LENGTH, CHASSIS_ID_VALUE, null),
+ awaitedBytes((byte) 0b00000110, TTL_LENGTH, TTL_VALUE, null),
+ awaitedBytes((byte) 0b00000100, PORT_LENGTH, PORT_VALUE, null),
+ awaitedBytes((byte) 0b00001010, SYSTEM_NAME_LENGTH, SYSTEM_NAME_VALUE, null),
+ awaitedBytes((byte) 0b00010010, SYSTEM_CAPABILITIES_LENGTH, SYSTEM_CAPABILITIES_VALUE, null),
+ awaitedBytes((byte) 0b11111110, CUSTOM_SUBTYPE_A_LENGTH, CUSTOM_SUBTYPE_A_VALUE,
+ BYTES_BEFORE_CUSTOM_A),
+ awaitedBytes((byte) 0b11111110, CUSTOM_SUBTYPE_B_LENGTH, CUSTOM_SUBTYPE_B_VALUE,
+ BYTES_BEFORE_CUSTOM_B));
+
+ lldpBuilder.deserialize(rawLldpTlv, 0, rawLldpTlv.length * NetUtils.NumBitsInAByte);
+ Assert.assertEquals("chassis", new String(lldpBuilder.getChassisId().getValue()));
+ Assert.assertArrayEquals(TTL_VALUE, lldpBuilder.getTtl().getValue());
+ Assert.assertEquals("dummy port id", new String(lldpBuilder.getPortId().getValue()));
+ Assert.assertEquals("dummy system name", new String(lldpBuilder.getSystemNameId().getValue()));
+
+ // optional items check
+ Iterator<LLDPTLV> iteratorTlvOptional = lldpBuilder.getOptionalTLVList().iterator();
+
+ assertTrue(iteratorTlvOptional.hasNext());
+ LLDPTLV item0 = iteratorTlvOptional.next();
+ Assert.assertEquals(5, item0.getType());
+ Assert.assertEquals("dummy system name", new String(item0.getValue()));
+ assertTrue(iteratorTlvOptional.hasNext());
+
+ assertTrue(iteratorTlvOptional.hasNext());
+ LLDPTLV item1 = iteratorTlvOptional.next();
+ Assert.assertEquals(9, item1.getType());
+ Assert.assertEquals("dummy system capabilities", new String(item1.getValue()));
+ assertFalse(iteratorTlvOptional.hasNext());
+
+ // custom items check
+ Iterable<LLDPTLV> customTlvs = lldpBuilder.getCustomTlvList();
+ Iterator<LLDPTLV> iteratorLLDPTLV = customTlvs.iterator();
+ assertEquals(true, iteratorLLDPTLV.hasNext());
+ checkCustomTlv(iteratorLLDPTLV.next(), "first custom value A");
+ assertEquals(true, iteratorLLDPTLV.hasNext());
+ checkCustomTlv(iteratorLLDPTLV.next(), "second custom value B");
+ assertEquals(false, iteratorLLDPTLV.hasNext());
+ }
+
+ /**
+ * Test of {@link LLDP#addCustomTLV(LLDPTLV)}
+ *
+ * @throws PacketException
+ */
+ @Test
+ public void testAddCustomTLV() throws PacketException {
+ byte[] customA = awaitedBytes((byte) 0b11111110, CUSTOM_SUBTYPE_A_LENGTH, CUSTOM_SUBTYPE_A_VALUE,
+ BYTES_BEFORE_CUSTOM_A);
+ byte[] customB = awaitedBytes((byte) 0b11111110, CUSTOM_SUBTYPE_B_LENGTH, CUSTOM_SUBTYPE_B_VALUE,
+ BYTES_BEFORE_CUSTOM_B);
+
+ Packet lldptlvA = new LLDPTLV().deserialize(customA, 0, customA.length);
+ assertTrue(lldptlvA instanceof LLDPTLV);
+ Packet lldptlvB = new LLDPTLV().deserialize(customB, 0, customB.length);
+ assertTrue(lldptlvB instanceof LLDPTLV);
+
+ lldpBuilder.addCustomTLV((LLDPTLV) lldptlvA);
+ lldpBuilder.addCustomTLV((LLDPTLV) lldptlvB);
+
+ Iterator<LLDPTLV> customTLVsIterator = lldpBuilder.getCustomTlvList().iterator();
+ assertTrue(customTLVsIterator.hasNext());
+ customTLVsIterator.next();
+ assertTrue(customTLVsIterator.hasNext());
+ customTLVsIterator.next();
+ assertFalse(customTLVsIterator.hasNext());
+ }
+
+ @Test
+ public void testGetCustomTLV() throws PacketException {
+ int ouiInt = BitBufferHelper.getInt(OUI);
+ CustomTLVKey key = new CustomTLVKey(ouiInt, OUI_SUBTYPE_A[0]);
+ LLDPTLV customTLV = lldpBuilder.getCustomTLV(key);
+ assertNull(customTLV);
+
+ byte[] customA = awaitedBytes((byte) 0b11111110, CUSTOM_SUBTYPE_A_LENGTH, CUSTOM_SUBTYPE_A_VALUE,
+ BYTES_BEFORE_CUSTOM_A);
+ lldpBuilder.deserialize(customA, 0, customA.length);
+
+ customTLV = lldpBuilder.getCustomTLV(key);
+ assertNotNull(customTLV);
+ assertEquals(ouiInt, LLDPTLV.extractCustomOUI(customTLV));
+ assertEquals(OUI_SUBTYPE_A[0], LLDPTLV.extractCustomSubtype(customTLV));
+ }
+
+ /**
+ * @param customItem
+ * @param expectedValue
+ */
+ private static void checkCustomTlv(final LLDPTLV customItem, final String expectedValue) {
+ Assert.assertEquals(127, customItem.getType());
+ LOG.debug("custom TLV1.length: {}", customItem.getLength());
+ Assert.assertEquals(expectedValue,
+ new String(LLDPTLV.getCustomString(customItem.getValue(), customItem.getLength())));
+ }
+
+ private static int checkTLV(final byte[] serializedData, final int offset, final byte typeTLVBits, final String typeTLVName,
+ final short lengthTLV, final byte[] valueTLV, final byte... bytesBeforeValue) throws ArrayComparisonFailure {
+ byte[] concreteTlvAwaited = awaitedBytes(typeTLVBits, lengthTLV, valueTLV, bytesBeforeValue);
+ int concreteTlvAwaitLength = concreteTlvAwaited.length;
+ assertArrayEquals("Serialization problem " + typeTLVName, concreteTlvAwaited,
+ ArrayUtils.subarray(serializedData, offset, offset + concreteTlvAwaitLength));
+ return offset + concreteTlvAwaitLength;
+ }
+
+ private static byte[] awaitedBytes(final byte typeTLV, final short length, final byte[] value, final byte[] bytesBeforeValue) {
+ byte[] awaited = ArrayUtils.EMPTY_BYTE_ARRAY;
+
+ // 0 - the less meaning byte (right), 1 most meaning byte (left)
+ byte lengthByte0 = (byte) length;
+ byte lengthByte1 = (byte) (length >> 8);
+
+ awaited = ArrayUtils.addAll(awaited, (byte) (typeTLV | lengthByte1), lengthByte0);
+ awaited = ArrayUtils.addAll(awaited, bytesBeforeValue);
+ awaited = ArrayUtils.addAll(awaited, value);
+ return awaited;
+ }
+
+ private static LLDPTLV dummyCustomTlv(final byte tlvType, final byte[] oui, final byte[] ouiSubtype, final short customLength,
+ final byte[] subtypeValue) {
+ byte[] fullCustomValue = new byte[0];
+ fullCustomValue = ArrayUtils.addAll(fullCustomValue, oui);
+ fullCustomValue = ArrayUtils.addAll(fullCustomValue, ouiSubtype);
+ fullCustomValue = ArrayUtils.addAll(fullCustomValue, subtypeValue);
+ return dummyTlv(tlvType, customLength, fullCustomValue);
+ }
+
+ private static LLDPTLV dummyTlv(final byte concreteTlv, final short concreteLength, final byte[] concreteValue) {
+ LLDPTLV tlv = new LLDPTLV();
+ tlv.setType(concreteTlv).setLength(concreteLength).setValue(concreteValue);
+ return tlv;
+ }
+}
--- /dev/null
+/*
+ * Copyright (c) 2014, 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+package org.opendaylight.openflowplugin.libraries.sal.packet;
+
+import org.junit.Assert;
+import org.junit.Test;
+import org.opendaylight.openflowplugin.libraries.liblldp.BitBufferHelper;
+
+public class BitBufferHelperTest {
+
+ @Test
+ public void testGetByte() {
+ byte[] data = { 100 };
+ Assert.assertTrue(BitBufferHelper.getByte(data) == 100);
+ }
+
+ @Test
+ public void testGetBits() throws Exception {
+ byte[] data = { 10, 12, 14, 20, 55, 69, 82, 97, 109, 117, 127, -50 };
+ byte[] bits;
+
+ bits = BitBufferHelper.getBits(data, 88, 8); //BYTE extraOffsetBits = extranumBits = 0
+ Assert.assertTrue(bits[0] == -50);
+
+ bits = BitBufferHelper.getBits(data, 8, 16); //Short
+ Assert.assertTrue(bits[0] == 12);
+ Assert.assertTrue(bits[1] == 14);
+
+ bits = BitBufferHelper.getBits(data, 32, 32); //Int
+ Assert.assertTrue(bits[0] == 55);
+ Assert.assertTrue(bits[1] == 69);
+ Assert.assertTrue(bits[2] == 82);
+ Assert.assertTrue(bits[3] == 97);
+
+ bits = BitBufferHelper.getBits(data, 16, 48); //Long
+ Assert.assertTrue(bits[0] == 14);
+ Assert.assertTrue(bits[1] == 20);
+ Assert.assertTrue(bits[2] == 55);
+ Assert.assertTrue(bits[3] == 69);
+ Assert.assertTrue(bits[4] == 82);
+ Assert.assertTrue(bits[5] == 97);
+
+ bits = BitBufferHelper.getBits(data, 40, 7); //BYTE extraOffsetBits = extranumBits != 0
+ Assert.assertTrue(bits[0] == 34);
+
+ bits = BitBufferHelper.getBits(data, 8, 13); //Short
+ Assert.assertTrue(bits[0] == 1);
+ Assert.assertTrue(bits[1] == -127);
+
+ bits = BitBufferHelper.getBits(data, 32, 28); //Int
+ Assert.assertTrue(bits[0] == 3);
+ Assert.assertTrue(bits[1] == 116);
+ Assert.assertTrue(bits[2] == 85);
+ Assert.assertTrue(bits[3] == 38);
+
+ bits = BitBufferHelper.getBits(data, 16, 41); //Long
+ Assert.assertTrue(bits[0] == 0);
+ Assert.assertTrue(bits[1] == 28);
+ Assert.assertTrue(bits[2] == 40);
+ Assert.assertTrue(bits[3] == 110);
+ Assert.assertTrue(bits[4] == -118);
+ Assert.assertTrue(bits[5] == -92);
+
+ bits = BitBufferHelper.getBits(data, 3, 7); //BYTE extraOffsetBits != 0; extranumBits == 0
+ Assert.assertTrue(bits[0] == 40);
+
+ bits = BitBufferHelper.getBits(data, 13, 16); //Short
+ Assert.assertTrue(bits[0] == -127);
+ Assert.assertTrue(bits[1] == -62);
+
+ bits = BitBufferHelper.getBits(data, 5, 32); //Int
+ Assert.assertTrue(bits[0] == 65);
+ Assert.assertTrue(bits[1] == -127);
+ Assert.assertTrue(bits[2] == -62);
+ Assert.assertTrue(bits[3] == -122);
+
+ bits = BitBufferHelper.getBits(data, 23, 48); //Long
+ Assert.assertTrue(bits[0] == 10);
+ Assert.assertTrue(bits[1] == 27);
+ Assert.assertTrue(bits[2] == -94);
+ Assert.assertTrue(bits[3] == -87);
+ Assert.assertTrue(bits[4] == 48);
+ Assert.assertTrue(bits[5] == -74);
+
+ bits = BitBufferHelper.getBits(data, 66, 9); //BYTE extraOffsetBits != 0; extranumBits != 0
+ Assert.assertTrue(bits[0] == 1);
+ Assert.assertTrue(bits[1] == 107);
+
+ bits = BitBufferHelper.getBits(data, 13, 15); //Short
+ Assert.assertTrue(bits[0] == 64);
+ Assert.assertTrue(bits[1] == -31);
+
+ bits = BitBufferHelper.getBits(data, 5, 29); //Int
+ Assert.assertTrue(bits[0] == 8);
+ Assert.assertTrue(bits[1] == 48);
+ Assert.assertTrue(bits[2] == 56);
+ Assert.assertTrue(bits[3] == 80);
+
+ bits = BitBufferHelper.getBits(data, 31, 43); //Long
+ Assert.assertTrue(bits[0] == 0);
+ Assert.assertTrue(bits[1] == -35);
+ Assert.assertTrue(bits[2] == 21);
+ Assert.assertTrue(bits[3] == 73);
+ Assert.assertTrue(bits[4] == -123);
+ Assert.assertTrue(bits[5] == -75);
+
+ bits = BitBufferHelper.getBits(data, 4, 12); //Short
+ Assert.assertTrue(bits[0] == 10);
+ Assert.assertTrue(bits[1] == 12);
+
+ byte[] data1 = { 0, 8 };
+ bits = BitBufferHelper.getBits(data1, 7, 9); //Short
+ Assert.assertTrue(bits[0] == 0);
+ Assert.assertTrue(bits[1] == 8);
+
+ byte[] data2 = { 2, 8 };
+ bits = BitBufferHelper.getBits(data2, 0, 7); //Short
+ Assert.assertTrue(bits[0] == 1);
+
+ bits = BitBufferHelper.getBits(data2, 7, 9); //Short
+ Assert.assertTrue(bits[0] == 0);
+ Assert.assertTrue(bits[1] == 8);
+ }
+
+ // [01101100][01100000]
+ // [01100011]
+ @Test
+ public void testGetBytes() throws Exception {
+ byte data[] = { 108, 96, 125, -112, 5, 6, 108, 8, 9, 10, 11, 12, 13,
+ 14, 15, 16, 17, 18, 19, 20, 21, 22 };
+ byte[] x;
+
+ Assert.assertTrue(BitBufferHelper.getBits(data, 0, 8)[0] == 108);
+ Assert.assertTrue(BitBufferHelper.getBits(data, 8, 8)[0] == 96);
+
+ x = BitBufferHelper.getBits(data, 0, 10);
+ Assert.assertTrue(x[0] == 1);
+ Assert.assertTrue(x[1] == -79);
+
+ x = BitBufferHelper.getBits(data, 3, 8);
+ Assert.assertTrue(x[0] == 99);
+ //Assert.assertTrue(x[1] == 97);
+
+ }
+
+ @Test
+ public void testMSBMask() {
+ int numBits = 1; //MSB
+ int mask = BitBufferHelper.getMSBMask(numBits);
+ Assert.assertTrue(mask == 128);
+
+ numBits = 8;
+ mask = BitBufferHelper.getMSBMask(numBits);
+ Assert.assertTrue(mask == 255);
+
+ numBits = 2;
+ mask = BitBufferHelper.getMSBMask(numBits);
+ Assert.assertTrue(mask == 192);
+ }
+
+ @Test
+ public void testLSBMask() {
+ int numBits = 1; //LSB
+ int mask = BitBufferHelper.getLSBMask(numBits);
+ Assert.assertTrue(mask == 1);
+
+ numBits = 3;
+ mask = BitBufferHelper.getLSBMask(numBits);
+ Assert.assertTrue(mask == 7);
+
+ numBits = 8;
+ mask = BitBufferHelper.getLSBMask(numBits);
+ Assert.assertTrue(mask == 255);
+ }
+
+ @Test
+ public void testToByteArray() {
+ short sh = Short.MAX_VALUE;
+ byte[] data_sh = new byte[Byte.SIZE / 8];
+ data_sh = BitBufferHelper.toByteArray(sh);
+ Assert.assertTrue(data_sh[0] == 127);
+ Assert.assertTrue(data_sh[1] == -1);
+
+ short sh2 = Short.MIN_VALUE;
+ byte[] data_sh2 = new byte[Byte.SIZE / 8];
+ data_sh2 = BitBufferHelper.toByteArray(sh2);
+ Assert.assertTrue(data_sh2[0] == -128);
+ Assert.assertTrue(data_sh2[1] == 0);
+
+ short sh3 = 16384;
+ byte[] data_sh3 = new byte[Byte.SIZE / 8];
+ data_sh3 = BitBufferHelper.toByteArray(sh3);
+ Assert.assertTrue(data_sh3[0] == 64);
+ Assert.assertTrue(data_sh3[1] == 0);
+
+ short sh4 = 146; //TCP headerlenflags - startoffset = 103
+ byte[] data_sh4 = new byte[Byte.SIZE / 8];
+ data_sh4 = BitBufferHelper.toByteArray(sh4);
+ Assert.assertTrue(data_sh4[0] == 0);
+ Assert.assertTrue(data_sh4[1] == -110);
+
+ short sh4_2 = 5000; //IPv4 Offset - startOffset = 51 (to 63)
+ byte[] data_sh4_2 = new byte[Byte.SIZE / 8];
+ data_sh4_2 = BitBufferHelper.toByteArray(sh4_2);
+ Assert.assertTrue(data_sh4_2[0] == 19);
+ Assert.assertTrue(data_sh4_2[1] == -120);
+
+ short sh4_3 = 5312; //numEndRestBits < numBitstoShiftBy
+ byte[] data_sh4_3 = new byte[Byte.SIZE / 8];
+ data_sh4_3 = BitBufferHelper.toByteArray(sh4_3);
+ Assert.assertTrue(data_sh4_3[0] == 20);
+ Assert.assertTrue(data_sh4_3[1] == -64);
+
+ int Int = Integer.MAX_VALUE;
+ byte[] data_Int = new byte[Integer.SIZE / 8];
+ data_Int = BitBufferHelper.toByteArray(Int);
+ Assert.assertTrue(data_Int[0] == 127);
+ Assert.assertTrue(data_Int[1] == -1);
+ Assert.assertTrue(data_Int[2] == -1);
+ Assert.assertTrue(data_Int[3] == -1);
+
+ int Int2 = Integer.MIN_VALUE;
+ byte[] data_Int2 = new byte[Integer.SIZE / 8];
+ data_Int2 = BitBufferHelper.toByteArray(Int2);
+ Assert.assertTrue(data_Int2[0] == -128);
+ Assert.assertTrue(data_Int2[1] == 0);
+ Assert.assertTrue(data_Int2[2] == 0);
+ Assert.assertTrue(data_Int2[3] == 0);
+
+ int Int3 = 1077952576;
+ byte[] data_Int3 = new byte[Integer.SIZE / 8];
+ data_Int3 = BitBufferHelper.toByteArray(Int3);
+ Assert.assertTrue(data_Int3[0] == 64);
+ Assert.assertTrue(data_Int3[1] == 64);
+ Assert.assertTrue(data_Int3[2] == 64);
+ Assert.assertTrue(data_Int3[3] == 64);
+
+ long Lng = Long.MAX_VALUE;
+ byte[] data_lng = new byte[Long.SIZE / 8];
+ data_lng = BitBufferHelper.toByteArray(Lng);
+ Assert.assertTrue(data_lng[0] == 127);
+ Assert.assertTrue(data_lng[1] == -1);
+ Assert.assertTrue(data_lng[2] == -1);
+ Assert.assertTrue(data_lng[3] == -1);
+ Assert.assertTrue(data_lng[4] == -1);
+ Assert.assertTrue(data_lng[5] == -1);
+ Assert.assertTrue(data_lng[6] == -1);
+ Assert.assertTrue(data_lng[7] == -1);
+
+ long Lng2 = Long.MIN_VALUE;
+ byte[] data_lng2 = new byte[Long.SIZE / 8];
+ data_lng2 = BitBufferHelper.toByteArray(Lng2);
+ Assert.assertTrue(data_lng2[0] == -128);
+ Assert.assertTrue(data_lng2[1] == 0);
+ Assert.assertTrue(data_lng2[2] == 0);
+ Assert.assertTrue(data_lng2[3] == 0);
+ Assert.assertTrue(data_lng2[4] == 0);
+ Assert.assertTrue(data_lng2[5] == 0);
+ Assert.assertTrue(data_lng2[6] == 0);
+ Assert.assertTrue(data_lng2[7] == 0);
+
+ byte B = Byte.MAX_VALUE;
+ byte[] data_B = new byte[Byte.SIZE / 8];
+ data_B = BitBufferHelper.toByteArray(B);
+ Assert.assertTrue(data_B[0] == 127);
+
+ byte B1 = Byte.MIN_VALUE;
+ byte[] data_B1 = new byte[Byte.SIZE / 8];
+ data_B1 = BitBufferHelper.toByteArray(B1);
+ Assert.assertTrue(data_B1[0] == -128);
+
+ byte B2 = 64;
+ byte[] data_B2 = new byte[Byte.SIZE / 8];
+ data_B2 = BitBufferHelper.toByteArray(B2);
+ Assert.assertTrue(data_B2[0] == 64);
+
+ byte B3 = 32;
+ byte[] data_B3 = new byte[Byte.SIZE / 8];
+ data_B3 = BitBufferHelper.toByteArray(B3);
+ Assert.assertTrue(data_B3[0] == 32);
+
+ }
+
+ @Test
+ public void testToByteArrayVariable() {
+ int len = 9;
+ byte[] data_sh;
+ data_sh = BitBufferHelper.toByteArray(511, len);
+ Assert.assertTrue(data_sh[0] == (byte) 255);
+ Assert.assertTrue(data_sh[1] == (byte) 128);
+
+ data_sh = BitBufferHelper.toByteArray(511, len);
+ Assert.assertTrue(data_sh[0] == (byte) 255);
+ Assert.assertTrue(data_sh[1] == (byte) 128);
+
+ data_sh = BitBufferHelper.toByteArray((long) 511, len);
+ Assert.assertTrue(data_sh[0] == (byte) 255);
+ Assert.assertTrue(data_sh[1] == (byte) 128);
+ }
+
+ @Test
+ public void testToInt() {
+ byte data[] = { 1 };
+ Assert.assertTrue(BitBufferHelper.toNumber(data) == 1);
+
+ byte data2[] = { 1, 1 };
+ Assert.assertTrue(BitBufferHelper.toNumber(data2) == 257);
+
+ byte data3[] = { 1, 1, 1 };
+ Assert.assertTrue(BitBufferHelper.toNumber(data3) == 65793);
+ }
+
+ @Test
+ public void testToLongGetter() {
+ byte data[] = { 1, 1 };
+ Assert.assertTrue(BitBufferHelper.getLong(data) == 257L);
+ }
+
+ @Test
+ public void testSetByte() throws Exception {
+ byte input;
+ byte[] data = new byte[20];
+
+ input = 125;
+ BitBufferHelper.setByte(data, input, 0, Byte.SIZE);
+ Assert.assertTrue(data[0] == 125);
+
+ input = 109;
+ BitBufferHelper.setByte(data, input, 152, Byte.SIZE);
+ Assert.assertTrue(data[19] == 109);
+ }
+
+ @Test
+ public void testSetBytes() throws Exception {
+ byte[] input = { 0, 1 };
+ byte[] data = { 6, 0 };
+
+ BitBufferHelper.setBytes(data, input, 7, 9);
+ Assert.assertTrue(data[0] == 6);
+ Assert.assertTrue(data[1] == 1);
+ }
+
+ //@Test
+ //INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001]*/
+ public void testInsertBits() throws Exception {
+ //CASE 1: startOffset%8 == 0 && numBits%8 == 0
+ byte inputdata[] = { 75, 110, 107, 80, 10, 12, 35, 100, 125, 65 };
+ int startOffset = 0;
+ int numBits = 8;
+
+ byte data1[] = new byte[2];
+ startOffset = 0;
+ numBits = 16;
+ BitBufferHelper.insertBits(data1, inputdata, startOffset, numBits);
+ Assert.assertTrue(data1[0] == 75);
+ Assert.assertTrue(data1[1] == 110);
+
+ byte data2[] = new byte[4];
+ startOffset = 0;
+ numBits = 32;
+ BitBufferHelper.insertBits(data2, inputdata, startOffset, numBits);
+ Assert.assertTrue(data2[0] == 75);
+ Assert.assertTrue(data2[1] == 110);
+ Assert.assertTrue(data2[2] == 107);
+ Assert.assertTrue(data2[3] == 80);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] // OUTPUT: [01001011] [01101000] = {75, 104}
+ byte data10[] = new byte[2];
+ startOffset = 0;
+ numBits = 13;
+ BitBufferHelper.insertBits(data10, inputdata, startOffset, numBits);
+ Assert.assertTrue(data10[0] == 75);
+ Assert.assertTrue(data10[1] == 104);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] // OUTPUT: [01001000] = {72}
+ byte data11[] = new byte[4];
+ startOffset = 8;
+ numBits = 6;
+ BitBufferHelper.insertBits(data11, inputdata, startOffset, numBits);
+ Assert.assertTrue(data11[1] == 72);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [01001011] [01101110] [01101000] = {75, 110, 105}
+ byte data12[] = new byte[4];
+ startOffset = 0;
+ numBits = 23;
+ BitBufferHelper.insertBits(data12, inputdata, startOffset, numBits);
+ Assert.assertTrue(data12[0] == 75);
+ Assert.assertTrue(data12[1] == 110);
+ Assert.assertTrue(data12[2] == 106);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [01001011] [01101110] [01100000] = {75, 110, 96}
+ byte data13[] = new byte[4];
+ startOffset = 8;
+ numBits = 20;
+ BitBufferHelper.insertBits(data13, inputdata, startOffset, numBits);
+ Assert.assertTrue(data13[1] == 75);
+ Assert.assertTrue(data13[2] == 110);
+ Assert.assertTrue(data13[3] == 96);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [01001011] [01101110] [01101011] [10100000]= {75, 110, 107, 80}
+ byte data14[] = new byte[4];
+ startOffset = 0;
+ numBits = 30;
+ BitBufferHelper.insertBits(data14, inputdata, startOffset, numBits);
+ Assert.assertTrue(data14[0] == 75);
+ Assert.assertTrue(data14[1] == 110);
+ Assert.assertTrue(data14[2] == 107);
+ Assert.assertTrue(data14[3] == 80);
+
+ //CASE 3: startOffset%8 != 0, numBits%8 = 0
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [10100000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00001001] [11000000] = {72, 96}
+ byte data16[] = new byte[5];
+ startOffset = 3;
+ numBits = 8;
+ BitBufferHelper.insertBits(data16, inputdata, startOffset, numBits);
+ Assert.assertTrue(data16[0] == 9);
+ Assert.assertTrue(data16[1] == 96);
+ Assert.assertTrue(data16[2] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [00000100] [1011 0110] [1110 0000] = {4, -54, -96}
+
+ startOffset = 3;
+ numBits = 16;
+ byte data17[] = new byte[5];
+ BitBufferHelper.insertBits(data17, inputdata, startOffset, numBits);
+ Assert.assertTrue(data17[0] == 9);
+ Assert.assertTrue(data17[1] == 109);
+ Assert.assertTrue(data17[2] == -64);
+ Assert.assertTrue(data17[3] == 0);
+
+ // INPUT: {79, 110, 111}
+ // = [01001111] [01101110] [01101111]
+ //OUTPUT: [0000 1001] [1110 1101] [110 00000] = {9, -19, -64}
+ byte data18[] = new byte[5];
+ byte inputdata3[] = { 79, 110, 111 };
+ startOffset = 3;
+ numBits = 16;
+ BitBufferHelper.insertBits(data18, inputdata3, startOffset, numBits);
+ Assert.assertTrue(data18[0] == 9);
+ Assert.assertTrue(data18[1] == -19);
+ Assert.assertTrue(data18[2] == -64);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 1001] [0110 1101] [1100 1101] [0110 1010] [0000 0001] = {9, 109, -51, 106, 0}
+
+ startOffset = 3;
+ numBits = 32;
+ byte data19[] = new byte[5];
+ BitBufferHelper.insertBits(data19, inputdata, startOffset, numBits);
+ Assert.assertTrue(data19[0] == 9);
+ Assert.assertTrue(data19[1] == 109);
+ Assert.assertTrue(data19[2] == -51);
+ Assert.assertTrue(data19[3] == 106);
+ Assert.assertTrue(data19[4] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: data[4, 5, 6] = [0 010 0101] [1 011 0111] [0 000 0000] = {37, -73, 0}
+ startOffset = 33;
+ numBits = 16;
+ byte data20[] = new byte[7];
+ BitBufferHelper.insertBits(data20, inputdata, startOffset, numBits);
+ Assert.assertTrue(data20[4] == 37);
+ Assert.assertTrue(data20[5] == -73);
+ Assert.assertTrue(data20[6] == 0);
+
+ //CASE 4: extranumBits != 0 AND extraOffsetBits != 0
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 1001] [0100 0000] = {9, 96}
+ startOffset = 3;
+ numBits = 7;
+ byte data21[] = new byte[7];
+ BitBufferHelper.insertBits(data21, inputdata, startOffset, numBits);
+ Assert.assertTrue(data21[0] == 9);
+ Assert.assertTrue(data21[1] == 64);
+ Assert.assertTrue(data21[2] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: data = [00000 010] [01011 011] [01110 000] = {37, -73, 0}
+ startOffset = 5;
+ numBits = 17;
+ byte data22[] = new byte[7];
+ BitBufferHelper.insertBits(data22, inputdata, startOffset, numBits);
+ Assert.assertTrue(data22[0] == 2);
+ Assert.assertTrue(data22[1] == 91);
+ Assert.assertTrue(data22[2] == 112);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 1001] [0110 1101] [110 01101] [01 00000] = {9, 109, -51, 64}
+ startOffset = 3;
+ numBits = 23;
+ byte data23[] = new byte[7];
+ BitBufferHelper.insertBits(data23, inputdata, startOffset, numBits);
+ Assert.assertTrue(data23[0] == 9);
+ Assert.assertTrue(data23[1] == 109);
+ Assert.assertTrue(data23[2] == -51);
+ Assert.assertTrue(data23[3] == 64);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 1001] [0110 1101] = {9, 109}
+ startOffset = 3;
+ numBits = 13;
+ byte data24[] = new byte[7];
+ BitBufferHelper.insertBits(data24, inputdata, startOffset, numBits);
+ Assert.assertTrue(data24[0] == 9);
+ Assert.assertTrue(data24[1] == 109);
+ Assert.assertTrue(data24[2] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 0100] [1011 0110] [1110 0110] = {4, -74, -26}
+ startOffset = 4;
+ numBits = 20;
+ byte data25[] = new byte[7];
+ BitBufferHelper.insertBits(data25, inputdata, startOffset, numBits);
+ Assert.assertTrue(data25[0] == 4);
+ Assert.assertTrue(data25[1] == -74);
+ Assert.assertTrue(data25[2] == -26);
+ Assert.assertTrue(data25[3] == -0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [0000 0010] [0101 1011] = {0, 2, 91, 0}
+ startOffset = 13;
+ numBits = 11;
+ byte data26[] = new byte[7];
+ BitBufferHelper.insertBits(data26, inputdata, startOffset, numBits);
+ Assert.assertTrue(data26[0] == 0);
+ Assert.assertTrue(data26[1] == 2);
+ Assert.assertTrue(data26[2] == 91);
+ Assert.assertTrue(data26[3] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [000 01001] [011 01101] [110 0 0000] = {9, 109, -64, 0}
+ startOffset = 3;
+ numBits = 17;
+ byte data27[] = new byte[7];
+ BitBufferHelper.insertBits(data27, inputdata, startOffset, numBits);
+ Assert.assertTrue(data27[0] == 9);
+ Assert.assertTrue(data27[1] == 109);
+ Assert.assertTrue(data27[2] == -64);
+ Assert.assertTrue(data27[3] == 0);
+
+ // INPUT: {75, 110, 107, 80, 10, 12, 35, 100, 125, 65} =
+ // [01001011] [01101110] [01101011] [01010000] [00001010] [00001100] [00100011] [01100100] [11111101] [01000001] //OUTPUT: [00000000] [00000100] [10110110] [11100000]= {0, 4, -54, -96}
+ // OUTPUT: [00 000000] [00 000000] [00 010010] [11 011011] [10 011010] [11 010100] [0000 0000] = {0, 0, 18, -37,-102,-44,0}
+ startOffset = 18;
+ numBits = 34;
+ byte data28[] = new byte[7];
+ BitBufferHelper.insertBits(data28, inputdata, startOffset, numBits);
+ Assert.assertTrue(data28[0] == 0);
+ Assert.assertTrue(data28[1] == 0);
+ Assert.assertTrue(data28[2] == 18);
+ Assert.assertTrue(data28[3] == -37);
+ Assert.assertTrue(data28[4] == -102);
+ Assert.assertTrue(data28[5] == -44);
+ Assert.assertTrue(data28[6] == 0);
+
+ }
+
+ @Test
+ public void testGetShort() throws Exception {
+ byte data[] = new byte[2];
+ data[0] = 7;
+ data[1] = 8;
+ int length = 9; // num bits
+ Assert.assertTrue(BitBufferHelper.getShort(data, length) == 264);
+
+ data[0] = 6;
+ data[1] = 8;
+ short result = BitBufferHelper.getShort(data, length);
+ Assert.assertTrue(result == 8);
+
+ data[0] = 8;
+ data[1] = 47;
+ result = BitBufferHelper.getShort(data, length);
+ Assert.assertTrue(result == 47);
+
+ //[0000 0001] [0001 0100] [0110 0100]
+ byte[] data1 = new byte[2];
+ data1[0] = 1;
+ data1[1] = 20; //data1[2] = 100;
+ length = 15;
+ result = BitBufferHelper.getShort(data1, length);
+ Assert.assertTrue(result == 276);
+
+ byte[] data2 = new byte[2];
+ data2[0] = 64;
+ data2[1] = 99; //data2[2] = 100;
+ length = 13;
+ result = BitBufferHelper.getShort(data2, length);
+ Assert.assertTrue(result == 99);
+
+ byte[] data3 = { 100, 50 };
+ result = BitBufferHelper.getShort(data3);
+ Assert.assertTrue(result == 25650);
+ }
+
+ @Test
+ public void testToIntVarLength() throws Exception {
+ byte data[] = { (byte) 255, (byte) 128 };
+ int length = 9; // num bits
+ Assert.assertTrue(BitBufferHelper.getInt(data, length) == 384);
+
+ byte data2[] = { 0, 8 };
+ Assert.assertTrue(BitBufferHelper.getInt(data2, 9) == 8);
+
+ byte data3[] = { 1, 1, 1 };
+ Assert.assertTrue(BitBufferHelper.getInt(data3) == 65793);
+
+ byte data4[] = { 1, 1, 1 };
+ Assert.assertTrue(BitBufferHelper.getInt(data4) == 65793);
+
+ byte data5[] = { 1, 1 };
+ Assert.assertTrue(BitBufferHelper.getInt(data5) == 257);
+
+ }
+
+ @Test
+ public void testShiftBitstoLSB() {
+ byte[] data = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
+
+ byte[] data2 = { 8, 9, 10 };
+ byte[] shiftedBytes2 = BitBufferHelper.shiftBitsToLSB(data2, 11);
+
+ Assert.assertTrue(shiftedBytes2[0] == 0);
+ Assert.assertTrue(shiftedBytes2[1] == 64);
+ Assert.assertTrue(shiftedBytes2[2] == 72);
+
+ byte[] shiftedBytes = BitBufferHelper.shiftBitsToLSB(data, 49);
+
+ Assert.assertTrue(shiftedBytes[0] == 0);
+ Assert.assertTrue(shiftedBytes[1] == 2);
+ Assert.assertTrue(shiftedBytes[2] == 4);
+ Assert.assertTrue(shiftedBytes[3] == 6);
+ Assert.assertTrue(shiftedBytes[4] == 8);
+ Assert.assertTrue(shiftedBytes[5] == 10);
+ Assert.assertTrue(shiftedBytes[6] == 12);
+ Assert.assertTrue(shiftedBytes[7] == 14);
+ Assert.assertTrue(shiftedBytes[8] == 16);
+ Assert.assertTrue(shiftedBytes[9] == 18);
+
+ byte[] data1 = { 1, 2, 3 };
+ byte[] shiftedBytes1 = BitBufferHelper.shiftBitsToLSB(data1, 18);
+ Assert.assertTrue(shiftedBytes1[0] == 0);
+ Assert.assertTrue(shiftedBytes1[1] == 4);
+ Assert.assertTrue(shiftedBytes1[2] == 8);
+
+ }
+
+ @Test
+ public void testShiftBitstoLSBMSB() {
+ byte[] data = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 0 };
+
+ byte[] clone = BitBufferHelper.shiftBitsToMSB(BitBufferHelper
+ .shiftBitsToLSB(data, 72), 72);
+
+ Assert.assertTrue(clone[0] == 1);
+ Assert.assertTrue(clone[1] == 2);
+ Assert.assertTrue(clone[2] == 3);
+ Assert.assertTrue(clone[3] == 4);
+ Assert.assertTrue(clone[4] == 5);
+ Assert.assertTrue(clone[5] == 6);
+ Assert.assertTrue(clone[6] == 7);
+ Assert.assertTrue(clone[7] == 8);
+ Assert.assertTrue(clone[8] == 9);
+ Assert.assertTrue(clone[9] == 0);
+ }
+
+}
--- /dev/null
+/*
+ * Copyright (c) 2014, 2015 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+
+/**
+ * @file EthernetAddressTest.java
+ *
+ * @brief Unit Tests for EthernetAddress class
+ *
+ * Unit Tests for EthernetAddress class
+ */
+package org.opendaylight.openflowplugin.libraries.sal.packet.address;
+
+import org.junit.Assert;
+import org.junit.Test;
+import org.opendaylight.openflowplugin.libraries.liblldp.ConstructionException;
+import org.opendaylight.openflowplugin.libraries.liblldp.EthernetAddress;
+
+public class EthernetAddressTest {
+ @Test
+ public void testNonValidConstructor() {
+ @SuppressWarnings("unused")
+ EthernetAddress ea1;
+ // Null input array
+ try {
+ ea1 = new EthernetAddress((byte[]) null);
+
+ // Exception is expected if NOT raised test will fail
+ Assert.assertTrue(false);
+ } catch (final ConstructionException e) {
+ }
+
+ // Array too short
+ try {
+ ea1 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0 });
+
+ // Exception is expected if NOT raised test will fail
+ Assert.assertTrue(false);
+ } catch (final ConstructionException e) {
+ }
+
+ // Array too long
+ try {
+ ea1 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x0,
+ (byte) 0x0 });
+
+ // Exception is expected if NOT raised test will fail
+ Assert.assertTrue(false);
+ } catch (final ConstructionException e) {
+ }
+ }
+
+ @Test
+ public void testEquality() {
+ EthernetAddress ea1;
+ EthernetAddress ea2;
+ try {
+ ea1 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x1 });
+
+ ea2 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x1 });
+ Assert.assertTrue(ea1.equals(ea2));
+ } catch (final ConstructionException e) {
+ // Exception is NOT expected if raised test will fail
+ Assert.assertTrue(false);
+ }
+
+ try {
+ ea1 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x1 });
+
+ ea2 = ea1.clone();
+ Assert.assertTrue(ea1.equals(ea2));
+ } catch (final ConstructionException e) {
+ // Exception is NOT expected if raised test will fail
+ Assert.assertTrue(false);
+ }
+
+ // Check for well knowns
+ try {
+ ea1 = EthernetAddress.BROADCASTMAC;
+ ea2 = new EthernetAddress(new byte[] { (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff });
+ Assert.assertTrue(ea1.equals(ea2));
+ } catch (final ConstructionException e) {
+ // Exception is NOT expected if raised test will fail
+ Assert.assertTrue(false);
+ }
+ }
+
+ @Test
+ public void testUnEquality() {
+ EthernetAddress ea1;
+ EthernetAddress ea2;
+ try {
+ ea1 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x2 });
+
+ ea2 = new EthernetAddress(new byte[] { (byte) 0x0, (byte) 0x0,
+ (byte) 0x0, (byte) 0x0, (byte) 0x0, (byte) 0x1 });
+ Assert.assertTrue(!ea1.equals(ea2));
+ } catch (final ConstructionException e) {
+ // Exception is NOT expected if raised test will fail
+ Assert.assertTrue(false);
+ }
+ }
+}
--- /dev/null
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
+<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">
+
+ <appender name="console" class="org.apache.log4j.ConsoleAppender">
+ <layout class="org.apache.log4j.PatternLayout">
+ <param name="ConversionPattern" value="%-6p %d{HH:mm:ss.SSS} [%10.10t] %30.30c %x - %m%n" />
+ </layout>
+ </appender>
+
+ <logger name="org.opendaylight.openflowplugin.libraries.liblldp" additivity="false">
+ <level value="DEBUG" />
+ <appender-ref ref="console" />
+ </logger>
+
+ <root>
+ <priority value="INFO" />
+ <appender-ref ref="console" />
+ </root>
+</log4j:configuration>
--- /dev/null
+<?xml version="1.0" encoding="UTF-8"?>
+<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">
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-parent</artifactId>
+ <version>0.6.0-SNAPSHOT</version>
+ <relativePath>../parent</relativePath>
+ </parent>
+
+ <artifactId>libraries</artifactId>
+ <name>libraries</name>
+ <url>http://maven.apache.org</url>
+ <packaging>pom</packaging>
+
+ <build>
+ <plugins>
+ <!-- TODO: Fix checkstyle issues later
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-checkstyle-plugin</artifactId>
+ <configuration>
+ <propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
+ </configuration>
+ </plugin>
+ -->
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ </plugin>
+ </plugins>
+ </build>
+
+ <scm>
+ <connection>scm:git:ssh://git.opendaylight.org:29418/openflowplugin.git</connection>
+ <developerConnection>scm:git:ssh://git.opendaylight.org:29418/openflowplugin.git</developerConnection>
+ <url>https://wiki.opendaylight.org/view/OpenDaylight_OpenFlow_Plugin:Main</url>
+ <tag>HEAD</tag>
+ </scm>
+
+ <modules>
+ <module>liblldp</module>
+ </modules>
+</project>
\ No newline at end of file
<module>model-flow-statistics</module>
</modules>
- <properties>
- <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
- </properties>
-
<dependencies>
<dependency>
<groupId>org.opendaylight.mdsal</groupId>
</instructions>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>yang-binding</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <yangFilesRootDir>src/main/yang</yangFilesRootDir>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${salGeneratorPath}</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>target/site/models</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.wadl.generator.maven.WadlGenerator</codeGeneratorClass>
- <outputBaseDir>target/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- </plugin>
</plugins>
</build>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>feature-repo-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>single-feature-parent</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
<name>ODL :: openflowjava :: ${project.artifactId}</name>
<properties>
- <controller.mdsal.version>1.7.0-SNAPSHOT</controller.mdsal.version>
<mdsal.version>2.4.0-SNAPSHOT</mdsal.version>
<mdsal.model.version>0.12.0-SNAPSHOT</mdsal.model.version>
</properties>
<dependency>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odlparent-artifacts</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<scope>import</scope>
<type>pom</type>
</dependency>
<scope>import</scope>
<type>pom</type>
</dependency>
-
- <!-- Controller infrastructure -->
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>mdsal-artifacts</artifactId>
- <version>${controller.mdsal.version}</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
</dependencies>
</dependencyManagement>
<type>xml</type>
<classifier>features</classifier>
</dependency>
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>odl-mdsal-common</artifactId>
- <type>xml</type>
- <classifier>features</classifier>
- </dependency>
<dependency>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odl-netty-4</artifactId>
<parent>
<groupId>org.opendaylight.odlparent</groupId>
<artifactId>odlparent-lite</artifactId>
- <version>2.0.5</version>
+ <version>3.0.2</version>
<relativePath/>
</parent>
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>binding-parent</artifactId>
- <version>0.12.0-SNAPSHOT</version>
- <relativePath/>
+ <groupId>org.opendaylight.openflowplugin</groupId>
+ <artifactId>openflowplugin-parent</artifactId>
+ <version>0.6.0-SNAPSHOT</version>
+ <relativePath>../../parent</relativePath>
</parent>
<groupId>org.opendaylight.openflowplugin.openflowjava</groupId>
<artifactId>openflow-protocol-api</artifactId>
<tag>HEAD</tag>
</scm>
- <properties>
- <mdsal.version>2.4.0-SNAPSHOT</mdsal.version>
- <mdsal.model.version>0.12.0-SNAPSHOT</mdsal.model.version>
- </properties>
-
- <dependencyManagement>
- <dependencies>
- <!-- MD-SAL -->
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>mdsal-artifacts</artifactId>
- <version>${mdsal.version}</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
-
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>${mdsal.model.version}</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
<dependencies>
<dependency>
<groupId>org.opendaylight.mdsal</groupId>
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.system.rev130927.SystemNotificationsListener;
/**
+ * Manages a switch connection.
+ *
* @author mirehak
* @author michal.polkorab
*/
public interface ConnectionAdapter extends OpenflowProtocolService {
/**
- * disconnect corresponding switch
+ * Disconnect corresponding switch.
+ *
* @return future set to true, when disconnect completed
*/
Future<Boolean> disconnect();
/**
+ * Determines if the connection to the switch is alive.
+ *
* @return true, if connection to switch is alive
*/
boolean isAlive();
/**
+ * Returns the address of the connected switch.
+ *
* @return address of the remote end - address of a switch if connected
*/
InetSocketAddress getRemoteAddress();
/**
+ * Sets the protocol message listener.
+ *
* @param messageListener here will be pushed all messages from switch
*/
void setMessageListener(OpenflowProtocolListener messageListener);
/**
+ * Sets the system message listener.
+ *
* @param systemListener here will be pushed all system messages from library
*/
void setSystemListener(SystemNotificationsListener systemListener);
/**
- * Set handler for alien messages received from device
+ * Set handler for alien messages received from device.
+ *
* @param alienMessageListener here will be pushed all alien messages from switch
*/
void setAlienMessageListener(AlienMessageListener alienMessageListener);
/**
- * Throws exception if any of required listeners is missing
+ * Throws exception if any of required listeners is missing.
*/
void checkListeners();
/**
- * notify listener about connection ready-to-use event
+ * Notify listener about connection ready-to-use event.
*/
void fireConnectionReadyNotification();
/**
- * set listener for connection became ready-to-use event
+ * Set listener for connection became ready-to-use event.
+ *
* @param connectionReadyListener listens to connection ready event
*/
void setConnectionReadyListener(ConnectionReadyListener connectionReadyListener);
/**
- * sets option for automatic channel reading;
- * if set to false, incoming messages won't be read
+ * Sets option for automatic channel reading - if set to false, incoming messages won't be read.
*
* @param autoRead target value to be switched to
*/
void setAutoRead(boolean autoRead);
/**
- * @return true, if channel is configured to autoread
+ * Determines if the channel is configured to auto-read.
+ *
+ * @return true, if channel is configured to auto-read
*/
boolean isAutoRead();
/**
- * Registers a new bypass outbound queue
+ * Registers a new bypass outbound queue.
+ *
* @param <T> handler type
* @param handler queue handler
* @param maxQueueDepth max amount of not confirmed messaged in queue (i.e. edge for barrier message)
import java.net.InetAddress;
/**
+ * Configuration for a switch connection.
+ *
* @author mirehak
*/
public interface ConnectionConfiguration {
/**
+ * Returns address to bind.
+ *
* @return address to bind, if null, all available interfaces will be used
*/
InetAddress getAddress();
/**
+ * Returns the port to bind.
+ *
* @return port to bind
*/
int getPort();
/**
+ * Returns the transport protocol to use.
+ *
* @return transport protocol to use
*/
Object getTransferProtocol();
/**
+ * Returns the TLS configuration.
+ *
* @return TLS configuration object
*/
TlsConfiguration getTlsConfiguration();
/**
+ * Returns the swicth idle timeout.
+ *
* @return silence time (in milliseconds) - after this time
* {@link org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.system.rev130927.SwitchIdleEvent}
* message is sent upstream
long getSwitchIdleTimeout();
/**
+ * Returns the SSL context.
+ *
* @return seed for {@link javax.net.ssl.SSLEngine}
*/
Object getSslContext();
/**
+ * Returns the thread configuration.
+ *
* @return thread numbers for TcpHandler's eventloopGroups
*/
ThreadConfiguration getThreadConfiguration();
/**
+ * Determines if a barrier shoild be used.
+ *
* @return boolean value for usability of Barrier
*/
boolean useBarrier();
+
+ /**
+ * Checks if group add mod messages are enabled.
+ * @return true if group add mod messages are enabled
+ */
+ boolean isGroupAddModEnabled();
}
package org.opendaylight.openflowjava.protocol.api.connection;
/**
- * @author mirehak
+ * Listener that is notified when a switch connection is ready.
*
+ * @author mirehak
*/
public interface ConnectionReadyListener {
/**
- * fired when connection becomes ready-to-use
+ * Fired when connection becomes ready-to-use.
*/
void onConnectionReady();
}
import java.util.concurrent.Future;
/**
- * for testing purposed
+ * For testing purposes.
+ *
* @author mirehak
*/
public interface ListeningStatusProvider {
/**
+ * Determines if the plugin has successfully started.
+ *
* @return future holding startup result of all library instances under plugin's control
*/
Future<Boolean> isOnline();
* with a response, the object reported will be non-null. If the request's completion
* is implied by a barrier, the object reported will be null.
*
+ * <p>
* If this request fails on the remote device, {@link FutureCallback#onFailure(Throwable)}
* will be called with an instance of {@link DeviceRequestFailedException}.
*
+ * <p>
* If the request fails due to local reasons, {@link FutureCallback#onFailure(Throwable)}
* will be called with an instance of {@link OutboundQueueException}. In particular, if
* this request failed because the device disconnected, {@link OutboundQueueException#DEVICE_DISCONNECTED}
* with a response, the object reported will be non-null. If the request's completion
* is implied by a barrier, the object reported will be null.
*
+ * <p>
* If this request fails on the remote device, {@link FutureCallback#onFailure(Throwable)}
* will be called with an instance of {@link DeviceRequestFailedException}.
*
+ * <p>
* If the request fails due to local reasons, {@link FutureCallback#onFailure(Throwable)}
* will be called with an instance of {@link OutboundQueueException}. In particular, if
* this request failed because the device disconnected, {@link OutboundQueueException#DEVICE_DISCONNECTED}
package org.opendaylight.openflowjava.protocol.api.connection;
/**
- * Used for StatisticsCounter configuration
+ * Used for StatisticsCounter configuration.
*
* @author madamjak
*/
public interface StatisticsConfiguration {
/**
+ * Determines if statistics are enabled.
+ *
* @return true if statistics are / will be collected, false otherwise
*/
boolean getStatisticsCollect();
/**
+ * Returns the delay between two statistics logs.
+ *
* @return delay between two statistics logs (in milliseconds)
*/
int getLogReportDelay();
-}
\ No newline at end of file
+}
import java.net.InetAddress;
/**
+ * Handler for a swictch connection.
+ *
* @author mirehak
* @author michal.polkorab
*
public interface SwitchConnectionHandler {
/**
+ * Invoked when a switch connects.
+ *
* @param connection to switch proving message sending/receiving, connection management
*/
void onSwitchConnected(ConnectionAdapter connection);
/**
+ * Invoked to determine if a switch connection should be accepted.
+ *
* @param switchAddress address of incoming connection (address + port)
* @return true, if connection from switch having given address shell be accepted; false otherwise
*/
package org.opendaylight.openflowjava.protocol.api.connection;
/**
- * @author michal.polkorab
+ * Threading configuration.
*
+ * @author michal.polkorab
*/
public interface ThreadConfiguration {
/**
- * @return desired number of workerThreads processing the Openflow I/O
+ * Returns the desired number of Openflow I/O worker threads.
+ *
+ * @return desired number of worker threads processing the Openflow I/O
*/
int getWorkerThreadCount();
/**
- * @return desired number of bossThreads registering incomming Openflow connections
+ * Returns the desired number of incoming Openflow connection threads.
+ *
+ * @return desired number of bossThreads registering incoming Openflow connections
*/
int getBossThreadCount();
}
package org.opendaylight.openflowjava.protocol.api.connection;
import java.util.List;
-
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.KeystoreType;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.PathType;
/**
- * @author michal.polkorab
+ * Tls configuration.
*
+ * @author michal.polkorab
*/
public interface TlsConfiguration {
/**
- * @return keystore location
+ * Returns the key store location.
+ *
+ * @return key store location
*/
String getTlsKeystore();
/**
- * @return keystore type
+ * Returns the key store type.
+ *
+ * @return key store type
*/
KeystoreType getTlsKeystoreType();
/**
- * @return truststore location
+ * Returns the trust store location.
+ *
+ * @return trust store location
*/
String getTlsTruststore();
/**
- * @return truststore type
+ * Returns the trust store type.
+ *
+ * @return trust store type
*/
KeystoreType getTlsTruststoreType();
/**
- * @return keystore path type (CLASSPATH or PATH)
+ * Returns the key store path type.
+ *
+ * @return key store path type (CLASSPATH or PATH)
*/
PathType getTlsKeystorePathType();
/**
- * @return truststore path type (CLASSPATH or PATH)
+ * Returns the trust store path type.
+ *
+ * @return trust store path type (CLASSPATH or PATH)
*/
PathType getTlsTruststorePathType();
/**
- * @return password protecting specified keystore
+ * Returns the password protecting the key store.
+ *
+ * @return password protecting the specified key store
*/
String getKeystorePassword();
/**
+ * Returns the password protecting the certificate.
+ *
* @return password protecting certificate
*/
String getCertificatePassword();
/**
- * @return password protecting specified truststore
+ * Returns the password protecting the trust store.
+ *
+ * @return password protecting specified trust store
*/
String getTruststorePassword();
/**
+ * Returns the list of cipher suites for TLS connection.
+ *
* @return list of cipher suites for TLS connection
*/
List<String> getCipherSuites();
package org.opendaylight.openflowjava.protocol.api.connection;
import java.util.List;
-
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.KeystoreType;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.PathType;
/**
- * Class is used only for testing purposes - passwords are hardcoded
+ * Class is used only for testing purposes - passwords are hard-coded.
+ *
* @author michal.polkorab
*/
public class TlsConfigurationImpl implements TlsConfiguration {
- private KeystoreType trustStoreType;
- private String trustStore;
- private KeystoreType keyStoreType;
- private String keyStore;
- private PathType keystorePathType;
- private PathType truststorePathType;
- private List<String> cipherSuites;
+ private final KeystoreType trustStoreType;
+ private final String trustStore;
+ private final KeystoreType keyStoreType;
+ private final String keyStore;
+ private final PathType keystorePathType;
+ private final PathType truststorePathType;
+ private final List<String> cipherSuites;
/**
- * Default constructor
+ * Default constructor.
+ *
* @param trustStoreType JKS or PKCS12
* @param trustStore path to trustStore file
* @param trustStorePathType truststore path type (classpath or path)
public interface AlienMessageListener {
/**
- * Handler for alien but successfully deserialized messages for device
+ * Handler for alien but successfully deserialized messages for device.
+ *
* @param message alien message
* @return true if alien message was successfully processed
*/
boolean onAlienMessage(OfHeader message);
-}
\ No newline at end of file
+}
* vendor / experimenter subtype, vendor has to switch / choose between
* these subtypes.<br>
*
+ * <p>
* This has to be done in this way because of experimenter headers, which
* provide only vendor / experimenter ID. Subtype position may be different
* for different vendors (or not present at all) - that's why vendor has to
* Registers deserializer.
* Throws IllegalStateException when there is
* a deserializer already registered under given key.
+ *
* <p>
* If the deserializer implements {@link DeserializerRegistryInjector} interface,
* the deserializer is injected with DeserializerRegistry instance.
OFGeneralDeserializer deserializer);
/**
- * Unregisters custom deserializer
+ * Unregisters custom deserializer.
+ *
* @param key used for deserializer lookup
* @return true if deserializer was removed,
- * false if no deserializer was found under specified key
+ * false if no deserializer was found under specified key
*/
boolean unregisterDeserializer(ExperimenterDeserializerKey key);
/**
- * Registers action deserializer
+ * Registers action deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFGeneralDeserializer deserializer);
/**
- * Registers instruction deserializer
+ * Registers instruction deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFGeneralDeserializer deserializer);
/**
- * Registers match entry deserializer
+ * Registers match entry deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFGeneralDeserializer deserializer);
/**
- * Registers error message deserializer
+ * Registers error message deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFDeserializer<ErrorMessage> deserializer);
/**
- * Registers experimenter (vendor) message deserializer
+ * Registers experimenter (vendor) message deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFDeserializer<? extends ExperimenterDataOfChoice> deserializer);
/**
- * Registers multipart-reply (stats) message deserializer
+ * Registers multipart-reply (stats) message deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFDeserializer<? extends ExperimenterDataOfChoice> deserializer);
/**
- * Registers multipart-reply table-features message deserializer
+ * Registers multipart-reply table-features message deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFGeneralDeserializer deserializer);
/**
- * Registers meter band deserializer (used in multipart-reply meter-config)
+ * Registers meter band deserializer (used in multipart-reply meter-config).
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFDeserializer<MeterBandExperimenterCase> deserializer);
/**
- * Registers queue property (QUEUE_GET_CONFIG_REPLY message) deserializer
+ * Registers queue property (QUEUE_GET_CONFIG_REPLY message) deserializer.
+ *
* @param key used for deserializer lookup
* @param deserializer deserializer instance
*/
OFDeserializer<QueueProperty> deserializer);
/**
- * Registers type to class mapping used to assign return type when deserializing message
+ * Registers type to class mapping used to assign return type when deserializing message.
+ *
* @param key type to class key
* @param clazz return class
*/
void registerDeserializerMapping(TypeToClassKey key, Class<?> clazz);
/**
- * Unregisters type to class mapping used to assign return type when deserializing message
+ * Unregisters type to class mapping used to assign return type when deserializing message.
+ *
* @param key type to class key
* @return true if mapping was successfully removed
*/
import org.opendaylight.openflowjava.protocol.api.keys.MessageCodeKey;
-
/**
- * @author michal.polkorab
+ * Registry for deserializers.
*
+ * @author michal.polkorab
*/
public interface DeserializerRegistry {
/**
- * Initializes deserializers
+ * Initializes deserializers.
*/
void init();
/**
+ * Gets the deserializer for the given key.
+ *
* @param <T> type of particular deserializer
* @param key used for deserializer lookup
* @return deserializer found
T getDeserializer(MessageCodeKey key);
/**
- * Registers deserializer.
+ * Registers a deserializer.
* Throws IllegalStateException when there is
* a deserializer already registered under given key.
*
+ * <p>
* If the deserializer implements {@link DeserializerRegistryInjector} interface,
* the deserializer is injected with DeserializerRegistry instance.
*
OFGeneralDeserializer deserializer);
/**
- * Unregisters deserializer
+ * Unregisters a deserializer.
+ *
* @param key used for deserializer lookup
* @return true if deserializer was removed,
- * false if no deserializer was found under specified key
+ * false if no deserializer was found under specified key
*/
boolean unregisterDeserializer(MessageCodeKey key);
}
package org.opendaylight.openflowjava.protocol.api.extensibility;
/**
- * Injects registry
+ * Injects registries.
+ *
* @author michal.polkorab
*/
public interface DeserializerRegistryInjector {
/**
- * Injects deserializer registry into deserializer
+ * Injects deserializer registry into deserializer.
+ *
* @param deserializerRegistry registry of deserializers
*/
void injectDeserializerRegistry(DeserializerRegistry deserializerRegistry);
import org.opendaylight.openflowjava.protocol.api.keys.MessageCodeKey;
/**
- * @author michal.polkorab
+ * Enhanced MessageCodeKey.
*
+ * @author michal.polkorab
*/
public class EnhancedMessageCodeKey extends MessageCodeKey {
- private int msgType2;
+ private final int msgType2;
/**
- * Constructor
+ * Constructor.
+ *
* @param version wire protocol version
* @param value used as distinguisher
* @param value2 used as detailed distinguisher
public String toString() {
return super.toString() + " msgType2: " + msgType2;
}
-}
\ No newline at end of file
+}
/**
- * More specific key for {@link SerializerRegistry}
+ * More specific key for {@link SerializerRegistry}.
+ *
* @author michal.polkorab
* @param <E> main type
* @param <F> specific type
private final Class<F> msgType2;
/**
+ * Constructor.
+ *
* @param msgVersion protocol version
* @param msgType main type
* @param msgType2 subtype
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((msgType2 == null) ? 0 : msgType2.hashCode());
+ result = prime * result + (msgType2 == null ? 0 : msgType2.hashCode());
return result;
}
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
+ * Deserializes headers.
+ *
* @author michal.polkorab
* @param <E> output message type
*/
public interface HeaderDeserializer<E extends DataContainer> extends OFGeneralDeserializer {
/**
- * Deserializes byte message headers
+ * Deserializes a byte message headers.
*
* @param rawMessage message as bytes in ByteBuf
* @return POJO/DTO
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
- * Does only-header serialization (such as oxm_ids, action_ids, instruction_ids)
+ * Does only-header serialization (such as oxm_ids, action_ids, instruction_ids).
+ *
* @author michal.polkorab
* @param <T> input message type
*/
public interface HeaderSerializer<T extends DataContainer> extends OFGeneralSerializer {
/**
- * Serializes object headers (e.g. for Multipart message - Table Features)
+ * Serializes object headers (e.g. for Multipart message - Table Features).
+ *
* @param input object whose headers should be serialized
* @param outBuffer output buffer
*/
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
- * Uniform interface for deserializing factories
+ * Uniform interface for deserializing factories.
+ *
* @author michal.polkorab
* @author timotej.kubas
* @param <E> message code type
*/
package org.opendaylight.openflowjava.protocol.api.extensibility;
-
/**
+ * Unifying super interface for a general deserializer.
+ *
* @author michal.polkorab
*/
public interface OFGeneralDeserializer {
package org.opendaylight.openflowjava.protocol.api.extensibility;
/**
- * Unifying superinterface
+ * Unifying super interface for a general derializer.
+ *
* @author michal.polkorab
* */
public interface OFGeneralSerializer {
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
- * Uniform interface for serializers
+ * Uniform interface for serializers.
+ *
* @author michal.polkorab
* @author timotej.kubas
* @param <T> message type
* vendor / experimenter subtype, vendor has to switch / choose between
* these subtypes.<br>
*
+ * <p>
* This has to be done in this way because of unknown augmentations
* - that's why vendor has to handle it in his own implementations.
* @author michal.polkorab
public interface SerializerExtensionProvider {
/**
- * Registers serializer
+ * Registers a custom serializer.
+ *
* Throws IllegalStateException when there is
* a serializer already registered under given key.
*
OFGeneralSerializer serializer);
/**
- * Unregisters custom serializer
+ * Unregisters a custom serializer.
+ *
* @param key used for serializer lookup
- * @return true if serializer was removed,
- * false if no serializer was found under specified key
+ * @return true if serializer was removed, false if no serializer was found under specified key
*/
boolean unregisterSerializer(ExperimenterSerializerKey key);
/**
- * Registers action serializer
+ * Registers an action serializer.
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
OFGeneralSerializer serializer);
/**
- * Registers instruction serializer
+ * Registers an instruction serializer.
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
OFGeneralSerializer serializer);
/**
- * Registers match entry serializer
+ * Registers a match entry serializer.
+ *
* @param <C> oxm type
* @param <F> match field type
* @param key used for serializer lookup
MatchEntrySerializerKey<C, F> key,OFGeneralSerializer serializer);
/**
- * Registers experimenter (vendor) message serializer
+ * Registers an experimenter (vendor) message serializer.
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
OFSerializer<? extends ExperimenterDataOfChoice> serializer);
/**
- * Registers multipart-request (stats-request) serializer
+ * Registers a multipart-request (stats-request) serializer.
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
OFSerializer<? extends ExperimenterDataOfChoice> serializer);
/**
- * Registers multipart-request table-features serializer
+ * Registers a multipart-request table-features serializer.
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
OFGeneralSerializer serializer);
/**
- * @deprecated Since we use ExperimenterIdMeterSubTypeSerializerKey as MeterBandSerializer's key, in order to avoid
- * the occurrence of an error,we should discard this function
- * Registers meter band serializer (used in meter-mod messages)
+ * Registers a meter band serializer (used in meter-mod messages).
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
+ * @deprecated Since we use ExperimenterIdMeterSubTypeSerializerKey as MeterBandSerializer's key, in order to avoid
+ * the occurrence of an error,we should discard this function
*/
@Deprecated
void registerMeterBandSerializer(ExperimenterIdSerializerKey<MeterBandExperimenterCase> key,
OFSerializer<MeterBandExperimenterCase> serializer);
/**
- * Registers meter band serializer (used in meter-mod messages)
+ * Registers a meter band serializer (used in meter-mod messages).
+ *
* @param key used for serializer lookup
* @param serializer serializer implementation
*/
import org.opendaylight.openflowjava.protocol.api.keys.MessageTypeKey;
/**
- * Stores and handles serializers<br>
+ * Stores and handles serializers. <br>
* K - {@link MessageTypeKey} parameter type,<br>
* S - returned serializer type
* @author michal.polkorab
*/
public interface SerializerRegistry {
-
/**
- * Serializer registry provisioning
+ * Serializer registry provisioning.
*/
void init();
/**
+ * Gets the serializer for the given type.
+ *
* @param <K> input key type
* @param <S> type of resulting serializer
* @param msgTypeKey lookup key
<K, S extends OFGeneralSerializer> S getSerializer(MessageTypeKey<K> msgTypeKey);
/**
- * Registers serializer
+ * Registers a serializer.
+ *
* Throws IllegalStateException when there is
* a serializer already registered under given key.
*
OFGeneralSerializer serializer);
/**
- * Unregisters serializer
+ * Unregisters a serializer.
+ *
* @param <K> serializer key type
* @param key used for serializer lookup
* @return true if serializer was removed,
* false if no serializer was found under specified key
*/
<K> boolean unregisterSerializer(MessageTypeKey<K> key);
+
+ /**
+ * Checks if group add mod messages are enabled.
+ * @return true if group add mod messages are enabled
+ */
+ boolean isGroupAddModEnabled();
+
+ /**
+ *
+ * @param isGroupAddModEnabled true if group add mod messages are enabled
+ */
+ void setGroupAddModConfig(boolean isGroupAddModEnabled);
}
package org.opendaylight.openflowjava.protocol.api.extensibility;
/**
- * Serializer registry injector
+ * Serializer registry injector.
+ *
* @author michal.polkorab
*/
public interface SerializerRegistryInjector {
/**
- * Injects serializer registry
+ * Injects serializer registry.
+ *
* @param serializerRegistry registry instance
*/
void injectSerializerRegistry(SerializerRegistry serializerRegistry);
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.actions.grouping.Action;
/**
- * @author michal.polkorab
+ * Key for an action deserializer.
*
+ * @author michal.polkorab
*/
public class ActionDeserializerKey extends MessageCodeKey {
- private Long experimenterId;
+ private final Long experimenterId;
+
/**
+ * Constructor.
+ *
* @param version protocol wire version
* @param type action type
* @param experimenterId experimenter / vendor ID
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
return result;
}
public String toString() {
return super.toString() + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.actions.grouping.Action;
/**
+ * Key for an action serializer.
+ *
* @author michal.polkorab
* @param <T> action type
*/
public class ActionSerializerKey<T extends ActionChoice> extends MessageTypeKey<Action>
implements ExperimenterSerializerKey {
- private Class<T> actionType;
- private Long experimenterId;
+ private final Class<T> actionType;
+ private final Long experimenterId;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param actionType type of action
* @param experimenterId experimenter / vendor ID
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((actionType == null) ? 0 : actionType.hashCode());
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
+ result = prime * result + (actionType == null ? 0 : actionType.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
return result;
}
public String toString() {
return super.toString() + " action type: " + actionType.getName() + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Key for an experimenter action deserializer.
*
+ * @author michal.polkorab
*/
public final class ExperimenterActionDeserializerKey extends ActionDeserializerKey
implements ExperimenterDeserializerKey {
/**
+ * Constructor.
+ *
* @param version protocol wire version
* @param experimenterId experimenter / vendor ID
*/
public ExperimenterActionDeserializerKey(short version, Long experimenterId) {
super(version, EncodeConstants.EXPERIMENTER_VALUE, experimenterId);
}
-
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.ExperimenterActionSubType;
/**
+ * Key for an experimenter action serializer.
+ *
* @author michal.polkorab
*/
public final class ExperimenterActionSerializerKey extends ActionSerializerKey<ExperimenterIdCase>
implements ExperimenterSerializerKey {
- private Class<? extends ExperimenterActionSubType> actionSubType;
+ private final Class<? extends ExperimenterActionSubType> actionSubType;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param experimenterId experimenter / vendor ID
* @param actionSubType vendor defined subtype
*/
- public ExperimenterActionSerializerKey(short msgVersion, Long experimenterId, Class<? extends ExperimenterActionSubType> actionSubType) {
+ public ExperimenterActionSerializerKey(short msgVersion, Long experimenterId,
+ Class<? extends ExperimenterActionSubType> actionSubType) {
super(msgVersion, ExperimenterIdCase.class, experimenterId);
this.actionSubType = actionSubType;
}
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((actionSubType == null) ? 0 : actionSubType.hashCode());
+ result = prime * result + (actionSubType == null ? 0 : actionSubType.hashCode());
return result;
}
}
return true;
}
-}
\ No newline at end of file
+}
package org.opendaylight.openflowjava.protocol.api.keys;
/**
- * Marker interface - marks keys appropriate for experimenter deserializer registration
+ * Marker interface - marks keys appropriate for experimenter deserializer registration.
+ *
* @author michal.polkorab
*/
public interface ExperimenterDeserializerKey {
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
+ * Key for an experimenter id deserializer.
+ *
* @author michal.polkorab
*/
public class ExperimenterIdDeserializerKey extends MessageCodeKey implements ExperimenterDeserializerKey {
- private long experimenterId;
+ private final long experimenterId;
/**
+ * Constructor.
+ *
* @param <E> type of target experimenter object
* @param version protocol wire version
* @param experimenterId experimenter / vendor ID
}
protected int hashCodeOfLong(long longValue) {
- return (int) (longValue ^ (longValue >>> 32));
+ return (int) (longValue ^ longValue >>> 32);
}
@Override
public String toString() {
return super.toString() + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
- * Created by hyy on 2016/9/8.
+ * Key for an experimenter id meter subtype serializer.
+ *
+ * @author hyy on 2016/9/8.
*/
public class ExperimenterIdMeterSubTypeSerializerKey<T extends DataContainer> extends ExperimenterIdSerializerKey<T> {
- private Class<? extends ExperimenterMeterBandSubType> meterSubType;
+ private final Class<? extends ExperimenterMeterBandSubType> meterSubType;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param experimenterId experimenter / vendor ID
* @param objectClass class of object to be serialized
* @param meterSubType vendor defined subtype
*/
public ExperimenterIdMeterSubTypeSerializerKey(short msgVersion, long experimenterId,
- Class<T> objectClass, Class<? extends ExperimenterMeterBandSubType> meterSubType) {
+ Class<T> objectClass, Class<? extends ExperimenterMeterBandSubType> meterSubType) {
super(msgVersion, experimenterId, objectClass);
this.meterSubType = meterSubType;
}
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((meterSubType == null) ? 0 : meterSubType.hashCode());
+ result = prime * result + (meterSubType == null ? 0 : meterSubType.hashCode());
return result;
}
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
+ * Key for an experimenter id serializer.
+ *
* @author michal.polkorab
* @param <T> class of object to be serialized
*/
public class ExperimenterIdSerializerKey<T extends DataContainer> extends MessageTypeKey<T>
implements ExperimenterSerializerKey {
- private long experimenterId;
+ private final long experimenterId;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param experimenterId experimenter / vendor ID
* @param objectClass class of object to be serialized
}
protected int hashCodeOfLong(long longValue) {
- return (int) (longValue ^ (longValue >>> 32));
+ return (int) (longValue ^ longValue >>> 32);
}
@Override
public String toString() {
return super.toString() + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
+ * Key for an experimenter id type deserializer.
+ *
* @author michal.polkorab
*/
public class ExperimenterIdTypeDeserializerKey extends ExperimenterIdDeserializerKey {
- private long type;
+ private final long type;
/**
+ * Constructor.
+ *
* @param <T> type of target experimenter object
* @param version protocol wire version
* @param experimenterId experimenter / vendor ID
public String toString() {
return super.toString() + "; type: " + type;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yangtools.yang.binding.DataContainer;
/**
+ * Key for an experimenter id type serializer.
+ *
* @param <T> class of object to be serialized
* @author michal.polkorab
*/
public class ExperimenterIdTypeSerializerKey<T extends DataContainer> extends ExperimenterIdSerializerKey<T> {
- private long type;
+ private final long type;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param experimenterId experimenter / vendor ID
* @param type data type according to vendor implementation
public String toString() {
return super.toString() + "; type: " + type;
}
-}
\ No newline at end of file
+}
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Key for an experimenter instruction deserializer.
*
+ * @author michal.polkorab
*/
public final class ExperimenterInstructionDeserializerKey extends InstructionDeserializerKey
implements ExperimenterDeserializerKey {
/**
+ * Constructor.
+ *
* @param version protocol wire version
* @param experimenterId experimenter (vendor) identifier
*/
super(version, EncodeConstants.EXPERIMENTER_VALUE, experimenterId);
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.instruction.container.instruction.choice.ExperimenterIdCase;
/**
+ * Key for an experimenter instruction serializer.
+ *
* @author michal.polkorab
*/
public final class ExperimenterInstructionSerializerKey extends InstructionSerializerKey<ExperimenterIdCase>
implements ExperimenterSerializerKey {
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param experimenterId experimenter / vendor ID
*/
super(msgVersion, ExperimenterIdCase.class, experimenterId);
}
-}
\ No newline at end of file
+}
package org.opendaylight.openflowjava.protocol.api.keys;
/**
- * Marker interface - marks keys appropriate for experimenter serializer registration
+ * Marker interface - marks keys appropriate for experimenter serializer registration.
+ *
* @author michal.polkorab
*/
public interface ExperimenterSerializerKey {
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.grouping.Instruction;
/**
- * @author michal.polkorab
+ * Key for an instruction deserializer.
*
+ * @author michal.polkorab
*/
public class InstructionDeserializerKey extends MessageCodeKey {
- private Long experimenterId;
+ private final Long experimenterId;
+
/**
+ * Constructor.
+ *
* @param version protocol wire version
* @param type instruction type
* @param experimenterId experimenter (vendor) identifier
*/
- public InstructionDeserializerKey(short version, int type,
- Long experimenterId) {
+ public InstructionDeserializerKey(short version, int type, Long experimenterId) {
super(version, type, Instruction.class);
this.experimenterId = experimenterId;
}
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
return result;
}
public String toString() {
return super.toString() + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.grouping.Instruction;
/**
+ * Key for an instruction serializer.
+ *
* @author michal.polkorab
* @param <T> instruction type
*/
public class InstructionSerializerKey<T extends InstructionChoice>
extends MessageTypeKey<Instruction> implements ExperimenterSerializerKey {
- private Class<T> instructionType;
- private Long experimenterId;
+ private final Class<T> instructionType;
+ private final Long experimenterId;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param instructionType type of instruction
* @param experimenterId experimenter / vendor ID
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
- result = prime * result + ((instructionType == null) ? 0 : instructionType.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
+ result = prime * result + (instructionType == null ? 0 : instructionType.hashCode());
return result;
}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.entries.grouping.MatchEntry;
/**
- * @author michal.polkorab
+ * Key for a match entry deserializer.
*
+ * @author michal.polkorab
*/
public final class MatchEntryDeserializerKey extends MessageCodeKey
implements ExperimenterDeserializerKey {
- private int oxmField;
+ private final int oxmField;
private Long experimenterId;
/**
+ * Constructor.
+ *
* @param version protocol wire version
* @param oxmClass oxm_class (see specification)
* @param oxmField oxm_field (see specification)
}
/**
+ * Sets the experimenter id.
+ *
* @param experimenterId experimenter / vendor ID
*/
public void setExperimenterId(Long experimenterId) {
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
result = prime * result + oxmField;
return result;
}
public String toString() {
return super.toString() + " oxm_field: " + oxmField + " experimenterID: " + experimenterId;
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.entries.grouping.MatchEntry;
/**
+ * Key for a match entry serializer.
+ *
* @author michal.polkorab
* @param <C> oxm_class (see specification)
* @param <F> oxm_field (see specification)
public final class MatchEntrySerializerKey<C extends OxmClassBase, F extends MatchField>
extends MessageTypeKey<MatchEntry> implements ExperimenterSerializerKey {
- private Class<C> oxmClass;
- private Class<F> oxmField;
+ private final Class<C> oxmClass;
+ private final Class<F> oxmField;
private Long experimenterId;
/**
+ * Constructor.
+ *
* @param msgVersion protocol wire version
* @param oxmClass oxm_class (see specification)
* @param oxmField oxm_field (see specification)
}
/**
+ * Sets the experimenter id.
+ *
* @param experimenterId experimenter / vendor ID
*/
public void setExperimenterId(Long experimenterId) {
public int hashCode() {
final int prime = 31;
int result = super.hashCode();
- result = prime * result + ((experimenterId == null) ? 0 : experimenterId.hashCode());
- result = prime * result + ((oxmClass == null) ? 0 : oxmClass.hashCode());
- result = prime * result + ((oxmField == null) ? 0 : oxmField.hashCode());
+ result = prime * result + (experimenterId == null ? 0 : experimenterId.hashCode());
+ result = prime * result + (oxmClass == null ? 0 : oxmClass.hashCode());
+ result = prime * result + (oxmField == null ? 0 : oxmField.hashCode());
return result;
}
package org.opendaylight.openflowjava.protocol.api.keys;
/**
+ * Key for a message code.
+ *
* @author michal.polkorab
*/
public class MessageCodeKey {
- private short msgVersion;
- private int msgType;
- private Class<?> clazz;
+ private final short msgVersion;
+ private final int msgType;
+ private final Class<?> clazz;
/**
- * Constructor
+ * Constructor.
+ *
* @param version wire protocol version
* @param value used as distinguisher (read from binary data / buffer)
* @param clazz class of object that is going to be deserialized
public int hashCode() {
final int prime = 31;
int result = 1;
- result = prime * result + ((clazz == null) ? 0 : clazz.hashCode());
+ result = prime * result + (clazz == null ? 0 : clazz.hashCode());
result = prime * result + msgType;
result = prime * result + msgVersion;
return result;
public String toString() {
return "msgVersion: " + msgVersion + " objectClass: " + clazz.getName() + " msgType: " + msgType;
}
-}
\ No newline at end of file
+}
package org.opendaylight.openflowjava.protocol.api.keys;
/**
- * Class used as a key in {@link org.opendaylight.openflowjava.protocol.api.extensibility.SerializerRegistry}
+ * Class used as a key in {@link org.opendaylight.openflowjava.protocol.api.extensibility.SerializerRegistry}.
+ *
* @author michal.polkorab
* @author timotej.kubas
* @param <E> message type (class)
private final short msgVersion;
/**
+ * Constructor.
+ *
* @param msgVersion protocol version
* @param msgType type of message - class of serialized object
*/
public int hashCode() {
final int prime = 31;
int result = 1;
- result = prime * result + ((msgType == null) ? 0 : msgType.hashCode());
+ result = prime * result + (msgType == null ? 0 : msgType.hashCode());
result = prime * result + msgVersion;
return result;
}
package org.opendaylight.openflowjava.protocol.api.keys;
/**
- * @author michal.polkorab
+ * Key for a class type.
*
+ * @author michal.polkorab
*/
public class TypeToClassKey {
- private short version;
- private int type;
+ private final short version;
+ private final int type;
/**
- * Constructor
+ * Constructor.
+ *
* @param version wire protocol version
* @param type message type / code
*/
}
return true;
}
-}
\ No newline at end of file
+}
package org.opendaylight.openflowjava.protocol.api.util;
/**
- * @author michal.polkorab
+ * Conversion utilities.
*
+ * @author michal.polkorab
*/
public abstract class BinContent {
}
/**
+ * Converts an int to unsigned long.
+ *
* @param value input integer value (might be negative)
* @return int part wrapped in long (always positive)
*/
}
/**
+ * Converts an unsigned long to int.
+ *
* @param value input long value
* @return long cut into int
*/
/**
* Stores common constants.
+ *
* @author michal.polkorab
*/
-public abstract class EncodeConstants {
-
- /** Default OF padding (in bytes) */
- public static final byte PADDING = 8;
- /** OpenFlow v1.0 wire protocol number */
- public static final byte OF10_VERSION_ID = 0x01;
- /** OpenFlow v1.3 wire protocol number */
- public static final byte OF13_VERSION_ID = 0x04;
- /** OpenFlow v1.4 wire protocol number */
- public static final byte OF14_VERSION_ID = 0x05;
- /** OpenFlow v1.5 wire protocol number */
- public static final byte OF15_VERSION_ID = 0x06;
- /** OpenFlow Hello message type value */
- public static final byte OF_HELLO_MESSAGE_TYPE_VALUE = 0;
- /** OpenFlow PacketIn message type value */
- public static final byte OF_PACKETIN_MESSAGE_TYPE_VALUE = 10;
- /** Index of length in Openflow header */
- public static final int OFHEADER_LENGTH_INDEX = 2;
- /** Size of Openflow header */
- public static final int OFHEADER_SIZE = 8;
- /** Zero length - used when the length is updated later */
- public static final int EMPTY_LENGTH = 0;
-
- /** Length of mac address */
- public static final byte MAC_ADDRESS_LENGTH = 6;
- /** Number of groups in ipv4 address */
- public static final byte GROUPS_IN_IPV4_ADDRESS = 4;
- /** Number of groups in ipv6 address */
- public static final byte GROUPS_IN_IPV6_ADDRESS = 8;
- /** Length of ipv6 address in bytes */
- public static final byte SIZE_OF_IPV6_ADDRESS_IN_BYTES = (8 * Short.SIZE) / Byte.SIZE;
-
- /** Length of long in bytes */
- public static final byte SIZE_OF_LONG_IN_BYTES = Long.SIZE / Byte.SIZE;
- /** Length of int in bytes */
- public static final byte SIZE_OF_INT_IN_BYTES = Integer.SIZE / Byte.SIZE;
- /** Length of short in bytes */
- public static final byte SIZE_OF_SHORT_IN_BYTES = Short.SIZE / Byte.SIZE;
- /** Length of byte in bytes */
- public static final byte SIZE_OF_BYTE_IN_BYTES = Byte.SIZE / Byte.SIZE;
- /** Length of 3 bytes */
- public static final byte SIZE_OF_3_BYTES = 3;
-
- /** Empty (zero) int value */
- public static final int EMPTY_VALUE = 0;
- /** Common experimenter value */
- public static final int EXPERIMENTER_VALUE = 0xFFFF;
-
- /** OF v1.0 maximal port name length */
- public static final byte MAX_PORT_NAME_LENGTH = 16;
-
- /** ONF Approved Extensions Constants */
- /** Experimenter ID of ONF approved extensions */
- public static final long ONF_EXPERIMENTER_ID = 0x4F4E4600;
- /** ONFOXM_ET_TCP_FLAGS value */
- public static final int ONFOXM_ET_TCP_FLAGS = 42;
-
- private EncodeConstants() {
- //not called
- }
+public interface EncodeConstants {
+
+ /** Default OF padding (in bytes). */
+ byte PADDING = 8;
+
+ /** OpenFlow v1.0 wire protocol number. */
+ byte OF10_VERSION_ID = 0x01;
+
+ /** OpenFlow v1.3 wire protocol number. */
+ byte OF13_VERSION_ID = 0x04;
+
+ /** OpenFlow v1.4 wire protocol number. */
+ byte OF14_VERSION_ID = 0x05;
+
+ /** OpenFlow v1.5 wire protocol number. */
+ byte OF15_VERSION_ID = 0x06;
+
+ /** OpenFlow Hello message type value. */
+ byte OF_HELLO_MESSAGE_TYPE_VALUE = 0;
+
+ /** OpenFlow PacketIn message type value. */
+ byte OF_PACKETIN_MESSAGE_TYPE_VALUE = 10;
+
+ /** Index of length in Openflow header. */
+ int OFHEADER_LENGTH_INDEX = 2;
+
+ /** Size of Openflow header. */
+ int OFHEADER_SIZE = 8;
+
+ /** Zero length - used when the length is updated later. */
+ int EMPTY_LENGTH = 0;
+
+ /** Length of mac address. */
+ byte MAC_ADDRESS_LENGTH = 6;
+
+ /** Number of groups in ipv4 address. */
+ byte GROUPS_IN_IPV4_ADDRESS = 4;
+
+ /** Number of groups in ipv6 address. */
+ byte GROUPS_IN_IPV6_ADDRESS = 8;
+
+ /** Length of ipv6 address in bytes. */
+ byte SIZE_OF_IPV6_ADDRESS_IN_BYTES = 8 * Short.SIZE / Byte.SIZE;
+
+ /** Length of long in bytes. */
+ byte SIZE_OF_LONG_IN_BYTES = Long.SIZE / Byte.SIZE;
+
+ /** Length of int in bytes. */
+ byte SIZE_OF_INT_IN_BYTES = Integer.SIZE / Byte.SIZE;
+
+ /** Length of short in bytes. */
+ byte SIZE_OF_SHORT_IN_BYTES = Short.SIZE / Byte.SIZE;
+
+ /** Length of byte in bytes. */
+ byte SIZE_OF_BYTE_IN_BYTES = Byte.SIZE / Byte.SIZE;
+
+ /** Length of 3 bytes. */
+ byte SIZE_OF_3_BYTES = 3;
+
+ /** Empty (zero) int value. */
+ int EMPTY_VALUE = 0;
+
+ /** Common experimenter value. */
+ int EXPERIMENTER_VALUE = 0xFFFF;
+
+ /** OF v1.0 maximal port name length. */
+ byte MAX_PORT_NAME_LENGTH = 16;
+
+ // ONF Approved Extensions Constants.
+
+ /** Experimenter ID of ONF approved extensions. */
+ long ONF_EXPERIMENTER_ID = 0x4F4E4600;
+
+ /** ONFOXM_ET_TCP_FLAGS value. */
+ int ONFOXM_ET_TCP_FLAGS = 42;
}
/**
* Stores oxm_match constants.
+ *
* @author michal.polkorab
*/
-public abstract class OxmMatchConstants {
-
- /** Backward compatibility with NXM */
- public static final int NXM_0_CLASS = 0x0000;
- /** Backward compatibility with NXM */
- public static final int NXM_1_CLASS = 0x0001;
- /** Basic class for OpenFlow */
- public static final int OPENFLOW_BASIC_CLASS = 0x8000;
- /** Experimenter class */
- public static final int EXPERIMENTER_CLASS = 0xFFFF;
-
- /** Switch input port */
- public static final int IN_PORT = 0;
- /** Switch physical input port */
- public static final int IN_PHY_PORT = 1;
- /** Metadata passed between tables */
- public static final int METADATA = 2;
- /** Ethernet destination address */
- public static final int ETH_DST = 3;
- /** Ethernet source address */
- public static final int ETH_SRC = 4;
- /** Ethernet frame type */
- public static final int ETH_TYPE = 5;
+public interface OxmMatchConstants {
+
+ /** Backward compatibility with NXM. */
+ int NXM_0_CLASS = 0x0000;
+
+ /** Backward compatibility with NXM. */
+ int NXM_1_CLASS = 0x0001;
+
+ /** Basic class for OpenFlow. */
+ int OPENFLOW_BASIC_CLASS = 0x8000;
+
+ /** Experimenter class. */
+ int EXPERIMENTER_CLASS = 0xFFFF;
+
+ /** Switch input port. */
+ int IN_PORT = 0;
+
+ /** Switch physical input port. */
+ int IN_PHY_PORT = 1;
+
+ /** Metadata passed between tables. */
+ int METADATA = 2;
+
+ /** Ethernet destination address. */
+ int ETH_DST = 3;
+
+ /** Ethernet source address. */
+ int ETH_SRC = 4;
+
+ /** Ethernet frame type. */
+ int ETH_TYPE = 5;
+
/** VLAN id. */
- public static final int VLAN_VID = 6;
+ int VLAN_VID = 6;
+
/** VLAN priority. */
- public static final int VLAN_PCP = 7;
+ int VLAN_PCP = 7;
+
/** IP DSCP (6 bits in ToS field). */
- public static final int IP_DSCP = 8;
+ int IP_DSCP = 8;
+
/** IP ECN (2 bits in ToS field). */
- public static final int IP_ECN = 9;
+ int IP_ECN = 9;
+
/** IP protocol. */
- public static final int IP_PROTO = 10;
+ int IP_PROTO = 10;
+
/** IPv4 source address. */
- public static final int IPV4_SRC = 11;
+ int IPV4_SRC = 11;
+
/** IPv4 destination address. */
- public static final int IPV4_DST = 12;
+ int IPV4_DST = 12;
+
/** TCP source port. */
- public static final int TCP_SRC = 13;
+ int TCP_SRC = 13;
+
/** TCP destination port. */
- public static final int TCP_DST = 14;
+ int TCP_DST = 14;
+
/** UDP source port. */
- public static final int UDP_SRC = 15;
+ int UDP_SRC = 15;
+
/** UDP destination port. */
- public static final int UDP_DST = 16;
+ int UDP_DST = 16;
+
/** SCTP source port. */
- public static final int SCTP_SRC = 17;
+ int SCTP_SRC = 17;
+
/** SCTP destination port. */
- public static final int SCTP_DST = 18;
+ int SCTP_DST = 18;
+
/** ICMP type. */
- public static final int ICMPV4_TYPE = 19;
+ int ICMPV4_TYPE = 19;
+
/** ICMP code. */
- public static final int ICMPV4_CODE = 20;
+ int ICMPV4_CODE = 20;
+
/** ARP opcode. */
- public static final int ARP_OP = 21;
+ int ARP_OP = 21;
+
/** ARP source IPv4 address. */
- public static final int ARP_SPA = 22;
+ int ARP_SPA = 22;
+
/** ARP target IPv4 address. */
- public static final int ARP_TPA = 23;
+ int ARP_TPA = 23;
+
/** ARP source hardware address. */
- public static final int ARP_SHA = 24;
+ int ARP_SHA = 24;
+
/** ARP target hardware address. */
- public static final int ARP_THA = 25;
+ int ARP_THA = 25;
+
/** IPv6 source address. */
- public static final int IPV6_SRC = 26;
+ int IPV6_SRC = 26;
+
/** IPv6 destination address. */
- public static final int IPV6_DST = 27;
- /** IPv6 Flow Label */
- public static final int IPV6_FLABEL = 28;
+ int IPV6_DST = 27;
+
+ /** IPv6 Flow Label. */
+ int IPV6_FLABEL = 28;
+
/** ICMPv6 type. */
- public static final int ICMPV6_TYPE = 29;
+ int ICMPV6_TYPE = 29;
+
/** ICMPv6 code. */
- public static final int ICMPV6_CODE = 30;
+ int ICMPV6_CODE = 30;
+
/** Target address for ND. */
- public static final int IPV6_ND_TARGET = 31;
+ int IPV6_ND_TARGET = 31;
+
/** Source link-layer for ND. */
- public static final int IPV6_ND_SLL = 32;
+ int IPV6_ND_SLL = 32;
+
/** Target link-layer for ND. */
- public static final int IPV6_ND_TLL = 33;
+ int IPV6_ND_TLL = 33;
+
/** MPLS label. */
- public static final int MPLS_LABEL = 34;
+ int MPLS_LABEL = 34;
+
/** MPLS TC. */
- public static final int MPLS_TC = 35;
+ int MPLS_TC = 35;
+
/** MPLS BoS bit. */
- public static final int MPLS_BOS = 36;
+ int MPLS_BOS = 36;
+
/** PBB I-SID. */
- public static final int PBB_ISID = 37;
+ int PBB_ISID = 37;
+
/** Logical Port Metadata. */
- public static final int TUNNEL_ID = 38;
- /** IPv6 Extension Header pseudo-field */
- public static final int IPV6_EXTHDR = 39;
+ int TUNNEL_ID = 38;
+
+ /** IPv6 Extension Header pseudo-field. */
+ int IPV6_EXTHDR = 39;
/**
- * OFPXMC_NXM_1 class Constants
+ * OFPXMC_NXM_1 class Constants.
*/
- /** NXM IPv4 Tunnel Endpoint Source */
- public static final int NXM_NX_TUN_IPV4_SRC = 31;
- /** NXM IPv4 Tunnel Endpoint Destination */
- public static final int NXM_NX_TUN_IPV4_DST = 32;
- /** NXM TCP_Flag value */
- public static final int NXM_NX_TCP_FLAG = 34;
-
- private OxmMatchConstants() {
- //not called
- }
-}
\ No newline at end of file
+ /** NXM IPv4 Tunnel Endpoint Source. */
+ int NXM_NX_TUN_IPV4_SRC = 31;
+
+ /** NXM IPv4 Tunnel Endpoint Destination.
+ * */
+ int NXM_NX_TUN_IPV4_DST = 32;
+
+ /** NXM TCP_Flag value. */
+ int NXM_NX_TCP_FLAG = 34;
+}
package org.opendaylight.openflowjava.protocol.api.connection;
-import static org.junit.Assert.*;
+import static org.junit.Assert.assertEquals;
+import com.google.common.collect.Lists;
import java.util.List;
-
import org.junit.Test;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.KeystoreType;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.PathType;
-import com.google.common.collect.Lists;
-
/**
- * @author michal.polkorab
+ * Unit tests for TlsConfigurationImpl.
*
+ * @author michal.polkorab
*/
public class TlsConfigurationImplTest {
/**
- * Test correct TlsConfigurationImpl creation
+ * Test correct TlsConfigurationImpl creation.
*/
@Test
public void test() {
- List<String> cipherSuites = Lists.newArrayList("TLS_RSA_WITH_AES_128_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA256");
+ List<String> cipherSuites = Lists.newArrayList("TLS_RSA_WITH_AES_128_CBC_SHA",
+ "TLS_RSA_WITH_AES_128_CBC_SHA256");
TlsConfigurationImpl config = new TlsConfigurationImpl(KeystoreType.JKS,
"user/dir", PathType.CLASSPATH, KeystoreType.PKCS12, "/var/lib", PathType.PATH, cipherSuites);
assertEquals("Wrong keystore location", "/var/lib", config.getTlsKeystore());
assertEquals("Wrong truststore password", "opendaylight", config.getTruststorePassword());
assertEquals("Wrong cipher suites", cipherSuites, config.getCipherSuites());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.BarrierOutput;
/**
- * @author michal.polkorab
+ * Unit tests for EnhancedMessageCodeKey.
*
+ * @author michal.polkorab
*/
public class EnhancedMessageCodeKeyTest {
/**
- * Test EnhancedMessageCodeKey equals and hashCode
+ * Test EnhancedMessageCodeKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test EnhancedMessageTypeKey equals - additional test
+ * Test EnhancedMessageTypeKey equals - additional test.
*/
@Test
public void testEquals() {
}
/**
- * Test EnhancedMessageCodeKey toString()
+ * Test EnhancedMessageCodeKey toString().
*/
@Test
public void testToString() {
EnhancedMessageCodeKey key1 =
new EnhancedMessageCodeKey(EncodeConstants.OF10_VERSION_ID, 4, 8, BarrierInput.class);
- Assert.assertEquals("Wrong toString()", "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn.opendaylight"
+ Assert.assertEquals("Wrong toString()",
+ "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn.opendaylight"
+ ".openflow.protocol.rev130731.BarrierInput msgType: 4 msgType2: 8", key1.toString());
}
}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.grouping.Instruction;
/**
- * @author michal.polkorab
+ * Unit tests for EnhancedMessageTypeKey.
*
+ * @author michal.polkorab
*/
public class EnhancedMessageTypeKeyTest {
/**
- * Test EnhancedMessageTypeKey equals and hashCode
+ * Test EnhancedMessageTypeKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test EnhancedMessageTypeKey equals - additional test
+ * Test EnhancedMessageTypeKey equals - additional test.
*/
@Test
public void testEquals() {
}
/**
- * Test EnhancedMessageTypeKey toString()
+ * Test EnhancedMessageTypeKey toString().
*/
@Test
public void testToString() {
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.BarrierOutput;
/**
- * @author michal.polkorab
+ * Unit tests for MessageCodeKey.
*
+ * @author michal.polkorab
*/
public class MessageCodeKeyTest {
/**
- * Test MessageCodeKey equals and hashCode
+ * Test MessageCodeKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test MessageCodeKey equals - additional test
+ * Test MessageCodeKey equals - additional test.
*/
@Test
public void testEquals() {
}
/**
- * Test MessageCodeKey toString()
+ * Test MessageCodeKey toString().
*/
@Test
public void testToString() {
Assert.assertEquals("Wrong toString()", "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn"
+ ".opendaylight.openflow.protocol.rev130731.BarrierInput msgType: 4", key1.toString());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.BarrierOutput;
/**
- * @author michal.polkorab
+ * Unit tests for MessageTypeKey.
*
+ * @author michal.polkorab
*/
public class MessageTypeKeyTest {
/**
- * Test MessageTypeKey equals and hashCode
+ * Test MessageTypeKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test MessageTypeKey equals - additional test
+ * Test MessageTypeKey equals - additional test.
*/
@Test
public void testEquals() {
- MessageTypeKey<?> key1;
- MessageTypeKey<?> key2;
- key1 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, BarrierInput.class);
+ MessageTypeKey<?> key1 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, BarrierInput.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
Assert.assertFalse("Wrong equal to null.", key1.equals(null));
Assert.assertFalse("Wrong equal to different class.", key1.equals(new Object()));
key1 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, null);
- key2 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, BarrierInput.class);
+ MessageTypeKey<?> key2 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, BarrierInput.class);
Assert.assertFalse("Wrong equal by msgType.", key1.equals(key2));
key2 = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID, null);
}
/**
- * Test MessageTypeKey toString()
+ * Test MessageTypeKey toString().
*/
@Test
public void testToString() {
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for ActionDeserializerKey.
*
+ * @author michal.polkorab
*/
public class ActionDeserializerKeyTest {
/**
- * Test ActionDeserializerKey equals and hashCode
+ * Test ActionDeserializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test ActionDeserializerKey equals - additional test
+ * Test ActionDeserializerKey equals - additional test.
*/
@Test
- public void testEquals(){
+ public void testEquals() {
ActionDeserializerKey key1 = new ActionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, null);
ActionDeserializerKey key2 = new ActionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, 42L);
}
/**
- * Test InstructionDeserializerKey toString()
+ * Test InstructionDeserializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
ActionDeserializerKey key1 = new ActionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, null);
Assert.assertEquals("Wrong toString()", "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn"
+ ".opendaylight.openflow.common.action.rev150203.actions.grouping.Action msgType: 11"
+ " experimenterID: null", key1.toString());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.action.grouping.action.choice.CopyTtlOutCase;
/**
- * @author michal.polkorab
+ * Unit tests for ActionSerializerKey.
*
+ * @author michal.polkorab
*/
public class ActionSerializerKeyTest {
/**
- * Test ActionSerializerKey equals and hashCode
+ * Test ActionSerializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test ActionSerializerKey equals - additional test
+ * Test ActionSerializerKey equals - additional test.
*/
@Test
- public void testEquals(){
+ public void testEquals() {
ActionSerializerKey<?> key1 = new ActionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, null, 42L);
ActionSerializerKey<?> key2 = new ActionSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
CopyTtlInCase.class, 42L);
}
/**
- * Test ActionSerializerKey toString()
+ * Test ActionSerializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
ActionSerializerKey<CopyTtlInCase> key1 = new ActionSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
CopyTtlInCase.class, 42L);
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for InstructionDeserializerKey.
*
+ * @author michal.polkorab
*/
public class InstructionDeserializerKeyTest {
/**
- * Test InstructionDeserializerKey equals and hashCode
+ * Test InstructionDeserializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test InstructionDeserializerKey equals - additional test
+ * Test InstructionDeserializerKey equals - additional test.
*/
@Test
- public void testEquals(){
+ public void testEquals() {
InstructionDeserializerKey key1 = new InstructionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, null);
InstructionDeserializerKey key2 = new InstructionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, 24L);
}
/**
- * Test InstructionDeserializerKey toString()
+ * Test InstructionDeserializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
InstructionDeserializerKey key1 = new InstructionDeserializerKey(EncodeConstants.OF10_VERSION_ID, 11, null);
- Assert.assertEquals("Wrong toString()", "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn.opendaylight"
+ Assert.assertEquals("Wrong toString()",
+ "msgVersion: 1 objectClass: org.opendaylight.yang.gen.v1.urn.opendaylight"
+ ".openflow.common.instruction.rev130731.instructions.grouping.Instruction msgType: 11"
+ " experimenterID: null", key1.toString());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instruction.grouping.instruction.choice.WriteActionsCase;
/**
- * @author michal.polkorab
+ * Unit tests for InstructionSerializerKey.
*
+ * @author michal.polkorab
*/
public class InstructionSerializerKeyTest {
/**
- * Test InstructionSerializerKey equals and hashCode
+ * Test InstructionSerializerKey equals and hashCode.
*/
@Test
public void test() {
InstructionSerializerKey<?> key1 =
new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
- InstructionSerializerKey<?> key2 =
+ InstructionSerializerKey<?> key2 =
new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
Assert.assertTrue("Wrong equals", key1.equals(key2));
Assert.assertTrue("Wrong hashCode", key1.hashCode() == key2.hashCode());
}
/**
- * Test InstructionSerializerKey equals - additional test
+ * Test InstructionSerializerKey equals - additional test.
*/
@Test
- public void testEquals(){
+ public void testEquals() {
InstructionSerializerKey<?> key1 =
new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
- InstructionSerializerKey<?> key2 =
- new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
Assert.assertFalse("Wrong equal to different class.", key1.equals(new Object()));
+ InstructionSerializerKey<?> key2 =
+ new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
key1 = new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, null);
Assert.assertFalse("Wrong equal by experimenterId.", key1.equals(key2));
}
/**
- * Test InstructionSerializerKey toString()
+ * Test InstructionSerializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
InstructionSerializerKey<?> key1 =
new InstructionSerializerKey<>(EncodeConstants.OF10_VERSION_ID, ApplyActionsCase.class, 42L);
+ "instructionType type: org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction"
+ ".rev130731.instruction.grouping.instruction.choice.ApplyActionsCase vendorID: 42", key1.toString());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.OpenflowBasicClass;
/**
+ * Unit tests for keys.
+ *
* @author michal.polkorab
*/
public class KeysTest {
/**
- * Testing equals() and hashcode() methods of extension deserializer's keys
+ * Testing equals() and hashcode() methods of extension deserializer's keys.
*/
@Test
public void testEqualsAndHashcodeOfDeserializerKeys() {
InstructionDeserializerKey instructionDeserializerKey = new InstructionDeserializerKey(
EncodeConstants.OF13_VERSION_ID, EncodeConstants.EXPERIMENTER_VALUE, 1L);
- ExperimenterInstructionDeserializerKey experimenterInstructionDeserializerKey = new ExperimenterInstructionDeserializerKey(
+ ExperimenterInstructionDeserializerKey experimenterInstructionDeserializerKey =
+ new ExperimenterInstructionDeserializerKey(
EncodeConstants.OF13_VERSION_ID, 1L);
Assert.assertEquals(instructionDeserializerKey, experimenterInstructionDeserializerKey);
Assert.assertEquals(instructionDeserializerKey.hashCode(), experimenterInstructionDeserializerKey.hashCode());
}
/**
- * Testing equals() and hashcode() methods of extension serializer's keys
+ * Testing equals() and hashcode() methods of extension serializer's keys.
*/
@Test
public void testEqualsAndHashcodeOfActionDeserializerKeys() {
Assert.assertFalse(experimenterActionSerializerKey.equals(actionSerializerKey));
InstructionSerializerKey<org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225
- .instruction.container.instruction.choice.ExperimenterIdCase> instructionSerializerKey =
+ .instruction.container.instruction.choice.ExperimenterIdCase> instructionSerializerKey =
new InstructionSerializerKey<>(EncodeConstants.OF13_VERSION_ID, org.opendaylight.yang.gen.v1.urn
.opendaylight.openflow.augments.rev150225.instruction.container.instruction.choice
.ExperimenterIdCase.class, 1L);
- ExperimenterInstructionSerializerKey experimenterInstructionSerializerKey = new ExperimenterInstructionSerializerKey(EncodeConstants.OF13_VERSION_ID, 1L);
+ ExperimenterInstructionSerializerKey experimenterInstructionSerializerKey =
+ new ExperimenterInstructionSerializerKey(EncodeConstants.OF13_VERSION_ID, 1L);
Assert.assertEquals(instructionSerializerKey, experimenterInstructionSerializerKey);
Assert.assertEquals(instructionSerializerKey.hashCode(), experimenterInstructionSerializerKey.hashCode());
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for MatchEntryDeserializerKey.
*
+ * @author michal.polkorab
*/
public class MatchEntryDeserializerKeyTest {
/**
- * Test MatchEntryDeserializerKey equals and hashCode
+ * Test MatchEntryDeserializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test MatchEntryDeserializerKey equals - additional test
+ * Test MatchEntryDeserializerKey equals - additional test.
*/
@Test
public void testEquals() {
MatchEntryDeserializerKey key1 = new MatchEntryDeserializerKey(EncodeConstants.OF10_VERSION_ID, 0x8000, 42);
- MatchEntryDeserializerKey key2 = new MatchEntryDeserializerKey(EncodeConstants.OF10_VERSION_ID, 0x8000, 42);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
Assert.assertFalse("Wrong equal to different class.", key1.equals(new Object()));
- Long expId1=123456L;
- Long expId2=654321L;
+ MatchEntryDeserializerKey key2 = new MatchEntryDeserializerKey(EncodeConstants.OF10_VERSION_ID, 0x8000, 42);
+
+ Long expId2 = 654321L;
key1.setExperimenterId(null);
key2.setExperimenterId(expId2);
Assert.assertFalse("Wrong equal by experimeterId.", key1.equals(key2));
+ Long expId1 = 123456L;
key1.setExperimenterId(expId1);
Assert.assertFalse("Wrong equal by experimeterId.", key1.equals(key2));
Assert.assertFalse("Wrong equals with different object class", key1.equals(key2));
}
/**
- * Test MatchEntryDeserializerKey toString()
+ * Test MatchEntryDeserializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
MatchEntryDeserializerKey key1 = new MatchEntryDeserializerKey(EncodeConstants.OF13_VERSION_ID, 0x8000, 42);
Assert.assertEquals("Wrong toString()", "msgVersion: 4 objectClass: org.opendaylight.yang.gen.v1.urn"
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.OpenflowBasicClass;
/**
- * @author michal.polkorab
+ * Unit tests for MatchEntrySerializerKey.
*
+ * @author michal.polkorab
*/
public class MatchEntrySerializerKeyTest {
/**
- * Test MatchEntrySerializerKey equals and hashCode
+ * Test MatchEntrySerializerKey equals and hashCode.
*/
@Test
public void test() {
- MatchEntrySerializerKey<?, ?> key1 = new MatchEntrySerializerKey<>
- (EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
- MatchEntrySerializerKey<?, ?> key2 = new MatchEntrySerializerKey<>
- (EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
+ MatchEntrySerializerKey<?, ?> key1 = new MatchEntrySerializerKey<>(
+ EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
+ MatchEntrySerializerKey<?, ?> key2 = new MatchEntrySerializerKey<>(
+ EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
Assert.assertTrue("Wrong equals", key1.equals(key2));
Assert.assertTrue("Wrong hashCode", key1.hashCode() == key2.hashCode());
key2 = new MatchEntrySerializerKey<>(EncodeConstants.OF13_VERSION_ID,
}
/**
- * Test MatchEntrySerializerKey equals - additional test
+ * Test MatchEntrySerializerKey equals - additional test.
*/
@Test
- public void testEquals(){
+ public void testEquals() {
MatchEntrySerializerKey<?, ?> key1;
MatchEntrySerializerKey<?, ?> key2;
key1 = new MatchEntrySerializerKey<>(EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
Assert.assertFalse("Wrong equal to different class.", key1.equals(new Object()));
- Long expId1 = 987654331L;
Long expId2 = 123456789L;
key1.setExperimenterId(null);
key2.setExperimenterId(expId2);
Assert.assertFalse("Wrong equal by experimenterId", key1.equals(key2));
+
+ Long expId1 = 987654331L;
key1.setExperimenterId(expId1);
Assert.assertFalse("Wrong equal by experimenterId", key1.equals(key2));
key1 = new MatchEntrySerializerKey<>(EncodeConstants.OF13_VERSION_ID, null, InPort.class);
}
/**
- * Test MatchEntrySerializerKey toString()
+ * Test MatchEntrySerializerKey toString().
*/
@Test
- public void testToString(){
+ public void testToString() {
MatchEntrySerializerKey<?, ?> key1;
key1 = new MatchEntrySerializerKey<>(EncodeConstants.OF13_VERSION_ID, OpenflowBasicClass.class, InPort.class);
+ ".OpenflowBasicClass oxm_field: org.opendaylight.yang.gen.v1.urn.opendaylight.openflow"
+ ".oxm.rev150225.InPort experimenterID: null", key1.toString());
}
-}
\ No newline at end of file
+}
import org.junit.Assert;
import org.junit.Test;
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
+
/**
+ * Unit tests for TypeToClassKey.
*
* @author madamjak
- *
*/
public class TypeToClassKeyTest {
/**
- * Test equals
+ * Test equals.
*/
@Test
- public void test(){
+ public void test() {
final short ver10 = EncodeConstants.OF10_VERSION_ID;
final short ver13 = EncodeConstants.OF13_VERSION_ID;
final int type1 = 1;
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterActionDeserializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterActionDeserializerKeyTest {
/**
- * Test ExperimenterActionDeserializerKey equals and hashCode
+ * Test ExperimenterActionDeserializerKey equals and hashCode.
*/
@Test
public void test() {
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.ExperimenterActionSubType;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterActionSerializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterActionSerializerKeyTest {
-
/**
- * Test ExperimenterActionSerializerKey equals and hashCode
+ * Test ExperimenterActionSerializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test ExperimenterActionSerializerKey equals
+ * Test ExperimenterActionSerializerKey equals.
*/
@Test
public void testEquals() {
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.ExperimenterMessage;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterIdDeserializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterIdDeserializerKeyTest {
/**
- * Test ExperimenterIdDeserializerKey equals and hashCode
+ * Test ExperimenterIdDeserializerKey equals and hashCode.
*/
@Test
public void test() {
}
/**
- * Test ExperimenterIdDeserializerKey equals - additional test
+ * Test ExperimenterIdDeserializerKey equals - additional test.
*/
@Test
public void testEquals() {
ExperimenterIdDeserializerKey key1 =
new ExperimenterIdDeserializerKey(EncodeConstants.OF10_VERSION_ID, 0L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
- MessageCodeKey mk = new MessageCodeKey(EncodeConstants.OF10_VERSION_ID,EncodeConstants.EXPERIMENTER_VALUE, ExperimenterMessage.class);
+ MessageCodeKey mk = new MessageCodeKey(EncodeConstants.OF10_VERSION_ID,
+ EncodeConstants.EXPERIMENTER_VALUE, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal to different class.", key1.equals(mk));
ExperimenterIdDeserializerKey key2 =
new ExperimenterIdDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, ExperimenterMessage.class);
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.ExperimenterMessage;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterIdSerializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterIdSerializerKeyTest {
/**
- * Test ExperimenterIdSerializerKey equals and hashCode
+ * Test ExperimenterIdSerializerKey equals and hashCode.
*/
@Test
public void testHashCodeAndEquals() {
}
/**
- * Test ExperimenterIdSerializerKey equals - additional test
+ * Test ExperimenterIdSerializerKey equals - additional test.
*/
@Test
public void testEquals() {
ExperimenterIdSerializerKey<?> key1 =
new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 41L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
- MessageTypeKey<?>mk = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID,ExperimenterMessage.class);
+ MessageTypeKey<?> mk = new MessageTypeKey<>(EncodeConstants.OF10_VERSION_ID,ExperimenterMessage.class);
Assert.assertFalse("Wrong equal to different class.", key1.equals(mk));
ExperimenterIdSerializerKey<?> key2 =
new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal by experimenterId.", key1.equals(key2));
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.ExperimenterMessage;
/**
+ * Unit tests for ExperimenterIdTypeDeserializerKey.
+ *
* @author michal.polkorab
*/
public class ExperimenterIdTypeDeserializerKeyTest {
/**
- * Test ExperimenterIdTypeDeserializerKey equals and hashCode
+ * Test ExperimenterIdTypeDeserializerKey equals and hashCode.
*/
@Test
public void testHashCodeAndEquals() {
- ExperimenterIdTypeDeserializerKey key1 =
- new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
- ExperimenterIdTypeDeserializerKey key2 =
- new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeDeserializerKey key1 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID,
+ 42L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeDeserializerKey key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID,
+ 42L, 1L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equals", key1.equals(key2));
Assert.assertTrue("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF13_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF13_VERSION_ID, 42L, 1L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 55L, 1L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 55L, 1L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 55L, 1L, null);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, 2L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, 2L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
}
/**
- * Test ExperimenterIdTypeDeserializerKey equals - additional test
+ * Test ExperimenterIdTypeDeserializerKey equals - additional test.
*/
@Test
public void testEquals() {
- ExperimenterIdTypeDeserializerKey key1 =
- new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 41L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeDeserializerKey key1 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID,
+ 41L, 1L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
- ExperimenterIdSerializerKey<?> mk = new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, ExperimenterMessage.class);
+ ExperimenterIdSerializerKey<?> mk = new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equal to different class.", key1.equals(mk));
- ExperimenterIdTypeDeserializerKey key2 =
- new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeDeserializerKey key2 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID,
+ 42L, 1L, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal by experimenterId.", key1.equals(key2));
- ExperimenterIdTypeDeserializerKey key3 =
- new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID, 41L, 2L, ExperimenterMessage.class);
+ ExperimenterIdTypeDeserializerKey key3 = new ExperimenterIdTypeDeserializerKey(EncodeConstants.OF10_VERSION_ID,
+ 41L, 2L, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal by type.", key1.equals(key3));
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.ExperimenterMessage;
/**
+ * Unit tests for ExperimenterIdTypeSerializerKey.
+ *
* @author michal.polkorab
*/
public class ExperimenterIdTypeSerializerKeyTest {
/**
- * Test ExperimenterIdTypeSerializerKey equals and hashCode
+ * Test ExperimenterIdTypeSerializerKey equals and hashCode.
*/
@Test
public void testHashCodeAndEquals() {
ExperimenterIdTypeSerializerKey<?> key1 =
- new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
- ExperimenterIdTypeSerializerKey<?> key2 =
- new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 1L,
+ ExperimenterMessage.class);
+ ExperimenterIdTypeSerializerKey<?> key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
+ 42L, 1L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equals", key1.equals(key2));
Assert.assertTrue("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF13_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF13_VERSION_ID, 42L, 1L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 55L, 1L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 55L, 1L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 55L, 1L, null);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
- key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 2L, ExperimenterMessage.class);
+ key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 2L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
}
/**
- * Test ExperimenterIdTypeSerializerKey equals - additional test
+ * Test ExperimenterIdTypeSerializerKey equals - additional test.
*/
@Test
public void testEquals() {
- ExperimenterIdTypeSerializerKey<?> key1 =
- new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 41L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeSerializerKey<?> key1 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
+ 41L, 1L, ExperimenterMessage.class);
Assert.assertTrue("Wrong equal to identical object.", key1.equals(key1));
- ExperimenterIdSerializerKey<?> mk = new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, ExperimenterMessage.class);
+ ExperimenterIdSerializerKey<?> mk = new ExperimenterIdSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L,
+ ExperimenterMessage.class);
Assert.assertFalse("Wrong equal to different class.", key1.equals(mk));
- ExperimenterIdTypeSerializerKey<?> key2 =
- new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 42L, 1L, ExperimenterMessage.class);
+ ExperimenterIdTypeSerializerKey<?> key2 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
+ 42L, 1L, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal by experimenterId.", key1.equals(key2));
- ExperimenterIdTypeSerializerKey<?> key3 =
- new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID, 41L, 2L, ExperimenterMessage.class);
+ ExperimenterIdTypeSerializerKey<?> key3 = new ExperimenterIdTypeSerializerKey<>(EncodeConstants.OF10_VERSION_ID,
+ 41L, 2L, ExperimenterMessage.class);
Assert.assertFalse("Wrong equal by type.", key1.equals(key3));
}
-
-}
\ No newline at end of file
+}
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterInstructionDeserializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterInstructionDeserializerKeyTest {
/**
- * Test ExperimenterInstructionDeserializerKey equals and hashCode
+ * Test ExperimenterInstructionDeserializerKey equals and hashCode.
*/
@Test
public void test() {
Assert.assertFalse("Wrong equals", key1.equals(key2));
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
}
-}
\ No newline at end of file
+}
import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
/**
- * @author michal.polkorab
+ * Unit tests for ExperimenterInstructionSerializerKey.
*
+ * @author michal.polkorab
*/
public class ExperimenterInstructionSerializerKeyTest {
/**
- * Test ExperimenterInstructionSerializerKey equals and hashCode
+ * Test ExperimenterInstructionSerializerKey equals and hashCode.
*/
@Test
public void test() {
Assert.assertFalse("Wrong hashcode", key1.hashCode() == key2.hashCode());
}
-}
\ No newline at end of file
+}
import org.junit.Test;
/**
+ * Unit tests for BinContent.
+ *
* @author michal.polkorab
*/
public class BinContentTest {
/**
- * Testing correct conversion from signed int value to unsigned long value
+ * Testing correct conversion from signed int value to unsigned long value.
*/
@Test
public void testIntToUnsignedLong() {
- int a = 0;
- int b = 1;
- int c = -1;
- int d = Integer.MAX_VALUE;
- int e = Integer.MIN_VALUE;
- int f = 12345;
- Assert.assertEquals("Wrong conversion", 0, BinContent.intToUnsignedLong(a));
- Assert.assertEquals("Wrong conversion", 1, BinContent.intToUnsignedLong(b));
- Assert.assertEquals("Wrong conversion", 4294967295L, BinContent.intToUnsignedLong(c));
- Assert.assertEquals("Wrong conversion", Integer.MAX_VALUE, BinContent.intToUnsignedLong(d));
- Assert.assertEquals("Wrong conversion", ((long) Integer.MAX_VALUE) + 1, BinContent.intToUnsignedLong(e));
- Assert.assertEquals("Wrong conversion", 12345, BinContent.intToUnsignedLong(f));
+ Assert.assertEquals("Wrong conversion", 0, BinContent.intToUnsignedLong(0));
+ Assert.assertEquals("Wrong conversion", 1, BinContent.intToUnsignedLong(1));
+ Assert.assertEquals("Wrong conversion", 4294967295L, BinContent.intToUnsignedLong(-1));
+ Assert.assertEquals("Wrong conversion", Integer.MAX_VALUE, BinContent.intToUnsignedLong(Integer.MAX_VALUE));
+ Assert.assertEquals("Wrong conversion", (long) Integer.MAX_VALUE + 1,
+ BinContent.intToUnsignedLong(Integer.MIN_VALUE));
+ Assert.assertEquals("Wrong conversion", 12345, BinContent.intToUnsignedLong(12345));
}
/**
- * Testing correct conversion from unsigned long value to signed int value
+ * Testing correct conversion from unsigned long value to signed int value.
*/
@Test
public void testLongToSignedInt() {
- long a = 0;
- long b = 1;
- long c = -1;
- long d = Integer.MAX_VALUE;
- long e = Integer.MIN_VALUE;
- long f = 12345;
- long g = Long.MAX_VALUE;
- long h = 1094624935644L;
- long i = ((long) Integer.MAX_VALUE) + 1;
- Assert.assertEquals("Wrong conversion", 0, BinContent.longToSignedInt(a));
- Assert.assertEquals("Wrong conversion", 1, BinContent.longToSignedInt(b));
- Assert.assertEquals("Wrong conversion", -1, BinContent.longToSignedInt(c));
- Assert.assertEquals("Wrong conversion", Integer.MAX_VALUE, BinContent.longToSignedInt(d));
- Assert.assertEquals("Wrong conversion", Integer.MIN_VALUE, BinContent.longToSignedInt(e));
- Assert.assertEquals("Wrong conversion", 12345, BinContent.longToSignedInt(f));
- Assert.assertEquals("Wrong conversion", -1, BinContent.longToSignedInt(g));
- Assert.assertEquals("Wrong conversion", -591724836, BinContent.longToSignedInt(h));
- Assert.assertEquals("Wrong conversion", Integer.MIN_VALUE, BinContent.longToSignedInt(i));
+ Assert.assertEquals("Wrong conversion", 0, BinContent.longToSignedInt(0L));
+ Assert.assertEquals("Wrong conversion", 1, BinContent.longToSignedInt(1L));
+ Assert.assertEquals("Wrong conversion", -1, BinContent.longToSignedInt(-1L));
+ Assert.assertEquals("Wrong conversion", Integer.MAX_VALUE, BinContent.longToSignedInt(Integer.MAX_VALUE));
+ Assert.assertEquals("Wrong conversion", Integer.MIN_VALUE, BinContent.longToSignedInt(Integer.MIN_VALUE));
+ Assert.assertEquals("Wrong conversion", 12345, BinContent.longToSignedInt(12345L));
+ Assert.assertEquals("Wrong conversion", -1, BinContent.longToSignedInt(Long.MAX_VALUE));
+ Assert.assertEquals("Wrong conversion", -591724836, BinContent.longToSignedInt(1094624935644L));
+ Assert.assertEquals("Wrong conversion", Integer.MIN_VALUE, BinContent.longToSignedInt(Integer.MAX_VALUE + 1L));
}
}
</instructions>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${salGeneratorPath}</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<groupId>${project.groupId}</groupId>
<artifactId>openflowjava-util</artifactId>
</dependency>
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>sal-common-util</artifactId>
- <exclusions>
- <exclusion>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>sal-common-api</artifactId>
- </exclusion>
- <exclusion>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>concepts</artifactId>
- </exclusion>
- </exclusions>
- </dependency>
<dependency>
<groupId>io.netty</groupId>
<artifactId>netty-handler</artifactId>
@Override
public SwitchConnectionProvider newInstance(SwitchConnectionConfig config) {
- SwitchConnectionProviderImpl switchConnectionProviderImpl = new SwitchConnectionProviderImpl();
- switchConnectionProviderImpl.setConfiguration(new ConnectionConfigurationImpl(config));
+ SwitchConnectionProviderImpl switchConnectionProviderImpl =
+ new SwitchConnectionProviderImpl(new ConnectionConfigurationImpl(config));
return switchConnectionProviderImpl;
}
public boolean useBarrier() {
return config.isUseBarrier();
}
+
+ @Override
+ public boolean isGroupAddModEnabled() {
+ return config.isGroupAddModEnabled();
+ }
}
}
.getLogger(SwitchConnectionProviderImpl.class);
private SwitchConnectionHandler switchConnectionHandler;
private ServerFacade serverFacade;
- private ConnectionConfiguration connConfig;
+ private final ConnectionConfiguration connConfig;
private final SerializationFactory serializationFactory;
private final SerializerRegistry serializerRegistry;
private final DeserializerRegistry deserializerRegistry;
private final DeserializationFactory deserializationFactory;
private TcpConnectionInitializer connectionInitializer;
- /** Constructor */
- public SwitchConnectionProviderImpl() {
+ public SwitchConnectionProviderImpl(ConnectionConfiguration connConfig) {
+ this.connConfig = connConfig;
serializerRegistry = new SerializerRegistryImpl();
+ if (connConfig != null) {
+ serializerRegistry.setGroupAddModConfig(connConfig.isGroupAddModEnabled());
+ }
serializerRegistry.init();
serializationFactory = new SerializationFactory();
serializationFactory.setSerializerTable(serializerRegistry);
deserializationFactory.setRegistry(deserializerRegistry);
}
- @Override
- public void setConfiguration(final ConnectionConfiguration connConfig) {
- this.connConfig = connConfig;
- }
-
@Override
public void setSwitchConnectionHandler(final SwitchConnectionHandler switchConnectionHandler) {
LOG.debug("setSwitchConnectionHandler");
registryHelper.registerSerializer(GetConfigInput.class, new GetConfigInputMessageFactory());
registryHelper.registerSerializer(GetFeaturesInput.class, new GetFeaturesInputMessageFactory());
registryHelper.registerSerializer(GetQueueConfigInput.class, new GetQueueConfigInputMessageFactory());
- registryHelper.registerSerializer(GroupModInput.class, new GroupModInputMessageFactory());
+ registryHelper.registerSerializer(GroupModInput.class,
+ new GroupModInputMessageFactory(serializerRegistry.isGroupAddModEnabled()));
registryHelper.registerSerializer(HelloInput.class, new HelloInputMessageFactory());
registryHelper.registerSerializer(MeterModInput.class, new MeterModInputMessageFactory());
registryHelper.registerSerializer(MultipartRequestInput.class, new MultipartRequestInputFactory());
private static final short OF13 = EncodeConstants.OF13_VERSION_ID;
private Map<MessageTypeKey<?>, OFGeneralSerializer> registry;
+ private boolean isGroupAddModEnabled = false;
+
@Override
public void init() {
registry = new HashMap<>();
InstructionsInitializer.registerInstructionSerializers(this);
}
+ public void setGroupAddModConfig(boolean isGroupAddModEnabled) {
+ this.isGroupAddModEnabled = isGroupAddModEnabled;
+ }
+
+ @Override
+ public boolean isGroupAddModEnabled() {
+ return isGroupAddModEnabled;
+ }
+
/**
* @param msgTypeKey
* @return encoder for current type of message (msgTypeKey)
import org.opendaylight.openflowjava.protocol.impl.util.ListSerializer;
import org.opendaylight.openflowjava.protocol.impl.util.TypeKeyMakerFactory;
import org.opendaylight.openflowjava.util.ByteBufUtils;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.GroupModCommand;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.GroupMod;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.buckets.grouping.BucketsList;
private static final byte MESSAGE_TYPE = 15;
private static final byte PADDING_IN_GROUP_MOD_MESSAGE = 1;
private static final byte PADDING_IN_BUCKET = 4;
+ private static final int OFPGC_ADD_OR_MOD = 32768;
private SerializerRegistry registry;
+ private final boolean isGroupAddModEnaled;
+
+ public GroupModInputMessageFactory(final boolean isGroupAddModEnaled) {
+ this.isGroupAddModEnaled = isGroupAddModEnaled;
+ }
@Override
public void serialize(GroupMod message, ByteBuf outBuffer) {
int index = outBuffer.writerIndex();
ByteBufUtils.writeOFHeader(MESSAGE_TYPE, message, outBuffer, EncodeConstants.EMPTY_LENGTH);
- outBuffer.writeShort(message.getCommand().getIntValue());
+ if (isGroupAddModEnaled) {
+ if (message.getCommand().equals(GroupModCommand.OFPGCADD)
+ || message.getCommand().equals(GroupModCommand.OFPGCMODIFY)) {
+ outBuffer.writeShort(OFPGC_ADD_OR_MOD);
+ } else {
+ outBuffer.writeShort(message.getCommand().getIntValue());
+ }
+ } else {
+ outBuffer.writeShort(message.getCommand().getIntValue());
+ }
outBuffer.writeByte(message.getType().getIntValue());
outBuffer.writeZero(PADDING_IN_GROUP_MOD_MESSAGE);
outBuffer.writeInt(message.getGroupId().getValue().intValue());
private final long switchIdleTimeout;
private ThreadConfiguration threadConfig;
private final boolean useBarrier;
+ private final boolean isGroupAddModEnabled;
/**
* Creates {@link ConnectionConfigurationImpl}
* @param useBarrier
*/
public ConnectionConfigurationImpl(final InetAddress address, final int port, final TlsConfiguration tlsConfig,
- final long switchIdleTimeout, final boolean useBarrier) {
+ final long switchIdleTimeout, final boolean useBarrier, final boolean isGroupAddModEnabled) {
this.address = address;
this.port = port;
this.tlsConfig = tlsConfig;
this.switchIdleTimeout = switchIdleTimeout;
this.useBarrier = useBarrier;
+ this.isGroupAddModEnabled = isGroupAddModEnabled;
}
@Override
public boolean useBarrier() {
return useBarrier;
}
+
+ @Override
+ public boolean isGroupAddModEnabled() {
+ return isGroupAddModEnabled;
+ }
}
\ No newline at end of file
@Mock OFSerializer<ExperimenterDataOfChoice> serializerExperimenterInput;
@Mock OFSerializer<ExperimenterDataOfChoice> serializerMultipartRequestExpCase;
@Mock OFSerializer<MeterBandExperimenterCase> serializerMeterBandExpCase;
+ @Mock ConnectionConfigurationImpl config;
private static final int SWITCH_IDLE_TIMEOUT = 2000;
private InetAddress startupAddress;
private TlsConfiguration tlsConfiguration;
private SwitchConnectionProviderImpl provider;
- private ConnectionConfigurationImpl config;
/**
* Creates new {@link SwitchConnectionProvider} instance for each test
if (protocol != null) {
createConfig(protocol);
}
- provider = new SwitchConnectionProviderImpl();
+ provider = new SwitchConnectionProviderImpl(config);
}
private void createConfig(final TransportProtocol protocol) {
"/selfSignedController", PathType.CLASSPATH,
Lists.newArrayList("TLS_RSA_WITH_AES_128_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA256")) ;
}
- config = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true);
+ config = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true, false);
config.setTransferProtocol(protocol);
}
@Test
public void testServerFacade(){
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
final ListenableFuture<Boolean> future = provider.startup();
final ServerFacade serverFacade = provider.getServerFacade();
Assert.assertNotNull("Wrong -- getServerFacade return null",serverFacade);
@Test
public void testUnregisterWrongKeys(){
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
final ExperimenterInstructionSerializerKey testSerKey
= new ExperimenterInstructionSerializerKey(EncodeConstants.OF10_VERSION_ID,42L);
Assert.assertFalse("Wrong -- unregisterSerializer",provider.unregisterSerializer(testSerKey));
@Test
public void testUnregisterExistingKeys(){
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
// -- registerActionSerializer
final ExperimenterActionSerializerKey key1
= new ExperimenterActionSerializerKey(EncodeConstants.OF10_VERSION_ID, 42L, TestSubType.class);
if (protocol != null) {
createConfig(protocol);
}
- provider = new SwitchConnectionProviderImpl();
+ provider = new SwitchConnectionProviderImpl(config);
}
private void createConfig(final TransportProtocol protocol) {
"/selfSignedController", PathType.CLASSPATH,
Lists.newArrayList("TLS_RSA_WITH_AES_128_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA256")) ;
}
- config = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true);
+ config = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true, false);
config.setTransferProtocol(protocol);
}
*/
@Test
public void testStartup1() {
- provider = new SwitchConnectionProviderImpl();
+ provider = new SwitchConnectionProviderImpl(config);
final ListenableFuture<Boolean> future = provider.startup();
try {
future.get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS);
@Test
public void testStartup3() {
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
final ListenableFuture<Boolean> future = provider.startup();
try {
future.get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS);
@Test
public void testStartup4() {
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
provider.setSwitchConnectionHandler(handler);
try {
Assert.assertTrue("Failed to start", provider.startup().get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS));
@Test
public void testStartup5() {
startUp(TransportProtocol.TLS);
- provider.setConfiguration(config);
provider.setSwitchConnectionHandler(handler);
try {
Assert.assertTrue("Failed to start", provider.startup().get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS));
@Test
public void testStartup6() {
startUp(TransportProtocol.UDP);
- provider.setConfiguration(config);
provider.setSwitchConnectionHandler(handler);
try {
Assert.assertTrue("Failed to start", provider.startup().get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS));
@Test
public void testShutdown() {
startUp(TransportProtocol.TCP);
- provider.setConfiguration(config);
provider.setSwitchConnectionHandler(handler);
try {
Assert.assertTrue("Failed to start", provider.startup().get(WAIT_TIMEOUT, TimeUnit.MILLISECONDS));
private static final byte MESSAGE_TYPE = 15;
private static final byte PADDING_IN_GROUP_MOD_MESSAGE = 1;
private SerializerRegistry registry;
- private OFSerializer<GroupModInput> groupModFactory;
+ private GroupModInputMessageFactory groupModFactory;
/**
* Initializes serializer registry and stores correct factory in field
public void startUp() {
registry = new SerializerRegistryImpl();
registry.init();
- groupModFactory = registry.getSerializer(
- new MessageTypeKey<>(EncodeConstants.OF13_VERSION_ID, GroupModInput.class));
+ groupModFactory = new GroupModInputMessageFactory(false);
}
/**
out.writeShort(3);
groupModFactory.serialize(message, out);
-
// read parent message
out.readInt();
out.skipBytes(2);
"/selfSignedController", PathType.CLASSPATH,
new ArrayList<String>());
}
- connConfig = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true);
+ connConfig = new ConnectionConfigurationImpl(startupAddress, 0, tlsConfiguration, SWITCH_IDLE_TIMEOUT, true, false);
connConfig.setTransferProtocol(protocol);
mockPlugin = new MockPlugin();
- switchConnectionProvider = new SwitchConnectionProviderImpl();
+ switchConnectionProvider = new SwitchConnectionProviderImpl(connConfig);
switchConnectionProvider.setSwitchConnectionHandler(mockPlugin);
- switchConnectionProvider.setConfiguration(connConfig);
switchConnectionProvider.startup().get(CONNECTION_TIMEOUT, TimeUnit.MILLISECONDS);
if (protocol.equals(TransportProtocol.TCP) || protocol.equals(TransportProtocol.TLS)) {
final TcpHandler tcpHandler = (TcpHandler) switchConnectionProvider.getServerFacade();
</instructions>
</configuration>
</plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${salGeneratorPath}</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
- </plugin>
</plugins>
</build>
public interface SwitchConnectionProvider extends AutoCloseable,
SerializerExtensionProvider, DeserializerExtensionProvider {
- /**
- * @param configuration [protocol, port, address and supported features]
- */
- void setConfiguration(ConnectionConfiguration configuration);
-
/**
* return the connection configuration
* @return configuration [protocol, port, address and supported features]
default true;
}
+ leaf group-add-mod-enabled {
+ description "Group Add Mod Enabled";
+ type boolean;
+ default false;
+ }
+
leaf switch-idle-timeout {
description "idle timeout in [ms]";
type uint32;
<instance-name>openflow-switch-connection-provider-default-impl</instance-name>
<port>6653</port>
<transport-protocol>TCP</transport-protocol>
+ <group-add-mod-enabled>false</group-add-mod-enabled>
<tls>
<keystore>configuration/ssl/ctl.jks</keystore>
<keystore-type>JKS</keystore-type>
<certificate-password>opendaylight</certificate-password>
<cipher-suites></cipher-suites>
</tls>
-</switch-connection-config>
\ No newline at end of file
+</switch-connection-config>
<instance-name>openflow-switch-connection-provider-legacy-impl</instance-name>
<port>6633</port>
<transport-protocol>TCP</transport-protocol>
+ <group-add-mod-enabled>false</group-add-mod-enabled>
<tls>
<keystore>configuration/ssl/ctl.jks</keystore>
<keystore-type>JKS</keystore-type>
* and is available at http://www.eclipse.org/legal/epl-v10.html
*/
-
package org.opendaylight.openflowjava.util;
import com.google.common.base.Preconditions;
import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.MacAddress;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.OfHeader;
-/** Class for common operations on ByteBuf
+/**
+ * Class for common operations on ByteBuf.
+ *
* @author michal.polkorab
* @author timotej.kubas
*/
}
/**
- * Converts ByteBuf into String
+ * Converts ByteBuf into String.
+ *
* @param bb input ByteBuf
* @return String
*/
public static String byteBufToHexString(final ByteBuf bb) {
StringBuilder sb = new StringBuilder();
- for (int i = bb.readerIndex(); i < (bb.readerIndex() + bb.readableBytes()); i++) {
+ for (int i = bb.readerIndex(); i < bb.readerIndex() + bb.readableBytes(); i++) {
sb.append(String.format(" %02x", bb.getUnsignedByte(i)));
}
return sb.toString().trim();
}
/**
- * Converts String into byte[]
+ * Converts String into byte[].
+ *
* @param hexSrc input String
* @return byte[] filled with input data
*/
}
/**
- * Converts String into byte[]
+ * Converts String into byte[].
+ *
* @param hexSrc input String
* @param withSpaces if there are spaces in string
* @return byte[] filled with input data
final Splitter splitter = withSpaces ? HEXSTRING_SPLITTER : HEXSTRING_NOSPACE_SPLITTER;
List<String> byteChips = Lists.newArrayList(splitter.split(hexSrc));
byte[] result = new byte[byteChips.size()];
- int i = 0;
+ int index = 0;
for (String chip : byteChips) {
- result[i] = (byte) Short.parseShort(chip, 16);
- i++;
+ result[index] = (byte) Short.parseShort(chip, 16);
+ index++;
}
return result;
}
/**
- * Creates ByteBuf filled with specified data
+ * Creates ByteBuf filled with specified data.
+ *
* @param hexSrc input String of bytes in hex format
* @return ByteBuf with specified hexString converted
*/
}
/**
- * Creates ByteBuf filled with specified data
+ * Creates ByteBuf filled with specified data.
+ *
* @param hexSrc input String of bytes in hex format
* @param out ByteBuf with specified hexString converted
*/
}
/**
- * Fills specified ByteBuf with 0 (zeros) of desired length, used for padding
- * @param length
+ * Fills specified ByteBuf with 0 (zeros) of desired length, used for padding.
+ *
+ * @param length the desired length
* @param out ByteBuf to be padded
* @deprecated Use {@link ByteBuf#writeZero(int)} directly.
*/
}
/**
- * Create standard OF header
+ * Create standard OF header.
+ *
* @param msgType message code
* @param message POJO
* @param out writing buffer
* @param length ofheader length
*/
- public static <E extends OfHeader> void writeOFHeader(final byte msgType, final E message, final ByteBuf out, final int length) {
+ public static <E extends OfHeader> void writeOFHeader(final byte msgType, final E message, final ByteBuf out,
+ final int length) {
out.writeByte(message.getVersion());
out.writeByte(msgType);
out.writeShort(length);
}
/**
- * Write length standard OF header
+ * Write length standard OF header.
+ *
* @param out writing buffer
*/
public static void updateOFHeaderLength(final ByteBuf out) {
}
/**
- * Write length OF header
+ * Write length OF header.
+ *
* @param out writing buffer
* @param index writing index
*/
}
/**
- * Fills the bitmask from boolean map where key is bit position
+ * Fills the bitmask from boolean map where key is bit position.
+ *
* @param booleanMap bit to boolean mapping
* @return bit mask
*/
public static int fillBitMask(final int offset, final boolean... values) {
int bitmask = 0;
- int i = offset;
+ int index = offset;
for (boolean v : values) {
if (v) {
- bitmask |= 1 << i;
+ bitmask |= 1 << index;
}
- ++i;
+ ++index;
}
return bitmask;
}
/**
- * Fills the bitmask from boolean list where key is bit position
+ * Fills the bitmask from boolean list where key is bit position.
+ *
* @param booleanList bit to boolean mapping
* @return bit mask
*/
int[] bitmask;
int index = 0;
int arrayIndex = 0;
- if ((booleanList.size() % Integer.SIZE) != 0) {
+ if (booleanList.size() % Integer.SIZE != 0) {
bitmask = new int[booleanList.size() / Integer.SIZE + 1];
} else {
bitmask = new int[booleanList.size() / Integer.SIZE];
}
/**
- * Converts byte array into String
+ * Converts byte array into String.
+ *
* @param array input byte array
* @return String
*/
return sb.toString().trim();
}
- private static int hexValue(final char c) {
- if (c >= '0' && c <= '9') {
- return c - '0';
+ private static int hexValue(final char ch) {
+ if (ch >= '0' && ch <= '9') {
+ return ch - '0';
}
- if (c >= 'a' && c <= 'f') {
- return c - 'a' + 10;
+ if (ch >= 'a' && ch <= 'f') {
+ return ch - 'a' + 10;
}
- if (c >= 'A' && c <= 'F') {
- return c - 'A' + 10;
+ if (ch >= 'A' && ch <= 'F') {
+ return ch - 'A' + 10;
}
- throw new IllegalArgumentException(String.format("Invalid character '%s' encountered", c));
+ throw new IllegalArgumentException(String.format("Invalid character '%s' encountered", ch));
}
/**
* Converts macAddress to byte array.
* See also {@link org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.MacAddress}.
*
- * @param macAddress
+ * @param macAddress the mac address to convert
* @return byte representation of mac address
*/
+ @SuppressWarnings("checkstyle:IllegalCatch")
public static byte[] macAddressToBytes(final String macAddress) {
final byte[] result = new byte[EncodeConstants.MAC_ADDRESS_LENGTH];
final char[] mac = macAddress.toCharArray();
offset++;
} else {
result[i] = UnsignedBytes.checkedCast(
- (hexValue(mac[offset]) << 4) | hexValue(mac[offset +1]));
+ hexValue(mac[offset]) << 4 | hexValue(mac[offset + 1]));
offset += 2;
}
Preconditions.checkArgument(mac[offset] == ':', "Invalid value: %s", macAddress);
offset++;
}
- if (offset == (mac.length - 1)) {
+ if (offset == mac.length - 1) {
result[EncodeConstants.MAC_ADDRESS_LENGTH - 1] = UnsignedBytes.checkedCast(hexValue(mac[offset]));
} else {
result[EncodeConstants.MAC_ADDRESS_LENGTH - 1] =
- UnsignedBytes.checkedCast(hexValue(mac[offset]) << 4 | hexValue(mac[offset +1]));
+ UnsignedBytes.checkedCast(hexValue(mac[offset]) << 4 | hexValue(mac[offset + 1]));
offset++;
}
- if (offset != (mac.length -1)) {
+ if (offset != mac.length - 1) {
throw new IllegalArgumentException("Incorrect MAC address length");
}
- } catch (Exception e) {
+ } catch (RuntimeException e) {
throw new IllegalArgumentException("Unable to serialize MAC address for input: " + macAddress
+ ". \n" + e);
}
return result;
}
- private static final void appendHexByte(final StringBuilder sb, final byte b) {
- final int v = UnsignedBytes.toInt(b);
+ private static void appendHexByte(final StringBuilder sb, final byte value) {
+ final int v = UnsignedBytes.toInt(value);
sb.append(HEX_CHARS[v >>> 4]);
sb.append(HEX_CHARS[v & 15]);
}
private static void appendHexUnsignedShort(final StringBuilder sb, final int val) {
- sb.append(ByteBufUtils.HEX_CHARS[(val >>> 12) & 15]);
- sb.append(ByteBufUtils.HEX_CHARS[(val >>> 8) & 15]);
- sb.append(ByteBufUtils.HEX_CHARS[(val >>> 4) & 15]);
+ sb.append(ByteBufUtils.HEX_CHARS[val >>> 12 & 15]);
+ sb.append(ByteBufUtils.HEX_CHARS[val >>> 8 & 15]);
+ sb.append(ByteBufUtils.HEX_CHARS[val >>> 4 & 15]);
sb.append(ByteBufUtils.HEX_CHARS[ val & 15]);
}
* Converts a MAC address represented in bytes to String.
* See also {@link org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.MacAddress}.
*
- * @param address
+ * @param address the MAC address to convert
* @return String representation of a MAC address
*/
public static String macAddressToString(final byte[] address) {
}
/**
- * Reads and parses null-terminated string from ByteBuf
- * @param rawMessage
+ * Reads and parses null-terminated string from ByteBuf.
+ *
+ * @param rawMessage the message to parse
* @param length maximal length of String
* @return String with name of port
*/
return IetfYangUtil.INSTANCE.macAddressFor(tmp);
}
- public static byte[] serializeList(final List<Short> list) throws IOException{
+ public static byte[] serializeList(final List<Short> list) throws IOException {
ByteBuffer byteBuffer = ByteBuffer.allocate(list.size() * 2);
- for (Short aShort : list) {
- byteBuffer.putShort(aShort);
+ for (Short shortValue : list) {
+ byteBuffer.putShort(shortValue);
}
return byteBuffer.array();
}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
/**
+ * Factory for creating experimenter deserializer keys.
+ *
* @author michal.polkorab
*/
-public abstract class ExperimenterDeserializerKeyFactory {
+public final class ExperimenterDeserializerKeyFactory {
private ExperimenterDeserializerKeyFactory() {
//not called
}
/**
+ * Creates an experimenter error deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
}
/**
+ * Creates an experimenter message deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @param type experimenter type according to vendor implementation
}
/**
- * @param version openflow wire version
+ * Creates a vendor message deserializer key.
+ *
+ * @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
*/
}
/**
+ * Creates a multi-part reply message deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
- * @param type
+ * @param type the type
* @return key instance
*/
public static ExperimenterIdTypeDeserializerKey createMultipartReplyMessageDeserializerKey(
}
/**
- * @param version openflow wire version
+ * Creates a multi-part reply vendor message deserializer key.
+ *
+ * @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
*/
}
/**
+ * Creates a multi-part reply TF deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
}
/**
+ * Creates a queue property deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
}
/**
+ * Creates a meter band deserializer key.
+ *
* @param version openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
short version, Long experimenterId) {
return new ExperimenterIdDeserializerKey(version, experimenterId, MeterBandExperimenterCase.class);
}
-
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
/**
+ * Factory for creating experimenter serializer keys.
+ *
* @author michal.polkorab
*/
public abstract class ExperimenterSerializerKeyFactory {
/**
+ * Creates an experimenter message serializer key.
+ *
* @param msgVersion openflow wire version
* @param experimenterId experimenter / vendor ID
* @param type experimenter type according to vendor implementation
}
/**
+ * Creates a multi-part request serializer key.
+ *
* @param msgVersion openflow wire version
* @param experimenterId experimenter / vendor ID
* @param type experimenter type according to vendor implementation
}
/**
+ * Creates a multi-part request TF serializer key.
+ *
* @param msgVersion openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
}
/**
+ * Creates a meter band serializer key.
+ *
* @param msgVersion openflow wire version
* @param experimenterId experimenter / vendor ID
* @return key instance
*/
public static ExperimenterIdSerializerKey<MeterBandExperimenterCase> createMeterBandSerializerKey(
short msgVersion, long experimenterId) {
- return new ExperimenterIdMeterSubTypeSerializerKey<>(msgVersion, experimenterId, MeterBandExperimenterCase.class, null);
+ return new ExperimenterIdMeterSubTypeSerializerKey<>(msgVersion, experimenterId,
+ MeterBandExperimenterCase.class, null);
}
public static ExperimenterIdSerializerKey<MeterBandExperimenterCase> createMeterBandSerializerKey(
short msgVersion, long experimenterId, Class<? extends ExperimenterMeterBandSubType> meterSubType) {
- return new ExperimenterIdMeterSubTypeSerializerKey<>(msgVersion, experimenterId, MeterBandExperimenterCase.class, meterSubType);
+ return new ExperimenterIdMeterSubTypeSerializerKey<>(msgVersion, experimenterId,
+ MeterBandExperimenterCase.class, meterSubType);
}
-
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.HelloInputBuilder;
/**
- * @author michal.polkorab
+ * Unit tests for ByteBufUtils.
*
+ * @author michal.polkorab
*/
public class ByteBufUtilsTest {
- private final byte[] EXPECTED = new byte[]{0x01, 0x02, 0x03, 0x04, 0x05, (byte) 0xff};
- private final byte[] EXPECTEDVALUES1AND255 = new byte[]{0x00, 0x01, 0x00, (byte) 0xff};
+ private static final byte[] EXPECTED = new byte[]{0x01, 0x02, 0x03, 0x04, 0x05, (byte) 0xff};
+ private static final byte[] EXPECTEDVALUES1AND255 = new byte[]{0x00, 0x01, 0x00, (byte) 0xff};
/**
- * Test of {@link org.opendaylight.openflowjava.util.ByteBufUtils#hexStringToBytes(String)}
+ * Test of {@link org.opendaylight.openflowjava.util.ByteBufUtils#hexStringToBytes(String)}.
*/
@Test
public void testHexStringToBytes() {
}
/**
- * Test of {@link ByteBufUtils#hexStringToBytes(String, boolean)}
+ * Test of {@link ByteBufUtils#hexStringToBytes(String, boolean)}.
*/
@Test
public void testHexStringToBytes2() {
}
/**
- * Test of {@link ByteBufUtils#hexStringToByteBuf(String)}
+ * Test of {@link ByteBufUtils#hexStringToByteBuf(String)}.
*/
@Test
public void testHexStringToByteBuf() {
}
/**
- * Test of {@link ByteBufUtils#hexStringToByteBuf(String, ByteBuf)}
+ * Test of {@link ByteBufUtils#hexStringToByteBuf(String, ByteBuf)}.
*/
@Test
public void testHexStringToGivenByteBuf() {
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}.
*/
@Test
public void testFillBitmaskByEmptyMap() {
private static String toBinaryString(Map<Integer, Boolean> emptyMap, int length) {
String binaryString = Integer.toBinaryString(ByteBufUtils.fillBitMaskFromMap(emptyMap));
- return String.format("%"+length+"s", binaryString).replaceAll(" ", "0");
+ return String.format("%" + length + "s", binaryString).replaceAll(" ", "0");
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}.
*/
@Test
public void testFillBitmaskByFullMap() {
Map<Integer, Boolean> fullMap = new HashMap<>();
String expectedBinaryString = "11111111111111111111111111111111";
String bitmaskValueInBinarySytring;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
fullMap.put(i, true);
}
bitmaskValueInBinarySytring = toBinaryString(fullMap, 32);
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}.
*/
@Test
public void testFillBitmaskByZeroMap() {
Map<Integer, Boolean> zeroMap = new HashMap<>();
String expectedBinaryString = "00000000000000000000000000000000";
String bitmaskValueInBinarySytring;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
zeroMap.put(i, false);
}
bitmaskValueInBinarySytring = toBinaryString(zeroMap, 32);
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromMap(java.util.Map)}.
*/
@Test
public void testFillBitmaskByRandomSet() {
String expectedBinaryString = "00000000000000000111100000000000";
String bitmaskValueInBinarySytring;
Boolean mapValue;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
mapValue = false;
- if(i>=11 && i<=14) {
+ if (i >= 11 && i <= 14) {
mapValue = true;
}
randomMap.put(i, mapValue);
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}.
*/
@Test
public void testFillBitmaskByEmptyList() {
int[] bitMaskArray;
bitMaskArray = ByteBufUtils.fillBitMaskFromList(emptyList);
String binaryString = Integer.toBinaryString(bitMaskArray[0]);
- return String.format("%"+length+"s", binaryString).replaceAll(" ", "0");
+ return String.format("%" + length + "s", binaryString).replaceAll(" ", "0");
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}.
*/
@Test
public void testFillBitmaskByFullList() {
List<Boolean> fullList = new ArrayList<>();
String expectedBinaryString = "11111111111111111111111111111111";
String bitmaskValueInBinarySytring;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
fullList.add(true);
}
bitmaskValueInBinarySytring = listToBinaryString(fullList, 32);
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}.
*/
@Test
public void testFillBitmaskByZeroList() {
List<Boolean> zeroList = new ArrayList<>();
String expectedBinaryString = "00000000000000000000000000000000";
String bitmaskValueInBinarySytring;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
zeroList.add(false);
}
bitmaskValueInBinarySytring = listToBinaryString(zeroList, 32);
}
/**
- * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}
+ * Test of {@link ByteBufUtils#fillBitMaskFromList(List)}.
*/
@Test
public void testFillBitmaskFromRandomList() {
String expectedBinaryString = "00000000000000000111100000000000";
String bitmaskValueInBinarySytring;
Boolean listValue;
- for(Integer i=0;i<=31;i++) {
+ for (Integer i = 0; i <= 31; i++) {
listValue = false;
- if(i>=11 && i<=14) {
+ if (i >= 11 && i <= 14) {
listValue = true;
}
randomList.add(listValue);
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
@Test
public void testMacToBytes() {
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytes2() {
Assert.assertArrayEquals("Wrong byte array", new byte[]{0, 1, 2, 3, (byte) 255, 5},
ByteBufUtils.macAddressToBytes("00:01:02:03:FF:0G"));
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesTooShort() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesTooShort2() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF:");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testIncorrectMacToBytes() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF::");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testIncorrectMacToBytes2() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF:::");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesTooLong() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF:05:85");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesInvalidOctet() {
ByteBufUtils.macAddressToBytes("00:01:02:03:FF:05d");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesInvalidOctet2() {
ByteBufUtils.macAddressToBytes("00:01:rr:03:FF:05");
}
/**
- * Test of {@link ByteBufUtils#macAddressToBytes(String)}
+ * Test of {@link ByteBufUtils#macAddressToBytes(String)}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToBytesInvalidOctet3() {
ByteBufUtils.macAddressToBytes("00:01:05d:03:FF:02");
}
/**
- * Test of {@link ByteBufUtils#macAddressToString(byte[])}
+ * Test of {@link ByteBufUtils#macAddressToString(byte[])}.
*/
- @Test(expected=IllegalArgumentException.class)
+ @Test(expected = IllegalArgumentException.class)
public void testMacToString() {
Assert.assertEquals("Wrong string decoded", "00:01:02:03:FF:05",
ByteBufUtils.macAddressToString(new byte[]{0, 1, 2, 3, (byte) 255, 5}));
}
/**
- * Test of {@link ByteBufUtils#decodeNullTerminatedString(ByteBuf, int)}
+ * Test of {@link ByteBufUtils#decodeNullTerminatedString(ByteBuf, int)}.
*/
@Test
public void testDecodeString() {
}
/**
- * Test of {@link ByteBufUtils#byteBufToHexString(ByteBuf)}
+ * Test of {@link ByteBufUtils#byteBufToHexString(ByteBuf)}.
*/
@Test
public void testByteBufToHexString() {
}
/**
- * Buffer padding test
+ * Buffer padding test.
*/
@Test
public void testPadBuffer() {
}
/**
- * Write OF header test
+ * Write OF header test.
*/
@Test
public void testWriteHeader() {
- ByteBuf buf = PooledByteBufAllocator.DEFAULT.buffer();
HelloInputBuilder helloBuilder = new HelloInputBuilder();
helloBuilder.setVersion((short) EncodeConstants.OF13_VERSION_ID);
helloBuilder.setXid(12345L);
helloBuilder.setElements(null);
HelloInput helloInput = helloBuilder.build();
+ ByteBuf buf = PooledByteBufAllocator.DEFAULT.buffer();
ByteBufUtils.writeOFHeader((byte) 0, helloInput, buf, EncodeConstants.OFHEADER_SIZE);
Assert.assertEquals("Wrong version", EncodeConstants.OF13_VERSION_ID, buf.readUnsignedByte());
Assert.assertEquals("Wrong type", 0, buf.readUnsignedByte());
}
/**
- * Fill bitmask test
+ * Fill bitmask test.
*/
@Test
public void testFillBitmask() {
}
/**
- * Test bytes to hex string
+ * Test bytes to hex string.
*/
@Test
public void testBytesToHexString() {
}
/**
- * Test ipv4 address conversion
+ * Test ipv4 address conversion.
*/
- @Test(expected=IndexOutOfBoundsException.class)
+ @Test(expected = IndexOutOfBoundsException.class)
public void testReadIpv4Address() {
ByteBuf buffer = PooledByteBufAllocator.DEFAULT.buffer();
buffer.writeByte(10);
}
/**
- * Test ipv6 address conversion
+ * Test ipv6 address conversion.
*/
- @Test(expected=IndexOutOfBoundsException.class)
+ @Test(expected = IndexOutOfBoundsException.class)
public void testReadIpv6Address() {
ByteBuf buffer = PooledByteBufAllocator.DEFAULT.buffer();
buffer.writeShort(10);
shorts.add((short) 255);
final byte[] bytes = ByteBufUtils.serializeList(shorts);
- Assert.assertTrue(bytes.length == shorts.size()*2);
+ Assert.assertTrue(bytes.length == shorts.size() * 2);
Assert.assertArrayEquals(EXPECTEDVALUES1AND255, bytes);
}
public void testUpdateHeader() throws IOException {
ByteBuf buffer = PooledByteBufAllocator.DEFAULT.buffer();
buffer.writeInt(1);
- int start = buffer.writerIndex();
+ final int start = buffer.writerIndex();
buffer.writeShort(4);
buffer.writeShort(EncodeConstants.EMPTY_LENGTH);
buffer.writeLong(8);
- int end = buffer.writerIndex();
+ final int end = buffer.writerIndex();
ByteBufUtils.updateOFHeaderLength(buffer, start);
Assert.assertEquals(buffer.readInt(), 1);
Assert.assertEquals(buffer.readShort(), 4);
Assert.assertEquals(buffer.readShort(), 12);
- Assert.assertEquals(buffer.readLong(), 8l);
+ Assert.assertEquals(buffer.readLong(), 8L);
Assert.assertEquals(buffer.getShort(start + EncodeConstants.OFHEADER_LENGTH_INDEX), end - start);
}
}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
/**
+ * Unit tests for ExperimenterDeserializerKeyFactory.
+ *
* @author michal.polkorab
*/
public class ExperimenterDeserializerKeyFactoryTest {
43L, ExperimenterDataOfChoice.class);
Assert.assertEquals("Wrong key created", comparationKey, createdKey);
}
-}
\ No newline at end of file
+}
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
/**
- * Test ExperimenterSerializerKeyFactory key creation
- * @author michal.polkorab
+ * Test ExperimenterSerializerKeyFactory key creation.
*
+ * @author michal.polkorab
*/
public class ExperimenterSerializerKeyFactoryTest {
@Test
public void testCreateMeterBandSubTypeSerializerKey() throws Exception {
- ExperimenterIdSerializerKey<?> createdKey;
- ExperimenterIdSerializerKey<?> comparationKey1;
- ExperimenterIdSerializerKey<?> comparationKey2;
- ExperimenterIdSerializerKey<?> comparationKey3;
- ExperimenterIdSerializerKey<?> comparationKey4;
- ExperimenterIdSerializerKey<?> comparationKey5;
+ final ExperimenterIdSerializerKey<?> createdKey;
+ final ExperimenterIdSerializerKey<?> comparationKey1;
+ final ExperimenterIdSerializerKey<?> comparationKey2;
+ final ExperimenterIdSerializerKey<?> comparationKey3;
+ final ExperimenterIdSerializerKey<?> comparationKey4;
+ final ExperimenterIdSerializerKey<?> comparationKey5;
createdKey = ExperimenterSerializerKeyFactory.createMeterBandSerializerKey(
EncodeConstants.OF10_VERSION_ID, 43L, ExperimenterMeterBandSubType.class);
Assert.assertNotEquals("Wrong key created", comparationKey4, createdKey);
Assert.assertEquals("Wrong key created", comparationKey5, createdKey);
}
-}
\ No newline at end of file
+}
<manifestLocation>${project.build.directory}/META-INF</manifestLocation>
</configuration>
</plugin>
- <plugin>
- <groupId>org.codehaus.mojo</groupId>
- <artifactId>build-helper-maven-plugin</artifactId>
- <executions>
- <execution>
- <id>add-yang-sources</id>
- <phase>generate-sources</phase>
- <goals>
- <goal>add-source</goal>
- </goals>
- <configuration>
- <sources>
- <source>${salGeneratorPath}</source>
- </sources>
- </configuration>
- </execution>
- </executions>
- </plugin>
</plugins>
<pluginManagement>
<plugins>
</configuration>
</plugin>
<plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <executions>
- <execution>
- <goals>
- <goal>generate-sources</goal>
- </goals>
- <configuration>
- <codeGenerators>
- <generator>
- <codeGeneratorClass>
- org.opendaylight.mdsal.binding.maven.api.gen.plugin.CodeGeneratorImpl
- </codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/generated-sources/sal</outputBaseDir>
- </generator>
- <generator>
- <codeGeneratorClass>org.opendaylight.mdsal.binding.yang.unified.doc.generator.maven.DocumentationGeneratorImpl</codeGeneratorClass>
- <outputBaseDir>${project.build.directory}/site/models</outputBaseDir>
- </generator>
- </codeGenerators>
- <inspectDependencies>true</inspectDependencies>
- </configuration>
- </execution>
- </executions>
- <dependencies>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>maven-sal-api-gen-plugin</artifactId>
- <version>${mdsal.model.version}</version>
- <type>jar</type>
- </dependency>
- </dependencies>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>findbugs-maven-plugin</artifactId>
+ <configuration>
+ <failOnError>true</failOnError>
+ </configuration>
</plugin>
</plugins>
</build>
<artifactId>diagstatus-api</artifactId>
<version>${infrautils.version}</version>
</dependency>
+ <dependency>
+ <groupId>org.opendaylight.mdsal</groupId>
+ <artifactId>mdsal-eos-binding-api</artifactId>
+ </dependency>
</dependencies>
</project>
* terms of the Eclipse Public License v1.0 which accompanies this distribution,
* and is available at http://www.eclipse.org/legal/epl-v10.html
*/
-package org.opendaylight.openflowplugin.impl.diagstatus;
+package org.opendaylight.openflowplugin.api.diagstatus;
+import java.io.IOException;
+import java.net.Socket;
import org.opendaylight.infrautils.diagstatus.DiagStatusService;
import org.opendaylight.infrautils.diagstatus.ServiceDescriptor;
import org.opendaylight.infrautils.diagstatus.ServiceState;
import org.opendaylight.infrautils.diagstatus.ServiceStatusProvider;
-
-import org.ops4j.pax.cdi.api.OsgiServiceProvider;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-@OsgiServiceProvider(classes = ServiceStatusProvider.class)
public class OpenflowPluginDiagStatusProvider implements ServiceStatusProvider {
private static final Logger LOG = LoggerFactory.getLogger(OpenflowPluginDiagStatusProvider.class);
private static final String OPENFLOW_SERVICE_NAME = "OPENFLOW";
+ private static final int OF_PORT_11 = 6633;
+ private static final int OF_PORT_13 = 6653;
private final DiagStatusService diagStatusService;
private volatile ServiceDescriptor serviceDescriptor;
@Override
public ServiceDescriptor getServiceDescriptor() {
- // TODO Check 6653/6633 port status to report dynamic status
+
+ if (serviceDescriptor.getServiceState().equals(ServiceState.OPERATIONAL)) {
+ if (getApplicationNetworkState(OF_PORT_13) && getApplicationNetworkState(OF_PORT_11)) {
+ return serviceDescriptor;
+ } else {
+ serviceDescriptor = new ServiceDescriptor(OPENFLOW_SERVICE_NAME, ServiceState.ERROR,
+ "OF::PORTS:: 6653 and 6633 are not up yet");
+ return serviceDescriptor;
+ }
+ }
return serviceDescriptor;
}
+
+ private boolean getApplicationNetworkState(int port) {
+ Socket socket = null;
+ try {
+ socket = new Socket("localhost", port);
+ LOG.debug("Socket connection established");
+ return true;
+ } catch (IOException e) {
+ return false;
+ } finally {
+ try {
+ if (socket != null) {
+ socket.close();
+ }
+ } catch (IOException ex) {
+ LOG.error("Failed to close socket : {}", socket, ex);
+ }
+ }
+ }
}
\ No newline at end of file
import java.util.List;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
-import org.opendaylight.infrautils.diagstatus.DiagStatusService;
+import org.opendaylight.infrautils.ready.SystemReadyMonitor;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.openflowjava.protocol.spi.connection.SwitchConnectionProvider;
+import org.opendaylight.openflowplugin.api.diagstatus.OpenflowPluginDiagStatusProvider;
import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
import org.opendaylight.openflowplugin.api.openflow.mastership.MastershipChangeServiceManager;
List<SwitchConnectionProvider> switchConnectionProviders,
ClusterSingletonServiceProvider singletonServiceProvider,
MastershipChangeServiceManager mastershipChangeServiceManager,
- DiagStatusService diagStatusService);
+ OpenflowPluginDiagStatusProvider ofPluginDiagstatusProvider,
+ SystemReadyMonitor systemReadyMonitor);
}
+++ /dev/null
-/*
- * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
- *
- * This program and the accompanying materials are made available under the
- * terms of the Eclipse Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/epl-v10.html
- */
-
-package org.opendaylight.openflowplugin.api.openflow;
-
-import io.netty.util.HashedWheelTimer;
-
-/**
- * Created by Martin Bobak <mbobak@cisco.com> on 4.4.2015.
- */
-public interface OpenFlowPluginTimer {
-
- HashedWheelTimer getTimer();
-}
package org.opendaylight.openflowplugin.api.openflow.configuration;
import com.google.common.collect.ImmutableMap;
+import java.util.Locale;
import java.util.Map;
/**
*/
@Override
public String toString() {
- return this.name().toLowerCase().replace('_', '-');
+ return this.name().toLowerCase(Locale.ENGLISH).replace('_', '-');
}
}
*/
package org.opendaylight.openflowplugin.api.openflow.lifecycle;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipListener;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipListener;
import org.opendaylight.openflowplugin.api.openflow.OFPManager;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceContext;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceManager;
*/
Short getVersion();
- /**
- * Setter.
- * @param errorHandler the errorHandler to set
- */
- void setErrorHandler(ErrorHandler errorHandler);
-
- /**
- * Setter.
- * @param handshakeListener the handshakeListener to set
- */
- void setHandshakeListener(HandshakeListener handshakeListener);
-
- /**
- * should use negotiation bit map.
- * @param isBitmapNegotiationEnable yes/no
- */
- void setUseVersionBitmap(boolean isBitmapNegotiationEnable);
-
/**
* process current handshake step.
* @param receivedHello message from device we need to act upon
<reference id="dataBroker" interface="org.opendaylight.controller.md.sal.binding.api.DataBroker" odl:type="pingpong"/>
<reference id="rpcRegistry" interface="org.opendaylight.controller.sal.binding.api.RpcProviderRegistry"/>
<reference id="notificationPublishService" interface="org.opendaylight.controller.md.sal.binding.api.NotificationPublishService"/>
- <reference id="entityOwnershipService" interface="org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService"/>
+ <reference id="entityOwnershipService" interface="org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService"/>
<reference id="clusterSingletonServiceProvider" interface="org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider"/>
<reference id="diagStatusService" interface="org.opendaylight.infrautils.diagstatus.DiagStatusService" />
+ <reference id="systemReadyMonitor" interface="org.opendaylight.infrautils.ready.SystemReadyMonitor" />
<reference id="defaultSwitchConnProvider" interface="org.opendaylight.openflowjava.protocol.spi.connection.SwitchConnectionProvider"
odl:type="openflow-switch-connection-provider-default-impl"/>
update-method="update"/>
</bean>
+ <bean id="ofPluginDiagstatusProvider"
+ class="org.opendaylight.openflowplugin.api.diagstatus.OpenflowPluginDiagStatusProvider">
+ <argument ref="diagStatusService"/>
+ </bean>
+
+ <service ref="ofPluginDiagstatusProvider" interface="org.opendaylight.infrautils.diagstatus.ServiceStatusProvider"/>
+
<service ref="configurationService" interface="org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService"/>
<bean id="openflowPluginProvider"
</argument>
<argument ref="clusterSingletonServiceProvider"/>
<argument ref="mastershipChangeServiceManager"/>
- <argument ref="diagStatusService"/>
+ <argument ref="ofPluginDiagstatusProvider"/>
+ <argument ref="systemReadyMonitor"/>
</bean>
<service ref="openflowPluginProvider" odl:type="openflow-plugin-provider-impl">
<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">
<modelVersion>4.0.0</modelVersion>
+
<parent>
<groupId>org.opendaylight.openflowplugin</groupId>
<artifactId>openflowplugin-parent</artifactId>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
<configuration>
- <propertyExpansion>checkstyle.violationSeverity=warning</propertyExpansion>
+ <propertyExpansion>checkstyle.violationSeverity=error</propertyExpansion>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>findbugs-maven-plugin</artifactId>
+ <configuration>
+ <failOnError>true</failOnError>
</configuration>
</plugin>
</plugins>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</dependency>
- <dependency>
- <groupId>org.opendaylight.controller</groupId>
- <artifactId>sal-binding-api</artifactId>
- </dependency>
+ <dependency>
+ <groupId>org.opendaylight.controller</groupId>
+ <artifactId>sal-binding-api</artifactId>
+ </dependency>
<dependency>
<groupId>junit</groupId>
}
/**
- * Method change status for TxChainManager to {@link TransactionChainManagerStatus#WORKING} and it has to make
+ * Method change status for TxChainManager to WORKING and it has to make
* registration for this class instance as {@link TransactionChainListener} to provide possibility a make DS
* transactions. Call this method for MASTER role only.
*/
}
/**
- * Method change status for TxChainManger to {@link TransactionChainManagerStatus#SLEEPING} and it unregisters
+ * Method change status for TxChainManger to SLEEPING and it unregisters
* this class instance as {@link TransactionChainListener} so it broke a possibility to write something to DS.
* Call this method for SLAVE only.
* @return Future
}
@Override
- public void onFailure(@Nonnull final Throwable t) {
+ public void onFailure(@Nonnull final Throwable throwable) {
closeTransactionChain();
}
- });
+ }, MoreExecutors.directExecutor());
} else {
// ignoring redundant deactivate invocation
future = Futures.immediateFuture(null);
return true;
}
- public <T extends DataObject> void addDeleteOperationTotTxChain(final LogicalDatastoreType store,
- final InstanceIdentifier<T> path){
+ public <T extends DataObject> void addDeleteOperationToTxChain(final LogicalDatastoreType store,
+ final InstanceIdentifier<T> path) {
synchronized (txLock) {
ensureTransaction();
if (writeTx == null) {
public <T extends DataObject> void writeToTransaction(final LogicalDatastoreType store,
final InstanceIdentifier<T> path,
final T data,
- final boolean createParents){
+ final boolean createParents) {
synchronized (txLock) {
ensureTransaction();
if (writeTx == null) {
public <T extends DataObject> void mergeToTransaction(final LogicalDatastoreType store,
final InstanceIdentifier<T> path,
final T data,
- final boolean createParents){
+ final boolean createParents) {
synchronized (txLock) {
ensureTransaction();
if (writeTx == null) {
}
public <T extends DataObject> CheckedFuture<com.google.common.base.Optional<T>, ReadFailedException>
- readFromTransaction(final LogicalDatastoreType store,
- final InstanceIdentifier<T> path){
+ readFromTransaction(final LogicalDatastoreType store, final InstanceIdentifier<T> path) {
synchronized (txLock) {
ensureTransaction();
if (writeTx == null) {
public void onTransactionChainFailed(final TransactionChain<?, ?> chain,
final AsyncTransaction<?, ?> transaction, final Throwable cause) {
synchronized (txLock) {
- if (TransactionChainManagerStatus.WORKING == transactionChainManagerStatus &&
- chain.equals(this.transactionChain)) {
+ if (TransactionChainManagerStatus.WORKING == transactionChainManagerStatus
+ && chain.equals(this.transactionChain)) {
LOG.warn("Transaction chain failed, recreating chain due to ", cause);
closeTransactionChain();
createTxChain();
}
@GuardedBy("txLock")
- private void ensureTransaction() {
+ private void ensureTransaction() {
if (writeTx == null && TransactionChainManagerStatus.WORKING == transactionChainManagerStatus
- && transactionChain != null) {
- writeTx = transactionChain.newReadWriteTransaction();
+ && transactionChain != null) {
+ writeTx = transactionChain.newReadWriteTransaction();
}
}
import java.util.List;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
-import org.opendaylight.infrautils.diagstatus.DiagStatusService;
+import org.opendaylight.infrautils.ready.SystemReadyMonitor;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.openflowjava.protocol.spi.connection.SwitchConnectionProvider;
+import org.opendaylight.openflowplugin.api.diagstatus.OpenflowPluginDiagStatusProvider;
import org.opendaylight.openflowplugin.api.openflow.OpenFlowPluginProvider;
import org.opendaylight.openflowplugin.api.openflow.OpenFlowPluginProviderFactory;
import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
final List<SwitchConnectionProvider> switchConnectionProviders,
final ClusterSingletonServiceProvider singletonServiceProvider,
final MastershipChangeServiceManager mastershipChangeServiceManager,
- final DiagStatusService diagStatusService) {
+ final OpenflowPluginDiagStatusProvider ofPluginDiagstatusProvider,
+ final SystemReadyMonitor systemReadyMonitor) {
LOG.info("Initializing new OFP southbound.");
final OpenFlowPluginProvider openflowPluginProvider = new OpenFlowPluginProviderImpl(
configurationService,
singletonServiceProvider,
entityOwnershipService,
mastershipChangeServiceManager,
- diagStatusService);
+ ofPluginDiagstatusProvider,
+ systemReadyMonitor);
openflowPluginProvider.initialize();
return openflowPluginProvider;
import javax.management.ObjectName;
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
-import org.opendaylight.infrautils.diagstatus.DiagStatusService;
import org.opendaylight.infrautils.diagstatus.ServiceState;
+import org.opendaylight.infrautils.ready.SystemReadyListener;
+import org.opendaylight.infrautils.ready.SystemReadyMonitor;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.openflowjava.protocol.spi.connection.SwitchConnectionProvider;
+import org.opendaylight.openflowplugin.api.diagstatus.OpenflowPluginDiagStatusProvider;
import org.opendaylight.openflowplugin.api.openflow.OpenFlowPluginProvider;
import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionManager;
import org.opendaylight.openflowplugin.impl.device.DeviceManagerImpl;
import org.opendaylight.openflowplugin.impl.device.initialization.DeviceInitializerProvider;
import org.opendaylight.openflowplugin.impl.device.initialization.DeviceInitializerProviderFactory;
-import org.opendaylight.openflowplugin.impl.diagstatus.OpenflowPluginDiagStatusProvider;
import org.opendaylight.openflowplugin.impl.lifecycle.ContextChainHolderImpl;
import org.opendaylight.openflowplugin.impl.protocol.deserialization.DeserializerInjector;
import org.opendaylight.openflowplugin.impl.protocol.serialization.SerializerInjector;
public class OpenFlowPluginProviderImpl implements
OpenFlowPluginProvider,
- OpenFlowPluginExtensionRegistratorProvider {
+ OpenFlowPluginExtensionRegistratorProvider,
+ SystemReadyListener {
private static final Logger LOG = LoggerFactory.getLogger(OpenFlowPluginProviderImpl.class);
final ClusterSingletonServiceProvider singletonServiceProvider,
final EntityOwnershipService entityOwnershipService,
final MastershipChangeServiceManager mastershipChangeServiceManager,
- final DiagStatusService diagStatusService) {
+ final OpenflowPluginDiagStatusProvider openflowPluginStatusMonitor,
+ final SystemReadyMonitor systemReadyMonitor) {
this.switchConnectionProviders = switchConnectionProviders;
this.dataBroker = dataBroker;
this.rpcProviderRegistry = rpcProviderRegistry;
deviceInitializerProvider = DeviceInitializerProviderFactory.createDefaultProvider();
config = new OpenFlowProviderConfigImpl(configurationService);
this.mastershipChangeServiceManager = mastershipChangeServiceManager;
- openflowPluginStatusMonitor = new OpenflowPluginDiagStatusProvider(diagStatusService);
+ this.openflowPluginStatusMonitor = openflowPluginStatusMonitor;
+ systemReadyMonitor.registerListener(this);
+ LOG.debug("registered onSystemBootReady() listener for deferred startSwitchConnections()");
}
+ @Override
+ public void onSystemBootReady() {
+ LOG.debug("onSystemBootReady() received, starting the switch connections");
+ startSwitchConnections();
+ }
private void startSwitchConnections() {
Futures.addCallback(Futures.allAsList(switchConnectionProviders.stream().map(switchConnectionProvider -> {
// Inject OpenFlowPlugin custom serializers and deserializers into OpenFlowJava
if (config.isUseSingleLayerSerialization()) {
- SerializerInjector.injectSerializers(switchConnectionProvider);
+ SerializerInjector.injectSerializers(switchConnectionProvider,
+ switchConnectionProvider.getConfiguration().isGroupAddModEnabled());
DeserializerInjector.injectDeserializers(switchConnectionProvider);
} else {
DeserializerInjector.revertDeserializers(switchConnectionProvider);
LOG.warn("Some switchConnectionProviders failed to start.", throwable);
openflowPluginStatusMonitor.reportStatus(ServiceState.ERROR, "some switch connections failed to start");
}
- });
+ }, MoreExecutors.directExecutor());
}
private ListenableFuture<List<Boolean>> shutdownSwitchConnections() {
public void onFailure(@Nonnull final Throwable throwable) {
LOG.warn("Some switchConnectionProviders failed to shutdown.", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return listListenableFuture;
}
connectionManager.setDeviceDisconnectedHandler(contextChainHolder);
deviceManager.initialize();
- startSwitchConnections();
}
@Override
private OutboundQueueHandlerRegistration<OutboundQueueProvider> outboundQueueHandlerRegistration;
private HandshakeContext handshakeContext;
private DeviceInfo deviceInfo;
- private List<PortStatusMessage> portStatusMessages = new ArrayList<>();
+ private final List<PortStatusMessage> portStatusMessages = new ArrayList<>();
/**
* Constructor.
}
@Override
- public void setFeatures(final FeaturesReply featuresReply) {
- this.featuresReply = featuresReply;
+ public void setFeatures(final FeaturesReply newFeaturesReply) {
+ this.featuresReply = newFeaturesReply;
}
@Override
}
@Override
- public void setOutboundQueueHandleRegistration(OutboundQueueHandlerRegistration<OutboundQueueProvider>
- outboundQueueHandlerRegistration) {
- this.outboundQueueHandlerRegistration = outboundQueueHandlerRegistration;
+ public void setOutboundQueueHandleRegistration(
+ OutboundQueueHandlerRegistration<OutboundQueueProvider> newRegistration) {
+ this.outboundQueueHandlerRegistration = newRegistration;
}
private void unregisterOutboundQueue() {
return result;
}
- private class DeviceInfoImpl implements DeviceInfo {
+ private static class DeviceInfoImpl implements DeviceInfo {
private final NodeId nodeId;
private final KeyedInstanceIdentifier<Node, NodeKey> nodeII;
DeviceInfoImpl that = (DeviceInfoImpl) object;
- return (nodeId.equals(that.nodeId)
+ return nodeId.equals(that.nodeId)
&& nodeII.equals(that.nodeII)
&& version.equals(that.version)
- && datapathId.equals(that.datapathId));
+ && datapathId.equals(that.datapathId);
}
final HandshakeListener handshakeListener) {
HandshakeManagerImpl handshakeManager = new HandshakeManagerImpl(connectionAdapter,
OFConstants.VERSION_ORDER.get(0),
- OFConstants.VERSION_ORDER);
- handshakeManager.setUseVersionBitmap(BITMAP_NEGOTIATION_ENABLED);
- handshakeManager.setHandshakeListener(handshakeListener);
- handshakeManager.setErrorHandler(new ErrorHandlerSimpleImpl());
+ OFConstants.VERSION_ORDER, new ErrorHandlerSimpleImpl(), handshakeListener, BITMAP_NEGOTIATION_ENABLED);
return handshakeManager;
}
*/
package org.opendaylight.openflowplugin.impl.connection;
+import com.google.common.annotations.VisibleForTesting;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
import java.util.List;
import java.util.Objects;
import java.util.concurrent.Future;
private Short lastReceivedVersion;
private final List<Short> versionOrder;
-
private final ConnectionAdapter connectionAdapter;
private Short version;
- private ErrorHandler errorHandler;
+ private final ErrorHandler errorHandler;
- private Short highestVersion;
+ private final Short highestVersion;
private Long activeXid;
- private HandshakeListener handshakeListener;
+ private final HandshakeListener handshakeListener;
- private boolean useVersionBitmap;
+ private boolean useVersionBitmap; // not final just for unit test
/**
* Constructor.
* @param connectionAdapter connection adaptor for switch
* @param highestVersion highest openflow version
* @param versionOrder list of version in order for connection protocol negotiation
+ * @param errorHandler the ErrorHandler
+ * @param handshakeListener the HandshakeListener
+ * @param useVersionBitmap should use negotiation bit map
*/
- public HandshakeManagerImpl(ConnectionAdapter connectionAdapter, Short highestVersion, List<Short> versionOrder) {
+ public HandshakeManagerImpl(ConnectionAdapter connectionAdapter, Short highestVersion, List<Short> versionOrder,
+ ErrorHandler errorHandler, HandshakeListener handshakeListener, boolean useVersionBitmap) {
this.highestVersion = highestVersion;
this.versionOrder = versionOrder;
this.connectionAdapter = connectionAdapter;
- }
-
- @Override
- public void setHandshakeListener(HandshakeListener handshakeListener) {
+ this.errorHandler = errorHandler;
this.handshakeListener = handshakeListener;
+ this.useVersionBitmap = useVersionBitmap;
}
@Override
@Override
public void onSuccess(Void result) {
try {
- stepByStepVersionSubStep(remoteVersion, lastProposedVersion);
+ stepByStepVersionSubStep(remoteVersion);
} catch (Exception e) {
errorHandler.handleException(e);
handshakeListener.onHandshakeFailure();
LOG.info("hello sending seriously failed [{}]", nextHelloXid);
LOG.trace("detail of hello send problem", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
} else {
- stepByStepVersionSubStep(remoteVersion, lastProposedVersion);
+ stepByStepVersionSubStep(remoteVersion);
}
}
- private void stepByStepVersionSubStep(Short remoteVersion, Short lastProposedVersion) throws Exception {
+ private void stepByStepVersionSubStep(Short remoteVersion) throws Exception {
if (remoteVersion.equals(lastProposedVersion)) {
postHandshake(lastProposedVersion, getNextXid());
LOG.trace("ret - OK - switch answered with lastProposedVersion");
} else {
checkNegotiationStalling(remoteVersion);
- if (remoteVersion > (lastProposedVersion == null ? highestVersion : this.lastProposedVersion)) {
+ if (remoteVersion > (lastProposedVersion == null ? highestVersion : lastProposedVersion)) {
// wait for next version
LOG.trace("ret - wait");
} else {
public void onFailure(Throwable throwable) {
// NOOP
}
- });
+ }, MoreExecutors.directExecutor());
LOG.trace("next proposal [{}] with versionBitmap hooked ..", nexHelloXid);
} else {
LOG.trace("ret - DONE - versionBitmap");
*/
protected Short proposeCommonBitmapVersion(List<Elements> list) {
Short supportedHighestVersion = null;
- if ((null != list) && (0 != list.size())) {
+ if (null != list && 0 != list.size()) {
for (Elements element : list) {
List<Boolean> bitmap = element.getVersionBitmap();
// check for version bitmap
resultFtr.cancel(false);
handshakeListener.onHandshakeFailure();
}
- });
+ }, MoreExecutors.directExecutor());
LOG.trace("sending hello message [{}] - result hooked ..", helloXid);
return resultFtr;
}
connectionAdapter.getRemoteAddress(), throwable.getMessage());
LOG.trace("DETAIL of sending of hello failure:", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
LOG.debug("future features [{}] hooked ..", xid);
}
- @Override
- public void setUseVersionBitmap(boolean useVersionBitmap) {
+ /**
+ * Method for unit testing, only.
+ * This method is not thread safe and can only safely be used from a test.
+ */
+ @VisibleForTesting
+ @SuppressFBWarnings("IS2_INCONSISTENT_SYNC") // because shake() is synchronized
+ void setUseVersionBitmap(boolean useVersionBitmap) {
this.useVersionBitmap = useVersionBitmap;
}
- @Override
- public void setErrorHandler(ErrorHandler errorHandler) {
- this.errorHandler = errorHandler;
- }
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import javax.annotation.Nullable;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionContext;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionStatus;
// fire barrier in order to sweep all handshake and posthandshake messages before continue
final ListenableFuture<RpcResult<BarrierOutput>> barrier = fireBarrier(version, 0L);
- Futures.addCallback(barrier, addBarrierCallback());
+ Futures.addCallback(barrier, addBarrierCallback(), MoreExecutors.directExecutor());
}
private FutureCallback<RpcResult<BarrierOutput>> addBarrierCallback() {
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import io.netty.util.HashedWheelTimer;
import java.util.Collection;
import java.util.Collections;
public <T extends DataObject> void addDeleteToTxChain(final LogicalDatastoreType store,
final InstanceIdentifier<T> path) {
if (initialized.get()) {
- transactionChainManager.addDeleteOperationTotTxChain(store, path);
+ transactionChainManager.addDeleteOperationToTxChain(store, path);
}
}
public void processReply(final OfHeader ofHeader) {
messageSpy.spyMessage(
ofHeader.getImplementedInterface(),
- (ofHeader instanceof Error)
+ ofHeader instanceof Error
? MessageSpy.StatisticsGroup.FROM_SWITCH_PUBLISHED_FAILURE
: MessageSpy.StatisticsGroup.FROM_SWITCH_PUBLISHED_SUCCESS);
}
public void processReply(final Xid xid, final List<? extends OfHeader> ofHeaderList) {
ofHeaderList.forEach(header -> messageSpy.spyMessage(
header.getImplementedInterface(),
- (header instanceof Error)
+ header instanceof Error
? MessageSpy.StatisticsGroup.FROM_SWITCH_PUBLISHED_FAILURE
: MessageSpy.StatisticsGroup.FROM_SWITCH_PUBLISHED_SUCCESS));
}
portStatusMessage.getPortNo(),
OpenflowVersion.get(deviceInfo.getVersion()))));
- if (PortReason.OFPPRADD.equals(portStatusMessage.getReason())
- || PortReason.OFPPRMODIFY.equals(portStatusMessage.getReason())) {
- // because of ADD status node connector has to be created
- writeToTransaction(LogicalDatastoreType.OPERATIONAL, iiToNodeConnector, new NodeConnectorBuilder()
- .setKey(iiToNodeConnector.getKey())
- .addAugmentation(FlowCapableNodeConnectorStatisticsData.class, new
- FlowCapableNodeConnectorStatisticsDataBuilder().build())
- .addAugmentation(FlowCapableNodeConnector.class, flowCapableNodeConnector)
- .build());
- } else if (PortReason.OFPPRDELETE.equals(portStatusMessage.getReason())) {
+ writeToTransaction(LogicalDatastoreType.OPERATIONAL, iiToNodeConnector, new NodeConnectorBuilder()
+ .setKey(iiToNodeConnector.getKey())
+ .addAugmentation(FlowCapableNodeConnectorStatisticsData.class, new
+ FlowCapableNodeConnectorStatisticsDataBuilder().build())
+ .addAugmentation(FlowCapableNodeConnector.class, flowCapableNodeConnector)
+ .build());
+ submitTransaction();
+ if (PortReason.OFPPRDELETE.equals(portStatusMessage.getReason())) {
addDeleteToTxChain(LogicalDatastoreType.OPERATIONAL, iiToNodeConnector);
+ submitTransaction();
}
}
LOG.trace("notification offer failed..", throwable);
packetInLimiter.releasePermit();
}
- });
+ }, MoreExecutors.directExecutor());
}
@Override
}
@Override
- public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher contextChainMastershipWatcher) {
- this.contextChainMastershipWatcher = contextChainMastershipWatcher;
+ public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher newWatcher) {
+ this.contextChainMastershipWatcher = newWatcher;
}
@Nonnull
transactionChainManager.close();
transactionChainManager = null;
}
- });
+ }, MoreExecutors.directExecutor());
}
requestContexts.forEach(requestContext -> RequestContextUtil
// TODO: exception handling should be fixed by using custom checked exception, never RuntimeExceptions
@Override
- @SuppressWarnings({"checkstyle:IllegalCatch", "checkstyle:AvoidHidingCauseExceptionCheck"})
+ @SuppressWarnings({"checkstyle:IllegalCatch"})
public void instantiateServiceInstance() {
lazyTransactionManagerInitialization();
submitTransaction();
} catch (final Exception ex) {
throw new RuntimeException(String.format("Error processing port status messages from device %s: %s",
- deviceInfo.toString(),
- ex.toString()));
+ deviceInfo.toString(), ex.toString()), ex);
}
final Optional<AbstractDeviceInitializer> initializer = deviceInitializerProvider
} catch (TimeoutException ex) {
initialize.cancel(true);
throw new RuntimeException(String.format("Failed to initialize device %s in %ss: %s",
- deviceInfo.toString(),
- String.valueOf(DEVICE_INIT_TIMEOUT / 1000),
- ex.toString()));
+ deviceInfo.toString(), String.valueOf(DEVICE_INIT_TIMEOUT / 1000), ex.toString()), ex);
} catch (ExecutionException | InterruptedException ex) {
- throw new RuntimeException(String.format("Device %s cannot be initialized: %s",
- deviceInfo.toString(),
- ex.toString()));
+ throw new RuntimeException(
+ String.format("Device %s cannot be initialized: %s", deviceInfo.toString(), ex.toString()), ex);
}
} else {
throw new RuntimeException(String.format("Unsupported version %s for device %s",
final ListenableFuture<List<com.google.common.base.Optional<FlowCapableNode>>> deviceFlowRegistryFill =
getDeviceFlowRegistry().fill();
Futures.addCallback(deviceFlowRegistryFill,
- new DeviceFlowRegistryCallback(deviceFlowRegistryFill, contextChainMastershipWatcher));
+ new DeviceFlowRegistryCallback(deviceFlowRegistryFill, contextChainMastershipWatcher),
+ MoreExecutors.directExecutor());
}
@VisibleForTesting
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.List;
import java.util.concurrent.Future;
import javax.annotation.Nonnull;
LOG.warn("Error occurred in preparation node {} for protocol 1.0", deviceInfo);
LOG.trace("Error for node {} : ", deviceInfo, throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return Futures.transform(future, new Function<Boolean, Void>() {
@Nullable
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
return null;
}
});
- });
+ }, MoreExecutors.directExecutor());
}
LOG.warn("Request of type {} for static info of node {} failed.",
type, deviceContext.getDeviceInfo());
}
- });
+ }, MoreExecutors.directExecutor());
}
/**
import java.util.stream.Collectors;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipChange;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipListenerRegistration;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipChange;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipListenerRegistration;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.openflowplugin.api.openflow.OFPManager;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionContext;
import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.FeaturesReply;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.mdsal.core.general.entity.rev150930.Entity;
import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.openflowplugin.rf.state.rev170713.ResultState;
import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
-import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@Override
public void ownershipChanged(EntityOwnershipChange entityOwnershipChange) {
- if (entityOwnershipChange.hasOwner()) {
+ if (entityOwnershipChange.getState().hasOwner()) {
return;
}
- final String entityName = getEntityNameFromOwnershipChange(entityOwnershipChange);
+ final String entityName = entityOwnershipChange
+ .getEntity()
+ .getIdentifier()
+ .firstKeyOf(Entity.class)
+ .getName();
if (Objects.nonNull(entityName)) {
LOG.debug("Entity {} has no owner", entityName);
- final NodeId nodeId = new NodeId(entityName);
-
try {
- final KeyedInstanceIdentifier<Node, NodeKey> nodeInstanceIdentifier = DeviceStateUtil
- .createNodeInstanceIdentifier(nodeId);
-
+ //TODO:Remove notifications
+ final KeyedInstanceIdentifier<Node, NodeKey> nodeInstanceIdentifier =
+ DeviceStateUtil.createNodeInstanceIdentifier(new NodeId(entityName));
deviceManager.sendNodeRemovedNotification(nodeInstanceIdentifier);
- LOG.info("Try to remove device {} from operational DS", nodeId);
+ LOG.info("Try to remove device {} from operational DS", entityName);
deviceManager.removeDeviceFromOperationalDS(nodeInstanceIdentifier)
.get(REMOVE_DEVICE_FROM_DS_TIMEOUT, TimeUnit.MILLISECONDS);
- LOG.info("Removing device from operational DS {} was successful", nodeId);
+ LOG.info("Removing device from operational DS {} was successful", entityName);
} catch (TimeoutException | ExecutionException | NullPointerException | InterruptedException e) {
- LOG.warn("Not able to remove device {} from operational DS. ", nodeId, e);
+ LOG.warn("Not able to remove device {} from operational DS. ", entityName, e);
}
}
}
.isMastered(ContextChainMastershipState.CHECK, false)).isPresent();
}
- private String getEntityNameFromOwnershipChange(final EntityOwnershipChange entityOwnershipChange) {
- final YangInstanceIdentifier.NodeIdentifierWithPredicates lastIdArgument
- = (YangInstanceIdentifier.NodeIdentifierWithPredicates) entityOwnershipChange.getEntity().getId()
- .getLastPathArgument();
-
- return lastIdArgument.getKeyValues().values().iterator().next().toString();
- }
-
@Override
public void onDeviceRemoved(final DeviceInfo deviceInfo) {
contextChainMap.remove(deviceInfo);
deviceRemovedHandlers.add(deviceRemovedHandler);
}
- private void changeMastershipState(final ContextChainState contextChainState) {
+ private void changeMastershipState(final ContextChainState newContextChainState) {
if (ContextChainState.CLOSED.equals(this.contextChainState.get())) {
return;
}
boolean propagate = ContextChainState.UNDEFINED.equals(this.contextChainState.get());
- this.contextChainState.set(contextChainState);
+ this.contextChainState.set(newContextChainState);
if (propagate) {
contexts.forEach(context -> {
if (context.map(ContextChainStateListener.class::isInstance)) {
- context.map(ContextChainStateListener.class::cast).onStateAcquired(contextChainState);
+ context.map(ContextChainStateListener.class::cast).onStateAcquired(newContextChainState);
}
});
}
/**
* Injects message serializers into provided
* {@link org.opendaylight.openflowjava.protocol.api.extensibility.SerializerExtensionProvider}.
- *
* @param provider OpenflowJava serializer extension provider
+ * @param isGroupAddModEnabled config to enale/disable GroupAddMod Message
*/
- static void injectSerializers(final SerializerExtensionProvider provider) {
+ static void injectSerializers(final SerializerExtensionProvider provider, final boolean isGroupAddModEnabled) {
// Inject new message serializers here using injector created by createInjector method
final Function<Class<?>, Consumer<OFSerializer<? extends OfHeader>>> injector =
createInjector(provider, EncodeConstants.OF13_VERSION_ID);
injector.apply(FlowMessage.class).accept(new FlowMessageSerializer());
injector.apply(MeterMessage.class).accept(new MeterMessageSerializer());
injector.apply(PortMessage.class).accept(new PortMessageSerializer());
- injector.apply(GroupMessage.class).accept(new GroupMessageSerializer());
+ injector.apply(GroupMessage.class).accept(new GroupMessageSerializer(isGroupAddModEnabled));
injector.apply(MultipartRequest.class).accept(new MultipartRequestMessageSerializer());
injector.apply(AsyncConfigMessage.class).accept(new AsyncConfigMessageSerializer());
}
/**
* Injects serializers into provided
* {@link org.opendaylight.openflowjava.protocol.api.extensibility.SerializerExtensionProvider}.
- *
* @param provider OpenflowJava serializer extension provider
+ * @param isGroupAddModEnabled config to enale/disable GroupAddMod Message
*/
- public static void injectSerializers(final SerializerExtensionProvider provider) {
+ public static void injectSerializers(final SerializerExtensionProvider provider,
+ final boolean isGroupAddModEnabled) {
// Inject new serializers here
MatchSerializerInjector.injectSerializers(provider);
ActionSerializerInjector.injectSerializers(provider);
InstructionSerializerInjector.injectSerializers(provider);
MultipartSerializerInjector.injectSerializers(provider);
- MessageSerializerInjector.injectSerializers(provider);
+ MessageSerializerInjector.injectSerializers(provider, isGroupAddModEnabled);
}
}
* OF protocol versions: 1.3.
*/
public class GroupMessageSerializer extends AbstractMessageSerializer<GroupMessage> implements
- SerializerRegistryInjector {
+ SerializerRegistryInjector {
private static final byte PADDING_IN_GROUP_MOD_MESSAGE = 1;
private static final byte PADDING_IN_BUCKET = 4;
+ private static final int OFPGC_ADD_OR_MOD = 32768;
+ private final boolean isGroupAddModEnabled;
private static final Comparator<Bucket> COMPARATOR = (bucket1, bucket2) -> {
if (bucket1.getBucketId() == null || bucket2.getBucketId() == null) {
private SerializerRegistry registry;
+ public GroupMessageSerializer(boolean isGroupAddModEnabled) {
+ this.isGroupAddModEnabled = isGroupAddModEnabled;
+ }
+
@Override
public void serialize(GroupMessage message, ByteBuf outBuffer) {
final int index = outBuffer.writerIndex();
super.serialize(message, outBuffer);
- outBuffer.writeShort(message.getCommand().getIntValue());
+ if (isGroupAddModEnabled) {
+ if (message.getCommand().equals(GroupModCommand.OFPGCADD)
+ || message.getCommand().equals(GroupModCommand.OFPGCMODIFY)) {
+ outBuffer.writeShort(OFPGC_ADD_OR_MOD);
+ } else {
+ outBuffer.writeShort(message.getCommand().getIntValue());
+ }
+ } else {
+ outBuffer.writeShort(message.getCommand().getIntValue());
+ }
outBuffer.writeByte(message.getGroupType().getIntValue());
outBuffer.writeZero(PADDING_IN_GROUP_MOD_MESSAGE);
outBuffer.writeInt(message.getGroupId().getValue().intValue());
outBuffer.setShort(bucketIndex, outBuffer.writerIndex() - bucketIndex);
}));
-
outBuffer.setShort(index + 2, outBuffer.writerIndex() - index);
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
// Even when read operation failed, close the transaction
transaction.close();
}
- });
+ }, MoreExecutors.directExecutor());
return future;
}
}
@Override
- public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher contextChainMastershipWatcher) {
- this.contextChainMastershipWatcher = contextChainMastershipWatcher;
+ public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher newWatcher) {
+ this.contextChainMastershipWatcher = newWatcher;
}
@Override
}
@Override
- public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher contextChainMastershipWatcher) {
- this.contextChainMastershipWatcher = contextChainMastershipWatcher;
+ public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher newWatcher) {
+ this.contextChainMastershipWatcher = newWatcher;
}
@Override
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.math.BigInteger;
import java.util.Collection;
LOG.info("onFailure - getGenerationIdFromDevice RPC error {}", throwable);
finalFuture.setException(new ExecutionException(throwable));
}
- });
+ }, MoreExecutors.directExecutor());
return finalFuture;
}
getDeviceInfo().getNodeId(), ofpRole, throwable);
finalFuture.setException(throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return finalFuture;
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.ArrayList;
import java.util.List;
}
}
- Futures.addCallback(multipartFuture, new CallBackImpl());
+ Futures.addCallback(multipartFuture, new CallBackImpl(), MoreExecutors.directExecutor());
return finalFuture;
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.ArrayList;
import java.util.Collections;
RpcResultBuilder<O> rpcResultBuilder = RpcResultBuilder.failed();
finalFuture.set(rpcResultBuilder.build());
}
- });
+ }, MoreExecutors.directExecutor());
return finalFuture;
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.math.BigInteger;
import java.util.ArrayList;
}
}
- Futures.addCallback(multipartFuture, new CallBackImpl());
+ Futures.addCallback(multipartFuture, new CallBackImpl(), MoreExecutors.directExecutor());
return finalFuture;
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.ArrayList;
import java.util.List;
RpcResultBuilder<Void> rpcResultBuilder = RpcResultBuilder.failed();
result.set(rpcResultBuilder.build());
}
- });
+ }, MoreExecutors.directExecutor());
return result;
}
}
\ No newline at end of file
import com.google.common.base.Preconditions;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Future;
for (int i = 0; i < batchJobsChain.size(); i++) {
batchJob = batchJobsChain.get(i);
// wire actual job with chain
- firedJobs.add(Futures.transformAsync(chainSummaryResult, batchJob.getStepFunction()));
+ firedJobs.add(Futures.transformAsync(chainSummaryResult, batchJob.getStepFunction(),
+ MoreExecutors.directExecutor()));
// if barrier after actual job is needed or it is the last job -> merge fired job results with chain result
if ((batchJob.getPlanStep().isBarrierAfter()) || (i == batchJobsChain.size() - 1)) {
firedJobs.add(0, chainSummaryResult);
*/
package org.opendaylight.openflowplugin.impl.services.sal;
-import com.google.common.annotations.VisibleForTesting;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.ArrayList;
import java.util.List;
import org.opendaylight.openflowplugin.impl.util.ErrorUtil;
import org.opendaylight.openflowplugin.impl.util.FlowCreatorUtil;
import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.ConvertorExecutor;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.Table;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.AddFlowInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.UpdateFlowOutput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.flow.update.OriginalFlow;
import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.flow.update.UpdatedFlow;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.FlowModInputBuilder;
-import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
import org.opendaylight.yangtools.yang.common.RpcError;
import org.opendaylight.yangtools.yang.common.RpcResult;
import org.opendaylight.yangtools.yang.common.RpcResultBuilder;
if (flowAddMessage.canUseSingleLayerSerialization()) {
future = flowAddMessage.handleServiceCall(input);
- Futures.addCallback(future, new AddFlowCallback(input, flowRegistryKey));
+ Futures.addCallback(future, new AddFlowCallback(input, flowRegistryKey), MoreExecutors.directExecutor());
} else {
future = flowAdd.processFlowModInputBuilders(flowAdd.toFlowModInputs(input));
- Futures.addCallback(future, new AddFlowCallback(input, flowRegistryKey));
+ Futures.addCallback(future, new AddFlowCallback(input, flowRegistryKey), MoreExecutors.directExecutor());
}
return future;
if (flowRemoveMessage.canUseSingleLayerSerialization()) {
future = flowRemoveMessage.handleServiceCall(input);
- Futures.addCallback(future, new RemoveFlowCallback(input));
+ Futures.addCallback(future, new RemoveFlowCallback(input), MoreExecutors.directExecutor());
} else {
future = flowRemove.processFlowModInputBuilders(flowRemove.toFlowModInputs(input));
- Futures.addCallback(future, new RemoveFlowCallback(input));
+ Futures.addCallback(future, new RemoveFlowCallback(input), MoreExecutors.directExecutor());
}
return future;
RpcResultBuilder<UpdateFlowOutput> rpcResultBuilder = RpcResultBuilder.failed();
objectSettableFuture.set(rpcResultBuilder.build());
}
- });
+ }, MoreExecutors.directExecutor());
future = objectSettableFuture;
} else {
future = flowUpdate.processFlowModInputBuilders(allFlowMods);
}
- Futures.addCallback(future, new UpdateFlowCallback(input));
+ Futures.addCallback(future, new UpdateFlowCallback(input), MoreExecutors.directExecutor());
return future;
}
- @VisibleForTesting
- private static KeyedInstanceIdentifier<Flow, FlowKey> createFlowPath(
- FlowDescriptor flowDescriptor,
- KeyedInstanceIdentifier<Node, NodeKey> nodePath) {
- return nodePath.augmentation(FlowCapableNode.class)
- .child(Table.class, flowDescriptor.getTableKey())
- .child(Flow.class, new FlowKey(flowDescriptor.getFlowId()));
- }
-
private final class AddFlowCallback implements FutureCallback<RpcResult<AddFlowOutput>> {
private final AddFlowInput input;
private final FlowRegistryKey flowRegistryKey;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.concurrent.Future;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceContext;
import org.opendaylight.openflowplugin.api.openflow.device.RequestContextStack;
import org.opendaylight.openflowplugin.impl.services.singlelayer.SingleLayerGroupService;
import org.opendaylight.openflowplugin.impl.util.ErrorUtil;
import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.ConvertorExecutor;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.AddGroupInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.AddGroupOutput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.RemoveGroupInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.UpdateGroupInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.UpdateGroupOutput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.Group;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.GroupId;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.groups.GroupKey;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
-import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
import org.opendaylight.yangtools.yang.common.RpcResult;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
input.getGroupId().getValue(),
throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
LOG.warn("Service call for updating group={} failed, reason: {}",
input.getOriginalGroup().getGroupId(), throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
LOG.warn("Service call for removing group={} failed, reason: {}",
input.getGroupId().getValue(), throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
- private static KeyedInstanceIdentifier<org.opendaylight.yang.gen.v1.urn
- .opendaylight.group.types.rev131018.groups.Group, GroupKey>
- createGroupPath(final GroupId groupId, final KeyedInstanceIdentifier<Node, NodeKey> nodePath) {
- return nodePath.augmentation(FlowCapableNode.class).child(org.opendaylight.yang.gen.v1.urn
- .opendaylight.group.types.rev131018.groups.Group.class, new GroupKey(groupId));
- }
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.concurrent.Future;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceContext;
import org.opendaylight.openflowplugin.api.openflow.device.RequestContextStack;
import org.opendaylight.openflowplugin.impl.services.singlelayer.SingleLayerMeterService;
import org.opendaylight.openflowplugin.impl.util.ErrorUtil;
import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.ConvertorExecutor;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.meters.MeterKey;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.AddMeterInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.AddMeterOutput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.RemoveMeterInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.UpdateMeterInput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.UpdateMeterOutput;
import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.Meter;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.MeterId;
-import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
import org.opendaylight.yangtools.yang.common.RpcResult;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public void onFailure(Throwable throwable) {
LOG.warn("Service call for adding meter={} failed, reason: {}", input.getMeterId(), throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
LOG.warn("Service call for updating meter={} failed, reason: {}",
input.getOriginalMeter().getMeterId(),throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
public void onFailure(Throwable throwable) {
LOG.warn("Service call for removing meter={} failed, reason: {}",input.getMeterId(),throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return resultFuture;
}
- private static KeyedInstanceIdentifier<org.opendaylight.yang.gen.v1.urn
- .opendaylight.flow.inventory.rev130819.meters.Meter, MeterKey> createMeterPath(
- final MeterId meterId,
- final KeyedInstanceIdentifier<Node, NodeKey> nodePath) {
- return nodePath.augmentation(FlowCapableNode.class)
- .child(org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.meters.Meter.class,
- new MeterKey(meterId));
- }
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.concurrent.Future;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionContext.CONNECTION_STATE;
final Future<RpcResult<SetRoleOutput>> submitRoleFuture =
roleService.submitRoleChange(role, getVersion(), nextGenerationId);
return JdkFutureAdapters.listenInPoolThread(submitRoleFuture);
- });
+ }, MoreExecutors.directExecutor());
}
private static BigInteger getNextGenerationId(final BigInteger generationId) {
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.util.List;
import java.util.concurrent.Future;
future.set(RpcResultBuilder.<SendExperimenterMpRequestOutput>failed()
.withError(ErrorType.RPC, "Future error", throwable).build());
}
- });
+ }, MoreExecutors.directExecutor());
return future;
}
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import com.google.common.util.concurrent.SettableFuture;
import java.math.BigInteger;
import java.util.List;
finalFuture.set(RpcResultBuilder.<UpdateTableOutput>failed()
.withError(ErrorType.RPC, "Future error", throwable).build());
}
- });
+ }, MoreExecutors.directExecutor());
return finalFuture;
}
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.ListeningExecutorService;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
private final long maximumPollingDelay;
private final boolean isUsingReconciliationFramework;
private final AtomicBoolean schedulingEnabled = new AtomicBoolean(true);
- private final AtomicReference<ListenableFuture<Boolean>> lastDataGathering = new AtomicReference<>();
- private final AtomicReference<StatisticsPollingService> statisticsPollingService = new AtomicReference<>();
+ private final AtomicReference<ListenableFuture<Boolean>> lastDataGatheringRef = new AtomicReference<>();
+ private final AtomicReference<StatisticsPollingService> statisticsPollingServiceRef = new AtomicReference<>();
private List<MultipartType> collectingStatType;
private StatisticsGatheringService<T> statisticsGatheringService;
private StatisticsGatheringOnTheFlyService<T> statisticsGatheringOnTheFlyService;
}
@Override
- public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher contextChainMastershipWatcher) {
- this.contextChainMastershipWatcher = contextChainMastershipWatcher;
+ public void registerMastershipWatcher(@Nonnull final ContextChainMastershipWatcher newWatcher) {
+ this.contextChainMastershipWatcher = newWatcher;
}
@Override
}
collectingStatType = ImmutableList.copyOf(statListForCollecting);
- Futures.addCallback(gatherDynamicData(), new InitialSubmitCallback());
+ Futures.addCallback(gatherDynamicData(), new InitialSubmitCallback(), MoreExecutors.directExecutor());
}
@Override
requestContexts.forEach(requestContext -> RequestContextUtil
.closeRequestContextWithRpcError(requestContext, CONNECTION_CLOSED));
}
- });
+ }, MoreExecutors.directExecutor());
}
private ListenableFuture<Boolean> gatherDynamicData() {
return Futures.immediateFuture(Boolean.TRUE);
}
- return this.lastDataGathering.updateAndGet(future -> {
+ return this.lastDataGatheringRef.updateAndGet(future -> {
// write start timestamp to state snapshot container
StatisticsGatheringUtils.markDeviceStateSnapshotStart(deviceInfo, deviceContext);
// build statistics gathering future
final ListenableFuture<Boolean> newDataGathering = collectingStatType.stream()
.reduce(lastDataGathering, this::statChainFuture,
- (listenableFuture, asyn) -> Futures.transformAsync(listenableFuture, result -> asyn));
+ (listenableFuture, asyn) -> Futures.transformAsync(listenableFuture, result -> asyn,
+ MoreExecutors.directExecutor()));
// write end timestamp to state snapshot container
Futures.addCallback(newDataGathering, new FutureCallback<Boolean>() {
StatisticsGatheringUtils.markDeviceStateSnapshotEnd(deviceInfo, deviceContext, false);
}
}
- });
+ }, MoreExecutors.directExecutor());
return newDataGathering;
});
getDeviceInfo(), multipartType, deviceContext, deviceContext, convertorExecutor,
statisticsWriterProvider, executorService) : Futures
.immediateFuture(Boolean.FALSE);
- });
+ }, MoreExecutors.directExecutor());
}
private void startGatheringData() {
schedulingEnabled.set(true);
statisticsPollingService.startAsync();
- this.statisticsPollingService.set(statisticsPollingService);
+ this.statisticsPollingServiceRef.set(statisticsPollingService);
}
private ListenableFuture<Void> stopGatheringData() {
LOG.info("Stopping running statistics gathering for node {}", deviceInfo);
cancelLastDataGathering();
- return Optional.ofNullable(statisticsPollingService.getAndSet(null)).map(StatisticsPollingService::stop)
+ return Optional.ofNullable(statisticsPollingServiceRef.getAndSet(null)).map(StatisticsPollingService::stop)
.orElseGet(() -> Futures.immediateFuture(null));
}
private void cancelLastDataGathering() {
- final ListenableFuture<Boolean> future = lastDataGathering.getAndSet(null);
+ final ListenableFuture<Boolean> future = lastDataGatheringRef.getAndSet(null);
if (Objects.nonNull(future) && !future.isDone() && !future.isCancelled()) {
future.cancel(true);
import com.google.common.base.Function;
import com.google.common.base.Optional;
+import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.ListeningExecutorService;
+import com.google.common.util.concurrent.MoreExecutors;
import java.text.SimpleDateFormat;
import java.util.Collections;
import java.util.Date;
import java.util.stream.Collectors;
import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
+import org.opendaylight.controller.md.sal.common.api.data.ReadFailedException;
import org.opendaylight.controller.md.sal.common.api.data.TransactionChainClosedException;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceInfo;
import org.opendaylight.openflowplugin.api.openflow.device.DeviceRegistry;
rpcResultIsNull ? "" : rpcResult.getErrors());
}
return false;
- }));
+ }), MoreExecutors.directExecutor());
}
private static boolean processStatistics(final MultipartType type, final List<? extends DataContainer> statistics,
return;
}
- final ReadOnlyTransaction readTx = txFacade.getReadTransaction();
+ final CheckedFuture<Optional<FlowCapableNode>, ReadFailedException> future;
+ try (ReadOnlyTransaction readTx = txFacade.getReadTransaction()) {
+ future = readTx.read(LogicalDatastoreType.OPERATIONAL, instanceIdentifier);
+ }
try {
- Futures.transform(Futures.catchingAsync(readTx.read(LogicalDatastoreType.OPERATIONAL, instanceIdentifier),
- Throwable.class, throwable -> {
- // we wish to close readTx for fallBack
- readTx.close();
- return Futures.immediateFailedFuture(throwable);
- }), (Function<Optional<FlowCapableNode>, Void>) flowCapNodeOpt -> {
+ Futures.transform(Futures.catchingAsync(future, Throwable.class, throwable -> {
+ return Futures.immediateFailedFuture(throwable);
+ }), (Function<Optional<FlowCapableNode>, Void>) flowCapNodeOpt -> {
// we have to read actual tables with all information before we set empty Flow list,
// merge is expensive and not applicable for lists
if (flowCapNodeOpt != null && flowCapNodeOpt.isPresent()) {
txFacade.writeToTransaction(LogicalDatastoreType.OPERATIONAL, iiToTable, table);
}
}
- readTx.close();
return null;
}).get();
} catch (InterruptedException | ExecutionException ex) {
package org.opendaylight.openflowplugin.impl.statistics.ofpspecific;
+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
delta = System.nanoTime();
}
+ @SuppressFBWarnings("VO_VOLATILE_INCREMENT") // counter++ is volatile, but this is synchronized, so OK
public synchronized void markEnd() {
if (0 == delta) {
return;
if (delta > maximum) {
maximum = delta;
}
- if (average > 0 && delta > (average * 1.8)) {
+ if (average > 0 && delta > average * 1.8) {
summary += average;
} else {
summary += delta;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.List;
import java.util.concurrent.atomic.AtomicLong;
LOG.debug("compatibility callback crashed - NOT emitting notification: {}",
input.getClass().getSimpleName(), throwable);
}
- });
+ }, MoreExecutors.directExecutor());
return RpcResultBuilder.<O>success(buildTxCapableResult(emulatedTxId)).buildFuture();
}
return new TranslatorLibraryImpl(translators);
}
- private final class TranslatorLibraryImpl implements TranslatorLibrary {
+ private static final class TranslatorLibraryImpl implements TranslatorLibrary {
private final Map<TranslatorKey, MessageTranslator<?, ?>> translators;
TranslatorLibraryImpl(final Map<TranslatorKey, MessageTranslator<?, ?>> translators) {
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import javax.annotation.Nullable;
import org.apache.commons.lang3.tuple.MutablePair;
import org.apache.commons.lang3.tuple.Pair;
resultPair.setLeft(interInput);
final SendBarrierInput barrierInput = createSendBarrierInput(nodeRef);
return JdkFutureAdapters.listenInPoolThread(transactionService.sendBarrier(barrierInput));
- });
+ }, MoreExecutors.directExecutor());
// store barrier result and return initiated pair
final ListenableFuture<Pair<RpcResult<T>, RpcResult<Void>>> compositeResult = Futures.transform(
barrierResult, new Function<RpcResult<Void>, Pair<RpcResult<T>, RpcResult<Void>>>() {
* @return batch flow operation output of given type containing list of flow-ids and corresponding success flag
*/
private static <T extends BatchFlowOutputListGrouping> RpcResultBuilder<T> createCumulativeRpcResult(
- final @Nullable RpcResult<List<BatchFailedFlowsOutput>> batchFlowsCumulativeResult,
+ final RpcResult<List<BatchFailedFlowsOutput>> batchFlowsCumulativeResult,
final T batchOutput) {
final RpcResultBuilder<T> resultBld;
if (batchFlowsCumulativeResult.isSuccessful()) {
for (org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.ActionType supportedActions
: actionsSupported) {
long supportActionBitmap = 0;
- supportActionBitmap |= supportedActions.isOFPATOUTPUT() ? (1) : 0;
- supportActionBitmap |= supportedActions.isOFPATCOPYTTLOUT() ? (1 << 11) : 0;
- supportActionBitmap |= supportedActions.isOFPATCOPYTTLIN() ? (1 << 12) : 0;
- supportActionBitmap |= supportedActions.isOFPATSETMPLSTTL() ? (1 << 15) : 0;
- supportActionBitmap |= supportedActions.isOFPATDECMPLSTTL() ? (1 << 16) : 0;
- supportActionBitmap |= supportedActions.isOFPATPUSHVLAN() ? (1 << 17) : 0;
- supportActionBitmap |= supportedActions.isOFPATPOPVLAN() ? (1 << 18) : 0;
- supportActionBitmap |= supportedActions.isOFPATPUSHMPLS() ? (1 << 19) : 0;
- supportActionBitmap |= supportedActions.isOFPATPOPMPLS() ? (1 << 20) : 0;
- supportActionBitmap |= supportedActions.isOFPATSETQUEUE() ? (1 << 21) : 0;
- supportActionBitmap |= supportedActions.isOFPATGROUP() ? (1 << 22) : 0;
- supportActionBitmap |= supportedActions.isOFPATSETNWTTL() ? (1 << 23) : 0;
- supportActionBitmap |= supportedActions.isOFPATDECNWTTL() ? (1 << 24) : 0;
- supportActionBitmap |= supportedActions.isOFPATSETFIELD() ? (1 << 25) : 0;
- supportActionBitmap |= supportedActions.isOFPATPUSHPBB() ? (1 << 26) : 0;
- supportActionBitmap |= supportedActions.isOFPATPOPPBB() ? (1 << 27) : 0;
+ supportActionBitmap |= supportedActions.isOFPATOUTPUT() ? 1 : 0;
+ supportActionBitmap |= supportedActions.isOFPATCOPYTTLOUT() ? 1 << 11 : 0;
+ supportActionBitmap |= supportedActions.isOFPATCOPYTTLIN() ? 1 << 12 : 0;
+ supportActionBitmap |= supportedActions.isOFPATSETMPLSTTL() ? 1 << 15 : 0;
+ supportActionBitmap |= supportedActions.isOFPATDECMPLSTTL() ? 1 << 16 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPUSHVLAN() ? 1 << 17 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPOPVLAN() ? 1 << 18 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPUSHMPLS() ? 1 << 19 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPOPMPLS() ? 1 << 20 : 0;
+ supportActionBitmap |= supportedActions.isOFPATSETQUEUE() ? 1 << 21 : 0;
+ supportActionBitmap |= supportedActions.isOFPATGROUP() ? 1 << 22 : 0;
+ supportActionBitmap |= supportedActions.isOFPATSETNWTTL() ? 1 << 23 : 0;
+ supportActionBitmap |= supportedActions.isOFPATDECNWTTL() ? 1 << 24 : 0;
+ supportActionBitmap |= supportedActions.isOFPATSETFIELD() ? 1 << 25 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPUSHPBB() ? 1 << 26 : 0;
+ supportActionBitmap |= supportedActions.isOFPATPOPPBB() ? 1 << 27 : 0;
supportActionByGroups.add(supportActionBitmap);
}
return supportActionByGroups;
* @return batch group operation output of given type containing list of group-ids and corresponding success flag
*/
private static <T extends BatchGroupOutputListGrouping> RpcResultBuilder<T> createCumulativeRpcResult(
- @Nullable
final RpcResult<List<BatchFailedGroupsOutput>> batchGroupsCumulativeResult, final T batchOutput) {
final RpcResultBuilder<T> resultBld;
if (batchGroupsCumulativeResult.isSuccessful()) {
*/
private static <T extends BatchMeterOutputListGrouping>
RpcResultBuilder<T> createCumulativeRpcResult(
- final @Nullable RpcResult<List<BatchFailedMetersOutput>> batchMetersCumulativeResult,
+ final RpcResult<List<BatchFailedMetersOutput>> batchMetersCumulativeResult,
final T batchOutput) {
final RpcResultBuilder<T> resultBld;
if (batchMetersCumulativeResult.isSuccessful()) {
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
import org.opendaylight.controller.md.sal.binding.api.WriteTransaction;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipListenerRegistration;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
import org.opendaylight.controller.sal.binding.api.BindingAwareBroker;
import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
-import org.opendaylight.infrautils.diagstatus.DiagStatusService;
+import org.opendaylight.infrautils.ready.SystemReadyMonitor;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipListenerRegistration;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.openflowjava.protocol.spi.connection.SwitchConnectionProvider;
-import org.opendaylight.openflowplugin.api.openflow.OpenFlowPluginProvider;
+import org.opendaylight.openflowplugin.api.diagstatus.OpenflowPluginDiagStatusProvider;
import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationProperty;
import org.opendaylight.openflowplugin.api.openflow.configuration.ConfigurationService;
import org.opendaylight.openflowplugin.api.openflow.mastership.MastershipChangeServiceManager;
NotificationPublishService notificationPublishService;
@Mock
- DiagStatusService diagStatusService;
+ OpenflowPluginDiagStatusProvider ofPluginDiagstatusProvider;
+
+ @Mock
+ SystemReadyMonitor systemReadyMonitor;
@Mock
WriteTransaction writeTransaction;
@Test
public void testInitializeAndClose() throws Exception {
- final OpenFlowPluginProvider provider = new OpenFlowPluginProviderFactoryImpl().newInstance(
+ final OpenFlowPluginProviderImpl provider = new OpenFlowPluginProviderImpl(
configurationService,
+ Lists.newArrayList(switchConnectionProvider),
dataBroker,
rpcProviderRegistry,
notificationPublishService,
- entityOwnershipService,
- Lists.newArrayList(switchConnectionProvider),
clusterSingletonServiceProvider,
+ entityOwnershipService,
mastershipChangeServiceManager,
- diagStatusService);
+ ofPluginDiagstatusProvider,
+ systemReadyMonitor);
+ provider.initialize();
+ // Calling the onSystemBootReady() callback
+ provider.onSystemBootReady();
verify(switchConnectionProvider).startup();
provider.close();
verify(switchConnectionProvider).shutdown();
*/
public class MultipartRequestInputFactoryTest {
- private long xid = 42L;
+ private final long xid = 42L;
private short ofVersion;
@Before
MultipartType mpType = MultipartType.OFPMPDESC;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestDescCase.class);
}
final MultipartType mpType = MultipartType.OFPMPFLOW;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestFlowCase);
ofVersion = OFConstants.OFP_VERSION_1_0;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestFlowCase);
MultipartType mpType = MultipartType.OFPMPAGGREGATE;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestAggregateCase.class);
}
MultipartType mpType = MultipartType.OFPMPTABLE;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestTableCase.class);
}
final MultipartType mpType = MultipartType.OFPMPPORTSTATS;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestPortStatsCase);
final MultipartType mpType = MultipartType.OFPMPQUEUE;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestQueueCase);
final MultipartType mpType = MultipartType.OFPMPGROUP;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestGroupCase);
MultipartType mpType = MultipartType.OFPMPGROUPDESC;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestGroupDescCase.class);
}
MultipartType mpType = MultipartType.OFPMPGROUPFEATURES;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestGroupFeaturesCase.class);
}
final MultipartType mpType = MultipartType.OFPMPMETER;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestMeterCase);
final MultipartType mpType = MultipartType.OFPMPMETERCONFIG;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestMeterConfigCase);
MultipartType mpType = MultipartType.OFPMPMETERFEATURES;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestMeterFeaturesCase.class);
}
final MultipartType mpType = MultipartType.OFPMPTABLEFEATURES;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
final MultipartRequestBody mpRqBody = mpRqInput.getMultipartRequestBody();
Assert.assertTrue(mpRqBody instanceof MultipartRequestTableFeaturesCase);
MultipartType mpType = MultipartType.OFPMPPORTDESC;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestPortDescCase.class);
}
MultipartType mpType = MultipartType.OFPMPEXPERIMENTER;
final MultipartRequestInput mpRqInput =
(MultipartRequestInput) MultipartRequestInputFactory.makeMultipartRequest(xid, ofVersion, mpType, false);
- checkHeader(mpRqInput, mpType, ofVersion);
+ checkHeader(mpRqInput, mpType);
checkEmptyBody(mpRqInput.getMultipartRequestBody(), MultipartRequestExperimenterCase.class);
}
- private void checkHeader(MultipartRequestInput mpRqInput, MultipartType mpType, short ofVersion) {
+ private void checkHeader(MultipartRequestInput mpRqInput, MultipartType mpType) {
Assert.assertFalse(mpRqInput.getFlags().isOFPMPFREQMORE());
Assert.assertEquals(ofVersion, mpRqInput.getVersion().shortValue());
Assert.assertEquals(mpType, mpRqInput.getType());
private RpcResult<GetFeaturesOutput> resultFeatures;
- private long helloXid = 42L;
+ private final long helloXid = 42L;
private int expectedErrors = 0;
*/
@Before
public void setUp() {
- handshakeManager = new HandshakeManagerImpl(adapter, OFConstants.OFP_VERSION_1_3, OFConstants.VERSION_ORDER);
- handshakeManager.setErrorHandler(errorHandler);
- handshakeManager.setHandshakeListener(handshakeListener);
- handshakeManager.setUseVersionBitmap(false);
+ handshakeManager = new HandshakeManagerImpl(adapter, OFConstants.OFP_VERSION_1_3, OFConstants.VERSION_ORDER,
+ errorHandler, handshakeListener, false);
resultFeatures = RpcResultBuilder.success(new GetFeaturesOutputBuilder().build()).build();
for (int index = 0; index <= elementsCount; index++) {
List<Boolean> booleanList = new ArrayList<>();
for (int i = 0; i < Integer.SIZE; i++) {
- if (value == ((index * Integer.SIZE) + i)) {
+ if (value == index * Integer.SIZE + i) {
booleanList.add(true);
- value = (orderIndex == 0) ? highestVersion : versionOrder.get(--orderIndex);
+ value = orderIndex == 0 ? highestVersion : versionOrder.get(--orderIndex);
} else {
booleanList.add(false);
}
import org.opendaylight.controller.md.sal.binding.api.DataBroker;
import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
-import org.opendaylight.controller.md.sal.binding.api.ReadTransaction;
import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
import org.opendaylight.controller.md.sal.common.api.data.ReadFailedException;
private OutboundQueueProvider outboundQueueProvider;
@Mock
private ConnectionAdapter connectionAdapter;
- private NodeId nodeId = new NodeId("h2g2:42");
- private KeyedInstanceIdentifier<Node, NodeKey> nodeKeyIdent = DeviceStateUtil.createNodeInstanceIdentifier(nodeId);
+ private final NodeId nodeId = new NodeId("h2g2:42");
+ private final KeyedInstanceIdentifier<Node, NodeKey> nodeKeyIdent =
+ DeviceStateUtil.createNodeInstanceIdentifier(nodeId);
@Mock
private TranslatorLibrary translatorLibrary;
@Mock
@Test
public void testGetReadTransaction() {
- final ReadTransaction readTx = deviceContext.getReadTransaction();
+ readTx = deviceContext.getReadTransaction();
assertNotNull(readTx);
assertEquals(this.readTx, readTx);
}
@Test
public void testAddDeleteOperationTotTxChain() throws Exception {
- txChainManager.addDeleteOperationTotTxChain(LogicalDatastoreType.CONFIGURATION, path);
+ txChainManager.addDeleteOperationToTxChain(LogicalDatastoreType.CONFIGURATION, path);
Mockito.verify(txChain).newReadWriteTransaction();
Mockito.verify(writeTx).delete(LogicalDatastoreType.CONFIGURATION, path);
};
private MessageIntelligenceAgency mi5;
+ @Override
public void doSetUp() {
clearStatsCommandProvider = new ClearStatsCommandProvider();
mi5 = OpenFlowPluginProviderImpl.getMessageIntelligenceAgency();
*/
@Test
public void testDoExecute_dirty() throws Exception {
- final MessageIntelligenceAgency mi5 = OpenFlowPluginProviderImpl.getMessageIntelligenceAgency();
+ mi5 = OpenFlowPluginProviderImpl.getMessageIntelligenceAgency();
Assert.assertTrue(checkNoActivity(mi5.provideIntelligence(), CHECK_NO_ACTIVITY_FUNCTION));
mi5.spyMessage(OfHeader.class, MessageSpy.StatisticsGroup.FROM_SWITCH);
Assert.assertFalse(checkNoActivity(mi5.provideIntelligence(), CHECK_NO_ACTIVITY_FUNCTION));
clearStatsCommandProvider.execute(cmdSession);
Assert.assertTrue(checkNoActivity(mi5.provideIntelligence(), CHECK_NO_ACTIVITY_FUNCTION));
}
-}
\ No newline at end of file
+}
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.runners.MockitoJUnitRunner;
-import org.opendaylight.controller.md.sal.common.api.clustering.Entity;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipChange;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipListenerRegistration;
-import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService;
+import org.opendaylight.mdsal.eos.binding.api.Entity;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipChange;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipListenerRegistration;
+import org.opendaylight.mdsal.eos.binding.api.EntityOwnershipService;
+import org.opendaylight.mdsal.eos.common.api.EntityOwnershipChangeState;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceProvider;
import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceRegistration;
import org.opendaylight.openflowplugin.api.openflow.connection.ConnectionContext;
contextChainHolder.onMasterRoleAcquired(deviceInfo, ContextChainMastershipState.INITIAL_SUBMIT);
EntityOwnershipChange ownershipChange = new EntityOwnershipChange(
new Entity(ENTITY_TEST, OPENFLOW_TEST),
- true,
- false,
- false
+ EntityOwnershipChangeState.LOCAL_OWNERSHIP_LOST_NO_OWNER
);
contextChainHolder.ownershipChanged(ownershipChange);
Mockito.verify(deviceManager).removeDeviceFromOperationalDS(Mockito.any());
contextChainHolder.onMasterRoleAcquired(deviceInfo, ContextChainMastershipState.INITIAL_SUBMIT);
EntityOwnershipChange ownershipChange = new EntityOwnershipChange(
new Entity(ENTITY_TEST, OPENFLOW_TEST),
- true,
- false,
- true
+ EntityOwnershipChangeState.LOCAL_OWNERSHIP_LOST_NEW_OWNER
);
contextChainHolder.ownershipChanged(ownershipChange);
Mockito.verify(deviceManager,Mockito.never()).removeDeviceFromOperationalDS(Mockito.any());
registry = new SerializerRegistryImpl();
registry.init();
provider = new SerializerExtensionProviderImpl(registry);
- SerializerInjector.injectSerializers(provider);
+ SerializerInjector.injectSerializers(provider, false);
init();
}
.build();
final Map<FlowRegistryKey, FlowDescriptor> allFlowDescriptors = fillRegistry(path, flowCapableNode);
- final FlowRegistryKey key = FlowRegistryKeyFactory.create(OFConstants.OFP_VERSION_1_3, flow);
+ key = FlowRegistryKeyFactory.create(OFConstants.OFP_VERSION_1_3, flow);
InOrder order = inOrder(dataBroker, readOnlyTransaction);
order.verify(dataBroker).newReadOnlyTransaction();
@Test
public void testForEach() throws Exception {
final AtomicInteger counter = new AtomicInteger(0);
- deviceFlowRegistry.forEach(key -> counter.incrementAndGet());
+ deviceFlowRegistry.forEach(k -> counter.incrementAndGet());
Assert.assertEquals(1, counter.get());
}
package org.opendaylight.openflowplugin.impl.registry.flow;
+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
import org.junit.Assert;
import org.junit.Test;
import org.opendaylight.openflowplugin.api.openflow.registry.flow.FlowDescriptor;
}
@Test(expected = Exception.class)
+ @SuppressFBWarnings("NP_NONNULL_PARAM_VIOLATION") // that is the point of this test
public void testCreateNegative1() throws Exception {
FlowDescriptorFactory.create((short) 1, null);
}
-}
\ No newline at end of file
+}
import com.google.common.util.concurrent.ListenableFuture;
import java.util.concurrent.Future;
import org.junit.Assert;
-import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Matchers;
private SalAsyncConfigServiceImpl salAsyncConfigService;
- @Before
- public void setUp() throws Exception {
+ @Override
+ public void setup() throws Exception {
salAsyncConfigService = new SalAsyncConfigServiceImpl(
mockedRequestContextStack, mockedDeviceContext);
}
verify(mockedOutboundQueue).commitEntry(Matchers.eq(ServiceMocking.DUMMY_XID_VALUE),
Matchers.<OfHeader>any(), Matchers.<FutureCallback<OfHeader>>any());
}
-}
\ No newline at end of file
+}
@Test
@SuppressWarnings("checkstyle:IllegalCatch")
public void testClose() throws Exception {
- final StatisticsContextImpl<MultipartReply> statisticsContext =
+ statisticsContext =
new StatisticsContextImpl<>(mockedDeviceContext,
convertorManager,
MultipartWriterProviderFactory
.thenReturn(new DeviceFlowRegistryImpl(OFConstants.OFP_VERSION_1_3, dataBroker, nodePath));
when(mockedDeviceContext.getDeviceState()).thenReturn(mockedDeviceState);
when(mockedDeviceContext.getMultiMsgCollector(
- Matchers.<RequestContext<List<MultipartReply>>>any())).thenAnswer(
+ Matchers.<RequestContext<List<MultipartReply>>>any())).thenAnswer(
invocation -> {
currentRequestContext = (RequestContext<List<MultipartReply>>) invocation.getArguments()[0];
return multiMagCollector;
- }
- );
+ });
when(rpcProviderRegistry.addRpcImplementation(
Matchers.eq(StatisticsManagerControlService.class),
Matchers.<StatisticsManagerControlService>any())).thenReturn(serviceControlRegistration);
service.handleAndNotify(input, notificationPublishService);
Assert.assertTrue(resultFuture.isDone());
- final RpcResult<GetAggregateFlowStatisticsFromFlowTableForAllFlowsOutput> rpcResult = resultFuture.get();
- Assert.assertTrue(rpcResult.isSuccessful());
+ final RpcResult<GetAggregateFlowStatisticsFromFlowTableForAllFlowsOutput> result = resultFuture.get();
+ Assert.assertTrue(result.isSuccessful());
Assert.assertEquals(MultipartType.OFPMPAGGREGATE, requestInput.getValue().getType());
Mockito.verify(notificationPublishService, Mockito.timeout(500))
.offerNotification(Matchers.any(AggregateFlowStatisticsUpdate.class));
@Mock
DeviceInfo deviceInfo;
@Mock
- List<PhyPort> phyPorts;
- @Mock
PhyPort phyPort;
ConvertorManager convertorManager;
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.Collection;
public void onFailure(Throwable throwable) {
LOG.error("Write of flow on device failed.", throwable);
}
- });
+ }, MoreExecutors.directExecutor());
}
//TODO move to separate test util class
import org.opendaylight.openflowjava.protocol.api.keys.MessageTypeKey;
import org.opendaylight.openflowplugin.extension.api.ConverterExtensionKey;
+import org.opendaylight.openflowplugin.extension.api.ConverterMessageToOFJava;
import org.opendaylight.openflowplugin.extension.api.ConvertorActionFromOFJava;
import org.opendaylight.openflowplugin.extension.api.ConvertorActionToOFJava;
import org.opendaylight.openflowplugin.extension.api.ConvertorFromOFJava;
import org.opendaylight.openflowplugin.extension.api.ConvertorMessageFromOFJava;
-import org.opendaylight.openflowplugin.extension.api.ConverterMessageToOFJava;
import org.opendaylight.openflowplugin.extension.api.ConvertorToOFJava;
import org.opendaylight.openflowplugin.extension.api.TypeVersionKey;
import org.opendaylight.openflowplugin.extension.api.path.AugmentationPath;
RegistrationCloser<ConverterExtensionKey<? extends ExtensionKey>, ConvertorToOFJava<TO>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
public static class RegistrationCloserFromOFJava<FROM extends DataContainer, PATH extends AugmentationPath> extends RegistrationCloser<MessageTypeKey<?>, ConvertorFromOFJava<FROM, PATH>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
RegistrationCloser<TypeVersionKey<? extends Action>, ConvertorActionToOFJava<Action, TO>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
RegistrationCloser<MessageTypeKey<?>, ConvertorActionFromOFJava<FROM, PATH>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
RegistrationCloser<TypeVersionKey<K>, ConverterMessageToOFJava<K, TO>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
RegistrationCloser<MessageTypeKey<?>, ConvertorMessageFromOFJava<FROM, PATH>> {
@Override
- public void close() throws Exception {
+ public void close() {
getRegistrator().unregister(getKey(), getConverter());
}
}
<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>org.opendaylight.odlparent</groupId>
- <artifactId>odlparent</artifactId>
- <version>2.0.5</version>
+ <groupId>org.opendaylight.mdsal</groupId>
+ <artifactId>binding-parent</artifactId>
+ <version>0.12.0-SNAPSHOT</version>
<relativePath/>
</parent>
<properties>
<project.build.sourceEncoding>utf-8</project.build.sourceEncoding>
- <sal.api.version>0.14.0-SNAPSHOT</sal.api.version>
- <salGeneratorPath>${project.build.directory}/generated-sources/sal</salGeneratorPath>
- <controller.distribution.version>0.7.0-SNAPSHOT</controller.distribution.version>
- <mdsal.version>1.7.0-SNAPSHOT</mdsal.version>
- <mdsal.model.version>0.12.0-SNAPSHOT</mdsal.model.version>
- <yangtools.version>1.2.0</yangtools.version>
- <argparse4j.version>0.7.0</argparse4j.version>
<exi.nagasena.version>0000.0002.0053.0</exi.nagasena.version>
<infrautils.version>1.3.0-SNAPSHOT</infrautils.version>
</properties>
<scope>import</scope>
<type>pom</type>
</dependency>
- <dependency>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yangtools-artifacts</artifactId>
- <version>${yangtools.version}</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
- <dependency>
- <groupId>org.opendaylight.mdsal</groupId>
- <artifactId>mdsal-artifacts</artifactId>
- <version>2.4.0-SNAPSHOT</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
- <dependency>
- <groupId>org.opendaylight.mdsal.model</groupId>
- <artifactId>mdsal-model-artifacts</artifactId>
- <version>${mdsal.model.version}</version>
- <scope>import</scope>
- <type>pom</type>
- </dependency>
<dependency>
<groupId>org.opendaylight.controller</groupId>
<artifactId>mdsal-artifacts</artifactId>
- <version>${mdsal.version}</version>
- <scope>import</scope>
+ <version>1.7.0-SNAPSHOT</version>
<type>pom</type>
+ <scope>import</scope>
</dependency>
<dependency>
<groupId>org.opendaylight.controller</groupId>
<artifactId>liblldp</artifactId>
- <version>${sal.api.version}</version>
+ <version>0.14.0-SNAPSHOT</version>
</dependency>
<!-- thirdparty -->
<dependency>
<dependency>
<groupId>net.sourceforge.argparse4j</groupId>
<artifactId>argparse4j</artifactId>
- <version>${argparse4j.version}</version>
+ <version>0.7.0</version>
</dependency>
</dependencies>
</dependencyManagement>
</plugins>
<pluginManagement>
<plugins>
- <plugin>
- <artifactId>maven-clean-plugin</artifactId>
- <configuration>
- <filesets>
- <fileset>
- <directory>${salGeneratorPath}</directory>
- <includes>
- <include>**</include>
- </includes>
- </fileset>
- </filesets>
- </configuration>
- </plugin>
- <plugin>
- <groupId>org.codehaus.mojo</groupId>
- <artifactId>build-helper-maven-plugin</artifactId>
- <executions>
- <execution>
- <id>add-source</id>
- <phase>generate-sources</phase>
- <goals>
- <goal>add-source</goal>
- </goals>
- <configuration>
- <sources>
- <source>${salGeneratorPath}</source>
- </sources>
- </configuration>
- </execution>
- </executions>
- </plugin>
- <plugin>
- <groupId>org.opendaylight.yangtools</groupId>
- <artifactId>yang-maven-plugin</artifactId>
- <version>${yangtools.version}</version>
- </plugin>
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<modules>
<module>artifacts</module>
<module>parent</module>
+ <module>libraries</module>
<module>openflowjava</module>
<module>openflowplugin-api</module>
<module>openflowplugin</module>
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.JdkFutureAdapters;
import com.google.common.util.concurrent.ListenableFuture;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.concurrent.Callable;
import org.opendaylight.controller.md.sal.binding.api.NotificationService;
public void onFailure(final Throwable throwable) {
countFutureError();
}
- });
+ }, MoreExecutors.directExecutor());
}
/**
<dependency>
<groupId>org.eclipse.tycho</groupId>
<artifactId>org.eclipse.osgi</artifactId>
+ <version>3.10.101.v20150820-1432</version>
</dependency>
<dependency>
<groupId>commons-lang</groupId>
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.List;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-//import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.meters.M
-
public class OpenflowPluginBulkGroupTransactionProvider implements CommandProvider {
private static final Logger LOG = LoggerFactory.getLogger(OpenflowPluginBulkGroupTransactionProvider.class);
private NodeBuilder testNode;
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
private void deleteGroup(final CommandInterpreter ci, Group group, Group group1) {
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
private GroupBuilder createTestGroup(String actiontype, String type, String mod, String iD) {
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.List;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-//import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.meters.M
-
public class OpenflowPluginBulkTransactionProvider implements CommandProvider {
private static final Logger LOG = LoggerFactory.getLogger(OpenflowPluginBulkTransactionProvider.class);
LOG.error(throwable.getMessage(), throwable);
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
LOG.error(throwable.getMessage(), throwable);
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
/**
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.osgi.framework.console.CommandInterpreter;
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _addGroup(CommandInterpreter ci) {
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _modifyGroup(CommandInterpreter ci) {
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.osgi.framework.console.CommandInterpreter;
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _removeMeters(final CommandInterpreter ci) {
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _addMeter(CommandInterpreter ci) {
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
private void writeMeter(final CommandInterpreter ci, Meter meter, Meter meter1) {
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _modifyMeter(CommandInterpreter ci) {
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.Arrays;
public void onFailure(Throwable throwable) {
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _modifyTable(CommandInterpreter ci) {
import com.google.common.util.concurrent.CheckedFuture;
import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.MoreExecutors;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.Collection;
LOG.error(throwable.getMessage(), throwable);
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
/**
LOG.error(throwable.getMessage(), throwable);
ci.println(String.format("Status of Group Data Loaded Transaction : failure. Reason : %s", throwable));
}
- });
+ }, MoreExecutors.directExecutor());
}
public void _modifyMDFlow(final CommandInterpreter ci) {