[VOL-3260] Purging all meter state on OLT delete
Change-Id: I6323779d584b341d33cc91231197504b80a91fc4
diff --git a/app/src/main/java/org/opencord/olt/impl/Olt.java b/app/src/main/java/org/opencord/olt/impl/Olt.java
index fe2675e..1f3634b 100644
--- a/app/src/main/java/org/opencord/olt/impl/Olt.java
+++ b/app/src/main/java/org/opencord/olt/impl/Olt.java
@@ -83,7 +83,6 @@
import org.opencord.olt.AccessSubscriberId;
import org.opencord.olt.internalapi.AccessDeviceFlowService;
import org.opencord.olt.internalapi.AccessDeviceMeterService;
-import org.opencord.olt.internalapi.DeviceBandwidthProfile;
import org.opencord.sadis.BandwidthProfileInformation;
import org.opencord.sadis.BaseInformationService;
import org.opencord.sadis.SadisService;
@@ -695,28 +694,28 @@
// queue up the meters to be created
if (upMeterId == null) {
log.debug("Missing meter for upstream {}", upstreamBpInfo.id());
- checkAndCreateDevMeter(new DeviceBandwidthProfile(deviceId, upstreamBpInfo));
+ checkAndCreateDevMeter(deviceId, upstreamBpInfo);
}
if (downMeterId == null) {
log.debug("Missing meter for downstream {}", downstreamBpInfo.id());
- checkAndCreateDevMeter(new DeviceBandwidthProfile(deviceId, downstreamBpInfo));
+ checkAndCreateDevMeter(deviceId, downstreamBpInfo);
}
}
}
- private void checkAndCreateDevMeter(DeviceBandwidthProfile dm) {
- if (oltMeterService.isMeterPending(dm)) {
- log.debug("Meter is already pending {}", dm);
+ private void checkAndCreateDevMeter(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+ if (oltMeterService.isMeterPending(deviceId, bwpInfo)) {
+ log.debug("Meter is already pending {} on device {}", bwpInfo, deviceId);
return;
}
- oltMeterService.addToPendingMeters(dm);
- createMeter(dm);
+ oltMeterService.addToPendingMeters(deviceId, bwpInfo);
+ createMeter(deviceId, bwpInfo);
}
- private void createMeter(DeviceBandwidthProfile dm) {
- log.debug("Creating Meter {} from queue for subscriber", dm);
+ private void createMeter(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+ log.debug("Creating Meter with {} on {} for subscriber", bwpInfo, deviceId);
CompletableFuture<Object> meterFuture = new CompletableFuture<>();
- MeterId meterId = oltMeterService.createMeter(dm.getDevId(), dm.getBwInfo(),
+ MeterId meterId = oltMeterService.createMeter(deviceId, bwpInfo,
meterFuture);
meterFuture.thenAcceptAsync(result -> {
@@ -726,12 +725,12 @@
SubscriberFlowInfo fi = subsIterator.next();
if (result == null) {
// meter install sent to device
- log.debug("Meter {} installed for bw {}", meterId, dm.getBwInfo());
+ log.debug("Meter {} installed for bw {} on {}", meterId, bwpInfo, deviceId);
MeterId upMeterId = oltMeterService
- .getMeterIdFromBpMapping(dm.getDevId(), fi.getUpBpInfo());
+ .getMeterIdFromBpMapping(deviceId, fi.getUpBpInfo());
MeterId downMeterId = oltMeterService
- .getMeterIdFromBpMapping(dm.getDevId(), fi.getDownBpInfo());
+ .getMeterIdFromBpMapping(deviceId, fi.getDownBpInfo());
if (upMeterId != null && downMeterId != null) {
log.debug("Provisioning subscriber after meter {}" +
"installation and both meters are present " +
@@ -746,13 +745,13 @@
handleSubFlowsWithMeters(fi);
subsIterator.remove();
}
- oltMeterService.removeFromPendingMeters(new DeviceBandwidthProfile(dm.getDevId(), dm.getBwInfo()));
+ oltMeterService.removeFromPendingMeters(deviceId, bwpInfo);
} else {
// meter install failed
log.error("Addition of subscriber {} failed due to meter " +
"{} with result {}", fi, meterId, result);
subsIterator.remove();
- oltMeterService.removeFromPendingMeters(new DeviceBandwidthProfile(dm.getDevId(), dm.getBwInfo()));
+ oltMeterService.removeFromPendingMeters(deviceId, bwpInfo);
}
}
});
@@ -1054,6 +1053,8 @@
// on every instance, see how it's done in the InternalDeviceListener
// in FlowRuleManager: no mastership check for purgeOnDisconnection
flowRuleService.purgeFlowRules(devId);
+ oltFlowService.clearDeviceState(devId);
+ oltMeterService.clearDeviceState(devId);
return;
} else if (!isLocalLeader) {
log.debug("Not handling event because instance is not leader for {}", devId);
@@ -1180,6 +1181,11 @@
private void handleDeviceDisconnection(Device device, boolean sendUniEvent) {
programmedDevices.remove(device.id());
removeAllSubscribers(device.id());
+ //Handle case where OLT disconnects during subscriber provisioning
+ pendingSubscribers.removeIf(fi -> fi.getDevId().equals(device.id()));
+ oltFlowService.clearDeviceState(device.id());
+
+ //Complete meter and flow purge
flowRuleService.purgeFlowRules(device.id());
oltMeterService.clearMeters(device.id());
post(new AccessDeviceEvent(
diff --git a/app/src/main/java/org/opencord/olt/impl/OltFlowService.java b/app/src/main/java/org/opencord/olt/impl/OltFlowService.java
index b4dca74..a53e019 100644
--- a/app/src/main/java/org/opencord/olt/impl/OltFlowService.java
+++ b/app/src/main/java/org/opencord/olt/impl/OltFlowService.java
@@ -49,7 +49,6 @@
import org.onosproject.net.meter.MeterId;
import org.opencord.olt.internalapi.AccessDeviceFlowService;
import org.opencord.olt.internalapi.AccessDeviceMeterService;
-import org.opencord.olt.internalapi.DeviceBandwidthProfile;
import org.opencord.sadis.BandwidthProfileInformation;
import org.opencord.sadis.BaseInformationService;
import org.opencord.sadis.SadisService;
@@ -423,7 +422,6 @@
// check if meter exists and create it only for an install
final MeterId meterId = oltMeterService.getMeterIdFromBpMapping(devId, bpInfo.id());
- DeviceBandwidthProfile dm = new DeviceBandwidthProfile(devId, bpInfo);
if (meterId == null) {
if (install) {
log.debug("Need to install meter for EAPOL with bwp {}", bpInfo.id());
@@ -434,11 +432,12 @@
null, bpInfo.id());
pendingEapolForMeters.add(fi);
- if (oltMeterService.isMeterPending(dm)) {
- log.debug("Meter {} is already pending for EAPOL", dm);
+ if (oltMeterService.isMeterPending(devId, bpInfo)) {
+ log.debug("Meter is already pending for EAPOL on {} with bp {}",
+ devId, bpInfo);
return;
}
- oltMeterService.addToPendingMeters(dm);
+ oltMeterService.addToPendingMeters(devId, bpInfo);
MeterId innerMeterId = oltMeterService.createMeter(devId, bpInfo,
meterFuture);
fi.setUpMeterId(innerMeterId);
@@ -474,7 +473,7 @@
SubscriberFlowInfo fi = eapIterator.next();
if (result == null) {
MeterId mId = oltMeterService
- .getMeterIdFromBpMapping(dm.getDevId(), fi.getUpBpInfo());
+ .getMeterIdFromBpMapping(devId, fi.getUpBpInfo());
if (mId != null) {
handleEapol(filterFuture, install, cp, builder, treatmentBuilder, fi, mId);
eapIterator.remove();
@@ -484,8 +483,7 @@
"Result {} and MeterId {}", result, meterId);
eapIterator.remove();
}
- oltMeterService.removeFromPendingMeters(new DeviceBandwidthProfile(
- dm.getDevId(), dm.getBwInfo()));
+ oltMeterService.removeFromPendingMeters(devId, bpInfo);
}
});
}
@@ -518,8 +516,8 @@
.add(new ObjectiveContext() {
@Override
public void onSuccess(Objective objective) {
- log.info("Eapol filter for {} on {} {} with meter {}.",
- fi.getDevId(), fi.getUniPort(),
+ log.info("Eapol filter {} for {} on {} {} with meter {}.",
+ objective.id(), fi.getDevId(), fi.getUniPort(),
(install) ? INSTALLED : REMOVED, mId);
if (filterFuture != null) {
filterFuture.complete(null);
@@ -529,8 +527,8 @@
@Override
public void onError(Objective objective, ObjectiveError error) {
- log.error("Eapol filter for {} on {} with meter {} " +
- "failed {} because {}",
+ log.error("Eapol filter {} for {} on {} with meter {} " +
+ "failed {} because {}", objective.id(),
fi.getDevId(), fi.getUniPort(), mId,
(install) ? INSTALLATION : REMOVAL,
error);
@@ -708,6 +706,13 @@
return createForwardingObjectiveBuilder(selectorBuilder.build(), treatmentBuilder.build(), MIN_PRIORITY);
}
+ @Override
+ public void clearDeviceState(DeviceId deviceId) {
+ pendingEapolForMeters.removeIf(fi -> fi.getDevId().equals(deviceId));
+ pendingAddEapol.removeIf(connectPoint -> connectPoint.deviceId().equals(deviceId));
+
+ }
+
private DefaultForwardingObjective.Builder createForwardingObjectiveBuilder(TrafficSelector selector,
TrafficTreatment treatment,
Integer priority) {
diff --git a/app/src/main/java/org/opencord/olt/impl/OltMeterService.java b/app/src/main/java/org/opencord/olt/impl/OltMeterService.java
index 3cbdbd7..fc56066 100644
--- a/app/src/main/java/org/opencord/olt/impl/OltMeterService.java
+++ b/app/src/main/java/org/opencord/olt/impl/OltMeterService.java
@@ -42,7 +42,6 @@
import org.onosproject.store.service.Serializer;
import org.onosproject.store.service.StorageService;
import org.opencord.olt.internalapi.AccessDeviceMeterService;
-import org.opencord.olt.internalapi.DeviceBandwidthProfile;
import org.opencord.sadis.BandwidthProfileInformation;
import org.osgi.service.component.ComponentContext;
import org.osgi.service.component.annotations.Activate;
@@ -56,13 +55,14 @@
import java.util.ArrayList;
import java.util.Collection;
import java.util.Dictionary;
+import java.util.HashMap;
+import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import java.util.Set;
import java.util.concurrent.CompletableFuture;
-import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.atomic.AtomicInteger;
@@ -100,8 +100,6 @@
protected boolean deleteMeters = true;
- ConsistentMultimap<String, MeterKey> bpInfoToMeter;
-
private ApplicationId appId;
private static final String APP_NAME = "org.opencord.olt";
@@ -111,7 +109,9 @@
protected ExecutorService eventExecutor;
- private Set<DeviceBandwidthProfile> pendingMeters;
+ private Map<DeviceId, Set<BandwidthProfileInformation>> pendingMeters;
+ private Map<DeviceId, Map<MeterKey, AtomicInteger>> pendingRemoveMeters;
+ ConsistentMultimap<String, MeterKey> bpInfoToMeter;
@Activate
public void activate(ComponentContext context) {
@@ -133,7 +133,8 @@
meterService.addListener(meterListener);
componentConfigService.registerProperties(getClass());
- pendingMeters = ConcurrentHashMap.newKeySet();
+ pendingMeters = Maps.newConcurrentMap();
+ pendingRemoveMeters = Maps.newConcurrentMap();
log.info("Olt Meter service started");
}
@@ -250,26 +251,54 @@
}
@Override
- public void addToPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile) {
- pendingMeters.add(deviceBandwidthProfile);
+ public void addToPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+ if (deviceId == null) {
+ return;
+ }
+ pendingMeters.compute(deviceId, (id, bwps) -> {
+ if (bwps == null) {
+ bwps = new HashSet<>();
+ }
+ bwps.add(bwpInfo);
+ return bwps;
+ });
}
@Override
- public void removeFromPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile) {
- pendingMeters.remove(deviceBandwidthProfile);
+ public void removeFromPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+ if (deviceId == null) {
+ return;
+ }
+ pendingMeters.computeIfPresent(deviceId, (id, bwps) -> {
+ bwps.remove(bwpInfo);
+ return bwps;
+ });
}
@Override
- public boolean isMeterPending(DeviceBandwidthProfile deviceBandwidthProfile) {
- return pendingMeters.contains(deviceBandwidthProfile);
+ public boolean isMeterPending(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+ if (!pendingMeters.containsKey(deviceId)) {
+ return false;
+ }
+ return pendingMeters.get(deviceId).contains(bwpInfo);
}
@Override
public void clearMeters(DeviceId deviceId) {
log.debug("Removing all meters for device {}", deviceId);
+ clearDeviceState(deviceId);
meterService.purgeMeters(deviceId);
}
+ @Override
+ public void clearDeviceState(DeviceId deviceId) {
+ log.info("Clearing local device state for {}", deviceId);
+ pendingRemoveMeters.remove(deviceId);
+ removeMetersFromBpMapping(deviceId);
+ //Following call handles cornercase of OLT delete during meter provisioning
+ pendingMeters.remove(deviceId);
+ }
+
private List<Band> createMeterBands(BandwidthProfileInformation bpInfo) {
List<Band> meterBands = new ArrayList<>();
@@ -288,9 +317,23 @@
.build();
}
- private class InternalMeterListener implements MeterListener {
+ private void removeMeterFromBpMapping(MeterKey meterKey) {
+ List<Map.Entry<String, MeterKey>> meters = bpInfoToMeter.stream()
+ .filter(e -> e.getValue().equals(meterKey))
+ .collect(Collectors.toList());
- Map<MeterKey, AtomicInteger> pendingRemoveMeters = Maps.newConcurrentMap();
+ meters.forEach(e -> bpInfoToMeter.remove(e.getKey(), e.getValue()));
+ }
+
+ private void removeMetersFromBpMapping(DeviceId deviceId) {
+ List<Map.Entry<String, MeterKey>> meters = bpInfoToMeter.stream()
+ .filter(e -> e.getValue().deviceId().equals(deviceId))
+ .collect(Collectors.toList());
+
+ meters.forEach(e -> bpInfoToMeter.remove(e.getKey(), e.getValue()));
+ }
+
+ private class InternalMeterListener implements MeterListener {
@Override
public void event(MeterEvent meterEvent) {
@@ -302,33 +345,50 @@
}
MeterKey key = MeterKey.key(meter.deviceId(), meter.id());
if (deleteMeters && MeterEvent.Type.METER_REFERENCE_COUNT_ZERO.equals(meterEvent.type())) {
- log.info("Zero Count Meter Event is received. Meter is {}", meter.id());
- incrementMeterCount(key);
+ log.info("Zero Count Meter Event is received. Meter is {} on {}",
+ meter.id(), meter.deviceId());
+ incrementMeterCount(meter.deviceId(), key);
- if (appId.equals(meter.appId()) && pendingRemoveMeters.get(key).get() == 3) {
- log.info("Deleting unreferenced, no longer programmed Meter {}", meter.id());
+ if (appId.equals(meter.appId()) && pendingRemoveMeters.get(meter.deviceId())
+ .get(key).get() == 3) {
+ log.info("Deleting unreferenced, no longer programmed Meter {} on {}",
+ meter.id(), meter.deviceId());
deleteMeter(meter.deviceId(), meter.id());
}
}
if (MeterEvent.Type.METER_REMOVED.equals(meterEvent.type())) {
- log.info("Meter Removed Event is received for {}", meter.id());
- pendingRemoveMeters.remove(key);
+ log.info("Meter Removed Event is received for {} on {}",
+ meter.id(), meter.deviceId());
+ pendingRemoveMeters.computeIfPresent(meter.deviceId(),
+ (id, meters) -> {
+ if (meters.get(key) == null) {
+ log.info("Meters is not pending " +
+ "{} on {}", key, id);
+ return meters;
+ }
+ meters.remove(key);
+ return meters;
+ });
removeMeterFromBpMapping(key);
}
});
}
- private void incrementMeterCount(MeterKey key) {
+ private void incrementMeterCount(DeviceId deviceId, MeterKey key) {
if (key == null) {
return;
}
- pendingRemoveMeters.compute(key,
- (k, v) -> {
- if (v == null) {
- return new AtomicInteger(1);
+ pendingRemoveMeters.compute(deviceId,
+ (id, meters) -> {
+ if (meters == null) {
+ meters = new HashMap<>();
+
}
- v.addAndGet(1);
- return v;
+ if (meters.get(key) == null) {
+ meters.put(key, new AtomicInteger(1));
+ }
+ meters.get(key).addAndGet(1);
+ return meters;
});
}
@@ -346,13 +406,5 @@
meterService.withdraw(meterRequest, meterId);
}
}
-
- private void removeMeterFromBpMapping(MeterKey meterKey) {
- List<Map.Entry<String, MeterKey>> meters = bpInfoToMeter.stream()
- .filter(e -> e.getValue().equals(meterKey))
- .collect(Collectors.toList());
-
- meters.forEach(e -> bpInfoToMeter.remove(e.getKey(), e.getValue()));
- }
}
}
diff --git a/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java b/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
index 362b154..d4cc09f 100644
--- a/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
+++ b/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceFlowService.java
@@ -145,4 +145,10 @@
PortNumber subscriberPort,
MeterId downstreamMeterId,
UniTagInformation tagInformation);
+
+ /**
+ * Clears pending mappings and state for device.
+ * @param deviceId the device id
+ */
+ void clearDeviceState(DeviceId deviceId);
}
diff --git a/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceMeterService.java b/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceMeterService.java
index bad2e5b..4b921fb 100644
--- a/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceMeterService.java
+++ b/app/src/main/java/org/opencord/olt/internalapi/AccessDeviceMeterService.java
@@ -70,31 +70,41 @@
/**
* Adds the DeviceBandwidthProfile to the pendingMeters.
*
- * @param deviceBandwidthProfile the device to bandwidth profile mapping
+ * @param deviceId the device
+ * @param bwpInfo the bandwidth profile info
*/
- void addToPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile);
+ void addToPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo);
/**
* Removes the DeviceBandwidthProfile from the pendingMeters.
*
- * @param deviceBandwidthProfile the device to bandwidth profile mapping
+ * @param deviceId the device
+ * @param bwpInfo the bandwidth profile info
*
*/
- void removeFromPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile);
+ void removeFromPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo);
/**
* Checks if DeviceBandwidthProfile is pending.
*
- * @param deviceBandwidthProfile the device to bandwidth profile mapping
+ * @param deviceId the device
+ * @param bwpInfo the bandwidth profile info
*
* @return true if pending.
*/
- boolean isMeterPending(DeviceBandwidthProfile deviceBandwidthProfile);
+ boolean isMeterPending(DeviceId deviceId, BandwidthProfileInformation bwpInfo);
/**
- * Clears out bandwidth profile to meter mappings for the given device.
+ * Clears out meters for the given device.
*
* @param deviceId device ID
*/
void clearMeters(DeviceId deviceId);
+
+ /**
+ * Clears out local state for the given device.
+ *
+ * @param deviceId device ID
+ */
+ void clearDeviceState(DeviceId deviceId);
}
diff --git a/app/src/main/java/org/opencord/olt/internalapi/DeviceBandwidthProfile.java b/app/src/main/java/org/opencord/olt/internalapi/DeviceBandwidthProfile.java
deleted file mode 100644
index 8f676ec..0000000
--- a/app/src/main/java/org/opencord/olt/internalapi/DeviceBandwidthProfile.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright 2020-present Open Networking Foundation
- *
- * 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.opencord.olt.internalapi;
-
-import org.onosproject.net.DeviceId;
-import org.opencord.sadis.BandwidthProfileInformation;
-
-import java.util.Objects;
-
-/**
- * Class containing a mapping of DeviceId to BandwidthProfileInformation.
- */
-public class DeviceBandwidthProfile {
- private final DeviceId devId;
- private BandwidthProfileInformation bwInfo;
-
- /**
- * Creates the Mapping.
- *
- * @param devId the device id
- * @param bwInfo the bandwidth profile information
- */
- public DeviceBandwidthProfile(DeviceId devId, BandwidthProfileInformation bwInfo) {
- this.devId = devId;
- this.bwInfo = bwInfo;
- }
-
- /**
- * Returns the device id.
- *
- * @return device id.
- */
- public DeviceId getDevId() {
- return devId;
- }
-
- /**
- * Returns the Bandwidth profile for this device.
- *
- * @return bandwidth profile information
- */
- public BandwidthProfileInformation getBwInfo() {
- return bwInfo;
- }
-
- @Override
- public boolean equals(Object o) {
- if (this == o) {
- return true;
- }
- if (o == null || getClass() != o.getClass()) {
- return false;
- }
- DeviceBandwidthProfile that = (DeviceBandwidthProfile) o;
- return devId.equals(that.devId)
- && bwInfo.equals(that.bwInfo);
- }
-
- @Override
- public int hashCode() {
- return Objects.hash(devId, bwInfo);
- }
-
- @Override
- public String toString() {
- return com.google.common.base.MoreObjects.toStringHelper(this)
- .add("devId", devId)
- .add("bwInfo", bwInfo)
- .toString();
- }
-}
diff --git a/app/src/test/java/org/opencord/olt/impl/OltFlowTest.java b/app/src/test/java/org/opencord/olt/impl/OltFlowTest.java
index f259e6f..25bc87a 100644
--- a/app/src/test/java/org/opencord/olt/impl/OltFlowTest.java
+++ b/app/src/test/java/org/opencord/olt/impl/OltFlowTest.java
@@ -48,7 +48,6 @@
import org.onosproject.net.flowobjective.Objective;
import org.onosproject.net.meter.MeterId;
import org.onosproject.net.meter.MeterKey;
-import org.opencord.olt.internalapi.DeviceBandwidthProfile;
import org.opencord.sadis.BandwidthProfileInformation;
import org.opencord.sadis.UniTagInformation;
@@ -206,22 +205,29 @@
}
@Override
- public void addToPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile) {
+ public void addToPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
}
@Override
- public void removeFromPendingMeters(DeviceBandwidthProfile deviceBandwidthProfile) {
+ public void removeFromPendingMeters(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
+
}
@Override
- public boolean isMeterPending(DeviceBandwidthProfile deviceBandwidthProfile) {
+ public boolean isMeterPending(DeviceId deviceId, BandwidthProfileInformation bwpInfo) {
return false;
}
+
@Override
public void clearMeters(DeviceId deviceId) {
}
+
+ @Override
+ public void clearDeviceState(DeviceId deviceId) {
+
+ }
}
private class MockOltFlowObjectiveService implements org.onosproject.net.flowobjective.FlowObjectiveService {