// Copyright 2011 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package lzw

import (
	"bytes"
	"fmt"
	"internal/testenv"
	"io"
	"math"
	"os"
	"runtime"
	"testing"
)

var filenames = []string{
	"../testdata/gettysburg.txt",
	"../testdata/e.txt",
	"../testdata/pi.txt",
}

// testFile tests that compressing and then decompressing the given file with
// the given options yields equivalent bytes to the original file.
func testFile(t *testing.T, fn string, order Order, litWidth int) {
	// Read the file, as golden output.
	golden, err := os.Open(fn)
	if err != nil {
		t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err)
		return
	}
	defer golden.Close()

	// Read the file again, and push it through a pipe that compresses at the write end, and decompresses at the read end.
	raw, err := os.Open(fn)
	if err != nil {
		t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err)
		return
	}

	piper, pipew := io.Pipe()
	defer piper.Close()
	go func() {
		defer raw.Close()
		defer pipew.Close()
		lzww := NewWriter(pipew, order, litWidth)
		defer lzww.Close()
		var b [4096]byte
		for {
			n, err0 := raw.Read(b[:])
			if err0 != nil && err0 != io.EOF {
				t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err0)
				return
			}
			_, err1 := lzww.Write(b[:n])
			if err1 != nil {
				t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err1)
				return
			}
			if err0 == io.EOF {
				break
			}
		}
	}()
	lzwr := NewReader(piper, order, litWidth)
	defer lzwr.Close()

	// Compare the two.
	b0, err0 := io.ReadAll(golden)
	b1, err1 := io.ReadAll(lzwr)
	if err0 != nil {
		t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err0)
		return
	}
	if err1 != nil {
		t.Errorf("%s (order=%d litWidth=%d): %v", fn, order, litWidth, err1)
		return
	}
	if len(b1) != len(b0) {
		t.Errorf("%s (order=%d litWidth=%d): length mismatch %d != %d", fn, order, litWidth, len(b1), len(b0))
		return
	}
	for i := 0; i < len(b0); i++ {
		if b1[i] != b0[i] {
			t.Errorf("%s (order=%d litWidth=%d): mismatch at %d, 0x%02x != 0x%02x\n", fn, order, litWidth, i, b1[i], b0[i])
			return
		}
	}
}

func TestWriter(t *testing.T) {
	for _, filename := range filenames {
		for _, order := range [...]Order{LSB, MSB} {
			// The test data "2.71828 etcetera" is ASCII text requiring at least 6 bits.
			for litWidth := 6; litWidth <= 8; litWidth++ {
				if filename == "../testdata/gettysburg.txt" && litWidth == 6 {
					continue
				}
				testFile(t, filename, order, litWidth)
			}
		}
		if testing.Short() && testenv.Builder() == "" {
			break
		}
	}
}

func TestWriterReset(t *testing.T) {
	for _, order := range [...]Order{LSB, MSB} {
		t.Run(fmt.Sprintf("Order %d", order), func(t *testing.T) {
			for litWidth := 6; litWidth <= 8; litWidth++ {
				t.Run(fmt.Sprintf("LitWidth %d", litWidth), func(t *testing.T) {
					var data []byte
					if litWidth == 6 {
						data = []byte{1, 2, 3}
					} else {
						data = []byte(`lorem ipsum dolor sit amet`)
					}
					var buf bytes.Buffer
					w := NewWriter(&buf, order, litWidth)
					if _, err := w.Write(data); err != nil {
						t.Errorf("write: %v: %v", string(data), err)
					}

					if err := w.Close(); err != nil {
						t.Errorf("close: %v", err)
					}

					b1 := buf.Bytes()
					buf.Reset()

					w.(*Writer).Reset(&buf, order, litWidth)

					if _, err := w.Write(data); err != nil {
						t.Errorf("write: %v: %v", string(data), err)
					}

					if err := w.Close(); err != nil {
						t.Errorf("close: %v", err)
					}
					b2 := buf.Bytes()

					if !bytes.Equal(b1, b2) {
						t.Errorf("bytes written were not same")
					}
				})
			}
		})
	}
}

func TestWriterReturnValues(t *testing.T) {
	w := NewWriter(io.Discard, LSB, 8)
	n, err := w.Write([]byte("asdf"))
	if n != 4 || err != nil {
		t.Errorf("got %d, %v, want 4, nil", n, err)
	}
}

func TestSmallLitWidth(t *testing.T) {
	w := NewWriter(io.Discard, LSB, 2)
	if _, err := w.Write([]byte{0x03}); err != nil {
		t.Fatalf("write a byte < 1<<2: %v", err)
	}
	if _, err := w.Write([]byte{0x04}); err == nil {
		t.Fatal("write a byte >= 1<<2: got nil error, want non-nil")
	}
}

func TestStartsWithClearCode(t *testing.T) {
	// A literal width of 7 bits means that the code width starts at 8 bits,
	// which makes it easier to visually inspect the output (provided that the
	// output is short so codes don't get longer). Each byte is a code:
	//  - ASCII bytes are literal codes,
	//  - 0x80 is the clear code,
	//  - 0x81 is the end code.
	//  - 0x82 and above are copy codes (unused in this test case).
	for _, empty := range []bool{false, true} {
		var buf bytes.Buffer
		w := NewWriter(&buf, LSB, 7)
		if !empty {
			w.Write([]byte("Hi"))
		}
		w.Close()
		got := buf.String()

		want := "\x80\x81"
		if !empty {
			want = "\x80Hi\x81"
		}

		if got != want {
			t.Errorf("empty=%t: got %q, want %q", empty, got, want)
		}
	}
}

func BenchmarkEncoder(b *testing.B) {
	buf, err := os.ReadFile("../testdata/e.txt")
	if err != nil {
		b.Fatal(err)
	}
	if len(buf) == 0 {
		b.Fatalf("test file has no data")
	}

	for e := 4; e <= 6; e++ {
		n := int(math.Pow10(e))
		buf0 := buf
		buf1 := make([]byte, n)
		for i := 0; i < n; i += len(buf0) {
			if len(buf0) > n-i {
				buf0 = buf0[:n-i]
			}
			copy(buf1[i:], buf0)
		}
		buf0 = nil
		runtime.GC()
		b.Run(fmt.Sprint("1e", e), func(b *testing.B) {
			b.SetBytes(int64(n))
			for i := 0; i < b.N; i++ {
				w := NewWriter(io.Discard, LSB, 8)
				w.Write(buf1)
				w.Close()
			}
		})
		b.Run(fmt.Sprint("1e-Reuse", e), func(b *testing.B) {
			b.SetBytes(int64(n))
			w := NewWriter(io.Discard, LSB, 8)
			for i := 0; i < b.N; i++ {
				w.Write(buf1)
				w.Close()
				w.(*Writer).Reset(io.Discard, LSB, 8)
			}
		})
	}
}
