aboutsummaryrefslogtreecommitdiffstats
path: root/prog/minimization.go
diff options
context:
space:
mode:
authorAleksandr Nogikh <nogikh@google.com>2021-09-23 16:15:41 +0000
committerAleksandr Nogikh <wp32pw@gmail.com>2021-12-10 12:30:07 +0100
commitfd8caa5462e64f37cb9eebd75ffca1737dde447d (patch)
treebfa900ebf41099b21476e72acdf063ee630178c9 /prog/minimization.go
parent4d4ce9bc2a12073dcc8b917f9fc2a4ecba26c4c5 (diff)
all: replace collide mode by `async` call property
Replace the currently existing straightforward approach to race triggering (that was almost entirely implemented inside syz-executor) with a more flexible one. The `async` call property instructs syz-executor not to block until the call has completed execution and proceed immediately to the next call. The decision on what calls to mark with `async` is made by syz-fuzzer. Ultimately this should let us implement more intelligent race provoking strategies as well as make more fine-grained reproducers.
Diffstat (limited to 'prog/minimization.go')
-rw-r--r--prog/minimization.go30
1 files changed, 30 insertions, 0 deletions
diff --git a/prog/minimization.go b/prog/minimization.go
index 60a715b66..89ed6e142 100644
--- a/prog/minimization.go
+++ b/prog/minimization.go
@@ -5,6 +5,7 @@ package prog
import (
"fmt"
+ "reflect"
)
// Minimize minimizes program p into an equivalent program using the equivalence
@@ -28,6 +29,9 @@ func Minimize(p0 *Prog, callIndex0 int, crash bool, pred0 func(*Prog, int) bool)
// Try to remove all calls except the last one one-by-one.
p0, callIndex0 = removeCalls(p0, callIndex0, crash, pred)
+ // Try to reset all call props to their default values.
+ p0 = resetCallProps(p0, callIndex0, pred)
+
// Try to minimize individual calls.
for i := 0; i < len(p0.Calls); i++ {
ctx := &minimizeArgsCtx{
@@ -78,6 +82,23 @@ func removeCalls(p0 *Prog, callIndex0 int, crash bool, pred func(*Prog, int) boo
return p0, callIndex0
}
+func resetCallProps(p0 *Prog, callIndex0 int, pred func(*Prog, int) bool) *Prog {
+ // Try to reset all call props to their default values.
+ // This should be reasonable for many progs.
+ p := p0.Clone()
+ anyDifferent := false
+ for idx := range p.Calls {
+ if !reflect.DeepEqual(p.Calls[idx].Props, CallProps{}) {
+ p.Calls[idx].Props = CallProps{}
+ anyDifferent = true
+ }
+ }
+ if anyDifferent && pred(p, callIndex0) {
+ return p
+ }
+ return p0
+}
+
func minimizeCallProps(p0 *Prog, callIndex, callIndex0 int, pred func(*Prog, int) bool) *Prog {
props := p0.Calls[callIndex].Props
@@ -90,6 +111,15 @@ func minimizeCallProps(p0 *Prog, callIndex, callIndex0 int, pred func(*Prog, int
}
}
+ // Try to drop async.
+ if props.Async {
+ p := p0.Clone()
+ p.Calls[callIndex].Props.Async = false
+ if pred(p, callIndex0) {
+ p0 = p
+ }
+ }
+
return p0
}