// Copyright 2020 The Monogon Project Authors.
//
// SPDX-License-Identifier: Apache-2.0
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package loop

import (
	"encoding/binary"
	"io"
	"io/ioutil"
	"math"
	"os"
	"runtime"
	"syscall"
	"testing"
	"unsafe"

	"github.com/stretchr/testify/assert"
	"github.com/stretchr/testify/require"
	"golang.org/x/sys/unix"
)

// Write a test file with a very specific pattern (increasing little-endian 16 bit unsigned integers) to detect offset
// correctness. File is always 128KiB large (2^16 * 2 bytes).
func makeTestFile() *os.File {
	f, err := ioutil.TempFile("/tmp", "")
	if err != nil {
		panic(err)
	}
	for i := 0; i <= math.MaxUint16; i++ {
		if err := binary.Write(f, binary.LittleEndian, uint16(i)); err != nil {
			panic(err)
		}
	}
	if _, err := f.Seek(0, io.SeekStart); err != nil {
		panic(err)
	}
	return f
}

func getBlkdevSize(f *os.File) (size uint64) {
	if _, _, err := syscall.Syscall(syscall.SYS_IOCTL, f.Fd(), unix.BLKGETSIZE64, uintptr(unsafe.Pointer(&size))); err != 0 {
		panic(err)
	}
	return
}

func getOffsetFromContent(dev *Device) (firstIndex uint16) {
	if err := binary.Read(dev.dev, binary.LittleEndian, &firstIndex); err != nil {
		panic(err)
	}
	firstIndex *= 2 // 2 bytes per index
	return
}

func setupCreate(t *testing.T, config Config) *Device {
	f := makeTestFile()
	dev, err := Create(f, config)
	defer f.Close()
	assert.NoError(t, err)
	t.Cleanup(func() {
		if dev != nil {
			dev.Remove()
		}
		os.Remove(f.Name())
	})
	if dev == nil {
		t.FailNow()
	}
	return dev
}

func TestDeviceAccessors(t *testing.T) {
	if os.Getenv("IN_KTEST") != "true" {
		t.Skip("Not in ktest")
	}
	dev := setupCreate(t, Config{})

	devPath, err := dev.DevPath()
	assert.NoError(t, err)
	require.Equal(t, "/dev/loop0", devPath)

	var stat unix.Stat_t
	assert.NoError(t, unix.Stat("/dev/loop0", &stat))
	devNum, err := dev.Dev()
	assert.NoError(t, err)
	require.Equal(t, stat.Rdev, devNum)

	backingFile, err := dev.BackingFilePath()
	assert.NoError(t, err)
	// The filename of the temporary file is not available in this context, but we know that the file
	// needs to be in /tmp, which should be a good-enough test.
	assert.Contains(t, backingFile, "/tmp/")
}

func TestCreate(t *testing.T) {
	if os.Getenv("IN_KTEST") != "true" {
		t.Skip("Not in ktest")
	}
	t.Parallel()
	tests := []struct {
		name     string
		config   Config
		validate func(t *testing.T, dev *Device)
	}{
		{"NoOpts", Config{}, func(t *testing.T, dev *Device) {
			require.Equal(t, uint64(128*1024), getBlkdevSize(dev.dev))
			require.Equal(t, uint16(0), getOffsetFromContent(dev))

			_, err := dev.dev.WriteString("test")
			assert.NoError(t, err)
		}},
		{"DirectIO", Config{Flags: FlagDirectIO}, func(t *testing.T, dev *Device) {
			require.Equal(t, uint64(128*1024), getBlkdevSize(dev.dev))

			_, err := dev.dev.WriteString("test")
			assert.NoError(t, err)
		}},
		{"ReadOnly", Config{Flags: FlagReadOnly}, func(t *testing.T, dev *Device) {
			_, err := dev.dev.WriteString("test")
			assert.Error(t, err)
		}},
		{"Mapping", Config{BlockSize: 512, SizeLimit: 2048, Offset: 4096}, func(t *testing.T, dev *Device) {
			assert.Equal(t, uint16(4096), getOffsetFromContent(dev))
			assert.Equal(t, uint64(2048), getBlkdevSize(dev.dev))
		}},
	}
	for _, test := range tests {
		t.Run(test.name, func(t *testing.T) {
			dev := setupCreate(t, test.config)
			test.validate(t, dev)
			assert.NoError(t, dev.Remove())
		})
	}
}

func TestOpenBadDevice(t *testing.T) {
	if os.Getenv("IN_KTEST") != "true" {
		t.Skip("Not in ktest")
	}
	dev, err := Open("/dev/null")
	require.Error(t, err)
	if dev != nil { // Prevent leaks in case this test fails
		dev.Close()
	}
}

func TestOpen(t *testing.T) {
	if os.Getenv("IN_KTEST") != "true" {
		t.Skip("Not in ktest")
	}
	f := makeTestFile()
	defer os.Remove(f.Name())
	defer f.Close()
	dev, err := Create(f, Config{})
	assert.NoError(t, err)
	path, err := dev.DevPath()
	assert.NoError(t, err)
	assert.NoError(t, dev.Close())
	reopenedDev, err := Open(path)
	assert.NoError(t, err)
	defer reopenedDev.Remove()
	reopenedDevPath, err := reopenedDev.DevPath()
	assert.NoError(t, err)
	require.Equal(t, path, reopenedDevPath) // Still needs to be the same device
}

func TestResize(t *testing.T) {
	if os.Getenv("IN_KTEST") != "true" {
		t.Skip("Not in ktest")
	}
	f, err := ioutil.TempFile("/tmp", "")
	assert.NoError(t, err)
	empty1K := make([]byte, 1024)
	for i := 0; i < 64; i++ {
		_, err := f.Write(empty1K)
		assert.NoError(t, err)
	}
	dev, err := Create(f, Config{})
	assert.NoError(t, err)
	require.Equal(t, uint64(64*1024), getBlkdevSize(dev.dev))
	for i := 0; i < 32; i++ {
		_, err := f.Write(empty1K)
		assert.NoError(t, err)
	}
	assert.NoError(t, f.Sync())
	assert.NoError(t, dev.RefreshSize())
	require.Equal(t, uint64(96*1024), getBlkdevSize(dev.dev))
}

func TestStructSize(t *testing.T) {
	if runtime.GOOS != "linux" && runtime.GOARCH != "amd64" {
		t.Skip("Reference value not available")
	}
	require.Equal(t, uintptr(304), unsafe.Sizeof(loopConfig{}))
}
