Modified CienaWaverServer driver to change frequency rather then
channels when installing flows. Channels are not consistent amongst
the devices in a sense that different devices are using different
frequency schemes to represent channels.
Change-Id: Idb12ccd0c4dbdb89e61160b455b959b4c36034cb
diff --git a/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaFlowRuleProgrammable.java b/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaFlowRuleProgrammable.java
index d0e78fc..5e05232 100644
--- a/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaFlowRuleProgrammable.java
+++ b/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaFlowRuleProgrammable.java
@@ -30,6 +30,7 @@
import java.util.List;
import java.util.Collection;
import java.util.Collections;
+import java.util.Objects;
import java.util.stream.Collectors;
import static org.slf4j.LoggerFactory.getLogger;
@@ -62,8 +63,8 @@
}
// Apply the valid rules on the device
Collection<FlowRule> added = rules.stream()
- .map(r -> createCrossConnectFlowRule(r))
- .filter(xc -> installCrossConnect(xc))
+ .map(this::createCrossConnectFlowRule)
+ .filter(this::installCrossConnect)
.collect(Collectors.toList());
restCiena.setCrossConnectCache(added);
return added;
@@ -79,8 +80,8 @@
return Collections.emptyList();
}
Collection<FlowRule> removed = rules.stream()
- .map(r -> createCrossConnectFlowRule(r))
- .filter(xc -> xc != null)
+ .map(this::createCrossConnectFlowRule)
+ .filter(Objects::nonNull)
.collect(Collectors.toList());
restCiena.removeCrossConnectCache(removed);
return removed;
@@ -88,7 +89,7 @@
private CrossConnectFlowRule createCrossConnectFlowRule(FlowRule r) {
List<PortNumber> linePorts = CienaRestDevice.getLinesidePortId().stream()
- .map(p -> PortNumber.portNumber(p))
+ .map(PortNumber::portNumber)
.collect(Collectors.toList());
try {
return new CrossConnectFlowRule(r, linePorts);
@@ -129,7 +130,7 @@
/*
* rule is installed in three steps
* 1- disable port
- * 2- change channel
+ * 2- change frequency
* 3- enable port
*/
try {
@@ -143,8 +144,8 @@
if (!restCiena.disablePort(outPort)) {
return false;
}
- //2- change channel
- if (!restCiena.changeChannel(signal, outPort)) {
+ //2- change frequency
+ if (!restCiena.changeFrequency(signal, outPort)) {
return false;
}
//3- enable port
diff --git a/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaRestDevice.java b/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaRestDevice.java
index 0fce654..361d538 100644
--- a/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaRestDevice.java
+++ b/drivers/ciena/src/main/java/org/onosproject/drivers/ciena/CienaRestDevice.java
@@ -67,7 +67,7 @@
import static org.slf4j.LoggerFactory.getLogger;
public class CienaRestDevice {
- private static final Frequency BASE_FREQUENCY = Frequency.ofGHz(193_950);
+ private static final Frequency CENTER_FREQUENCY = Frequency.ofGHz(195_950);
private static final String ENABLED = "enabled";
private static final String DISABLED = "disabled";
private static final String VALUE = "value";
@@ -101,6 +101,7 @@
private static final String CHANNEL_URI = TRANSMITTER_URI + "/" + LINE_SYSTEM_CHANNEL_NUMBER;
private static final String ACTIVE_ALARMS_URL = ALARM_KEY + "/" + ACTIVE;
private static final List<String> LINESIDE_PORT_ID = ImmutableList.of("4", "48");
+ private static final ChannelSpacing CHANNEL_SPACING = ChannelSpacing.CHL_50GHZ;
private final Logger log = getLogger(getClass());
@@ -166,10 +167,10 @@
}
- private String genFrequencyChangeRequest(long frequency) {
+ private String genFrequencyChangeRequest(double frequency) {
String request = "{\n" +
"\"" + FREQUENCY_KEY + "\": {\n" +
- "\"" + VALUE + "\": " + Long.toString(frequency) + "\n" +
+ "\"" + VALUE + "\": " + Double.toString(frequency) + "\n" +
"}\n" +
"}";
log.debug("request:\n{}", request);
@@ -249,7 +250,7 @@
public final boolean changeFrequency(OchSignal signal, PortNumber outPort) {
String uri = genUri(FREQUENCY_URI, outPort);
- long frequency = toFrequency(signal);
+ double frequency = signal.centralFrequency().asGHz();
String request = genFrequencyChangeRequest(frequency);
boolean response = putNoReply(uri, request);
if (!response) {
@@ -271,13 +272,7 @@
return response;
}
- private final long toFrequency(OchSignal signal) {
- double frequency = BASE_FREQUENCY.asGHz() +
- (signal.channelSpacing().frequency().asGHz() * (double) signal.slotGranularity());
- return Double.valueOf(frequency).longValue();
- }
-
- private final int getChannel(PortNumber port) {
+ private int getChannel(PortNumber port) {
try {
String uri = genUri(CHANNEL_URI, port);
JsonNode response = get(uri);
@@ -290,6 +285,25 @@
}
+ private int getChannelFromFrequency(Frequency frequency) {
+ return (int) CENTER_FREQUENCY.subtract(frequency)
+ .floorDivision(CHANNEL_SPACING.frequency().asHz()).asHz();
+
+ }
+
+ private Frequency getFrequency(PortNumber port) {
+ try {
+ String uri = genUri(FREQUENCY_URI, port);
+ JsonNode response = get(uri);
+ return Frequency.ofGHz(response.get(FREQUENCY_KEY).get(VALUE).asDouble());
+ } catch (IOException e) {
+ // this is expected for client side ports as they don't contain channel data
+ log.error("unable to get frequency for port {} on device {}:\n{}", port, deviceId, e);
+ return null;
+ }
+
+ }
+
private AlarmEntityId getAlarmSource(String instance) {
AlarmEntityId source;
if (instance.contains(PORT)) {
@@ -346,8 +360,8 @@
try {
List<JsonNode> alarms = Lists.newArrayList(get(ACTIVE_ALARMS_URL).get(ACTIVE).elements());
return alarms.stream()
- .map(a -> newAlarmFromJsonNode(a))
- .filter(a -> a != null)
+ .map(this::newAlarmFromJsonNode)
+ .filter(Objects::nonNull)
.collect(Collectors.toList());
} catch (IOException e) {
log.error("unable to get active alarms for device {}:\n", deviceId, e);
@@ -362,17 +376,17 @@
return ports.stream()
.filter(p -> LINESIDE_PORT_ID.contains(p.number().name()))
.map(p -> fetchRule(p.number()))
- .filter(p -> p != null)
+ .filter(Objects::nonNull)
.map(fr -> new DefaultFlowEntry(fr, FlowEntry.FlowEntryState.ADDED, 0, 0, 0))
.collect(Collectors.toList());
}
private FlowRule fetchRule(PortNumber port) {
- int channel = getChannel(port);
- if (channel == -1) {
+ Frequency frequency = getFrequency(port);
+ if (frequency == null) {
return null;
}
-
+ int channel = getChannelFromFrequency(frequency);
/*
* both inPort and outPort will be same as WaveServer only deal with same port ptp-indexes
* channel and spaceMultiplier are same.
@@ -382,7 +396,7 @@
TrafficSelector selector = DefaultTrafficSelector.builder()
.matchInPort(port)
.add(Criteria.matchOchSignalType(OchSignalType.FIXED_GRID))
- .add(Criteria.matchLambda(OchSignal.newDwdmSlot(ChannelSpacing.CHL_50GHZ, channel)))
+ .add(Criteria.matchLambda(OchSignal.newDwdmSlot(CHANNEL_SPACING, channel)))
.build();
TrafficTreatment treatment = DefaultTrafficTreatment.builder()
.setOutput(port)
@@ -394,7 +408,7 @@
return null;
}
- FlowRule fr = DefaultFlowRule.builder()
+ return DefaultFlowRule.builder()
.forDevice(deviceId)
.makePermanent()
.withSelector(selector)
@@ -402,8 +416,6 @@
.withPriority(lookup.getRight())
.withCookie(lookup.getLeft().value())
.build();
-
- return fr;
}
public List<Alarm> getAlarms() {