Commit 432668ed authored by Michal Majewski's avatar Michal Majewski Committed by Commit Bot

[test] Add option to disable analysis phase

Introduce option to run fuzzer processor without analysis phase.
It will be used in fuzzing combined tests.

Bug: v8:6917
Change-Id: Ic96d6b8c5a35c81da80340555bdd75c0d518cb5a
Reviewed-on: https://chromium-review.googlesource.com/880948
Commit-Queue: Michał Majewski <majeski@google.com>
Reviewed-by: 's avatarMichael Achenbach <machenbach@chromium.org>
Cr-Commit-Position: refs/heads/master@{#50810}
parent f3fdcfc1
...@@ -75,6 +75,7 @@ class NumFuzzer(base_runner.BaseTestRunner): ...@@ -75,6 +75,7 @@ class NumFuzzer(base_runner.BaseTestRunner):
help="Indicates running test driver on swarming.", help="Indicates running test driver on swarming.",
default=False, action="store_true") default=False, action="store_true")
# Stress gc
parser.add_option("--stress-marking", default=0, type="int", parser.add_option("--stress-marking", default=0, type="int",
help="probability [0-10] of adding --stress-marking " help="probability [0-10] of adding --stress-marking "
"flag to the test") "flag to the test")
...@@ -87,6 +88,8 @@ class NumFuzzer(base_runner.BaseTestRunner): ...@@ -87,6 +88,8 @@ class NumFuzzer(base_runner.BaseTestRunner):
parser.add_option("--stress-gc", default=0, type="int", parser.add_option("--stress-gc", default=0, type="int",
help="probability [0-10] of adding --random-gc-interval " help="probability [0-10] of adding --random-gc-interval "
"flag to the test") "flag to the test")
# Stress deopt
parser.add_option("--stress-deopt", default=0, type="int", parser.add_option("--stress-deopt", default=0, type="int",
help="probability [0-10] of adding --deopt-every-n-times " help="probability [0-10] of adding --deopt-every-n-times "
"flag to the test") "flag to the test")
...@@ -99,6 +102,12 @@ class NumFuzzer(base_runner.BaseTestRunner): ...@@ -99,6 +102,12 @@ class NumFuzzer(base_runner.BaseTestRunner):
parser.add_option("--total-timeout-sec", default=0, type="int", parser.add_option("--total-timeout-sec", default=0, type="int",
help="How long should fuzzer run. It overrides " help="How long should fuzzer run. It overrides "
"--tests-count") "--tests-count")
# Combine multiple tests
parser.add_option("--combine-tests", default=False, action="store_true",
help="Combine multiple tests as one and run with "
"try-catch wrapper")
return parser return parser
...@@ -142,6 +151,7 @@ class NumFuzzer(base_runner.BaseTestRunner): ...@@ -142,6 +151,7 @@ class NumFuzzer(base_runner.BaseTestRunner):
options.tests_count, options.tests_count,
self._create_fuzzer_configs(options), self._create_fuzzer_configs(options),
options.total_timeout_sec, options.total_timeout_sec,
disable_analysis=options.combine_tests,
) )
results = ResultsTracker() results = ResultsTracker()
...@@ -251,17 +261,15 @@ class NumFuzzer(base_runner.BaseTestRunner): ...@@ -251,17 +261,15 @@ class NumFuzzer(base_runner.BaseTestRunner):
def _create_fuzzer_configs(self, options): def _create_fuzzer_configs(self, options):
fuzzers = [] fuzzers = []
if options.stress_compaction: def add(name, prob, *args):
fuzzers.append(fuzzer.create_compaction_config(options.stress_compaction)) if prob:
if options.stress_marking: fuzzers.append(fuzzer.create_fuzzer_config(name, prob, *args))
fuzzers.append(fuzzer.create_marking_config(options.stress_marking))
if options.stress_scavenge: add('compaction', options.stress_compaction)
fuzzers.append(fuzzer.create_scavenge_config(options.stress_scavenge)) add('marking', options.stress_marking)
if options.stress_gc: add('scavenge', options.stress_scavenge)
fuzzers.append(fuzzer.create_gc_interval_config(options.stress_gc)) add('gc_interval', options.stress_gc)
if options.stress_deopt: add('deopt', options.stress_deopt, options.stress_deopt_min)
fuzzers.append(fuzzer.create_deopt_config(options.stress_deopt,
options.stress_deopt_min))
return fuzzers return fuzzers
def _create_rerun_proc(self, options): def _create_rerun_proc(self, options):
......
...@@ -38,20 +38,23 @@ class Fuzzer(object): ...@@ -38,20 +38,23 @@ class Fuzzer(object):
rng: random number generator rng: random number generator
test: test for which to create flags test: test for which to create flags
analysis_value: value returned by the analyzer. None if there is no analysis_value: value returned by the analyzer. None if there is no
corresponding analyzer to this fuzzer corresponding analyzer to this fuzzer or the analysis phase is disabled
""" """
raise NotImplementedError() raise NotImplementedError()
# TODO(majeski): Allow multiple subtests to run at once. # TODO(majeski): Allow multiple subtests to run at once.
class FuzzerProc(base.TestProcProducer): class FuzzerProc(base.TestProcProducer):
def __init__(self, rng, count, fuzzers, fuzz_duration_sec=0): def __init__(self, rng, count, fuzzers, fuzz_duration_sec=0,
disable_analysis=False):
""" """
Args: Args:
rng: random number generator used to select flags and values for them rng: random number generator used to select flags and values for them
count: number of tests to generate based on each base test count: number of tests to generate based on each base test
fuzzers: list of FuzzerConfig instances fuzzers: list of FuzzerConfig instances
fuzz_duration_sec: how long it should run, overrides count fuzz_duration_sec: how long it should run, overrides count
disable_analysis: disable analysis phase and filtering base on it. When
set, processor passes None as analysis result to fuzzers
""" """
super(FuzzerProc, self).__init__('Fuzzer') super(FuzzerProc, self).__init__('Fuzzer')
...@@ -59,6 +62,7 @@ class FuzzerProc(base.TestProcProducer): ...@@ -59,6 +62,7 @@ class FuzzerProc(base.TestProcProducer):
self._count = count self._count = count
self._fuzzer_configs = fuzzers self._fuzzer_configs = fuzzers
self._fuzz_duration_sec = fuzz_duration_sec self._fuzz_duration_sec = fuzz_duration_sec
self._disable_analysis = disable_analysis
self._gens = {} self._gens = {}
self._start_time = None self._start_time = None
...@@ -73,6 +77,17 @@ class FuzzerProc(base.TestProcProducer): ...@@ -73,6 +77,17 @@ class FuzzerProc(base.TestProcProducer):
if not self._start_time: if not self._start_time:
self._start_time = time.time() self._start_time = time.time()
analysis_subtest = self._create_analysis_subtest(test)
if analysis_subtest:
self._send_test(analysis_subtest)
else:
self._gens[test.procid] = self._create_gen(test)
self._try_send_next_test(test)
def _create_analysis_subtest(self, test):
if self._disable_analysis:
return None
analysis_flags = [] analysis_flags = []
for fuzzer_config in self._fuzzer_configs: for fuzzer_config in self._fuzzer_configs:
if fuzzer_config.analyzer: if fuzzer_config.analyzer:
...@@ -80,13 +95,9 @@ class FuzzerProc(base.TestProcProducer): ...@@ -80,13 +95,9 @@ class FuzzerProc(base.TestProcProducer):
if analysis_flags: if analysis_flags:
analysis_flags = list(set(analysis_flags)) analysis_flags = list(set(analysis_flags))
subtest = self._create_subtest(test, 'analysis', flags=analysis_flags, return self._create_subtest(test, 'analysis', flags=analysis_flags,
keep_output=True) keep_output=True)
self._send_test(subtest)
return
self._gens[test.procid] = self._create_gen(test)
self._try_send_next_test(test)
def _result_for(self, test, subtest, result): def _result_for(self, test, subtest, result):
if self._fuzz_duration_sec and not self._stop: if self._fuzz_duration_sec and not self._stop:
...@@ -94,12 +105,13 @@ class FuzzerProc(base.TestProcProducer): ...@@ -94,12 +105,13 @@ class FuzzerProc(base.TestProcProducer):
print '>>> Stopping fuzzing' print '>>> Stopping fuzzing'
self._stop = True self._stop = True
if result is not None: if not self._disable_analysis:
# Analysis phase, for fuzzing we drop the result. if result is not None:
if result.has_unexpected_output: # Analysis phase, for fuzzing we drop the result.
self._send_result(test, None) if result.has_unexpected_output:
return self._send_result(test, None)
self._gens[test.procid] = self._create_gen(test, result) return
self._gens[test.procid] = self._create_gen(test, result)
self._try_send_next_test(test) self._try_send_next_test(test)
...@@ -110,7 +122,7 @@ class FuzzerProc(base.TestProcProducer): ...@@ -110,7 +122,7 @@ class FuzzerProc(base.TestProcProducer):
indexes = [] indexes = []
for i, fuzzer_config in enumerate(self._fuzzer_configs): for i, fuzzer_config in enumerate(self._fuzzer_configs):
analysis_value = None analysis_value = None
if fuzzer_config.analyzer: if analysis_result and fuzzer_config.analyzer:
analysis_value = fuzzer_config.analyzer.do_analysis(analysis_result) analysis_value = fuzzer_config.analyzer.do_analysis(analysis_result)
if not analysis_value: if not analysis_value:
# Skip fuzzer for this test since it doesn't have analysis data # Skip fuzzer for this test since it doesn't have analysis data
...@@ -158,23 +170,6 @@ class FuzzerProc(base.TestProcProducer): ...@@ -158,23 +170,6 @@ class FuzzerProc(base.TestProcProducer):
return seed return seed
def create_scavenge_config(probability):
return FuzzerConfig(probability, ScavengeAnalyzer(), ScavengeFuzzer())
def create_marking_config(probability):
return FuzzerConfig(probability, MarkingAnalyzer(), MarkingFuzzer())
def create_gc_interval_config(probability):
return FuzzerConfig(probability, GcIntervalAnalyzer(), GcIntervalFuzzer())
def create_compaction_config(probability):
return FuzzerConfig(probability, None, CompactionFuzzer())
def create_deopt_config(probability, min_interval):
return FuzzerConfig(probability, DeoptAnalyzer(min_interval),
DeoptFuzzer(min_interval))
class ScavengeAnalyzer(Analyzer): class ScavengeAnalyzer(Analyzer):
def get_analysis_flags(self): def get_analysis_flags(self):
return ['--fuzzer-gc-analysis'] return ['--fuzzer-gc-analysis']
...@@ -188,7 +183,7 @@ class ScavengeAnalyzer(Analyzer): ...@@ -188,7 +183,7 @@ class ScavengeAnalyzer(Analyzer):
class ScavengeFuzzer(Fuzzer): class ScavengeFuzzer(Fuzzer):
def create_flags_generator(self, rng, test, analysis_value): def create_flags_generator(self, rng, test, analysis_value):
while True: while True:
yield ['--stress-scavenge=%d' % analysis_value] yield ['--stress-scavenge=%d' % (analysis_value or 100)]
class MarkingAnalyzer(Analyzer): class MarkingAnalyzer(Analyzer):
...@@ -204,7 +199,7 @@ class MarkingAnalyzer(Analyzer): ...@@ -204,7 +199,7 @@ class MarkingAnalyzer(Analyzer):
class MarkingFuzzer(Fuzzer): class MarkingFuzzer(Fuzzer):
def create_flags_generator(self, rng, test, analysis_value): def create_flags_generator(self, rng, test, analysis_value):
while True: while True:
yield ['--stress-marking=%d' % analysis_value] yield ['--stress-marking=%d' % (analysis_value or 100)]
class GcIntervalAnalyzer(Analyzer): class GcIntervalAnalyzer(Analyzer):
...@@ -219,7 +214,10 @@ class GcIntervalAnalyzer(Analyzer): ...@@ -219,7 +214,10 @@ class GcIntervalAnalyzer(Analyzer):
class GcIntervalFuzzer(Fuzzer): class GcIntervalFuzzer(Fuzzer):
def create_flags_generator(self, rng, test, analysis_value): def create_flags_generator(self, rng, test, analysis_value):
value = analysis_value / 10 if analysis_value:
value = analysis_value / 10
else:
value = 10000
while True: while True:
yield ['--random-gc-interval=%d' % value] yield ['--random-gc-interval=%d' % value]
...@@ -259,6 +257,26 @@ class DeoptFuzzer(Fuzzer): ...@@ -259,6 +257,26 @@ class DeoptFuzzer(Fuzzer):
def create_flags_generator(self, rng, test, analysis_value): def create_flags_generator(self, rng, test, analysis_value):
while True: while True:
value = analysis_value / 2 if analysis_value:
value = analysis_value / 2
else:
value = 10000
interval = rng.randint(self._min, max(value, self._min)) interval = rng.randint(self._min, max(value, self._min))
yield ['--deopt-every-n-times=%d' % interval] yield ['--deopt-every-n-times=%d' % interval]
FUZZERS = {
'scavenge': (ScavengeAnalyzer, ScavengeFuzzer),
'marking': (MarkingAnalyzer, MarkingFuzzer),
'gc_interval': (GcIntervalAnalyzer, GcIntervalFuzzer),
'compaction': (None, CompactionFuzzer),
'deopt': (DeoptAnalyzer, DeoptFuzzer),
}
def create_fuzzer_config(name, probability, *args, **kwargs):
analyzer_class, fuzzer_class = FUZZERS[name]
return FuzzerConfig(
probability,
analyzer_class(*args, **kwargs) if analyzer_class else None,
fuzzer_class(*args, **kwargs),
)
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment