diff --git a/pom.xml b/pom.xml index a6456429..0859fb3a 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ io.github.protocol-fuzzing protocol-state-fuzzer - 0.3.1 + 0.4.0 Protocol State Fuzzer A generic, modular, and extensible protocol state fuzzer for network protocol implementations. @@ -75,7 +75,7 @@ 0.9.9 4.13.2 0.1.1 - 0.18.0 + 19.0.0 2.26.1 0.1 4.10.5 diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/oracles/WpEQSequenceGenerator.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/oracles/WpEQSequenceGenerator.java index 8e417230..97a6cdf6 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/oracles/WpEQSequenceGenerator.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/oracles/WpEQSequenceGenerator.java @@ -33,7 +33,7 @@ public class WpEQSequenceGenerator { /** Stores the constructor parameter. */ - protected UniversalDeterministicAutomaton automaton; + protected UniversalDeterministicAutomaton.RegularAutomaton automaton; /** Stores the constructor parameter. */ protected Collection inputs; @@ -54,7 +54,7 @@ public class WpEQSequenceGenerator { * @param inputs the inputs of the automaton */ public WpEQSequenceGenerator( - UniversalDeterministicAutomaton automaton, + UniversalDeterministicAutomaton.RegularAutomaton automaton, Collection inputs) { this.automaton = automaton; @@ -100,7 +100,7 @@ public static Map>> computePredecessorMap( * @return the list of global suffixes */ private List> computeGlobalSuffixes( - UniversalDeterministicAutomaton automaton, + UniversalDeterministicAutomaton.RegularAutomaton automaton, Collection inputs) { List> globalSuffixes = new ArrayList<>(); @@ -117,7 +117,7 @@ private List> computeGlobalSuffixes( * @return the list of local suffixes */ private MutableMapping>> computeLocalSuffixSets( - UniversalDeterministicAutomaton automaton, + UniversalDeterministicAutomaton.RegularAutomaton automaton, Collection inputs) { MutableMapping>> localSuffixSets = automaton.createStaticStateMapping(); diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/AggregatedCounter.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/AggregatedCounter.java deleted file mode 100644 index 5af64be2..00000000 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/AggregatedCounter.java +++ /dev/null @@ -1,48 +0,0 @@ -package io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics; - -import de.learnlib.filter.statistic.Counter; - -import java.util.List; - -/** - * Aggregates multiple counters for parallel execution scenarios. - *

- * The aggregated counter only supports read operations ({@link #getCount()}). - * Write operations ({@link #increment()}) should be performed on the individual - * counters that make up this aggregation. - *

- */ -public class AggregatedCounter extends Counter { - - /** The list of individual counters to aggregate. */ - private final List counters; - - /** - * Constructs a new AggregatedCounter with the specified list of counters. - *

- * The aggregated counter will sum the counts from all provided counters - * when {@link #getCount()} is called. - *

- * - * @param counters a list of {@link Counter} instances to aggregate. - */ - public AggregatedCounter(List counters) { - super("AggregatedCounter", "#"); - this.counters = counters; - } - - @Override - public long getCount() { - long total = 0; - for (Counter counter: counters) { - total += counter.getCount(); - } - return total; - } - - @Override - public void increment() { - throw new UnsupportedOperationException( - "Increment should be called on individual counters, not on the aggregated counter"); - } -} diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTracker.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTracker.java index 67255d91..7e51bbb6 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTracker.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTracker.java @@ -1,6 +1,6 @@ package io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics; -import de.learnlib.filter.statistic.Counter; +import de.learnlib.statistic.StatisticsKey; import io.github.protocolfuzzing.protocolstatefuzzer.statefuzzer.core.config.StateFuzzerEnabler; import net.automatalib.alphabet.Alphabet; @@ -9,6 +9,7 @@ import java.io.PrintWriter; import java.nio.charset.StandardCharsets; import java.util.ArrayList; +import java.util.List; /** * Tracks learning related statistics during the learning process. @@ -21,10 +22,10 @@ public abstract class StatisticsTracker { /** Stores the constructor parameter. */ - protected Counter inputCounter; + protected List inputStatisticsKeys; /** Stores the constructor parameter. */ - protected Counter testCounter; + protected List testStatisticsKeys; /** Stores the Statistics instance that is being updated. */ protected Statistics statistics; @@ -59,12 +60,25 @@ protected enum State { /** * Creates a new instance from the given parameters. * - * @param inputCounter counter updated on every input of membership and equivalence queries - * @param testCounter counter updated on every membership and equivalence query (also named test) + * @param inputStatisticsKey key for counter updated on every input of membership and equivalence queries + * @param testStatisticsKey key for counter updated on every membership and equivalence query (also named test) */ - public StatisticsTracker(Counter inputCounter, Counter testCounter) { - this.inputCounter = inputCounter; - this.testCounter = testCounter; + public StatisticsTracker(StatisticsKey inputStatisticsKey, StatisticsKey testStatisticsKey) { + this.inputStatisticsKeys = List.of(inputStatisticsKey); + this.testStatisticsKeys = List.of(testStatisticsKey); + } + + /** + * Creates a new instance from the given parameters. + *

+ * This should be used when values of multiple counters should be aggregated to a single value + * + * @param inputStatisticsKeys keys for counter updated on every input of membership and equivalence queries + * @param testStatisticsKeys keys for counter updated on every membership and equivalence query (also named test) + */ + public StatisticsTracker(List inputStatisticsKeys, List testStatisticsKeys) { + this.inputStatisticsKeys = inputStatisticsKeys; + this.testStatisticsKeys = testStatisticsKeys; } /** @@ -175,19 +189,34 @@ public void startLearning(StateFuzzerEnabler stateFuzzerEnabler, Alphabet alp logStateChange(State.REFINEMENT); } + /** + * Returns the aggregated value of the counters behind the provided keys + * + * @param keys the keys to be used for the default StatisticsService + * + * @return the aggregated value + */ + protected long getCount(List keys) { + long total = 0; + for (StatisticsKey key: keys) { + total += de.learnlib.statistic.Statistics.getService().getCount(key).orElse(0L); + } + return total; + } + /** * Should be called every time learning produces a new hypothesis. * * @param hypothesis the new hypothesis that has been found */ public void newHypothesis(StateMachineWrapper hypothesis) { - long lastHypTests = testCounter.getCount(); + long lastHypTests = getCount(testStatisticsKeys); statistics.setLastHypTests(lastHypTests); long newLearnTests = statistics.getLearnTests() + lastHypTests - lastCETests; statistics.setLearnTests(newLearnTests); - long lastHypInputs = inputCounter.getCount(); + long lastHypInputs = getCount(inputStatisticsKeys); statistics.setLastHypInputs(lastHypInputs); long newLearnInputs = statistics.getLearnInputs() + lastHypInputs - lastCEInputs; @@ -208,8 +237,8 @@ public void newHypothesis(StateMachineWrapper hypothesis) { * @param counterexample the new counterexample that has been found */ public void newCounterExample(CE counterexample) { - lastCETests = testCounter.getCount(); - lastCEInputs = inputCounter.getCount(); + lastCETests = getCount(testStatisticsKeys); + lastCEInputs = getCount(inputStatisticsKeys); statistics.getCounterexamples().add(counterexample); @@ -240,8 +269,8 @@ public void finishedLearning(StateMachineWrapper learnedModel, boolean f statistics.setStates(learnedModel.getMachineSize()); } - statistics.setAllTests(testCounter.getCount()); - statistics.setAllInputs(inputCounter.getCount()); + statistics.setAllTests(getCount(testStatisticsKeys)); + statistics.setAllInputs(getCount(inputStatisticsKeys)); statistics.setDuration(System.currentTimeMillis() - startTime); statistics.setFinished(finished, notFinishedReason); @@ -259,13 +288,12 @@ public Statistics generateStatistics() { } /** - * Creates a new snapshot from the current values of {@link #testCounter}, - * {@link #inputCounter} and current running time. + * Creates a new snapshot from the current values of the counters and current running time. * * @return the current statistics snapshot */ protected StatisticsSnapshot createSnapshot() { - return new StatisticsSnapshot(testCounter.getCount(), inputCounter.getCount(), + return new StatisticsSnapshot(getCount(testStatisticsKeys), getCount(inputStatisticsKeys), System.currentTimeMillis() - startTime); } } diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerRA.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerRA.java index b1148346..c639ade8 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerRA.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerRA.java @@ -1,7 +1,7 @@ package io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics; -import de.learnlib.filter.statistic.Counter; import de.learnlib.query.DefaultQuery; +import de.learnlib.statistic.StatisticsKey; import net.automatalib.word.Word; /** @@ -17,13 +17,13 @@ public class StatisticsTrackerRA extends StatisticsTracker, /** * Creates a new instance from the given parameters. * - * @param inputCounter counter updated on every input of membership and - * equivalence queries - * @param testCounter counter updated on every membership and equivalence query - * (also named test) + * @param inputStatisticsKey key for counter updated on every input of membership and + * equivalence queries + * @param testStatisticsKey key for counter updated on every membership and equivalence query + * (also named test) */ - public StatisticsTrackerRA(Counter inputCounter, Counter testCounter) { - super(inputCounter, testCounter); + public StatisticsTrackerRA(StatisticsKey inputStatisticsKey, StatisticsKey testStatisticsKey) { + super(inputStatisticsKey, testStatisticsKey); } @Override diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerStandard.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerStandard.java index 97da76e3..f4712bf2 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerStandard.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/learner/statistics/StatisticsTrackerStandard.java @@ -1,9 +1,11 @@ package io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics; -import de.learnlib.filter.statistic.Counter; import de.learnlib.query.DefaultQuery; +import de.learnlib.statistic.StatisticsKey; import net.automatalib.word.Word; +import java.util.List; + /** * Standard implementation of the StatisticsTracker for specific input domain * and counterexample type. @@ -16,11 +18,23 @@ public class StatisticsTrackerStandard extends StatisticsTracker + * This should be used when values of multiple counters should be aggregated to a single value + * + * @param inputStatisticsKeys keys for counter updated on every input of membership and equivalence queries + * @param testStatisticsKeys keys for counter updated on every membership and equivalence query (also named test) */ - public StatisticsTrackerStandard(Counter inputCounter, Counter testCounter) { - super(inputCounter, testCounter); + public StatisticsTrackerStandard(List inputStatisticsKeys, List testStatisticsKeys) { + super(inputStatisticsKeys, testStatisticsKeys); } @Override diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapper.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapper.java index 384e3e87..3d6c936c 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapper.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapper.java @@ -1,6 +1,6 @@ package io.github.protocolfuzzing.protocolstatefuzzer.components.sul.core; -import de.learnlib.filter.statistic.Counter; +import de.learnlib.statistic.StatisticsKey; import de.learnlib.sul.SUL; import java.time.Duration; @@ -68,7 +68,7 @@ public interface SULWrapper { * * @return the input counter of the underlying abstract SUL */ - Counter getInputCounter(); + StatisticsKey getInputStatisticsKey(); /** * Returns the test counter used for counting all the tests (queries) @@ -76,5 +76,5 @@ public interface SULWrapper { * * @return the test counter of the underlying abstract SUL */ - Counter getTestCounter(); + StatisticsKey getTestStatisticsKey(); } diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapperStandard.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapperStandard.java index cd8e2ea8..ef69f330 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapperStandard.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/components/sul/core/SULWrapperStandard.java @@ -1,7 +1,7 @@ package io.github.protocolfuzzing.protocolstatefuzzer.components.sul.core; -import de.learnlib.filter.statistic.Counter; import de.learnlib.filter.statistic.sul.CounterSUL; +import de.learnlib.statistic.StatisticsKey; import de.learnlib.sul.SUL; import io.github.protocolfuzzing.protocolstatefuzzer.components.sul.core.config.SULConfig; import io.github.protocolfuzzing.protocolstatefuzzer.components.sul.core.sulwrappers.DynamicPortProvider; @@ -33,10 +33,10 @@ public class SULWrapperStandard implements SULWrapper { protected SUL wrappedSUL; /** The input counter used for the underlying abstract SUL. */ - protected Counter inputCounter; + protected StatisticsKey inputStatisticsKey; /** The test counter used for the underlying abstract SUL. */ - protected Counter testCounter; + protected StatisticsKey testStatisticsKey; /** The time limit to be set only once using {@link #setTimeLimit(Duration)}. */ protected Duration timeLimit; @@ -70,8 +70,8 @@ public SULWrapper wrap(AbstractSUL abstractSUL) { wrappedSUL = new SULLivenessWrapper<>(wrappedSUL, sulLivenessTracker, terminatedOutput); wrappedSUL = new CounterSUL<>(wrappedSUL); - inputCounter = CounterSUL.class.cast(wrappedSUL).getSymbolCounter(); - testCounter = CounterSUL.class.cast(wrappedSUL).getResetCounter(); + inputStatisticsKey = CounterSUL.KEY_SYMBOL; + testStatisticsKey = CounterSUL.KEY_QUERY; return this; } @@ -116,12 +116,12 @@ public SUL getWrappedSUL() { } @Override - public Counter getInputCounter() { - return inputCounter; + public StatisticsKey getInputStatisticsKey() { + return inputStatisticsKey; } @Override - public Counter getTestCounter() { - return testCounter; + public StatisticsKey getTestStatisticsKey() { + return testStatisticsKey; } } diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerRA.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerRA.java index 095b24ef..a75394db 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerRA.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerRA.java @@ -140,7 +140,7 @@ public StateFuzzerComposerRA( // initialize statistics tracker this.statisticsTracker = new StatisticsTrackerRA( - sulWrapper.getInputCounter(), sulWrapper.getTestCounter()); + sulWrapper.getInputStatisticsKey(), sulWrapper.getTestStatisticsKey()); } /** diff --git a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerStandard.java b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerStandard.java index e0008bc1..38b58bcb 100644 --- a/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerStandard.java +++ b/src/main/java/io/github/protocolfuzzing/protocolstatefuzzer/statefuzzer/core/StateFuzzerComposerStandard.java @@ -1,11 +1,11 @@ package io.github.protocolfuzzing.protocolstatefuzzer.statefuzzer.core; import de.learnlib.algorithm.LearningAlgorithm.MealyLearner; -import de.learnlib.filter.statistic.Counter; import de.learnlib.oracle.EquivalenceOracle; import de.learnlib.oracle.MembershipOracle; import de.learnlib.oracle.membership.SULOracle; import de.learnlib.query.DefaultQuery; +import de.learnlib.statistic.StatisticsKey; import de.learnlib.sul.SUL; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.alphabet.AlphabetBuilder; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.config.LearnerConfig; @@ -16,7 +16,6 @@ import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.oracles.MultipleRunsSULOracle; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.oracles.NonDeterminismRetryingSULOracle; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.oracles.ObservationTree; -import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics.AggregatedCounter; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics.StatisticsTracker; import io.github.protocolfuzzing.protocolstatefuzzer.components.learner.statistics.StatisticsTrackerStandard; import io.github.protocolfuzzing.protocolstatefuzzer.components.sul.core.AbstractSUL; @@ -120,8 +119,8 @@ public StateFuzzerComposerStandard( this.suls = new ArrayList<>(); - List inputCounters = new ArrayList<>(); - List testCounters = new ArrayList<>(); + List inputStatisticsKeys = new ArrayList<>(); + List testStatisticsKeys = new ArrayList<>(); // set up wrapped SUL (System Under Learning) SULConfig sulConfig = stateFuzzerEnabler.getSULConfig(); @@ -144,17 +143,15 @@ public StateFuzzerComposerStandard( .getWrappedSUL(); this.suls.add(sul); - inputCounters.add(sulWrapper.getInputCounter()); - testCounters.add(sulWrapper.getTestCounter()); + inputStatisticsKeys.add(sulWrapper.getInputStatisticsKey()); + testStatisticsKeys.add(sulWrapper.getTestStatisticsKey()); } // initialize cache as observation tree this.cache = new ObservationTree<>(); // initialize statistics tracker - AggregatedCounter aggregatedInputCounter = new AggregatedCounter(inputCounters); - AggregatedCounter aggregatedTestCounter = new AggregatedCounter(testCounters); - this.statisticsTracker = new StatisticsTrackerStandard<>(aggregatedInputCounter, aggregatedTestCounter); + this.statisticsTracker = new StatisticsTrackerStandard<>(inputStatisticsKeys, testStatisticsKeys); } /**