Priyanka B
Committed by Priyankab-Huawei

[ONOS] PCEP provider changes, added node listeners to topology provider

Change-Id: I98bc6445ee78a8f0bf53f897f0a25f678ec7fc99
Showing 19 changed files with 1081 additions and 19 deletions
COMPILE_DEPS = [
'//lib:CORE_DEPS',
'//protocols/pcep/pcepio:onos-protocols-pcep-pcepio',
'//apps/pcep-api:onos-apps-pcep-api',
]
osgi_jar_with_tests (
......
......@@ -26,6 +26,8 @@ public class ClientCapability {
private boolean pceccCapability;
private boolean statefulPceCapability;
private boolean pcInstantiationCapability;
private boolean labelStackCapability;
private boolean srCapability;
/**
* Creates new instance of client capability.
......@@ -33,11 +35,34 @@ public class ClientCapability {
* @param pceccCapability represents PCECC capability
* @param statefulPceCapability represents stateful PCE capability
* @param pcInstantiationCapability represents PC initiation capability
* @param labelStackCapability represents S bit is set in PCECC capability
* @param srCapability represents SR capability
*/
public ClientCapability(boolean pceccCapability, boolean statefulPceCapability, boolean pcInstantiationCapability) {
public ClientCapability(boolean pceccCapability, boolean statefulPceCapability, boolean pcInstantiationCapability,
boolean labelStackCapability, boolean srCapability) {
this.pceccCapability = pceccCapability;
this.statefulPceCapability = statefulPceCapability;
this.pcInstantiationCapability = pcInstantiationCapability;
this.labelStackCapability = labelStackCapability;
this.srCapability = srCapability;
}
/**
* Obtains label stack capability.
*
* @return true if client supports PCECC capability with S bit set otherwise false
*/
public boolean labelStackCapability() {
return labelStackCapability;
}
/**
* Obtains segment routing capability.
*
* @return true if client supports SR capability otherwise false
*/
public boolean srCapability() {
return srCapability;
}
/**
......@@ -69,7 +94,8 @@ public class ClientCapability {
@Override
public int hashCode() {
return Objects.hash(pceccCapability, statefulPceCapability, pcInstantiationCapability);
return Objects.hash(pceccCapability, statefulPceCapability, pcInstantiationCapability, labelStackCapability,
srCapability);
}
@Override
......@@ -81,7 +107,9 @@ public class ClientCapability {
ClientCapability other = (ClientCapability) obj;
return Objects.equals(pceccCapability, other.pceccCapability)
&& Objects.equals(statefulPceCapability, other.statefulPceCapability)
&& Objects.equals(pcInstantiationCapability, other.pcInstantiationCapability);
&& Objects.equals(pcInstantiationCapability, other.pcInstantiationCapability)
&& Objects.equals(labelStackCapability, other.labelStackCapability)
&& Objects.equals(srCapability, other.srCapability);
}
return false;
}
......@@ -92,6 +120,8 @@ public class ClientCapability {
.add("pceccCapability", pceccCapability)
.add("statefulPceCapability", statefulPceCapability)
.add("pcInstantiationCapability", pcInstantiationCapability)
.add("labelStackCapability", labelStackCapability)
.add("srCapability", srCapability)
.toString();
}
}
\ No newline at end of file
......
......@@ -135,4 +135,18 @@ public interface PcepClient {
* @return capability supported by client
*/
ClientCapability capability();
/**
* Adds PCEP device when session is successfully established.
*
* @param pc PCEP client details
*/
void addNode(PcepClient pc);
/**
* Removes PCEP device when session is disconnected.
*
* @param pccId PCEP client ID
*/
void deleteNode(PccId pccId);
}
......
......@@ -57,7 +57,7 @@ public interface PcepClientController {
void removeListener(PcepClientListener listener);
/**
* Register a listener for OF msg events.
* Register a listener for PCEP msg events.
*
* @param listener the listener to notify
*/
......@@ -71,6 +71,20 @@ public interface PcepClientController {
void removeEventListener(PcepEventListener listener);
/**
* Register a listener for PCEP msg events[carrying node descriptor details].
*
* @param listener the listener to notify
*/
void addNodeListener(PcepNodeListener listener);
/**
* Unregister a listener.
*
* @param listener the listener to be unregistered
*/
void removeNodeListener(PcepNodeListener listener);
/**
* Send a message to a particular pcc client.
*
* @param pccId the id of the client to send message.
......
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.pcep.controller;
/**
* Notifies providers about PCEP node events.
*/
public interface PcepNodeListener {
/**
* Notifies that the node was added.
*
* @param pc PCEP client details
*/
void addNode(PcepClient pc);
/**
* Notifies that the node was removed.
*
* @param pccId PCEP client ID
*/
void deleteNode(PccId pccId);
}
......@@ -60,4 +60,17 @@ public interface PcepAgent {
*/
void processPcepMessage(PccId pccId, PcepMessage m);
/**
* Adds PCEP device when session is successfully established.
*
* @param pc PCEP client details
*/
void addNode(PcepClient pc);
/**
* Removes PCEP device when session is disconnected.
*
* @param pccId PCEP client ID
*/
void deleteNode(PccId pccId);
}
......
......@@ -55,6 +55,7 @@ import org.onosproject.pcepio.protocol.PcepVersion;
import org.onosproject.pcepio.types.IPv4RouterIdOfLocalNodeSubTlv;
import org.onosproject.pcepio.types.NodeAttributesTlv;
import org.onosproject.pcepio.types.PceccCapabilityTlv;
import org.onosproject.pcepio.types.SrPceCapabilityTlv;
import org.onosproject.pcepio.types.StatefulPceCapabilityTlv;
import org.onosproject.pcepio.types.PcepErrorDetailInfo;
import org.onosproject.pcepio.types.PcepValueType;
......@@ -260,6 +261,8 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
disconnectDuplicate(h);
} else {
h.setState(ESTABLISHED);
//Session is established, add a PCEP device
h.addNode();
}
}
}
......@@ -469,6 +472,20 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
}
/**
* Adds PCEP device once session is established.
*/
private void addNode() {
pc.addNode(pc);
}
/**
* Deletes PCEP device when session is disconnected.
*/
private void deleteNode() {
pc.deleteNode(pc.getPccId());
}
/**
* Return a string describing this client based on the already available
* information (ip address and/or remote socket).
*
......@@ -523,6 +540,8 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
boolean pceccCapability = false;
boolean statefulPceCapability = false;
boolean pcInstantiationCapability = false;
boolean labelStackCapability = false;
boolean srCapability = false;
ListIterator<PcepValueType> listIterator = tlvList.listIterator();
while (listIterator.hasNext()) {
......@@ -531,6 +550,9 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
switch (tlv.getType()) {
case PceccCapabilityTlv.TYPE:
pceccCapability = true;
if (((PceccCapabilityTlv) tlv).sBit()) {
labelStackCapability = true;
}
break;
case StatefulPceCapabilityTlv.TYPE:
statefulPceCapability = true;
......@@ -539,11 +561,15 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
pcInstantiationCapability = true;
}
break;
case SrPceCapabilityTlv.TYPE:
srCapability = true;
break;
default:
continue;
}
}
this.capability = new ClientCapability(pceccCapability, statefulPceCapability, pcInstantiationCapability);
this.capability = new ClientCapability(pceccCapability, statefulPceCapability, pcInstantiationCapability,
labelStackCapability, srCapability);
}
/**
......@@ -563,6 +589,8 @@ class PcepChannelHandler extends IdleStateAwareChannelHandler {
*/
private void sendErrMsgAndCloseChannel() {
// TODO send error message
//Remove PCEP device from topology
deleteNode();
channel.close();
}
......
......@@ -25,12 +25,16 @@ import java.util.concurrent.ConcurrentHashMap;
import org.apache.felix.scr.annotations.Activate;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Deactivate;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.ReferenceCardinality;
import org.apache.felix.scr.annotations.Service;
import org.onosproject.net.device.DeviceService;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepClientController;
import org.onosproject.pcep.controller.PcepClientListener;
import org.onosproject.pcep.controller.PcepEventListener;
import org.onosproject.pcep.controller.PcepNodeListener;
import org.onosproject.pcep.controller.driver.PcepAgent;
import org.onosproject.pcepio.protocol.PcepError;
import org.onosproject.pcepio.protocol.PcepErrorInfo;
......@@ -55,6 +59,9 @@ public class PcepClientControllerImpl implements PcepClientController {
private static final Logger log = LoggerFactory.getLogger(PcepClientControllerImpl.class);
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected DeviceService deviceService;
protected ConcurrentHashMap<PccId, PcepClient> connectedClients =
new ConcurrentHashMap<>();
......@@ -62,6 +69,7 @@ public class PcepClientControllerImpl implements PcepClientController {
protected Set<PcepClientListener> pcepClientListener = new HashSet<>();
protected Set<PcepEventListener> pcepEventListener = Sets.newHashSet();
protected Set<PcepNodeListener> pcepNodeListener = Sets.newHashSet();
private final Controller ctrl = new Controller();
......@@ -117,6 +125,16 @@ public class PcepClientControllerImpl implements PcepClientController {
}
@Override
public void addNodeListener(PcepNodeListener listener) {
pcepNodeListener.add(listener);
}
@Override
public void removeNodeListener(PcepNodeListener listener) {
pcepNodeListener.remove(listener);
}
@Override
public void processClientMessage(PccId pccId, PcepMessage msg) {
PcepClient pc = getClient(pccId);
......@@ -173,6 +191,8 @@ public class PcepClientControllerImpl implements PcepClientController {
break;
case LABEL_RANGE_RESERV:
break;
case LS_REPORT: //TODO: need to handle LS report to add or remove node
break;
case MAX:
break;
case END:
......@@ -270,5 +290,19 @@ public class PcepClientControllerImpl implements PcepClientController {
public void processPcepMessage(PccId pccId, PcepMessage m) {
processClientMessage(pccId, m);
}
@Override
public void addNode(PcepClient pc) {
for (PcepNodeListener l : pcepNodeListener) {
l.addNode(pc);
}
}
@Override
public void deleteNode(PccId pccId) {
for (PcepNodeListener l : pcepNodeListener) {
l.deleteNode(pccId);
}
}
}
}
......
......@@ -26,6 +26,7 @@ import org.jboss.netty.channel.Channel;
import org.onlab.packet.IpAddress;
import org.onosproject.pcep.controller.ClientCapability;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepPacketStats;
import org.onosproject.pcep.controller.PcepSyncStatus;
import org.onosproject.pcep.controller.driver.PcepAgent;
......@@ -203,6 +204,16 @@ public class PcepClientImpl implements PcepClientDriver {
}
@Override
public void addNode(PcepClient pc) {
this.agent.addNode(pc);
}
@Override
public void deleteNode(PccId pccId) {
this.agent.deleteNode(pccId);
}
@Override
public final boolean connectClient() {
return this.agent.addConnectedClient(pccId, this);
}
......
......@@ -3,6 +3,9 @@ COMPILE_DEPS = [
'//protocols/ovsdb/api:onos-protocols-ovsdb-api',
'//protocols/ovsdb/rfc:onos-protocols-ovsdb-rfc',
'//apps/pcep-api:onos-apps-pcep-api',
'//protocols/pcep/api:onos-protocols-pcep-api',
'//protocols/pcep/pcepio:onos-protocols-pcep-pcepio',
'//core/api:onos-api-tests',
]
osgi_jar_with_tests (
......
......@@ -24,10 +24,20 @@
<artifactId>onos-pcep-provider-topology</artifactId>
<packaging>bundle</packaging>
<description>PCEP topology provider</description>
<dependencies>
<dependency>
<groupId>org.onosproject</groupId>
<artifactId>onos-app-pcep-api</artifactId>
</dependency>
</dependencies>
</project>
\ No newline at end of file
<dependencies>
<dependency>
<groupId>org.onosproject</groupId>
<artifactId>onos-app-pcep-api</artifactId>
</dependency>
<dependency>
<groupId>org.onosproject</groupId>
<artifactId>onos-pcep-controller-api</artifactId>
</dependency>
<dependency>
<groupId>org.onosproject</groupId>
<artifactId>onos-api</artifactId>
<classifier>tests</classifier>
<scope>test</scope>
</dependency>
</dependencies>
</project>
......
......@@ -62,6 +62,10 @@ import org.onosproject.pcep.api.PcepLinkListener;
import org.onosproject.pcep.api.PcepOperator.OperationType;
import org.onosproject.pcep.api.PcepSwitch;
import org.onosproject.pcep.api.PcepSwitchListener;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepClientController;
import org.onosproject.pcep.controller.PcepNodeListener;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
......@@ -115,18 +119,40 @@ public class PcepTopologyProvider extends AbstractProvider
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected ClusterService clusterService;
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
protected PcepClientController pcepClientController;
private DeviceProviderService deviceProviderService;
private LinkProviderService linkProviderService;
private HashMap<Long, List<PortDescription>> portMap = new HashMap<>();
private InternalLinkProvider listener = new InternalLinkProvider();
/*
* For the client supporting SR capability.
*/
public static final String SR_CAPABILITY = "srCapability";
/*
* For the client supporting PCECC capability.
*/
public static final String PCECC_CAPABILITY = "pceccCapability";
/*
* For the client supporting label stack capability.
*/
public static final String LABEL_STACK_CAPABILITY = "labelStackCapability";
public static final String LSRID = "lsrId";
private static final String UNKNOWN = "unknown";
@Activate
public void activate() {
linkProviderService = linkProviderRegistry.register(this);
deviceProviderService = deviceProviderRegistry.register(this);
controller.addListener(listener);
controller.addLinkListener(listener);
pcepClientController.addNodeListener(listener);
}
@Deactivate
......@@ -135,6 +161,7 @@ public class PcepTopologyProvider extends AbstractProvider
linkProviderService = null;
controller.removeListener(listener);
controller.removeLinkListener(listener);
pcepClientController.removeNodeListener(listener);
}
private List<PortDescription> buildPortDescriptions(PcepDpid dpid,
......@@ -225,7 +252,7 @@ public class PcepTopologyProvider extends AbstractProvider
}
private class InternalLinkProvider
implements PcepSwitchListener, PcepLinkListener {
implements PcepSwitchListener, PcepLinkListener, PcepNodeListener {
@Override
public void switchAdded(PcepDpid dpid) {
......@@ -306,6 +333,51 @@ public class PcepTopologyProvider extends AbstractProvider
}
}
@Override
public void addNode(PcepClient pc) {
if (deviceProviderService == null) {
return;
}
//Right now device URI for PCEP devices is their LSRID
DeviceId deviceId = deviceId(uri(new PcepDpid(pc.getPccId().id().getIp4Address().toInt())));
ChassisId cId = new ChassisId();
Device.Type deviceType = Device.Type.ROUTER;
DefaultAnnotations.Builder annotationBuilder = DefaultAnnotations.builder();
//PCC capabilities (SR, PCECC and PCECC-SR)
annotationBuilder.set(SR_CAPABILITY, String.valueOf(pc.capability().srCapability()));
annotationBuilder.set(PCECC_CAPABILITY, String.valueOf(pc.capability().pceccCapability()));
annotationBuilder.set(LABEL_STACK_CAPABILITY, String.valueOf(pc.capability().labelStackCapability()));
//PccId is the lsrId contained in openMsg, if not present it will be the socket address
annotationBuilder.set(LSRID, String.valueOf(pc.getPccId().id()));
DeviceDescription description = new DefaultDeviceDescription(
deviceId.uri(),
deviceType,
UNKNOWN,
UNKNOWN,
UNKNOWN,
UNKNOWN,
cId,
annotationBuilder.build());
deviceProviderService.deviceConnected(deviceId, description);
}
@Override
public void deleteNode(PccId pccId) {
if (deviceProviderService == null || deviceService == null) {
return;
}
//TODO: In device manager, in deviceDisconnected() method, get the device but null check is not validated
if (deviceService.getDevice(DeviceId.deviceId(uri(new PcepDpid(pccId.id()
.getIp4Address().toInt())))) == null) {
return;
}
deviceProviderService.deviceDisconnected(deviceId(uri(new PcepDpid(pccId.id().getIp4Address().toInt()))));
}
}
@Override
......
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.provider.pcep.topology.impl;
import static org.junit.Assert.assertNotNull;
import java.util.List;
import java.util.concurrent.RejectedExecutionException;
import org.jboss.netty.channel.Channel;
import org.onosproject.pcep.controller.ClientCapability;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepSyncStatus;
import org.onosproject.pcepio.protocol.PcepFactories;
import org.onosproject.pcepio.protocol.PcepFactory;
import org.onosproject.pcepio.protocol.PcepMessage;
import org.onosproject.pcepio.protocol.PcepVersion;
/**
* Representation of PCEP client adapter.
*/
public class PcepClientAdapter implements PcepClient {
private Channel channel;
protected String channelId;
private boolean connected;
private PccId pccId;
private ClientCapability capability;
private PcepVersion pcepVersion;
private PcepSyncStatus lspDbSyncStatus;
private PcepSyncStatus labelDbSyncStatus;
/**
* Initialize instance with specified parameters.
*
* @param pccId PCC id
* @param pcepVersion PCEP message version
*/
public void init(PccId pccId, PcepVersion pcepVersion) {
this.pccId = pccId;
this.pcepVersion = pcepVersion;
}
@Override
public final void disconnectClient() {
this.channel.close();
}
@Override
public final void sendMessage(PcepMessage m) {
}
@Override
public final void sendMessage(List<PcepMessage> msgs) {
try {
PcepMessage pcepMsg = msgs.get(0);
assertNotNull("PCEP MSG should be created.", pcepMsg);
} catch (RejectedExecutionException e) {
throw e;
}
}
@Override
public final boolean isConnected() {
return this.connected;
}
@Override
public String channelId() {
return channelId;
}
@Override
public final PccId getPccId() {
return this.pccId;
};
@Override
public final String getStringId() {
return this.pccId.toString();
}
@Override
public final void handleMessage(PcepMessage m) {
}
@Override
public boolean isOptical() {
return false;
}
@Override
public PcepFactory factory() {
return PcepFactories.getFactory(pcepVersion);
}
@Override
public void setLspDbSyncStatus(PcepSyncStatus syncStatus) {
this.lspDbSyncStatus = syncStatus;
}
@Override
public PcepSyncStatus lspDbSyncStatus() {
return lspDbSyncStatus;
}
@Override
public void setLabelDbSyncStatus(PcepSyncStatus syncStatus) {
this.labelDbSyncStatus = syncStatus;
}
@Override
public PcepSyncStatus labelDbSyncStatus() {
return labelDbSyncStatus;
}
@Override
public void setCapability(ClientCapability capability) {
this.capability = capability;
}
@Override
public ClientCapability capability() {
return capability;
}
@Override
public void addNode(PcepClient pc) {
}
@Override
public void deleteNode(PccId pccId) {
}
}
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.provider.pcep.topology.impl;
import java.util.Collection;
import java.util.Collections;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.felix.scr.annotations.Activate;
import org.apache.felix.scr.annotations.Deactivate;
import org.onlab.packet.IpAddress;
import org.onosproject.pcep.controller.ClientCapability;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepClientController;
import org.onosproject.pcep.controller.PcepClientListener;
import org.onosproject.pcep.controller.PcepEventListener;
import org.onosproject.pcep.controller.PcepNodeListener;
import org.onosproject.pcep.controller.driver.PcepAgent;
import org.onosproject.pcepio.protocol.PcepError;
import org.onosproject.pcepio.protocol.PcepErrorInfo;
import org.onosproject.pcepio.protocol.PcepErrorMsg;
import org.onosproject.pcepio.protocol.PcepErrorObject;
import org.onosproject.pcepio.protocol.PcepFactory;
import org.onosproject.pcepio.protocol.PcepMessage;
import org.onosproject.pcepio.protocol.PcepVersion;
import com.google.common.collect.Sets;
import static org.onosproject.pcepio.types.PcepErrorDetailInfo.ERROR_TYPE_19;
import static org.onosproject.pcepio.types.PcepErrorDetailInfo.ERROR_VALUE_5;
/**
* Representation of PCEP client controller adapter.
*/
public class PcepClientControllerAdapter implements PcepClientController {
protected ConcurrentHashMap<PccId, PcepClient> connectedClients =
new ConcurrentHashMap<PccId, PcepClient>();
protected PcepClientAgent agent = new PcepClientAgent();
protected Set<PcepClientListener> pcepClientListener = new HashSet<>();
protected Set<PcepEventListener> pcepEventListener = Sets.newHashSet();
public Set<PcepNodeListener> pcepNodeListener = Sets.newHashSet();
@Activate
public void activate() {
}
@Deactivate
public void deactivate() {
}
@Override
public Collection<PcepClient> getClients() {
return connectedClients.values();
}
@Override
public PcepClient getClient(PccId pccId) {
if (null != connectedClients.get(pccId)) {
return connectedClients.get(pccId);
}
PcepClientAdapter pc = new PcepClientAdapter();
if (pccId.ipAddress().equals(IpAddress.valueOf(0xC010103))
|| pccId.ipAddress().equals(IpAddress.valueOf(0xB6024E22))) {
pc.setCapability(new ClientCapability(true, false, false, false, false));
} else {
pc.setCapability(new ClientCapability(true, true, true, false, false));
}
pc.init(PccId.pccId(pccId.ipAddress()), PcepVersion.PCEP_1);
connectedClients.put(pccId, pc);
return pc;
}
@Override
public void addListener(PcepClientListener listener) {
if (!pcepClientListener.contains(listener)) {
this.pcepClientListener.add(listener);
}
}
@Override
public void addNodeListener(PcepNodeListener listener) {
pcepNodeListener.add(listener);
}
@Override
public void removeNodeListener(PcepNodeListener listener) {
pcepNodeListener.remove(listener);
}
@Override
public void removeListener(PcepClientListener listener) {
this.pcepClientListener.remove(listener);
}
@Override
public void addEventListener(PcepEventListener listener) {
pcepEventListener.add(listener);
}
@Override
public void removeEventListener(PcepEventListener listener) {
pcepEventListener.remove(listener);
}
@Override
public void writeMessage(PccId pccId, PcepMessage msg) {
this.getClient(pccId).sendMessage(msg);
}
@Override
public void processClientMessage(PccId pccId, PcepMessage msg) {
PcepClient pc = getClient(pccId);
switch (msg.getType()) {
case NONE:
break;
case OPEN:
break;
case KEEP_ALIVE:
//log.debug("Sending Keep Alive Message to {" + pccIpAddress.toString() + "}");
pc.sendMessage(Collections.singletonList(pc.factory().buildKeepaliveMsg().build()));
break;
case PATH_COMPUTATION_REQUEST:
break;
case PATH_COMPUTATION_REPLY:
break;
case NOTIFICATION:
break;
case ERROR:
break;
case CLOSE:
//log.debug("Sending Close Message to { }", pccIpAddress.toString());
pc.sendMessage(Collections.singletonList(pc.factory().buildCloseMsg().build()));
break;
case INITIATE:
if (!pc.capability().pcInstantiationCapability()) {
pc.sendMessage(Collections.singletonList(getErrMsg(pc.factory(),
ERROR_TYPE_19, ERROR_VALUE_5)));
}
break;
case REPORT:
//Only update the listener if respective capability is supported else send PCEP-ERR msg
if (pc.capability().statefulPceCapability()) {
for (PcepEventListener l : pcepEventListener) {
l.handleMessage(pccId, msg);
}
} else {
// Send PCEP-ERROR message.
pc.sendMessage(Collections.singletonList(getErrMsg(pc.factory(),
ERROR_TYPE_19, ERROR_VALUE_5)));
}
break;
case UPDATE:
if (!pc.capability().statefulPceCapability()) {
pc.sendMessage(Collections.singletonList(getErrMsg(pc.factory(),
ERROR_TYPE_19, ERROR_VALUE_5)));
}
break;
case LABEL_UPDATE:
if (!pc.capability().pceccCapability()) {
pc.sendMessage(Collections.singletonList(getErrMsg(pc.factory(),
ERROR_TYPE_19, ERROR_VALUE_5)));
}
break;
case MAX:
break;
case END:
break;
default:
break;
}
}
@Override
public void closeConnectedClients() {
PcepClient pc;
for (PccId id : connectedClients.keySet()) {
pc = getClient(id);
pc.disconnectClient();
}
}
private PcepErrorMsg getErrMsg(PcepFactory factory, byte errorType, byte errorValue) {
LinkedList<PcepError> llPcepErr = new LinkedList<>();
LinkedList<PcepErrorObject> llerrObj = new LinkedList<>();
PcepErrorMsg errMsg;
PcepErrorObject errObj = factory.buildPcepErrorObject().setErrorValue(errorValue).setErrorType(errorType)
.build();
llerrObj.add(errObj);
PcepError pcepErr = factory.buildPcepError().setErrorObjList(llerrObj).build();
llPcepErr.add(pcepErr);
PcepErrorInfo errInfo = factory.buildPcepErrorInfo().setPcepErrorList(llPcepErr).build();
errMsg = factory.buildPcepErrorMsg().setPcepErrorInfo(errInfo).build();
return errMsg;
}
/**
* Implementation of an Pcep Agent which is responsible for
* keeping track of connected clients and the state in which
* they are.
*/
public class PcepClientAgent implements PcepAgent {
@Override
public boolean addConnectedClient(PccId pccId, PcepClient pc) {
if (connectedClients.get(pccId) != null) {
return false;
} else {
connectedClients.put(pccId, pc);
for (PcepClientListener l : pcepClientListener) {
l.clientConnected(pccId);
}
return true;
}
}
@Override
public boolean validActivation(PccId pccId) {
if (connectedClients.get(pccId) == null) {
//log.error("Trying to activate client but is not in "
// + "connected switches: pccIp {}. Aborting ..", pccIpAddress.toString());
return false;
}
return true;
}
@Override
public void removeConnectedClient(PccId pccId) {
connectedClients.remove(pccId);
for (PcepClientListener l : pcepClientListener) {
//log.warn("removal for {}", pccIpAddress.toString());
l.clientDisconnected(pccId);
}
}
@Override
public void processPcepMessage(PccId pccId, PcepMessage m) {
processClientMessage(pccId, m);
}
@Override
public void addNode(PcepClient pc) {
for (PcepNodeListener l : pcepNodeListener) {
l.addNode(pc);
}
}
@Override
public void deleteNode(PccId pccId) {
for (PcepNodeListener l : pcepNodeListener) {
l.deleteNode(pccId);
}
}
}
}
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.provider.pcep.topology.impl;
import org.onosproject.net.DeviceId;
import org.onosproject.pcep.api.PcepController;
import org.onosproject.pcep.api.PcepDpid;
import org.onosproject.pcep.api.PcepLinkListener;
import org.onosproject.pcep.api.PcepSwitch;
import org.onosproject.pcep.api.PcepSwitchListener;
import org.onosproject.pcep.api.PcepTunnel;
import org.onosproject.pcep.api.PcepTunnelListener;
/**
* Implementation of PCEP controller.
*/
public class PcepControllerAdapter implements PcepController {
@Override
public Iterable<PcepSwitch> getSwitches() {
return null;
}
@Override
public PcepSwitch getSwitch(PcepDpid did) {
return null;
}
@Override
public void addListener(PcepSwitchListener listener) {
}
@Override
public void removeListener(PcepSwitchListener listener) {
}
@Override
public void addLinkListener(PcepLinkListener listener) {
}
@Override
public void removeLinkListener(PcepLinkListener listener) {
}
@Override
public void addTunnelListener(PcepTunnelListener listener) {
}
@Override
public void removeTunnelListener(PcepTunnelListener listener) {
}
@Override
public PcepTunnel applyTunnel(DeviceId srcDid, DeviceId dstDid, long srcPort, long dstPort, long bandwidth,
String name) {
return null;
}
@Override
public Boolean deleteTunnel(String id) {
return null;
}
@Override
public Boolean updateTunnelBandwidth(String id, long bandwidth) {
return null;
}
@Override
public void getTunnelStatistics(String pcepTunnelId) {
}
}
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
* an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
* specific language governing permissions and limitations under the License.
*/
package org.onosproject.provider.pcep.topology.impl;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.core.Is.is;
import static org.onosproject.net.Link.State.ACTIVE;
import static org.onosproject.provider.pcep.topology.impl.PcepTopologyProvider.LABEL_STACK_CAPABILITY;
import static org.onosproject.provider.pcep.topology.impl.PcepTopologyProvider.LSRID;
import static org.onosproject.provider.pcep.topology.impl.PcepTopologyProvider.PCECC_CAPABILITY;
import static org.onosproject.provider.pcep.topology.impl.PcepTopologyProvider.SR_CAPABILITY;
import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.onlab.packet.ChassisId;
import org.onlab.packet.IpAddress;
import org.onosproject.net.ConnectPoint;
import org.onosproject.net.DefaultDevice;
import org.onosproject.net.DefaultLink;
import org.onosproject.net.Device;
import org.onosproject.net.DeviceId;
import org.onosproject.net.Link;
import org.onosproject.net.MastershipRole;
import org.onosproject.net.device.DeviceDescription;
import org.onosproject.net.device.DeviceProvider;
import org.onosproject.net.device.DeviceProviderRegistry;
import org.onosproject.net.device.DeviceProviderService;
import org.onosproject.net.device.DeviceServiceAdapter;
import org.onosproject.net.device.PortDescription;
import org.onosproject.net.device.PortStatistics;
import org.onosproject.net.link.LinkDescription;
import org.onosproject.net.link.LinkProvider;
import org.onosproject.net.link.LinkProviderRegistry;
import org.onosproject.net.link.LinkProviderService;
import org.onosproject.net.provider.ProviderId;
import org.onosproject.pcep.controller.ClientCapability;
import org.onosproject.pcep.controller.PccId;
import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepNodeListener;
/**
* Test for PCEP topology provider.
*/
public class PcepTopologyProviderTest {
private static final String UNKNOWN = new String("unknown");
public static ProviderId providerId = new ProviderId("l3", "foo");
private final PcepClientControllerAdapter clientController = new PcepClientControllerAdapter();
private final PcepTopologyProvider provider = new PcepTopologyProvider();
private final MockDeviceRegistry nodeRegistry = new MockDeviceRegistry();
private final PcepControllerAdapter controller = new PcepControllerAdapter();
private final MockLinkRegistry linkRegistry = new MockLinkRegistry();
private final MockDeviceService deviceService = new MockDeviceService();
private Map<DeviceId, Device> deviceMap = new HashMap<>();
@Before
public void startUp() {
provider.pcepClientController = clientController;
provider.deviceProviderRegistry = nodeRegistry;
provider.linkProviderRegistry = linkRegistry;
provider.controller = controller;
provider.deviceService = deviceService;
provider.activate();
}
@After
public void tearDown() {
provider.deactivate();
provider.deviceProviderRegistry = null;
provider.pcepClientController = null;
provider.linkProviderRegistry = null;
provider.controller = null;
provider.deviceService = null;
}
/* Class implement device test registry */
private class MockLinkRegistry implements LinkProviderRegistry {
LinkProvider linkProvider;
Set<Link> links = new HashSet<>();
@Override
public LinkProviderService register(LinkProvider provider) {
this.linkProvider = provider;
return new MockProviderService();
}
@Override
public void unregister(LinkProvider provider) {
// TODO Auto-generated method stub
}
@Override
public Set<ProviderId> getProviders() {
return null;
}
private class MockProviderService implements LinkProviderService {
@Override
public void linkDetected(LinkDescription linkDescription) {
links.add(DefaultLink.builder().src(linkDescription.src())
.dst(linkDescription.dst()).state(ACTIVE).type(linkDescription.type())
.providerId(ProviderId.NONE).build());
}
@Override
public void linkVanished(LinkDescription linkDescription) {
links.remove(DefaultLink.builder().src(linkDescription.src())
.dst(linkDescription.dst()).state(ACTIVE).type(linkDescription.type())
.providerId(ProviderId.NONE).build());
}
@Override
public void linksVanished(ConnectPoint connectPoint) {
// TODO Auto-generated method stub
}
@Override
public void linksVanished(DeviceId deviceId) {
// TODO Auto-generated method stub
}
@Override
public LinkProvider provider() {
// TODO Auto-generated method stub
return null;
}
}
}
/* Class implement device test registry */
private class MockDeviceRegistry implements DeviceProviderRegistry {
DeviceProvider provider;
Set<DeviceId> connected = new HashSet<>();
@Override
public DeviceProviderService register(DeviceProvider provider) {
this.provider = provider;
return new MockProviderService();
}
@Override
public void unregister(DeviceProvider provider) {
}
@Override
public Set<ProviderId> getProviders() {
return null;
}
private class MockProviderService implements DeviceProviderService {
@Override
public DeviceProvider provider() {
return null;
}
@Override
public void deviceConnected(DeviceId deviceId, DeviceDescription deviceDescription) {
connected.add(deviceId);
Device device = new DefaultDevice(ProviderId.NONE, deviceId, Device.Type.ROUTER, UNKNOWN, UNKNOWN,
UNKNOWN, UNKNOWN, new ChassisId(), deviceDescription.annotations());
deviceMap.put(deviceId, device);
}
@Override
public void deviceDisconnected(DeviceId deviceId) {
connected.remove(deviceId);
deviceMap.remove(deviceId);
}
@Override
public void updatePorts(DeviceId deviceId, List<PortDescription> portDescriptions) {
// TODO Auto-generated method stub
}
@Override
public void portStatusChanged(DeviceId deviceId, PortDescription portDescription) {
// TODO Auto-generated method stub
}
@Override
public void receivedRoleReply(DeviceId deviceId, MastershipRole requested, MastershipRole response) {
// TODO Auto-generated method stub
}
@Override
public void updatePortStatistics(DeviceId deviceId, Collection<PortStatistics> portStatistics) {
// TODO Auto-generated method stub
}
}
}
/* Mock test for device service */
private class MockDeviceService extends DeviceServiceAdapter {
@Override
public Device getDevice(DeviceId deviceId) {
return deviceMap.get(deviceId);
}
}
/**
* Adds the PCEP device and removes it.
*/
@Test
public void testPcepTopologyProviderTestAddDevice1() {
PcepClient pc = clientController.getClient(PccId.pccId(IpAddress.valueOf("1.1.1.1")));
for (PcepNodeListener l : clientController.pcepNodeListener) {
pc.setCapability(new ClientCapability(true, true, false, true, true));
l.addNode(pc);
assertThat(nodeRegistry.connected.size(), is(1));
assertThat(deviceMap.keySet().iterator().next(), is(DeviceId.deviceId("l3:1.1.1.1")));
assertThat(deviceMap.values().iterator().next().annotations().value(LABEL_STACK_CAPABILITY), is("true"));
assertThat(deviceMap.values().iterator().next().annotations().value(LSRID), is("1.1.1.1"));
assertThat(deviceMap.values().iterator().next().annotations().value(PCECC_CAPABILITY), is("true"));
assertThat(deviceMap.values().iterator().next().annotations().value(SR_CAPABILITY), is("true"));
l.deleteNode(pc.getPccId());
assertThat(nodeRegistry.connected.size(), is(0));
}
}
}
......@@ -139,4 +139,12 @@ public class PcepClientAdapter implements PcepClient {
public ClientCapability capability() {
return capability;
}
@Override
public void addNode(PcepClient pc) {
}
@Override
public void deleteNode(PccId pccId) {
}
}
......
......@@ -31,6 +31,7 @@ import org.onosproject.pcep.controller.PcepClient;
import org.onosproject.pcep.controller.PcepClientController;
import org.onosproject.pcep.controller.PcepClientListener;
import org.onosproject.pcep.controller.PcepEventListener;
import org.onosproject.pcep.controller.PcepNodeListener;
import org.onosproject.pcep.controller.driver.PcepAgent;
import org.onosproject.pcepio.protocol.PcepError;
import org.onosproject.pcepio.protocol.PcepErrorInfo;
......@@ -57,6 +58,7 @@ public class PcepClientControllerAdapter implements PcepClientController {
protected Set<PcepClientListener> pcepClientListener = new HashSet<>();
protected Set<PcepEventListener> pcepEventListener = Sets.newHashSet();
public Set<PcepNodeListener> pcepNodeListener = Sets.newHashSet();
@Activate
public void activate() {
......@@ -79,9 +81,9 @@ public class PcepClientControllerAdapter implements PcepClientController {
PcepClientAdapter pc = new PcepClientAdapter();
if (pccId.ipAddress().equals(IpAddress.valueOf(0xC010103))
|| pccId.ipAddress().equals(IpAddress.valueOf(0xB6024E22))) {
pc.setCapability(new ClientCapability(true, false, false));
pc.setCapability(new ClientCapability(true, false, false, false, false));
} else {
pc.setCapability(new ClientCapability(true, true, true));
pc.setCapability(new ClientCapability(true, true, true, false, false));
}
pc.init(PccId.pccId(pccId.ipAddress()), PcepVersion.PCEP_1);
connectedClients.put(pccId, pc);
......@@ -96,6 +98,16 @@ public class PcepClientControllerAdapter implements PcepClientController {
}
@Override
public void addNodeListener(PcepNodeListener listener) {
pcepNodeListener.add(listener);
}
@Override
public void removeNodeListener(PcepNodeListener listener) {
pcepNodeListener.remove(listener);
}
@Override
public void removeListener(PcepClientListener listener) {
this.pcepClientListener.remove(listener);
}
......@@ -254,5 +266,19 @@ public class PcepClientControllerAdapter implements PcepClientController {
public void processPcepMessage(PccId pccId, PcepMessage m) {
processClientMessage(pccId, m);
}
@Override
public void addNode(PcepClient pc) {
for (PcepNodeListener l : pcepNodeListener) {
l.addNode(pc);
}
}
@Override
public void deleteNode(PccId pccId) {
for (PcepNodeListener l : pcepNodeListener) {
l.deleteNode(pccId);
}
}
}
}
......
......@@ -261,7 +261,7 @@ public class PcepTunnelAddedTest {
tunnelService.setupTunnel(null, null, tunnel, null);
PccId pccId = PccId.pccId(IpAddress.valueOf(0x4e1f0400));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true, false, false));
controller.getClient(pccId).setLspDbSyncStatus(SYNCED);
// Process update message.
......@@ -310,7 +310,7 @@ public class PcepTunnelAddedTest {
PccId pccId = PccId.pccId(IpAddress.valueOf("1.1.1.1"));
controller.getClient(pccId).setLspDbSyncStatus(SYNCED);
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true, false, false));
controller.processClientMessage(pccId, message);
assertThat(registry.tunnelIdCounter, is((long) 1));
......@@ -356,7 +356,7 @@ public class PcepTunnelAddedTest {
PcepMessage message1 = reader1.readFrom(buffer1);
PccId pccId = PccId.pccId(IpAddress.valueOf("1.1.1.1"));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true, false, false));
controller.processClientMessage(pccId, message1);
/* create 2nd LSP */
......@@ -495,7 +495,7 @@ public class PcepTunnelAddedTest {
PcepMessage message1 = reader1.readFrom(buffer1);
PccId pccId = PccId.pccId(IpAddress.valueOf("1.1.1.1"));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true));
controller.getClient(pccId).setCapability(new ClientCapability(true, true, true, false, false));
controller.processClientMessage(pccId, message1);
/* create 2nd LSP */
......