blob: 65a844c25d10d0c8f8f0e58c9479daa222b15164 [file] [log] [blame]
/*
* Copyright 2015 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.pcepio.protocol.ver1;
import java.util.LinkedList;
import java.util.ListIterator;
import org.jboss.netty.buffer.ChannelBuffer;
import org.onosproject.pcepio.exceptions.PcepParseException;
import org.onosproject.pcepio.protocol.PcepAttribute;
import org.onosproject.pcepio.protocol.PcepBandwidthObject;
import org.onosproject.pcepio.protocol.PcepIroObject;
import org.onosproject.pcepio.protocol.PcepLspaObject;
import org.onosproject.pcepio.protocol.PcepMetricObject;
import org.onosproject.pcepio.types.PcepObjectHeader;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.google.common.base.MoreObjects;
/**
* Provides PCEP Attribute List.
*/
public class PcepAttributeVer1 implements PcepAttribute {
/* Reference : RFC5440
* where:
* <attribute-list> ::=[<LSPA>]
* [<BANDWIDTH>]
* [<metric-list>]
* [<IRO>]
*
* <metric-list> ::=<METRIC>[<metric-list>]
*/
protected static final Logger log = LoggerFactory.getLogger(PcepAttributeVer1.class);
public static final int OBJECT_HEADER_LENGTH = 4;
//PCEP LSPA Object
private PcepLspaObject lspaObject;
private boolean isLspaObjectSet;
//PCEP Bandwidth Object
private PcepBandwidthObject bandwidthObject;
private boolean isBandwidthObjectSet;
//PCEP Metric list
private LinkedList<PcepMetricObject> llMetricList;
private boolean isMetricListSet;
//PCEP IRO object
private PcepIroObject iroObject;
private boolean isIroObjectSet;
/**
* Default constructor to initialize member variables.
*/
public PcepAttributeVer1() {
lspaObject = null;
bandwidthObject = null;
llMetricList = null;
iroObject = null;
this.isLspaObjectSet = false;
this.isBandwidthObjectSet = false;
this.isMetricListSet = false;
this.isIroObjectSet = false;
}
/**
* Constructor to initialize all parameters for PCEP attribute.
*
* @param lspaObject PCEP lspa Object.
* @param bandwidthObject PCEP bandwidth object.
* @param llMetricList list of PCEP metric objects.
* @param iroObject PCEP iro object.
*/
public PcepAttributeVer1(PcepLspaObject lspaObject, PcepBandwidthObject bandwidthObject,
LinkedList<PcepMetricObject> llMetricList, PcepIroObject iroObject) {
this.lspaObject = lspaObject;
this.bandwidthObject = bandwidthObject;
this.llMetricList = llMetricList;
this.iroObject = iroObject;
if (lspaObject == null) {
this.isLspaObjectSet = false;
} else {
this.isLspaObjectSet = true;
}
if (bandwidthObject == null) {
this.isBandwidthObjectSet = false;
} else {
this.isBandwidthObjectSet = true;
}
if (llMetricList == null) {
this.isMetricListSet = false;
} else {
this.isMetricListSet = true;
}
if (iroObject == null) {
this.isIroObjectSet = false;
} else {
this.isIroObjectSet = true;
}
}
/**
* constructor to initialize bandwidthObject.
*
* @param bandwidthObject bandwidth object
*/
public PcepAttributeVer1(PcepBandwidthObject bandwidthObject) {
this.isLspaObjectSet = false;
this.bandwidthObject = bandwidthObject;
this.isBandwidthObjectSet = true;
this.isMetricListSet = false;
this.isIroObjectSet = false;
}
/**
* Parse list for MeticObject.
*
* @param cb of type channel buffer
* @return true if parsing metric list is success
* @throws PcepParseException when a non metric object is received
*/
public boolean parseMetricList(ChannelBuffer cb) throws PcepParseException {
if (llMetricList == null) {
llMetricList = new LinkedList<>();
}
PcepMetricObject metriclist;
//caller should verify for metric object
byte yObjClass = PcepMetricObjectVer1.METRIC_OBJ_CLASS;
byte yObjType = PcepMetricObjectVer1.METRIC_OBJ_TYPE;
while ((yObjClass == PcepMetricObjectVer1.METRIC_OBJ_CLASS)
&& (yObjType == PcepMetricObjectVer1.METRIC_OBJ_TYPE)) {
metriclist = PcepMetricObjectVer1.read(cb);
llMetricList.add(metriclist);
yObjClass = 0;
yObjType = 0;
if (cb.readableBytes() > OBJECT_HEADER_LENGTH) {
cb.markReaderIndex();
PcepObjectHeader tempObjHeader = PcepObjectHeader.read(cb);
cb.resetReaderIndex();
yObjClass = tempObjHeader.getObjClass();
yObjType = tempObjHeader.getObjType();
}
}
return true;
}
/**
* Reads lspa , bandwidth , Metriclist and Iro objects and sets the objects.
*
* @param cb of type channel buffer
* @return instance of Pcep Attribute
* @throws PcepParseException while parsing Pcep Attributes from channel buffer
*/
public static PcepAttribute read(ChannelBuffer cb) throws PcepParseException {
if (cb.readableBytes() < OBJECT_HEADER_LENGTH) {
return null;
}
//check whether any pcep attribute is present
cb.markReaderIndex();
PcepObjectHeader tempObjHeader = PcepObjectHeader.read(cb);
cb.resetReaderIndex();
byte yObjClass = tempObjHeader.getObjClass();
if (PcepLspaObjectVer1.LSPA_OBJ_CLASS != yObjClass && PcepBandwidthObjectVer1.BANDWIDTH_OBJ_CLASS != yObjClass
&& PcepMetricObjectVer1.METRIC_OBJ_CLASS != yObjClass && PcepIroObjectVer1.IRO_OBJ_CLASS != yObjClass) {
//No PCEP attribute is present
return null;
}
PcepAttributeVer1 pcepAttribute = new PcepAttributeVer1();
//If LSPA present then store it.LSPA is optional
if (yObjClass == PcepLspaObjectVer1.LSPA_OBJ_CLASS) {
pcepAttribute.setLspaObject(PcepLspaObjectVer1.read(cb));
yObjClass = checkNextObject(cb);
}
//If BANDWIDTH present then store it.BANDWIDTH is optional
if (yObjClass == PcepBandwidthObjectVer1.BANDWIDTH_OBJ_CLASS) {
pcepAttribute.setBandwidthObject(PcepBandwidthObjectVer1.read(cb));
yObjClass = checkNextObject(cb);
}
//If Metric list present then store it.MetricList is optional
if (yObjClass == PcepMetricObjectVer1.METRIC_OBJ_CLASS) {
pcepAttribute.parseMetricList(cb);
yObjClass = checkNextObject(cb);
}
//If IRO present then store it.IRO is optional
if (yObjClass == PcepIroObjectVer1.IRO_OBJ_CLASS) {
pcepAttribute.setIroObject(PcepIroObjectVer1.read(cb));
}
PcepLspaObject lspaObject = pcepAttribute.getLspaObject();
PcepBandwidthObject bandwidthObject = pcepAttribute.getBandwidthObject();
LinkedList<PcepMetricObject> metriclist = pcepAttribute.llMetricList;
PcepIroObject iroObject = pcepAttribute.getIroObject();
return new PcepAttributeVer1(lspaObject, bandwidthObject, metriclist, iroObject);
}
/**
* Checks whether there is a more object or not.
*
* @param cb of type channel buffer
* @return instance of object header
*/
private static byte checkNextObject(ChannelBuffer cb) {
if (cb.readableBytes() < OBJECT_HEADER_LENGTH) {
return 0;
}
cb.markReaderIndex();
PcepObjectHeader tempObjHeader = PcepObjectHeader.read(cb);
cb.resetReaderIndex();
return tempObjHeader.getObjClass();
}
@Override
public int write(ChannelBuffer cb) throws PcepParseException {
int iLenStartIndex = cb.writerIndex();
//PCEP LSPA object is optional
if (this.isLspaObjectSet) {
this.lspaObject.write(cb);
}
//PCEP BANDWIDTH object is optional
if (this.isBandwidthObjectSet) {
this.bandwidthObject.write(cb);
}
//PCEP Metric list is optional
if (this.isMetricListSet) {
ListIterator<PcepMetricObject> listIterator = this.llMetricList.listIterator();
while (listIterator.hasNext()) {
listIterator.next().write(cb);
}
}
//PCEP IRO object is optional
if (this.isIroObjectSet) {
this.iroObject.write(cb);
}
return cb.writerIndex() - iLenStartIndex;
}
@Override
public PcepLspaObject getLspaObject() {
return lspaObject;
}
@Override
public PcepBandwidthObject getBandwidthObject() {
return bandwidthObject;
}
@Override
public LinkedList<PcepMetricObject> getMetricObjectList() {
return llMetricList;
}
@Override
public PcepIroObject getIroObject() {
return iroObject;
}
@Override
public void setBandwidthObject(PcepBandwidthObject bandwidthObject) {
this.isBandwidthObjectSet = true;
this.bandwidthObject = bandwidthObject;
}
@Override
public void setMetricObjectList(LinkedList<PcepMetricObject> llMetricList) {
this.isMetricListSet = true;
this.llMetricList = llMetricList;
}
@Override
public void setLspaObject(PcepLspaObject lspaObject) {
this.isLspaObjectSet = true;
this.lspaObject = lspaObject;
}
@Override
public void setIroObject(PcepIroObject iroObject) {
this.isIroObjectSet = true;
this.iroObject = iroObject;
}
/**
* Builder class for PCEP attributes.
*/
public static class Builder implements PcepAttribute.Builder {
//PCEP LSPA Object
private PcepLspaObject lspaObject;
private boolean isLspaObjectSet;
//PCEP BANDWIDTH Object
private PcepBandwidthObject bandwidthObject;
private boolean isBandwidthObjectSet;
//PCEP Metric list
private LinkedList<PcepMetricObject> llMetricList;
private boolean isMetricListSet;
//PCEP IRO object
private PcepIroObject iroObject;
private boolean isIroObjectSet;
@Override
public PcepAttribute build() {
//PCEP LSPA Object
PcepLspaObject lspaObject = null;
//PCEP BANDWIDTH Object
PcepBandwidthObject bandwidthObject = null;
//PCEP Metric list
LinkedList<PcepMetricObject> llMetricList = null;
//PCEP IRO object
PcepIroObject iroObject = null;
if (this.isLspaObjectSet) {
lspaObject = this.lspaObject;
}
if (this.isBandwidthObjectSet) {
bandwidthObject = this.bandwidthObject;
}
if (this.isMetricListSet) {
llMetricList = this.llMetricList;
}
if (this.isIroObjectSet) {
iroObject = this.iroObject;
}
return new PcepAttributeVer1(lspaObject, bandwidthObject, llMetricList, iroObject);
}
@Override
public PcepLspaObject getLspaObject() {
return this.lspaObject;
}
@Override
public PcepBandwidthObject getBandwidthObject() {
return this.bandwidthObject;
}
@Override
public LinkedList<PcepMetricObject> getMetricObjectList() {
return this.llMetricList;
}
@Override
public PcepIroObject getIroObject() {
return this.iroObject;
}
@Override
public Builder setBandwidthObject(PcepBandwidthObject bandwidthObject) {
this.isBandwidthObjectSet = true;
this.bandwidthObject = bandwidthObject;
return this;
}
@Override
public Builder setMetricObjectList(LinkedList<PcepMetricObject> llMetricList) {
this.isMetricListSet = true;
this.llMetricList = llMetricList;
return this;
}
@Override
public Builder setLspaObject(PcepLspaObject lspaObject) {
this.isLspaObjectSet = true;
this.lspaObject = lspaObject;
return this;
}
@Override
public Builder setIroObject(PcepIroObject iroObject) {
this.isIroObjectSet = true;
this.iroObject = iroObject;
return this;
}
}
@Override
public String toString() {
return MoreObjects.toStringHelper(getClass())
.omitNullValues()
.add("lspaObject", lspaObject)
.add("bandwidthObject", bandwidthObject)
.add("MetricObjectList", llMetricList)
.add("IroObject", iroObject)
.toString();
}
}