aboutsummaryrefslogtreecommitdiff
path: root/src/internal/fuzz
diff options
context:
space:
mode:
authorJay Conrod <jayconrod@google.com>2021-08-16 16:16:51 -0700
committerJay Conrod <jayconrod@google.com>2021-08-31 20:28:07 +0000
commit18c288ef8b8a3e7d2c02d3bb4c06e9f7c006b9da (patch)
tree86d07c1a7d15bc40a16e1d5a7770c93b0bd44aec /src/internal/fuzz
parent03b8d403dc620050cf5a5ded9be6c89bcd388a70 (diff)
downloadgo-18c288ef8b8a3e7d2c02d3bb4c06e9f7c006b9da.tar.xz
[dev.fuzz] internal/fuzz: ensure crash is written if minimization interrupted
If any error occurs when minimizing a crash, for example, the user presses ^C because minimization is taking too long, the coordinator will now write the unminimized crash to testdata. Change-Id: I0c754125781eb184846e496c728e0505a28639d9 Reviewed-on: https://go-review.googlesource.com/c/go/+/342995 Trust: Jay Conrod <jayconrod@google.com> Trust: Katie Hockman <katie@golang.org> Run-TryBot: Jay Conrod <jayconrod@google.com> TryBot-Result: Go Bot <gobot@golang.org> Reviewed-by: Katie Hockman <katie@golang.org>
Diffstat (limited to 'src/internal/fuzz')
-rw-r--r--src/internal/fuzz/fuzz.go29
1 files changed, 24 insertions, 5 deletions
diff --git a/src/internal/fuzz/fuzz.go b/src/internal/fuzz/fuzz.go
index b06ab146f7..9a9a4564c2 100644
--- a/src/internal/fuzz/fuzz.go
+++ b/src/internal/fuzz/fuzz.go
@@ -133,6 +133,27 @@ func CoordinateFuzzing(ctx context.Context, opts CoordinateFuzzingOpts) (err err
inputC = nil
}
+ // Ensure that any crash we find is written to the corpus, even if an error
+ // or interruption occurs while minimizing it.
+ var crashMinimizing *fuzzResult
+ crashWritten := false
+ defer func() {
+ if crashMinimizing == nil || crashWritten {
+ return
+ }
+ fileName, werr := writeToCorpus(crashMinimizing.entry.Data, opts.CorpusDir)
+ if werr != nil {
+ err = fmt.Errorf("%w\n%v", err, werr)
+ return
+ }
+ if err == nil {
+ err = &crashError{
+ name: filepath.Base(fileName),
+ err: errors.New(crashMinimizing.crasherMsg),
+ }
+ }
+ }()
+
// Start workers.
// TODO(jayconrod): do we want to support fuzzing different binaries?
dir := "" // same as self
@@ -175,8 +196,6 @@ func CoordinateFuzzing(ctx context.Context, opts CoordinateFuzzingOpts) (err err
statTicker := time.NewTicker(3 * time.Second)
defer statTicker.Stop()
defer c.logStats()
- crashMinimizing := false
- crashWritten := false
for {
select {
@@ -194,7 +213,7 @@ func CoordinateFuzzing(ctx context.Context, opts CoordinateFuzzingOpts) (err err
if result.crasherMsg != "" {
if c.canMinimize() && !result.minimizeAttempted {
- if crashMinimizing {
+ if crashMinimizing != nil {
// This crash is not minimized, and another crash is being minimized.
// Ignore this one and wait for the other one to finish.
break
@@ -202,7 +221,7 @@ func CoordinateFuzzing(ctx context.Context, opts CoordinateFuzzingOpts) (err err
// Found a crasher but haven't yet attempted to minimize it.
// Send it back to a worker for minimization. Disable inputC so
// other workers don't continue fuzzing.
- crashMinimizing = true
+ crashMinimizing = &result
inputC = nil
fmt.Fprintf(c.opts.Log, "found a crash, minimizing...\n")
c.minimizeC <- c.minimizeInputForResult(result)
@@ -304,7 +323,7 @@ func CoordinateFuzzing(ctx context.Context, opts CoordinateFuzzingOpts) (err err
}
}
}
- if inputC == nil && !crashMinimizing && !stopping && !c.coverageOnlyRun() {
+ if inputC == nil && crashMinimizing == nil && !stopping && !c.coverageOnlyRun() {
// Re-enable inputC if it was disabled earlier because we hit the limit
// on the number of inputs to fuzz (nextInput returned false). Workers
// can do less work than requested, so after receiving a result above,