Ray Milkey

Fix for ONOS-2572 - Excessive events delivered by AbstractAccumulator

- add synchronization to prevent prematurely scheduling a batch that
  isn't full.

Change-Id: I07d53ef4d81211909a6fcdd98bc937b49c7c4cca
......@@ -40,8 +40,8 @@ public abstract class AbstractAccumulator<T> implements Accumulator<T> {
private final int maxBatchMillis;
private final int maxIdleMillis;
private TimerTask idleTask = new ProcessorTask();
private TimerTask maxTask = new ProcessorTask();
private volatile TimerTask idleTask = new ProcessorTask();
private volatile TimerTask maxTask = new ProcessorTask();
private List<T> items = Lists.newArrayList();
......@@ -108,10 +108,14 @@ public abstract class AbstractAccumulator<T> implements Accumulator<T> {
private class ProcessorTask extends TimerTask {
@Override
public void run() {
synchronized (AbstractAccumulator.this) {
idleTask = cancelIfActive(idleTask);
}
if (isReady()) {
try {
synchronized (AbstractAccumulator.this) {
maxTask = cancelIfActive(maxTask);
}
List<T> items = finalizeCurrentBatch();
if (!items.isEmpty()) {
processItems(items);
......@@ -120,10 +124,12 @@ public abstract class AbstractAccumulator<T> implements Accumulator<T> {
log.warn("Unable to process batch due to {}", e);
}
} else {
synchronized (AbstractAccumulator.this) {
idleTask = schedule(maxIdleMillis);
}
}
}
}
// Demotes and returns the current batch of items and promotes a new one.
private synchronized List<T> finalizeCurrentBatch() {
......