mirror of
https://github.com/aljazceru/kata-containers.git
synced 2025-12-24 01:24:26 +01:00
virtcontainers: refactor device.go to device manager
Fixes #50 This is done for decoupling device management part from other parts. It seperate device.go to several dirs and files: ``` virtcontainers/device ├── api │ └── interface.go ├── config │ └── config.go ├── drivers │ ├── block.go │ ├── generic.go │ ├── utils.go │ ├── vfio.go │ ├── vhost_user_blk.go │ ├── vhost_user.go │ ├── vhost_user_net.go │ └── vhost_user_scsi.go └── manager ├── manager.go └── utils.go ``` * `api` contains interface definition of device management, so upper level caller should import and use the interface, and lower level should implement the interface. it's bridge to device drivers and callers. * `config` contains structed exported data. * `drivers` contains specific device drivers including block, vfio and vhost user devices. * `manager` exposes an external management package with a `DeviceManager`. Signed-off-by: Zhang Wei <zhangwei555@huawei.com>
This commit is contained in:
251
virtcontainers/utils/utils_test.go
Normal file
251
virtcontainers/utils/utils_test.go
Normal file
@@ -0,0 +1,251 @@
|
||||
// Copyright (c) 2017 Intel Corporation
|
||||
//
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
package utils
|
||||
|
||||
import (
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"reflect"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
|
||||
func TestFileCopySuccessful(t *testing.T) {
|
||||
fileContent := "testContent"
|
||||
|
||||
srcFile, err := ioutil.TempFile("", "test_src_copy")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
defer os.Remove(srcFile.Name())
|
||||
defer srcFile.Close()
|
||||
|
||||
dstFile, err := ioutil.TempFile("", "test_dst_copy")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
defer os.Remove(dstFile.Name())
|
||||
|
||||
dstPath := dstFile.Name()
|
||||
|
||||
if err := dstFile.Close(); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if _, err := srcFile.WriteString(fileContent); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if err := FileCopy(srcFile.Name(), dstPath); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
dstContent, err := ioutil.ReadFile(dstPath)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if string(dstContent) != fileContent {
|
||||
t.Fatalf("Got %q\nExpecting %q", string(dstContent), fileContent)
|
||||
}
|
||||
|
||||
srcInfo, err := srcFile.Stat()
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
dstInfo, err := os.Stat(dstPath)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if dstInfo.Mode() != srcInfo.Mode() {
|
||||
t.Fatalf("Got FileMode %d\nExpecting FileMode %d", dstInfo.Mode(), srcInfo.Mode())
|
||||
}
|
||||
|
||||
if dstInfo.IsDir() != srcInfo.IsDir() {
|
||||
t.Fatalf("Got IsDir() = %t\nExpecting IsDir() = %t", dstInfo.IsDir(), srcInfo.IsDir())
|
||||
}
|
||||
|
||||
if dstInfo.Size() != srcInfo.Size() {
|
||||
t.Fatalf("Got Size() = %d\nExpecting Size() = %d", dstInfo.Size(), srcInfo.Size())
|
||||
}
|
||||
}
|
||||
|
||||
func TestFileCopySourceEmptyFailure(t *testing.T) {
|
||||
if err := FileCopy("", "testDst"); err == nil {
|
||||
t.Fatal("This test should fail because source path is empty")
|
||||
}
|
||||
}
|
||||
|
||||
func TestFileCopyDestinationEmptyFailure(t *testing.T) {
|
||||
if err := FileCopy("testSrc", ""); err == nil {
|
||||
t.Fatal("This test should fail because destination path is empty")
|
||||
}
|
||||
}
|
||||
|
||||
func TestFileCopySourceNotExistFailure(t *testing.T) {
|
||||
srcFile, err := ioutil.TempFile("", "test_src_copy")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
srcPath := srcFile.Name()
|
||||
|
||||
if err := srcFile.Close(); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if err := os.Remove(srcPath); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if err := FileCopy(srcPath, "testDest"); err == nil {
|
||||
t.Fatal("This test should fail because source file does not exist")
|
||||
}
|
||||
}
|
||||
|
||||
func TestGenerateRandomBytes(t *testing.T) {
|
||||
bytesNeeded := 8
|
||||
randBytes, err := GenerateRandomBytes(bytesNeeded)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if len(randBytes) != bytesNeeded {
|
||||
t.Fatalf("Failed to generate %d random bytes", bytesNeeded)
|
||||
}
|
||||
}
|
||||
|
||||
func TestRevereString(t *testing.T) {
|
||||
str := "Teststr"
|
||||
reversed := ReverseString(str)
|
||||
|
||||
if reversed != "rtstseT" {
|
||||
t.Fatal("Incorrect String Reversal")
|
||||
}
|
||||
}
|
||||
|
||||
func TestWriteToFile(t *testing.T) {
|
||||
err := WriteToFile("/file-does-not-exist", []byte("test-data"))
|
||||
assert.NotNil(t, err)
|
||||
|
||||
tmpFile, err := ioutil.TempFile("", "test_append_file")
|
||||
assert.Nil(t, err)
|
||||
|
||||
filename := tmpFile.Name()
|
||||
defer os.Remove(filename)
|
||||
|
||||
tmpFile.Close()
|
||||
|
||||
testData := []byte("test-data")
|
||||
err = WriteToFile(filename, testData)
|
||||
assert.Nil(t, err)
|
||||
|
||||
data, err := ioutil.ReadFile(filename)
|
||||
assert.Nil(t, err)
|
||||
|
||||
assert.True(t, reflect.DeepEqual(testData, data))
|
||||
}
|
||||
|
||||
func TestConstraintsToVCPUs(t *testing.T) {
|
||||
assert := assert.New(t)
|
||||
|
||||
vcpus := ConstraintsToVCPUs(0, 100)
|
||||
assert.Zero(vcpus)
|
||||
|
||||
vcpus = ConstraintsToVCPUs(100, 0)
|
||||
assert.Zero(vcpus)
|
||||
|
||||
expectedVCPUs := uint(4)
|
||||
vcpus = ConstraintsToVCPUs(4000, 1000)
|
||||
assert.Equal(expectedVCPUs, vcpus)
|
||||
|
||||
vcpus = ConstraintsToVCPUs(4000, 1200)
|
||||
assert.Equal(expectedVCPUs, vcpus)
|
||||
}
|
||||
|
||||
func TestGetVirtDriveNameInvalidIndex(t *testing.T) {
|
||||
_, err := GetVirtDriveName(-1)
|
||||
|
||||
if err == nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestGetVirtDriveName(t *testing.T) {
|
||||
tests := []struct {
|
||||
index int
|
||||
expectedDrive string
|
||||
}{
|
||||
{0, "vda"},
|
||||
{25, "vdz"},
|
||||
{27, "vdab"},
|
||||
{704, "vdaac"},
|
||||
{18277, "vdzzz"},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
driveName, err := GetVirtDriveName(test.index)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if driveName != test.expectedDrive {
|
||||
t.Fatalf("Incorrect drive Name: Got: %s, Expecting :%s", driveName, test.expectedDrive)
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestGetSCSIIdLun(t *testing.T) {
|
||||
tests := []struct {
|
||||
index int
|
||||
expectedScsiID int
|
||||
expectedLun int
|
||||
}{
|
||||
{0, 0, 0},
|
||||
{1, 0, 1},
|
||||
{2, 0, 2},
|
||||
{255, 0, 255},
|
||||
{256, 1, 0},
|
||||
{257, 1, 1},
|
||||
{258, 1, 2},
|
||||
{512, 2, 0},
|
||||
{513, 2, 1},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
scsiID, lun, err := GetSCSIIdLun(test.index)
|
||||
assert.Nil(t, err)
|
||||
|
||||
if scsiID != test.expectedScsiID && lun != test.expectedLun {
|
||||
t.Fatalf("Expecting scsi-id:lun %d:%d, Got %d:%d", test.expectedScsiID, test.expectedLun, scsiID, lun)
|
||||
}
|
||||
}
|
||||
|
||||
_, _, err := GetSCSIIdLun(maxSCSIDevices + 1)
|
||||
assert.NotNil(t, err)
|
||||
}
|
||||
|
||||
func TestGetSCSIAddress(t *testing.T) {
|
||||
tests := []struct {
|
||||
index int
|
||||
expectedSCSIAddress string
|
||||
}{
|
||||
{0, "0:0"},
|
||||
{200, "0:200"},
|
||||
{255, "0:255"},
|
||||
{258, "1:2"},
|
||||
{512, "2:0"},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
scsiAddr, err := GetSCSIAddress(test.index)
|
||||
assert.Nil(t, err)
|
||||
assert.Equal(t, scsiAddr, test.expectedSCSIAddress)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user