X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=controller.git;a=blobdiff_plain;f=opendaylight%2Fforwardingrulesmanager_mdsal%2Fopenflow%2Fsrc%2Fmain%2Fjava%2Forg%2Fopendaylight%2Fcontroller%2Fforwardingrulesmanager_mdsal%2Fconsumer%2Fimpl%2FMeterConsumerImpl.java;h=34adc28fc5453c8816d4cab752020728d4589ded;hp=5eb971ed912e56f8f85cafa41962e3494a4b2064;hb=7d77087c3374f53b8f775a5ef427f868f7bf2596;hpb=1a898f3bd37baec93cc13140a5eb24b30d4ea999 diff --git a/opendaylight/forwardingrulesmanager_mdsal/openflow/src/main/java/org/opendaylight/controller/forwardingrulesmanager_mdsal/consumer/impl/MeterConsumerImpl.java b/opendaylight/forwardingrulesmanager_mdsal/openflow/src/main/java/org/opendaylight/controller/forwardingrulesmanager_mdsal/consumer/impl/MeterConsumerImpl.java index 5eb971ed91..34adc28fc5 100644 --- a/opendaylight/forwardingrulesmanager_mdsal/openflow/src/main/java/org/opendaylight/controller/forwardingrulesmanager_mdsal/consumer/impl/MeterConsumerImpl.java +++ b/opendaylight/forwardingrulesmanager_mdsal/openflow/src/main/java/org/opendaylight/controller/forwardingrulesmanager_mdsal/consumer/impl/MeterConsumerImpl.java @@ -1,13 +1,15 @@ package org.opendaylight.controller.forwardingrulesmanager_mdsal.consumer.impl; import java.util.ArrayList; +import java.util.Collection; import java.util.EnumSet; import java.util.HashMap; import java.util.HashSet; +import java.util.Iterator; import java.util.List; import java.util.Map; -import java.util.Set; import java.util.Map.Entry; +import java.util.Set; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentMap; @@ -16,16 +18,16 @@ import org.opendaylight.controller.clustering.services.CacheExistException; import org.opendaylight.controller.clustering.services.IClusterContainerServices; import org.opendaylight.controller.clustering.services.IClusterServices; import org.opendaylight.controller.md.sal.common.api.data.DataCommitHandler; -import org.opendaylight.controller.md.sal.common.api.data.DataModification; import org.opendaylight.controller.md.sal.common.api.data.DataCommitHandler.DataCommitTransaction; +import org.opendaylight.controller.md.sal.common.api.data.DataModification; import org.opendaylight.controller.sal.common.util.Rpcs; import org.opendaylight.controller.sal.core.IContainer; import org.opendaylight.controller.sal.core.Node; import org.opendaylight.controller.sal.utils.GlobalConstants; import org.opendaylight.controller.sal.utils.Status; import org.opendaylight.controller.sal.utils.StatusCode; -import org.opendaylight.controller.switchmanager.ISwitchManager; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.config.rev131024.Meters; +import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.config.rev131024.meters.Meter; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.config.rev131024.meters.MeterKey; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.AddMeterInputBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.MeterAdded; @@ -34,11 +36,11 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.Met import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.SalMeterListener; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.SalMeterService; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.UpdateMeterInputBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.meter.update.UpdatedMeterBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.band.type.BandType; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.band.type.band.type.Drop; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.band.type.band.type.DscpRemark; import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.types.rev130918.band.type.band.type.Experimenter; -import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.config.rev131024.meters.Meter; import org.opendaylight.yangtools.concepts.Registration; import org.opendaylight.yangtools.yang.binding.DataObject; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; @@ -47,60 +49,59 @@ import org.opendaylight.yangtools.yang.common.RpcResult; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -public class MeterConsumerImpl { +public class MeterConsumerImpl implements IForwardingRulesManager { protected static final Logger logger = LoggerFactory.getLogger(MeterConsumerImpl.class); - private MeterEventListener meterEventListener = new MeterEventListener(); + private final MeterEventListener meterEventListener = new MeterEventListener(); private Registration meterListener; - private SalMeterService meterService; + private SalMeterService meterService; private MeterDataCommitHandler commitHandler; - + private ConcurrentMap originalSwMeterView; private ConcurrentMap installedSwMeterView; - + private ConcurrentMap> nodeMeters; private ConcurrentMap inactiveMeters; - - private IClusterContainerServices clusterMeterContainerService = null; + + private IClusterContainerServices clusterMeterContainerService = null; private IContainer container; - + public MeterConsumerImpl() { - InstanceIdentifier path = InstanceIdentifier.builder().node(Meters.class).node(Meter.class).toInstance(); - meterService = FRMConsumerImpl.getProviderSession().getRpcService(SalMeterService.class); + InstanceIdentifier path = InstanceIdentifier.builder().node(Meters.class) + .node(Meter.class).toInstance(); + meterService = FRMConsumerImpl.getProviderSession().getRpcService(SalMeterService.class); clusterMeterContainerService = FRMConsumerImpl.getClusterContainerService(); - + container = FRMConsumerImpl.getContainer(); - + if (!(cacheStartup())) { logger.error("Unable to allocate/retrieve meter cache"); System.out.println("Unable to allocate/retrieve meter cache"); } - + if (null == meterService) { logger.error("Consumer SAL Meter Service is down or NULL. FRM may not function as intended"); System.out.println("Consumer SAL Meter Service is down or NULL."); return; - } - + } + // For switch/plugin events meterListener = FRMConsumerImpl.getNotificationService().registerNotificationListener(meterEventListener); - + if (null == meterListener) { logger.error("Listener to listen on meter data modifcation events"); System.out.println("Listener to listen on meter data modifcation events."); return; - } - + } + commitHandler = new MeterDataCommitHandler(); FRMConsumerImpl.getDataProviderService().registerCommitHandler(path, commitHandler); } - - - + private boolean allocateMeterCaches() { if (this.clusterMeterContainerService == null) { logger.warn("Meter: Un-initialized clusterMeterContainerService, can't create cache"); return false; - } + } try { clusterMeterContainerService.createCache("frm.originalSwMeterView", @@ -114,32 +115,36 @@ public class MeterConsumerImpl { clusterMeterContainerService.createCache("frm.nodeMeters", EnumSet.of(IClusterServices.cacheMode.TRANSACTIONAL)); - -//TODO for cluster mode - /* clusterMeterContainerService.createCache(WORK_STATUS_CACHE, - EnumSet.of(IClusterServices.cacheMode.NON_TRANSACTIONAL, IClusterServices.cacheMode.ASYNC)); - - clusterMeterContainerService.createCache(WORK_ORDER_CACHE, - EnumSet.of(IClusterServices.cacheMode.NON_TRANSACTIONAL, IClusterServices.cacheMode.ASYNC));*/ - - } catch (CacheConfigException cce) { + + // TODO for cluster mode + /* + * clusterMeterContainerService.createCache(WORK_STATUS_CACHE, + * EnumSet.of(IClusterServices.cacheMode.NON_TRANSACTIONAL, + * IClusterServices.cacheMode.ASYNC)); + * + * clusterMeterContainerService.createCache(WORK_ORDER_CACHE, + * EnumSet.of(IClusterServices.cacheMode.NON_TRANSACTIONAL, + * IClusterServices.cacheMode.ASYNC)); + */ + + } catch (CacheConfigException cce) { logger.error("Meter CacheConfigException"); return false; - + } catch (CacheExistException cce) { - logger.error(" Meter CacheExistException"); + logger.error(" Meter CacheExistException"); } - + return true; } - + private void nonClusterMeterObjectCreate() { originalSwMeterView = new ConcurrentHashMap(); installedSwMeterView = new ConcurrentHashMap(); - nodeMeters = new ConcurrentHashMap>(); + nodeMeters = new ConcurrentHashMap>(); inactiveMeters = new ConcurrentHashMap(); } - + @SuppressWarnings({ "unchecked" }) private boolean retrieveMeterCaches() { ConcurrentMap map; @@ -148,7 +153,7 @@ public class MeterConsumerImpl { logger.warn("Meter: un-initialized clusterMeterContainerService, can't retrieve cache"); nonClusterMeterObjectCreate(); return false; - } + } map = clusterMeterContainerService.getCache("frm.originalSwMeterView"); if (map != null) { @@ -181,34 +186,33 @@ public class MeterConsumerImpl { logger.error("Retrieval of cache(nodeMeter) failed"); return false; } - + return true; } - + private boolean cacheStartup() { if (allocateMeterCaches()) { if (retrieveMeterCaches()) { return true; } } - + return false; } - + /** * Adds Meter to the southbound plugin and our internal database * * @param path * @param dataObject */ - private Status addMeter(InstanceIdentifier path, Meter meterAddDataObject) { + private Status addMeter(InstanceIdentifier path, Meter meterAddDataObject) { MeterKey meterKey = meterAddDataObject.getKey(); - - if (null != meterKey && - validateMeter(meterAddDataObject, FRMUtil.operation.ADD).isSuccess()) { + + if (null != meterKey && validateMeter(meterAddDataObject, FRMUtil.operation.ADD).isSuccess()) { if (meterAddDataObject.isInstall()) { AddMeterInputBuilder meterBuilder = new AddMeterInputBuilder(); - + meterBuilder.setContainerName(meterAddDataObject.getContainerName()); meterBuilder.setFlags(meterAddDataObject.getFlags()); meterBuilder.setMeterBandHeaders(meterAddDataObject.getMeterBandHeaders()); @@ -217,151 +221,157 @@ public class MeterConsumerImpl { originalSwMeterView.put(meterKey, meterAddDataObject); meterService.addMeter(meterBuilder.build()); } - - originalSwMeterView.put(meterKey, meterAddDataObject); - } - else { + + originalSwMeterView.put(meterKey, meterAddDataObject); + } else { return new Status(StatusCode.BADREQUEST, "Meter Key or attribute validation failed"); } - + return new Status(StatusCode.SUCCESS); } - + /* * Update Meter to the southbound plugin and our internal database * * @param path + * * @param dataObject */ - private Status updateMeter(InstanceIdentifier path, Meter meterUpdateDataObject) { + private Status updateMeter(InstanceIdentifier path, Meter meterUpdateDataObject) { MeterKey meterKey = meterUpdateDataObject.getKey(); - - if (null != meterKey && - validateMeter(meterUpdateDataObject, FRMUtil.operation.ADD).isSuccess()) { - if (meterUpdateDataObject.isInstall()) { - UpdateMeterInputBuilder updateMeterBuilder = new UpdateMeterInputBuilder(); - + UpdatedMeterBuilder updateMeterBuilder = null; + + if (null != meterKey && validateMeter(meterUpdateDataObject, FRMUtil.operation.UPDATE).isSuccess()) { + + if (originalSwMeterView.containsKey(meterKey)) { + originalSwMeterView.remove(meterKey); originalSwMeterView.put(meterKey, meterUpdateDataObject); - meterService.updateMeter(updateMeterBuilder.build()); } - - originalSwMeterView.put(meterKey, meterUpdateDataObject); - } - else { + + if (meterUpdateDataObject.isInstall()) { + UpdateMeterInputBuilder updateMeterInputBuilder = new UpdateMeterInputBuilder(); + updateMeterBuilder = new UpdatedMeterBuilder(); + updateMeterBuilder.fieldsFrom(meterUpdateDataObject); + updateMeterInputBuilder.setUpdatedMeter(updateMeterBuilder.build()); + + if (installedSwMeterView.containsKey(meterKey)) { + installedSwMeterView.remove(meterKey); + installedSwMeterView.put(meterKey, meterUpdateDataObject); + } + + meterService.updateMeter(updateMeterInputBuilder.build()); + } + + } else { return new Status(StatusCode.BADREQUEST, "Meter Key or attribute validation failed"); } - + return new Status(StatusCode.SUCCESS); } - + /* * Remove Meter to the southbound plugin and our internal database * * @param path + * * @param dataObject */ - private Status RemoveMeter(InstanceIdentifier path, Meter meterUpdateDataObject) { + private Status RemoveMeter(InstanceIdentifier path, Meter meterUpdateDataObject) { MeterKey meterKey = meterUpdateDataObject.getKey(); - - if (null != meterKey && - validateMeter(meterUpdateDataObject, FRMUtil.operation.ADD).isSuccess()) { + + if (null != meterKey && validateMeter(meterUpdateDataObject, FRMUtil.operation.ADD).isSuccess()) { if (meterUpdateDataObject.isInstall()) { - UpdateMeterInputBuilder updateMeterBuilder = new UpdateMeterInputBuilder(); - - originalSwMeterView.put(meterKey, meterUpdateDataObject); + UpdateMeterInputBuilder updateMeterBuilder = new UpdateMeterInputBuilder(); + + installedSwMeterView.put(meterKey, meterUpdateDataObject); meterService.updateMeter(updateMeterBuilder.build()); } - - originalSwMeterView.put(meterKey, meterUpdateDataObject); - } - else { + + originalSwMeterView.put(meterKey, meterUpdateDataObject); + } else { return new Status(StatusCode.BADREQUEST, "Meter Key or attribute validation failed"); } - + return new Status(StatusCode.SUCCESS); } - + public Status validateMeter(Meter meter, FRMUtil.operation operation) { String containerName; String meterName; Status returnStatus = null; boolean returnResult; - + if (null != meter) { containerName = meter.getContainerName(); - + if (null == containerName) { containerName = GlobalConstants.DEFAULT.toString(); - } - else if (!FRMUtil.isNameValid(containerName)) { + } else if (!FRMUtil.isNameValid(containerName)) { logger.error("Container Name is invalid %s" + containerName); returnStatus = new Status(StatusCode.BADREQUEST, "Container Name is invalid"); return returnStatus; } - + meterName = meter.getMeterName(); if (!FRMUtil.isNameValid(meterName)) { logger.error("Meter Name is invalid %s" + meterName); returnStatus = new Status(StatusCode.BADREQUEST, "Meter Name is invalid"); return returnStatus; } - + returnResult = doesMeterEntryExists(meter.getKey(), meterName, containerName); - + if (FRMUtil.operation.ADD == operation && returnResult) { logger.error("Record with same Meter Name exists"); returnStatus = new Status(StatusCode.BADREQUEST, "Meter record exists"); return returnStatus; - } - else if (!returnResult) { + } else if (!returnResult) { logger.error("Group record does not exist"); returnStatus = new Status(StatusCode.BADREQUEST, "Meter record does not exist"); return returnStatus; } - + for (int i = 0; i < meter.getMeterBandHeaders().getMeterBandHeader().size(); i++) { if (!meter.getFlags().isMeterBurst()) { if (0 < meter.getMeterBandHeaders().getMeterBandHeader().get(i).getBurstSize()) { logger.error("Burst size should only be associated when Burst FLAG is set"); - returnStatus = new Status(StatusCode.BADREQUEST, "Burst size should only be associated when Burst FLAG is set"); + returnStatus = new Status(StatusCode.BADREQUEST, + "Burst size should only be associated when Burst FLAG is set"); break; } } } - + if (null != returnStatus && !returnStatus.isSuccess()) { return returnStatus; - } - else { + } else { BandType setBandType = null; DscpRemark dscpRemark = null; for (int i = 0; i < meter.getMeterBandHeaders().getMeterBandHeader().size(); i++) { setBandType = meter.getMeterBandHeaders().getMeterBandHeader().get(i).getBandType(); - if ( setBandType instanceof DscpRemark) { - dscpRemark = (DscpRemark)setBandType; + if (setBandType instanceof DscpRemark) { + dscpRemark = (DscpRemark) setBandType; if (0 > dscpRemark.getRate()) { - + } - } - else if (setBandType instanceof Drop) { + } else if (setBandType instanceof Drop) { if (0 < dscpRemark.getPercLevel()) { logger.error("Number of drop Precedence level"); - } - } - else if (setBandType instanceof Experimenter) { - + } + } else if (setBandType instanceof Experimenter) { + } - } + } } } return new Status(StatusCode.SUCCESS); } - + private boolean doesMeterEntryExists(MeterKey key, String meterName, String containerName) { - if (! originalSwMeterView.containsKey(key)) { + if (!originalSwMeterView.containsKey(key)) { return false; } - + for (Entry entry : originalSwMeterView.entrySet()) { if (entry.getValue().getMeterName().equals(meterName)) { if (entry.getValue().getContainerName().equals(containerName)) { @@ -372,30 +382,31 @@ public class MeterConsumerImpl { return false; } - private RpcResult commitToPlugin(internalTransaction transaction) { - for(Entry, Meter> entry :transaction.additions.entrySet()) { - - if (!addMeter(entry.getKey(),entry.getValue()).isSuccess()) { + for (Entry, Meter> entry : transaction.additions.entrySet()) { + + if (!addMeter(entry.getKey(), entry.getValue()).isSuccess()) { return Rpcs.getRpcResult(false, null, null); } } - for(@SuppressWarnings("unused") Entry, Meter> entry :transaction.updates.entrySet()) { - - if (!updateMeter(entry.getKey(),entry.getValue()).isSuccess()) { + for (@SuppressWarnings("unused") + Entry, Meter> entry : transaction.updates.entrySet()) { + + if (!updateMeter(entry.getKey(), entry.getValue()).isSuccess()) { return Rpcs.getRpcResult(false, null, null); } } - - for(InstanceIdentifier removal : transaction.removals) { - /* if (!removeMeter(entry.getKey(),entry.getValue()).isSuccess()) { - return Rpcs.getRpcResult(false, null, null); - }*/ + + for (InstanceIdentifier removal : transaction.removals) { + /* + * if (!removeMeter(entry.getKey(),entry.getValue()).isSuccess()) { + * return Rpcs.getRpcResult(false, null, null); } + */ } - + return Rpcs.getRpcResult(true, null, null); } - + private final class internalTransaction implements DataCommitTransaction, DataObject> { private final DataModification, DataObject> modification; @@ -416,14 +427,14 @@ public class MeterConsumerImpl { /** * We create a plan which flows will be added, which will be updated and * which will be removed based on our internal state. - * + * */ void prepareUpdate() { Set, DataObject>> puts = modification.getUpdatedConfigurationData().entrySet(); for (Entry, DataObject> entry : puts) { - if (entry.getValue() instanceof Meter) { - Meter Meter = (Meter) entry.getValue(); + if (entry.getValue() instanceof Meter) { + Meter Meter = (Meter) entry.getValue(); preparePutEntry(entry.getKey(), Meter); } @@ -433,46 +444,46 @@ public class MeterConsumerImpl { } private void preparePutEntry(InstanceIdentifier key, Meter meter) { - + Meter original = originalSwMeterView.get(key); if (original != null) { // It is update for us - - updates.put(key, meter); + + updates.put(key, meter); } else { // It is addition for us - + additions.put(key, meter); } } /** * We are OK to go with execution of plan - * + * */ @Override public RpcResult finish() throws IllegalStateException { - + RpcResult rpcStatus = commitToPlugin(this); // We return true if internal transaction is successful. - // return Rpcs.getRpcResult(true, null, Collections.emptySet()); + // return Rpcs.getRpcResult(true, null, Collections.emptySet()); return rpcStatus; } /** - * + * * We should rollback our preparation - * + * */ @Override public RpcResult rollback() throws IllegalStateException { // NOOP - we did not modified any internal state during // requestCommit phase - // return Rpcs.getRpcResult(true, null, Collections.emptySet()); + // return Rpcs.getRpcResult(true, null, Collections.emptySet()); return Rpcs.getRpcResult(true, null, null); - + } - + } private final class MeterDataCommitHandler implements DataCommitHandler, DataObject> { @@ -486,9 +497,9 @@ public class MeterConsumerImpl { return transaction; } } - + final class MeterEventListener implements SalMeterListener { - + List addedMeter = new ArrayList<>(); List removeMeter = new ArrayList<>(); List updatedMeter = new ArrayList<>(); @@ -496,19 +507,45 @@ public class MeterConsumerImpl { @Override public void onMeterAdded(MeterAdded notification) { // TODO Auto-generated method stub - + } @Override public void onMeterRemoved(MeterRemoved notification) { // TODO Auto-generated method stub - + } @Override public void onMeterUpdated(MeterUpdated notification) { // TODO Auto-generated method stub - - } + + } + } + + @Override + public List get() { + + List orderedList = new ArrayList(); + Collection meterList = originalSwMeterView.values(); + for (Iterator iterator = meterList.iterator(); iterator.hasNext();) { + orderedList.add(iterator.next()); + } + return orderedList; + } + + @Override + public DataObject getWithName(String name, Node n) { + if (this instanceof MeterConsumerImpl) { + Collection meterList = originalSwMeterView.values(); + for (Iterator iterator = meterList.iterator(); iterator.hasNext();) { + Meter meter = iterator.next(); + if (meter.getNode().equals(n) && meter.getMeterName().equals(name)) { + + return meter; + } + } + } + return null; } }