diff options
| author | Dmitry Vyukov <dvyukov@google.com> | 2024-08-07 16:11:32 +0200 |
|---|---|---|
| committer | Aleksandr Nogikh <nogikh@google.com> | 2024-08-07 18:47:26 +0000 |
| commit | 0f953f8412252770b055ec18242ea8d9b6cb0034 (patch) | |
| tree | db0beef8e72b496bd34c91a5e14e96e061ce7cd3 /prog | |
| parent | 7013cb0d7d7b78bb0160c45d13a8d7d472835513 (diff) | |
prog: don't minimize int/resource for corpus
It makes little sense to minimize int's for corpus.
Also replacing resource with a default value does not make sense as well.
For corpus we are only interesting in reducing total number of args
that will be considered for mutation.
Add CrashSnapshot mode, mainly to keep the minimization code "alive" for now.
Diffstat (limited to 'prog')
| -rw-r--r-- | prog/expr_test.go | 5 | ||||
| -rw-r--r-- | prog/minimization.go | 9 | ||||
| -rw-r--r-- | prog/minimization_test.go | 8 |
3 files changed, 14 insertions, 8 deletions
diff --git a/prog/expr_test.go b/prog/expr_test.go index 6b767cd11..aaae6a74a 100644 --- a/prog/expr_test.go +++ b/prog/expr_test.go @@ -135,6 +135,7 @@ func TestEvaluateConditionalFields(t *testing.T) { func TestConditionalMinimize(t *testing.T) { tests := []struct { + mode MinimizeMode input string pred func(*Prog, int) bool output string @@ -156,6 +157,7 @@ func TestConditionalMinimize(t *testing.T) { output: `test$conditional_struct(&(0x7f0000000040)={0x6, @value, @value=0x123})`, }, { + mode: MinimizeCrashSnapshot, input: `test$conditional_struct_minimize(&(0x7f0000000040)={0x1, @value=0xaa, 0x1, @value=0xbb})`, pred: func(p *Prog, _ int) bool { return bytes.Contains(p.Serialize(), []byte("0xaa")) @@ -163,6 +165,7 @@ func TestConditionalMinimize(t *testing.T) { output: `test$conditional_struct_minimize(&(0x7f0000000040)={0x1, @value=0xaa})`, }, { + mode: MinimizeCrashSnapshot, input: `test$conditional_struct_minimize(&(0x7f0000000040)={0x1, @value=0xaa, 0x1, @value=0xbb})`, pred: func(p *Prog, _ int) bool { return bytes.Contains(p.Serialize(), []byte("0xbb")) @@ -186,7 +189,7 @@ func TestConditionalMinimize(t *testing.T) { assert.NoError(tt, err) p, err := target.Deserialize([]byte(test.input), Strict) assert.NoError(tt, err) - p1, _ := Minimize(p, 0, MinimizeCorpus, test.pred) + p1, _ := Minimize(p, 0, test.mode, test.pred) res := p1.Serialize() assert.Equal(tt, test.output, strings.TrimSpace(string(res))) }) diff --git a/prog/minimization.go b/prog/minimization.go index 935c18232..5f138feb4 100644 --- a/prog/minimization.go +++ b/prog/minimization.go @@ -39,6 +39,9 @@ const ( // Minimize crash reproducer. // This mode assumes each test is expensive (need to reboot), so tries fewer things. MinimizeCrash + // Minimize crash reproducer in snapshot mode. + // This mode does not assume that tests are expensive, and tries to minimize for reproducer readability. + MinimizeCrashSnapshot // Only try to remove calls. MinimizeCallsOnly ) @@ -264,7 +267,7 @@ func (typ *ArrayType) minimize(ctx *minimizeArgsCtx, arg Arg, path string) bool elem := a.Inner[i] elemPath := fmt.Sprintf("%v-%v", path, i) // Try to remove individual elements one-by-one. - if ctx.mode == MinimizeCorpus && !ctx.triedPaths[elemPath] && + if ctx.mode != MinimizeCrash && !ctx.triedPaths[elemPath] && (typ.Kind == ArrayRandLen || typ.Kind == ArrayRangeLen && uint64(len(a.Inner)) > typ.RangeBegin) { ctx.triedPaths[elemPath] = true @@ -307,7 +310,7 @@ func (typ *ProcType) minimize(ctx *minimizeArgsCtx, arg Arg, path string) bool { func minimizeInt(ctx *minimizeArgsCtx, arg Arg, path string) bool { // TODO: try to reset bits in ints // TODO: try to set separate flags - if ctx.mode == MinimizeCrash { + if ctx.mode != MinimizeCrashSnapshot { return false } a := arg.(*ConstArg) @@ -335,7 +338,7 @@ func minimizeInt(ctx *minimizeArgsCtx, arg Arg, path string) bool { } func (typ *ResourceType) minimize(ctx *minimizeArgsCtx, arg Arg, path string) bool { - if ctx.mode == MinimizeCrash { + if ctx.mode != MinimizeCrashSnapshot { return false } a := arg.(*ResultArg) diff --git a/prog/minimization_test.go b/prog/minimization_test.go index 7862bcc01..6a3fb4e4e 100644 --- a/prog/minimization_test.go +++ b/prog/minimization_test.go @@ -52,7 +52,7 @@ func TestMinimize(t *testing.T) { // Aim at removal of sched_yield. return len(p.Calls) == 2 && p.Calls[0].Meta.Name == "mmap" && p.Calls[1].Meta.Name == "pipe2" }, - "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x0, 0x10, 0xffffffffffffffff, 0x0)\n" + + "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x3, 0x32, 0xffffffffffffffff, 0x0)\n" + "pipe2(0x0, 0x0)\n", 1, }, @@ -87,7 +87,7 @@ func TestMinimize(t *testing.T) { func(p *Prog, callIndex int) bool { return p.String() == "mmap-write-sched_yield" }, - "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x0, 0x10, 0xffffffffffffffff, 0x0)\n" + + "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x3, 0x32, 0xffffffffffffffff, 0x0)\n" + "write(0xffffffffffffffff, 0x0, 0x0)\n" + "sched_yield()\n", 2, @@ -103,7 +103,7 @@ func TestMinimize(t *testing.T) { func(p *Prog, callIndex int) bool { return p.String() == "mmap-write-sched_yield" }, - "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x0, 0x10, 0xffffffffffffffff, 0x0)\n" + + "mmap(&(0x7f0000000000/0x1000)=nil, 0x1000, 0x3, 0x32, 0xffffffffffffffff, 0x0)\n" + "write(0xffffffffffffffff, 0x0, 0x0)\n" + "sched_yield()\n", -1, @@ -148,7 +148,7 @@ func TestMinimize(t *testing.T) { "minimize$0(0x1, 0x1)\n", -1, func(p *Prog, callIndex int) bool { return len(p.Calls) == 1 }, - "minimize$0(0x1, 0xffffffffffffffff)\n", + "minimize$0(0x1, 0x1)\n", -1, }, // Clear unneeded fault injection. |
