github.com/ledgerwatch/erigon-lib@v1.0.0/compress/decompress_fuzz_test.go (about)

     1  package compress
     2  
     3  import (
     4  	"bytes"
     5  	"context"
     6  	"fmt"
     7  	"math/rand"
     8  	"path/filepath"
     9  	"testing"
    10  
    11  	"github.com/ledgerwatch/erigon-lib/common/cmp"
    12  	"github.com/ledgerwatch/log/v3"
    13  )
    14  
    15  func FuzzDecompressMatch(f *testing.F) {
    16  	logger := log.New()
    17  	f.Fuzz(func(t *testing.T, x []byte, pos []byte, workers int8) {
    18  		t.Helper()
    19  		t.Parallel()
    20  		if len(pos) < 1 || workers < 1 {
    21  			t.Skip()
    22  			return
    23  		}
    24  		var a [][]byte
    25  		j := 0
    26  		for i := 0; i < len(pos) && j < len(x); i++ {
    27  			if pos[i] == 0 {
    28  				continue
    29  			}
    30  			next := cmp.Min(j+int(pos[i]*10), len(x)-1)
    31  			bbb := x[j:next]
    32  			a = append(a, bbb)
    33  			j = next
    34  		}
    35  
    36  		ctx := context.Background()
    37  		tmpDir := t.TempDir()
    38  		file := filepath.Join(tmpDir, fmt.Sprintf("compressed-%d", rand.Int31()))
    39  		c, err := NewCompressor(ctx, t.Name(), file, tmpDir, 2, int(workers), log.LvlDebug, logger)
    40  		if err != nil {
    41  			t.Fatal(err)
    42  		}
    43  		c.DisableFsync()
    44  		defer c.Close()
    45  		for _, b := range a {
    46  			if err = c.AddWord(b); err != nil {
    47  				t.Fatal(err)
    48  			}
    49  		}
    50  		if err = c.Compress(); err != nil {
    51  			t.Fatal(err)
    52  		}
    53  		c.Close()
    54  		d, err := NewDecompressor(file)
    55  		if err != nil {
    56  			t.Fatal(err)
    57  		}
    58  		defer d.Close()
    59  		g := d.MakeGetter()
    60  		buf := make([]byte, (1 << 16))
    61  		word_idx := 0
    62  		for g.HasNext() {
    63  			expected := a[word_idx]
    64  			savePos := g.dataP
    65  			cmp := g.MatchCmp(expected)
    66  			pos1 := g.dataP
    67  			if cmp != 0 {
    68  				t.Fatalf("MatchCmp: expected match: %v\n", expected)
    69  			}
    70  			g.Reset(savePos)
    71  			ok, _ := g.Match(expected)
    72  			pos2 := g.dataP
    73  			if !ok {
    74  				t.Fatalf("MatchBool: expected match: %v\n", expected)
    75  			}
    76  			g.Reset(savePos)
    77  			word, nexPos := g.Next(nil)
    78  			if bytes.Compare(word, expected) != 0 {
    79  				t.Fatalf("bytes.Compare: expected match: %v with word %v\n", expected, word)
    80  			}
    81  			if pos1 != pos2 && pos2 != nexPos {
    82  				t.Fatalf("pos1 %v != pos2 %v != nexPos %v\n", pos1, pos2, nexPos)
    83  			}
    84  			g.Reset(savePos)
    85  			word2, nexPos2 := g.FastNext(buf)
    86  			if bytes.Compare(word2, expected) != 0 {
    87  				t.Fatalf("bytes.Compare: expected match: %v with word %v\n", expected, word)
    88  			}
    89  			if pos1 != pos2 && pos2 != nexPos && nexPos != nexPos2 {
    90  				t.Fatalf("pos1 %v != pos2 %v != nexPos %v\n", pos1, pos2, nexPos)
    91  			}
    92  			word_idx++
    93  		}
    94  	})
    95  
    96  }