vc: add rootless dir to path variables

Modify some path variables to be functions that return the path
with the rootless directory prefix if running rootlessly.

Fixes: #1827

Signed-off-by: Gabi Beyer <gabrielle.n.beyer@intel.com>
This commit is contained in:
Gabi Beyer 2019-07-11 19:32:46 +00:00 committed by Marco Vedovati
parent cdd6f7e4d5
commit 5f0799f1b7
16 changed files with 180 additions and 72 deletions

View File

@ -370,7 +370,7 @@ func (a *acrn) startSandbox(timeoutSecs int) error {
a.Logger().WithField("default-kernel-parameters", formatted).Debug() a.Logger().WithField("default-kernel-parameters", formatted).Debug()
} }
vmPath := filepath.Join(store.RunVMStoragePath, a.id) vmPath := filepath.Join(store.RunVMStoragePath(), a.id)
err := os.MkdirAll(vmPath, store.DirMode) err := os.MkdirAll(vmPath, store.DirMode)
if err != nil { if err != nil {
return err return err
@ -574,7 +574,7 @@ func (a *acrn) getSandboxConsole(id string) (string, error) {
span, _ := a.trace("getSandboxConsole") span, _ := a.trace("getSandboxConsole")
defer span.Finish() defer span.Finish()
return utils.BuildSocketPath(store.RunVMStoragePath, id, acrnConsoleSocket) return utils.BuildSocketPath(store.RunVMStoragePath(), id, acrnConsoleSocket)
} }
func (a *acrn) saveSandbox() error { func (a *acrn) saveSandbox() error {

View File

@ -199,7 +199,7 @@ func TestAcrnGetSandboxConsole(t *testing.T) {
ctx: context.Background(), ctx: context.Background(),
} }
sandboxID := "testSandboxID" sandboxID := "testSandboxID"
expected := filepath.Join(store.RunVMStoragePath, sandboxID, consoleSocket) expected := filepath.Join(store.RunVMStoragePath(), sandboxID, consoleSocket)
result, err := a.getSandboxConsole(sandboxID) result, err := a.getSandboxConsole(sandboxID)
assert.NoError(err) assert.NoError(err)

View File

@ -307,7 +307,7 @@ func ListSandbox(ctx context.Context) ([]SandboxStatus, error) {
span, ctx := trace(ctx, "ListSandbox") span, ctx := trace(ctx, "ListSandbox")
defer span.Finish() defer span.Finish()
dir, err := os.Open(store.ConfigStoragePath) dir, err := os.Open(store.ConfigStoragePath())
if err != nil { if err != nil {
if os.IsNotExist(err) { if os.IsNotExist(err) {
// No sandbox directory is not an error // No sandbox directory is not an error

View File

@ -1103,7 +1103,7 @@ func (c *Container) stop(force bool) error {
return err return err
} }
if err := bindUnmountContainerRootfs(c.ctx, kataHostSharedDir, c.sandbox.id, c.id); err != nil && !force { if err := bindUnmountContainerRootfs(c.ctx, kataHostSharedDir(), c.sandbox.id, c.id); err != nil && !force {
return err return err
} }
@ -1350,7 +1350,7 @@ func (c *Container) plugDevice(devicePath string) error {
if c.checkBlockDeviceSupport() && stat.Mode&unix.S_IFBLK == unix.S_IFBLK { if c.checkBlockDeviceSupport() && stat.Mode&unix.S_IFBLK == unix.S_IFBLK {
b, err := c.sandbox.devManager.NewDevice(config.DeviceInfo{ b, err := c.sandbox.devManager.NewDevice(config.DeviceInfo{
HostPath: devicePath, HostPath: devicePath,
ContainerPath: filepath.Join(kataGuestSharedDir, c.id), ContainerPath: filepath.Join(kataGuestSharedDir(), c.id),
DevType: "b", DevType: "b",
Major: int64(unix.Major(stat.Rdev)), Major: int64(unix.Major(stat.Rdev)),
Minor: int64(unix.Minor(stat.Rdev)), Minor: int64(unix.Minor(stat.Rdev)),

View File

@ -688,7 +688,7 @@ func generateVMSocket(id string, useVsock bool) (interface{}, error) {
}, nil }, nil
} }
path, err := utils.BuildSocketPath(filepath.Join(store.RunVMStoragePath, id), defaultSocketName) path, err := utils.BuildSocketPath(filepath.Join(store.RunVMStoragePath(), id), defaultSocketName)
if err != nil { if err != nil {
return nil, err return nil, err
} }

View File

@ -23,6 +23,7 @@ import (
aTypes "github.com/kata-containers/agent/pkg/types" aTypes "github.com/kata-containers/agent/pkg/types"
kataclient "github.com/kata-containers/agent/protocols/client" kataclient "github.com/kata-containers/agent/protocols/client"
"github.com/kata-containers/agent/protocols/grpc" "github.com/kata-containers/agent/protocols/grpc"
"github.com/kata-containers/runtime/pkg/rootless"
"github.com/kata-containers/runtime/virtcontainers/device/config" "github.com/kata-containers/runtime/virtcontainers/device/config"
persistapi "github.com/kata-containers/runtime/virtcontainers/persist/api" persistapi "github.com/kata-containers/runtime/virtcontainers/persist/api"
vcAnnotations "github.com/kata-containers/runtime/virtcontainers/pkg/annotations" vcAnnotations "github.com/kata-containers/runtime/virtcontainers/pkg/annotations"
@ -56,10 +57,10 @@ var (
defaultRequestTimeout = 60 * time.Second defaultRequestTimeout = 60 * time.Second
errorMissingProxy = errors.New("Missing proxy pointer") errorMissingProxy = errors.New("Missing proxy pointer")
errorMissingOCISpec = errors.New("Missing OCI specification") errorMissingOCISpec = errors.New("Missing OCI specification")
kataHostSharedDir = "/run/kata-containers/shared/sandboxes/" defaultKataHostSharedDir = "/run/kata-containers/shared/sandboxes/"
kataGuestSharedDir = "/run/kata-containers/shared/containers/" defaultKataGuestSharedDir = "/run/kata-containers/shared/containers/"
mountGuest9pTag = "kataShared" mountGuest9pTag = "kataShared"
kataGuestSandboxDir = "/run/kata-containers/sandbox/" defaultKataGuestSandboxDir = "/run/kata-containers/sandbox/"
type9pFs = "9p" type9pFs = "9p"
typeVirtioFS = "virtio_fs" typeVirtioFS = "virtio_fs"
typeVirtioFSNoCache = "none" typeVirtioFSNoCache = "none"
@ -71,11 +72,11 @@ var (
kataNvdimmDevType = "nvdimm" kataNvdimmDevType = "nvdimm"
kataVirtioFSDevType = "virtio-fs" kataVirtioFSDevType = "virtio-fs"
sharedDir9pOptions = []string{"trans=virtio,version=9p2000.L,cache=mmap", "nodev"} sharedDir9pOptions = []string{"trans=virtio,version=9p2000.L,cache=mmap", "nodev"}
sharedDirVirtioFSOptions = []string{"default_permissions,allow_other,rootmode=040000,user_id=0,group_id=0,tag=" + mountGuest9pTag, "nodev"} sharedDirVirtioFSOptions = []string{"default_permissions,allow_other,rootmode=040000,user_id=0,group_id=0,dax,tag=" + mountGuest9pTag, "nodev"}
sharedDirVirtioFSDaxOptions = "dax" sharedDirVirtioFSDaxOptions = "dax"
shmDir = "shm" shmDir = "shm"
kataEphemeralDevType = "ephemeral" kataEphemeralDevType = "ephemeral"
ephemeralPath = filepath.Join(kataGuestSandboxDir, kataEphemeralDevType) defaultEphemeralPath = filepath.Join(defaultKataGuestSandboxDir, kataEphemeralDevType)
grpcMaxDataSize = int64(1024 * 1024) grpcMaxDataSize = int64(1024 * 1024)
localDirOptions = []string{"mode=0777"} localDirOptions = []string{"mode=0777"}
maxHostnameLen = 64 maxHostnameLen = 64
@ -124,6 +125,40 @@ const (
grpcStopTracingRequest = "grpc.StopTracingRequest" grpcStopTracingRequest = "grpc.StopTracingRequest"
) )
// The function is declared this way for mocking in unit tests
var kataHostSharedDir = func() string {
if rootless.IsRootless() {
// filepath.Join removes trailing slashes, but it is necessary for mounting
return filepath.Join(rootless.GetRootlessDir(), defaultKataHostSharedDir) + "/"
}
return defaultKataHostSharedDir
}
// The function is declared this way for mocking in unit tests
var kataGuestSharedDir = func() string {
if rootless.IsRootless() {
// filepath.Join removes trailing slashes, but it is necessary for mounting
return filepath.Join(rootless.GetRootlessDir(), defaultKataGuestSharedDir) + "/"
}
return defaultKataGuestSharedDir
}
// The function is declared this way for mocking in unit tests
var kataGuestSandboxDir = func() string {
if rootless.IsRootless() {
// filepath.Join removes trailing slashes, but it is necessary for mounting
return filepath.Join(rootless.GetRootlessDir(), defaultKataGuestSandboxDir) + "/"
}
return defaultKataGuestSandboxDir
}
func ephemeralPath() string {
if rootless.IsRootless() {
return filepath.Join(kataGuestSandboxDir(), kataEphemeralDevType)
}
return defaultEphemeralPath
}
// KataAgentConfig is a structure storing information needed // KataAgentConfig is a structure storing information needed
// to reach the Kata Containers agent. // to reach the Kata Containers agent.
type KataAgentConfig struct { type KataAgentConfig struct {
@ -182,11 +217,11 @@ func (k *kataAgent) Logger() *logrus.Entry {
} }
func (k *kataAgent) getVMPath(id string) string { func (k *kataAgent) getVMPath(id string) string {
return filepath.Join(store.RunVMStoragePath, id) return filepath.Join(store.RunVMStoragePath(), id)
} }
func (k *kataAgent) getSharePath(id string) string { func (k *kataAgent) getSharePath(id string) string {
return filepath.Join(kataHostSharedDir, id) return filepath.Join(kataHostSharedDir(), id)
} }
// KataAgentSetDefaultTraceConfigOptions validates agent trace options and // KataAgentSetDefaultTraceConfigOptions validates agent trace options and
@ -838,7 +873,7 @@ func setupStorages(sandbox *Sandbox) []*grpc.Storage {
sharedVolume := &grpc.Storage{ sharedVolume := &grpc.Storage{
Driver: kataVirtioFSDevType, Driver: kataVirtioFSDevType,
Source: "none", Source: "none",
MountPoint: kataGuestSharedDir, MountPoint: kataGuestSharedDir(),
Fstype: typeVirtioFS, Fstype: typeVirtioFS,
Options: sharedDirVirtioFSOptions, Options: sharedDirVirtioFSOptions,
} }
@ -850,7 +885,7 @@ func setupStorages(sandbox *Sandbox) []*grpc.Storage {
sharedVolume := &grpc.Storage{ sharedVolume := &grpc.Storage{
Driver: kata9pDevType, Driver: kata9pDevType,
Source: mountGuest9pTag, Source: mountGuest9pTag,
MountPoint: kataGuestSharedDir, MountPoint: kataGuestSharedDir(),
Fstype: type9pFs, Fstype: type9pFs,
Options: sharedDir9pOptions, Options: sharedDir9pOptions,
} }
@ -860,7 +895,7 @@ func setupStorages(sandbox *Sandbox) []*grpc.Storage {
} }
if sandbox.shmSize > 0 { if sandbox.shmSize > 0 {
path := filepath.Join(kataGuestSandboxDir, shmDir) path := filepath.Join(kataGuestSandboxDir(), shmDir)
shmSizeOption := fmt.Sprintf("size=%d", sandbox.shmSize) shmSizeOption := fmt.Sprintf("size=%d", sandbox.shmSize)
shmStorage := &grpc.Storage{ shmStorage := &grpc.Storage{
@ -970,7 +1005,7 @@ func (k *kataAgent) replaceOCIMountsForStorages(spec *specs.Spec, volumeStorages
// Create a temporary location to mount the Storage. Mounting to the correct location // Create a temporary location to mount the Storage. Mounting to the correct location
// will be handled by the OCI mount structure. // will be handled by the OCI mount structure.
filename := fmt.Sprintf("%s-%s", uuid.Generate().String(), filepath.Base(m.Destination)) filename := fmt.Sprintf("%s-%s", uuid.Generate().String(), filepath.Base(m.Destination))
path := filepath.Join(kataGuestSharedDir, filename) path := filepath.Join(kataGuestSharedDir(), filename)
k.Logger().Debugf("Replacing OCI mount source (%s) with %s", m.Source, path) k.Logger().Debugf("Replacing OCI mount source (%s) with %s", m.Source, path)
ociMounts[index].Source = path ociMounts[index].Source = path
@ -1052,7 +1087,7 @@ func (k *kataAgent) handleShm(grpcSpec *grpc.Spec, sandbox *Sandbox) {
if sandbox.shmSize > 0 { if sandbox.shmSize > 0 {
grpcSpec.Mounts[idx].Type = "bind" grpcSpec.Mounts[idx].Type = "bind"
grpcSpec.Mounts[idx].Options = []string{"rbind"} grpcSpec.Mounts[idx].Options = []string{"rbind"}
grpcSpec.Mounts[idx].Source = filepath.Join(kataGuestSandboxDir, shmDir) grpcSpec.Mounts[idx].Source = filepath.Join(kataGuestSandboxDir(), shmDir)
k.Logger().WithField("shm-size", sandbox.shmSize).Info("Using sandbox shm") k.Logger().WithField("shm-size", sandbox.shmSize).Info("Using sandbox shm")
} else { } else {
sizeOption := fmt.Sprintf("size=%d", DefaultShmSize) sizeOption := fmt.Sprintf("size=%d", DefaultShmSize)
@ -1121,7 +1156,7 @@ func (k *kataAgent) rollbackFailingContainerCreation(c *Container) {
k.Logger().WithError(err2).Error("rollback failed unmountHostMounts()") k.Logger().WithError(err2).Error("rollback failed unmountHostMounts()")
} }
if err2 := bindUnmountContainerRootfs(k.ctx, kataHostSharedDir, c.sandbox.id, c.id); err2 != nil { if err2 := bindUnmountContainerRootfs(k.ctx, kataHostSharedDir(), c.sandbox.id, c.id); err2 != nil {
k.Logger().WithError(err2).Error("rollback failed bindUnmountContainerRootfs()") k.Logger().WithError(err2).Error("rollback failed bindUnmountContainerRootfs()")
} }
} }
@ -1189,7 +1224,7 @@ func (k *kataAgent) buildContainerRootfs(sandbox *Sandbox, c *Container, rootPat
// (kataGuestSharedDir) is already mounted in the // (kataGuestSharedDir) is already mounted in the
// guest. We only need to mount the rootfs from // guest. We only need to mount the rootfs from
// the host and it will show up in the guest. // the host and it will show up in the guest.
if err := bindMountContainerRootfs(k.ctx, kataHostSharedDir, sandbox.id, c.id, c.rootFs.Target, false); err != nil { if err := bindMountContainerRootfs(k.ctx, kataHostSharedDir(), sandbox.id, c.id, c.rootFs.Target, false); err != nil {
return nil, err return nil, err
} }
@ -1215,7 +1250,7 @@ func (k *kataAgent) createContainer(sandbox *Sandbox, c *Container) (p *Process,
var rootfs *grpc.Storage var rootfs *grpc.Storage
// This is the guest absolute root path for that container. // This is the guest absolute root path for that container.
rootPathParent := filepath.Join(kataGuestSharedDir, c.id) rootPathParent := filepath.Join(kataGuestSharedDir(), c.id)
rootPath := filepath.Join(rootPathParent, c.rootfsSuffix) rootPath := filepath.Join(rootPathParent, c.rootfsSuffix)
// In case the container creation fails, the following defer statement // In case the container creation fails, the following defer statement
@ -1242,7 +1277,7 @@ func (k *kataAgent) createContainer(sandbox *Sandbox, c *Container) (p *Process,
} }
// Handle container mounts // Handle container mounts
newMounts, ignoredMounts, err := c.mountSharedDirMounts(kataHostSharedDir, kataGuestSharedDir) newMounts, ignoredMounts, err := c.mountSharedDirMounts(kataHostSharedDir(), kataGuestSharedDir())
if err != nil { if err != nil {
return nil, err return nil, err
} }
@ -1345,7 +1380,7 @@ func (k *kataAgent) handleEphemeralStorage(mounts []specs.Mount) []*grpc.Storage
for idx, mnt := range mounts { for idx, mnt := range mounts {
if mnt.Type == KataEphemeralDevType { if mnt.Type == KataEphemeralDevType {
// Set the mount source path to a path that resides inside the VM // Set the mount source path to a path that resides inside the VM
mounts[idx].Source = filepath.Join(ephemeralPath, filepath.Base(mnt.Source)) mounts[idx].Source = filepath.Join(ephemeralPath(), filepath.Base(mnt.Source))
// Set the mount type to "bind" // Set the mount type to "bind"
mounts[idx].Type = "bind" mounts[idx].Type = "bind"
@ -1374,7 +1409,7 @@ func (k *kataAgent) handleLocalStorage(mounts []specs.Mount, sandboxID string, r
// We rely on the fact that the first container in the VM has the same ID as the sandbox ID. // We rely on the fact that the first container in the VM has the same ID as the sandbox ID.
// In Kubernetes, this is usually the pause container and we depend on it existing for // In Kubernetes, this is usually the pause container and we depend on it existing for
// local directories to work. // local directories to work.
mounts[idx].Source = filepath.Join(kataGuestSharedDir, sandboxID, rootfsSuffix, KataLocalDevType, filepath.Base(mnt.Source)) mounts[idx].Source = filepath.Join(kataGuestSharedDir(), sandboxID, rootfsSuffix, KataLocalDevType, filepath.Base(mnt.Source))
// Create a storage struct so that the kata agent is able to create the // Create a storage struct so that the kata agent is able to create the
// directory inside the VM. // directory inside the VM.

View File

@ -6,6 +6,7 @@
package virtcontainers package virtcontainers
import ( import (
"bufio"
"context" "context"
"fmt" "fmt"
"io/ioutil" "io/ioutil"
@ -25,6 +26,7 @@ import (
aTypes "github.com/kata-containers/agent/pkg/types" aTypes "github.com/kata-containers/agent/pkg/types"
pb "github.com/kata-containers/agent/protocols/grpc" pb "github.com/kata-containers/agent/protocols/grpc"
"github.com/kata-containers/runtime/pkg/rootless"
"github.com/kata-containers/runtime/virtcontainers/device/api" "github.com/kata-containers/runtime/virtcontainers/device/api"
"github.com/kata-containers/runtime/virtcontainers/device/config" "github.com/kata-containers/runtime/virtcontainers/device/config"
"github.com/kata-containers/runtime/virtcontainers/device/drivers" "github.com/kata-containers/runtime/virtcontainers/device/drivers"
@ -359,7 +361,7 @@ func TestHandleEphemeralStorage(t *testing.T) {
epheStorages := k.handleEphemeralStorage(ociMounts) epheStorages := k.handleEphemeralStorage(ociMounts)
epheMountPoint := epheStorages[0].GetMountPoint() epheMountPoint := epheStorages[0].GetMountPoint()
expected := filepath.Join(ephemeralPath, filepath.Base(mountSource)) expected := filepath.Join(ephemeralPath(), filepath.Base(mountSource))
assert.Equal(t, epheMountPoint, expected, assert.Equal(t, epheMountPoint, expected,
"Ephemeral mount point didn't match: got %s, expecting %s", epheMountPoint, expected) "Ephemeral mount point didn't match: got %s, expecting %s", epheMountPoint, expected)
} }
@ -384,7 +386,7 @@ func TestHandleLocalStorage(t *testing.T) {
assert.Equal(t, len(localStorages), 1) assert.Equal(t, len(localStorages), 1)
localMountPoint := localStorages[0].GetMountPoint() localMountPoint := localStorages[0].GetMountPoint()
expected := filepath.Join(kataGuestSharedDir, sandboxID, rootfsSuffix, KataLocalDevType, filepath.Base(mountSource)) expected := filepath.Join(kataGuestSharedDir(), sandboxID, rootfsSuffix, KataLocalDevType, filepath.Base(mountSource))
assert.Equal(t, localMountPoint, expected) assert.Equal(t, localMountPoint, expected)
} }
@ -531,7 +533,7 @@ func TestHandleShm(t *testing.T) {
assert.NotEmpty(g.Mounts[0].Destination) assert.NotEmpty(g.Mounts[0].Destination)
assert.Equal(g.Mounts[0].Destination, "/dev/shm") assert.Equal(g.Mounts[0].Destination, "/dev/shm")
assert.Equal(g.Mounts[0].Type, "bind") assert.Equal(g.Mounts[0].Type, "bind")
assert.NotEmpty(g.Mounts[0].Source, filepath.Join(kataGuestSharedDir, shmDir)) assert.NotEmpty(g.Mounts[0].Source, filepath.Join(kataGuestSharedDir(), shmDir))
assert.Equal(g.Mounts[0].Options, []string{"rbind"}) assert.Equal(g.Mounts[0].Options, []string{"rbind"})
sandbox.shmSize = 0 sandbox.shmSize = 0
@ -896,7 +898,10 @@ func TestKataCleanupSandbox(t *testing.T) {
assert := assert.New(t) assert := assert.New(t)
kataHostSharedDirSaved := kataHostSharedDir kataHostSharedDirSaved := kataHostSharedDir
kataHostSharedDir, _ = ioutil.TempDir("", "kata-cleanup") kataHostSharedDir = func() string {
td, _ := ioutil.TempDir("", "kata-cleanup")
return td
}
defer func() { defer func() {
kataHostSharedDir = kataHostSharedDirSaved kataHostSharedDir = kataHostSharedDirSaved
}() }()
@ -904,7 +909,7 @@ func TestKataCleanupSandbox(t *testing.T) {
s := Sandbox{ s := Sandbox{
id: "testFoo", id: "testFoo",
} }
dir := path.Join(kataHostSharedDir, s.id) dir := path.Join(kataHostSharedDir(), s.id)
err := os.MkdirAll(dir, 0777) err := os.MkdirAll(dir, 0777)
assert.Nil(err) assert.Nil(err)
@ -1110,3 +1115,29 @@ func TestKataAgentSetDefaultTraceConfigOptions(t *testing.T) {
} }
} }
} }
func TestKataAgentDirs(t *testing.T) {
assert := assert.New(t)
uidmapFile, err := os.OpenFile("/proc/self/uid_map", os.O_RDONLY, 0)
assert.NoError(err)
line, err := bufio.NewReader(uidmapFile).ReadBytes('\n')
assert.NoError(err)
uidmap := strings.Fields(string(line))
expectedRootless := (uidmap[0] == "0" && uidmap[1] != "0")
assert.Equal(expectedRootless, rootless.IsRootless())
if expectedRootless {
assert.Equal(kataHostSharedDir(), os.Getenv("XDG_RUNTIME_DIR")+defaultKataHostSharedDir)
assert.Equal(kataGuestSharedDir(), os.Getenv("XDG_RUNTIME_DIR")+defaultKataGuestSharedDir)
assert.Equal(kataGuestSandboxDir(), os.Getenv("XDG_RUNTIME_DIR")+defaultKataGuestSandboxDir)
assert.Equal(ephemeralPath(), os.Getenv("XDG_RUNTIME_DIR")+defaultEphemeralPath)
} else {
assert.Equal(kataHostSharedDir(), defaultKataHostSharedDir)
assert.Equal(kataGuestSharedDir(), defaultKataGuestSharedDir)
assert.Equal(kataGuestSandboxDir(), defaultKataGuestSandboxDir)
assert.Equal(ephemeralPath(), defaultEphemeralPath)
}
}

View File

@ -338,7 +338,7 @@ func (q *qemu) memoryTopology() (govmmQemu.Memory, error) {
} }
func (q *qemu) qmpSocketPath(id string) (string, error) { func (q *qemu) qmpSocketPath(id string) (string, error) {
return utils.BuildSocketPath(store.RunVMStoragePath, id, qmpSocket) return utils.BuildSocketPath(store.RunVMStoragePath(), id, qmpSocket)
} }
func (q *qemu) getQemuMachine() (govmmQemu.Machine, error) { func (q *qemu) getQemuMachine() (govmmQemu.Machine, error) {
@ -582,7 +582,7 @@ func (q *qemu) createSandbox(ctx context.Context, id string, networkNS NetworkNa
VGA: "none", VGA: "none",
GlobalParam: "kvm-pit.lost_tick_policy=discard", GlobalParam: "kvm-pit.lost_tick_policy=discard",
Bios: firmwarePath, Bios: firmwarePath,
PidFile: filepath.Join(store.RunVMStoragePath, q.id, "pid"), PidFile: filepath.Join(store.RunVMStoragePath(), q.id, "pid"),
} }
if ioThread != nil { if ioThread != nil {
@ -604,14 +604,14 @@ func (q *qemu) createSandbox(ctx context.Context, id string, networkNS NetworkNa
} }
func (q *qemu) vhostFSSocketPath(id string) (string, error) { func (q *qemu) vhostFSSocketPath(id string) (string, error) {
return utils.BuildSocketPath(store.RunVMStoragePath, id, vhostFSSocket) return utils.BuildSocketPath(store.RunVMStoragePath(), id, vhostFSSocket)
} }
func (q *qemu) virtiofsdArgs(sockPath string) []string { func (q *qemu) virtiofsdArgs(sockPath string) []string {
// The daemon will terminate when the vhost-user socket // The daemon will terminate when the vhost-user socket
// connection with QEMU closes. Therefore we do not keep track // connection with QEMU closes. Therefore we do not keep track
// of this child process after returning from this function. // of this child process after returning from this function.
sourcePath := filepath.Join(kataHostSharedDir, q.id) sourcePath := filepath.Join(kataHostSharedDir(), q.id)
args := []string{ args := []string{
"-o", "vhost_user_socket=" + sockPath, "-o", "vhost_user_socket=" + sockPath,
"-o", "source=" + sourcePath, "-o", "source=" + sourcePath,
@ -732,7 +732,7 @@ func (q *qemu) startSandbox(timeout int) error {
q.fds = []*os.File{} q.fds = []*os.File{}
}() }()
vmPath := filepath.Join(store.RunVMStoragePath, q.id) vmPath := filepath.Join(store.RunVMStoragePath(), q.id)
err := os.MkdirAll(vmPath, store.DirMode) err := os.MkdirAll(vmPath, store.DirMode)
if err != nil { if err != nil {
return err return err
@ -908,7 +908,7 @@ func (q *qemu) stopSandbox() error {
func (q *qemu) cleanupVM() error { func (q *qemu) cleanupVM() error {
// cleanup vm path // cleanup vm path
dir := filepath.Join(store.RunVMStoragePath, q.id) dir := filepath.Join(store.RunVMStoragePath(), q.id)
// If it's a symlink, remove both dir and the target. // If it's a symlink, remove both dir and the target.
// This can happen when vm template links a sandbox to a vm. // This can happen when vm template links a sandbox to a vm.
@ -1623,7 +1623,7 @@ func (q *qemu) getSandboxConsole(id string) (string, error) {
span, _ := q.trace("getSandboxConsole") span, _ := q.trace("getSandboxConsole")
defer span.Finish() defer span.Finish()
return utils.BuildSocketPath(store.RunVMStoragePath, id, consoleSocket) return utils.BuildSocketPath(store.RunVMStoragePath(), id, consoleSocket)
} }
func (q *qemu) saveSandbox() error { func (q *qemu) saveSandbox() error {

View File

@ -289,7 +289,7 @@ func TestQemuGetSandboxConsole(t *testing.T) {
ctx: context.Background(), ctx: context.Background(),
} }
sandboxID := "testSandboxID" sandboxID := "testSandboxID"
expected := filepath.Join(store.RunVMStoragePath, sandboxID, consoleSocket) expected := filepath.Join(store.RunVMStoragePath(), sandboxID, consoleSocket)
result, err := q.getSandboxConsole(sandboxID) result, err := q.getSandboxConsole(sandboxID)
assert.NoError(err) assert.NoError(err)
@ -496,7 +496,9 @@ func TestQemuVirtiofsdArgs(t *testing.T) {
} }
savedKataHostSharedDir := kataHostSharedDir savedKataHostSharedDir := kataHostSharedDir
kataHostSharedDir = "test-share-dir" kataHostSharedDir = func() string {
return "test-share-dir"
}
defer func() { defer func() {
kataHostSharedDir = savedKataHostSharedDir kataHostSharedDir = savedKataHostSharedDir
}() }()

View File

@ -1423,8 +1423,8 @@ func checkSandboxRemains() error {
if err = checkDirNotExist(sandboxDirState); err != nil { if err = checkDirNotExist(sandboxDirState); err != nil {
return fmt.Errorf("%s still exists", sandboxDirState) return fmt.Errorf("%s still exists", sandboxDirState)
} }
if err = checkDirNotExist(path.Join(kataHostSharedDir, testSandboxID)); err != nil { if err = checkDirNotExist(path.Join(kataHostSharedDir(), testSandboxID)); err != nil {
return fmt.Errorf("%s still exists", path.Join(kataHostSharedDir, testSandboxID)) return fmt.Errorf("%s still exists", path.Join(kataHostSharedDir(), testSandboxID))
} }
if _, err = globalSandboxList.lookupSandbox(testSandboxID); err == nil { if _, err = globalSandboxList.lookupSandbox(testSandboxID); err == nil {
return fmt.Errorf("globalSandboxList for %s stil exists", testSandboxID) return fmt.Errorf("globalSandboxList for %s stil exists", testSandboxID)

View File

@ -14,6 +14,7 @@ import (
"path/filepath" "path/filepath"
"syscall" "syscall"
"github.com/kata-containers/runtime/pkg/rootless"
"github.com/kata-containers/runtime/virtcontainers/pkg/uuid" "github.com/kata-containers/runtime/virtcontainers/pkg/uuid"
opentracing "github.com/opentracing/opentracing-go" opentracing "github.com/opentracing/opentracing-go"
"github.com/sirupsen/logrus" "github.com/sirupsen/logrus"
@ -65,15 +66,36 @@ const VMPathSuffix = "vm"
// ConfigStoragePath is the sandbox configuration directory. // ConfigStoragePath is the sandbox configuration directory.
// It will contain one config.json file for each created sandbox. // It will contain one config.json file for each created sandbox.
var ConfigStoragePath = filepath.Join("/var/lib", StoragePathSuffix, SandboxPathSuffix) // The function is declared this way for mocking in unit tests
var ConfigStoragePath = func() string {
path := filepath.Join("/var/lib", StoragePathSuffix, SandboxPathSuffix)
if rootless.IsRootless() {
return filepath.Join(rootless.GetRootlessDir(), path)
}
return path
}
// RunStoragePath is the sandbox runtime directory. // RunStoragePath is the sandbox runtime directory.
// It will contain one state.json and one lock file for each created sandbox. // It will contain one state.json and one lock file for each created sandbox.
var RunStoragePath = filepath.Join("/run", StoragePathSuffix, SandboxPathSuffix) // The function is declared this way for mocking in unit tests
var RunStoragePath = func() string {
path := filepath.Join("/run", StoragePathSuffix, SandboxPathSuffix)
if rootless.IsRootless() {
return filepath.Join(rootless.GetRootlessDir(), path)
}
return path
}
// RunVMStoragePath is the vm directory. // RunVMStoragePath is the vm directory.
// It will contain all guest vm sockets and shared mountpoints. // It will contain all guest vm sockets and shared mountpoints.
var RunVMStoragePath = filepath.Join("/run", StoragePathSuffix, VMPathSuffix) // The function is declared this way for mocking in unit tests
var RunVMStoragePath = func() string {
path := filepath.Join("/run", StoragePathSuffix, VMPathSuffix)
if rootless.IsRootless() {
return filepath.Join(rootless.GetRootlessDir(), path)
}
return path
}
func itemToFile(item Item) (string, error) { func itemToFile(item Item) (string, error) {
switch item { switch item {

View File

@ -112,17 +112,24 @@ func TestMain(m *testing.M) {
panic(err) panic(err)
} }
ConfigStoragePathSaved := ConfigStoragePath
RunStoragePathSaved := RunStoragePath
// allow the tests to run without affecting the host system. // allow the tests to run without affecting the host system.
ConfigStoragePath = filepath.Join(testDir, StoragePathSuffix, "config") ConfigStoragePath = func() string { return filepath.Join(testDir, StoragePathSuffix, "config") }
RunStoragePath = filepath.Join(testDir, StoragePathSuffix, "run") RunStoragePath = func() string { return filepath.Join(testDir, StoragePathSuffix, "run") }
defer func() {
ConfigStoragePath = ConfigStoragePathSaved
RunStoragePath = RunStoragePathSaved
}()
// set now that ConfigStoragePath has been overridden. // set now that ConfigStoragePath has been overridden.
sandboxDirConfig = filepath.Join(ConfigStoragePath, testSandboxID) sandboxDirConfig = filepath.Join(ConfigStoragePath(), testSandboxID)
sandboxFileConfig = filepath.Join(ConfigStoragePath, testSandboxID, ConfigurationFile) sandboxFileConfig = filepath.Join(ConfigStoragePath(), testSandboxID, ConfigurationFile)
sandboxDirState = filepath.Join(RunStoragePath, testSandboxID) sandboxDirState = filepath.Join(RunStoragePath(), testSandboxID)
sandboxDirLock = filepath.Join(RunStoragePath, testSandboxID) sandboxDirLock = filepath.Join(RunStoragePath(), testSandboxID)
sandboxFileState = filepath.Join(RunStoragePath, testSandboxID, StateFile) sandboxFileState = filepath.Join(RunStoragePath(), testSandboxID, StateFile)
sandboxFileLock = filepath.Join(RunStoragePath, testSandboxID, LockFile) sandboxFileLock = filepath.Join(RunStoragePath(), testSandboxID, LockFile)
ret := m.Run() ret := m.Run()

View File

@ -233,13 +233,14 @@ func (s *VCStore) Unlock(token string) error {
// SandboxConfigurationRoot returns a virtcontainers sandbox configuration root URL. // SandboxConfigurationRoot returns a virtcontainers sandbox configuration root URL.
// This will hold across host reboot persistent data about a sandbox configuration. // This will hold across host reboot persistent data about a sandbox configuration.
// It should look like file:///var/lib/vc/sbs/<sandboxID>/ // It should look like file:///var/lib/vc/sbs/<sandboxID>/
// Or for rootless: file://<rootlessDir>/var/lib/vc/sbs/<sandboxID>/
func SandboxConfigurationRoot(id string) string { func SandboxConfigurationRoot(id string) string {
return filesystemScheme + "://" + filepath.Join(ConfigStoragePath, id) return filesystemScheme + "://" + filepath.Join(ConfigStoragePath(), id)
} }
// SandboxConfigurationRootPath returns a virtcontainers sandbox configuration root path. // SandboxConfigurationRootPath returns a virtcontainers sandbox configuration root path.
func SandboxConfigurationRootPath(id string) string { func SandboxConfigurationRootPath(id string) string {
return filepath.Join(ConfigStoragePath, id) return filepath.Join(ConfigStoragePath(), id)
} }
// SandboxConfigurationItemPath returns a virtcontainers sandbox configuration item path. // SandboxConfigurationItemPath returns a virtcontainers sandbox configuration item path.
@ -253,20 +254,21 @@ func SandboxConfigurationItemPath(id string, item Item) (string, error) {
return "", err return "", err
} }
return filepath.Join(ConfigStoragePath, id, itemFile), nil return filepath.Join(ConfigStoragePath(), id, itemFile), nil
} }
// SandboxRuntimeRoot returns a virtcontainers sandbox runtime root URL. // SandboxRuntimeRoot returns a virtcontainers sandbox runtime root URL.
// This will hold data related to a sandbox run-time state that will not // This will hold data related to a sandbox run-time state that will not
// be persistent across host reboots. // be persistent across host reboots.
// It should look like file:///run/vc/sbs/<sandboxID>/ // It should look like file:///run/vc/sbs/<sandboxID>/
// or if rootless: file://<rootlessDir>/run/vc/sbs/<sandboxID>/
func SandboxRuntimeRoot(id string) string { func SandboxRuntimeRoot(id string) string {
return filesystemScheme + "://" + filepath.Join(RunStoragePath, id) return filesystemScheme + "://" + filepath.Join(RunStoragePath(), id)
} }
// SandboxRuntimeRootPath returns a virtcontainers sandbox runtime root path. // SandboxRuntimeRootPath returns a virtcontainers sandbox runtime root path.
func SandboxRuntimeRootPath(id string) string { func SandboxRuntimeRootPath(id string) string {
return filepath.Join(RunStoragePath, id) return filepath.Join(RunStoragePath(), id)
} }
// SandboxRuntimeItemPath returns a virtcontainers sandbox runtime item path. // SandboxRuntimeItemPath returns a virtcontainers sandbox runtime item path.
@ -280,32 +282,34 @@ func SandboxRuntimeItemPath(id string, item Item) (string, error) {
return "", err return "", err
} }
return filepath.Join(RunStoragePath, id, itemFile), nil return filepath.Join(RunStoragePath(), id, itemFile), nil
} }
// ContainerConfigurationRoot returns a virtcontainers container configuration root URL. // ContainerConfigurationRoot returns a virtcontainers container configuration root URL.
// This will hold across host reboot persistent data about a container configuration. // This will hold across host reboot persistent data about a container configuration.
// It should look like file:///var/lib/vc/sbs/<sandboxID>/<containerID> // It should look like file:///var/lib/vc/sbs/<sandboxID>/<containerID>
// Or if rootless file://<rootlessDir>/var/lib/vc/sbs/<sandboxID>/<containerID>
func ContainerConfigurationRoot(sandboxID, containerID string) string { func ContainerConfigurationRoot(sandboxID, containerID string) string {
return filesystemScheme + "://" + filepath.Join(ConfigStoragePath, sandboxID, containerID) return filesystemScheme + "://" + filepath.Join(ConfigStoragePath(), sandboxID, containerID)
} }
// ContainerConfigurationRootPath returns a virtcontainers container configuration root path. // ContainerConfigurationRootPath returns a virtcontainers container configuration root path.
func ContainerConfigurationRootPath(sandboxID, containerID string) string { func ContainerConfigurationRootPath(sandboxID, containerID string) string {
return filepath.Join(ConfigStoragePath, sandboxID, containerID) return filepath.Join(ConfigStoragePath(), sandboxID, containerID)
} }
// ContainerRuntimeRoot returns a virtcontainers container runtime root URL. // ContainerRuntimeRoot returns a virtcontainers container runtime root URL.
// This will hold data related to a container run-time state that will not // This will hold data related to a container run-time state that will not
// be persistent across host reboots. // be persistent across host reboots.
// It should look like file:///run/vc/sbs/<sandboxID>/<containerID>/ // It should look like file:///run/vc/sbs/<sandboxID>/<containerID>/
// Or for rootless file://<rootlessDir>/run/vc/sbs/<sandboxID>/<containerID>/
func ContainerRuntimeRoot(sandboxID, containerID string) string { func ContainerRuntimeRoot(sandboxID, containerID string) string {
return filesystemScheme + "://" + filepath.Join(RunStoragePath, sandboxID, containerID) return filesystemScheme + "://" + filepath.Join(RunStoragePath(), sandboxID, containerID)
} }
// ContainerRuntimeRootPath returns a virtcontainers container runtime root path. // ContainerRuntimeRootPath returns a virtcontainers container runtime root path.
func ContainerRuntimeRootPath(sandboxID, containerID string) string { func ContainerRuntimeRootPath(sandboxID, containerID string) string {
return filepath.Join(RunStoragePath, sandboxID, containerID) return filepath.Join(RunStoragePath(), sandboxID, containerID)
} }
// VCSandboxStoreExists returns true if a sandbox store already exists. // VCSandboxStoreExists returns true if a sandbox store already exists.

View File

@ -14,7 +14,7 @@ import (
) )
func TestStoreVCRoots(t *testing.T) { func TestStoreVCRoots(t *testing.T) {
rootURL := filesystemScheme + "://" + ConfigStoragePath rootURL := filesystemScheme + "://" + ConfigStoragePath()
sandboxID := "sandbox" sandboxID := "sandbox"
containerID := "container" containerID := "container"
sConfigRoot := rootURL + "/" + sandboxID sConfigRoot := rootURL + "/" + sandboxID

View File

@ -126,18 +126,25 @@ func TestMain(m *testing.M) {
setupAcrn() setupAcrn()
ConfigStoragePathSaved := store.ConfigStoragePath
RunStoragePathSaved := store.RunStoragePath
// allow the tests to run without affecting the host system. // allow the tests to run without affecting the host system.
store.ConfigStoragePath = filepath.Join(testDir, store.StoragePathSuffix, "config") store.ConfigStoragePath = func() string { return filepath.Join(testDir, store.StoragePathSuffix, "config") }
store.RunStoragePath = filepath.Join(testDir, store.StoragePathSuffix, "run") store.RunStoragePath = func() string { return filepath.Join(testDir, store.StoragePathSuffix, "run") }
fs.TestSetRunStoragePath(filepath.Join(testDir, "vc", "sbs")) fs.TestSetRunStoragePath(filepath.Join(testDir, "vc", "sbs"))
defer func() {
store.ConfigStoragePath = ConfigStoragePathSaved
store.RunStoragePath = RunStoragePathSaved
}()
// set now that configStoragePath has been overridden. // set now that configStoragePath has been overridden.
sandboxDirConfig = filepath.Join(store.ConfigStoragePath, testSandboxID) sandboxDirConfig = filepath.Join(store.ConfigStoragePath(), testSandboxID)
sandboxFileConfig = filepath.Join(store.ConfigStoragePath, testSandboxID, store.ConfigurationFile) sandboxFileConfig = filepath.Join(store.ConfigStoragePath(), testSandboxID, store.ConfigurationFile)
sandboxDirState = filepath.Join(store.RunStoragePath, testSandboxID) sandboxDirState = filepath.Join(store.RunStoragePath(), testSandboxID)
sandboxDirLock = filepath.Join(store.RunStoragePath, testSandboxID) sandboxDirLock = filepath.Join(store.RunStoragePath(), testSandboxID)
sandboxFileState = filepath.Join(store.RunStoragePath, testSandboxID, store.StateFile) sandboxFileState = filepath.Join(store.RunStoragePath(), testSandboxID, store.StateFile)
sandboxFileLock = filepath.Join(store.RunStoragePath, testSandboxID, store.LockFile) sandboxFileLock = filepath.Join(store.RunStoragePath(), testSandboxID, store.LockFile)
testHyperstartCtlSocket = filepath.Join(testDir, "test_hyper.sock") testHyperstartCtlSocket = filepath.Join(testDir, "test_hyper.sock")
testHyperstartTtySocket = filepath.Join(testDir, "test_tty.sock") testHyperstartTtySocket = filepath.Join(testDir, "test_tty.sock")

View File

@ -286,7 +286,7 @@ func NewVMFromGrpc(ctx context.Context, v *pb.GrpcVM, config VMConfig) (*VM, err
} }
func buildVMSharePath(id string) string { func buildVMSharePath(id string) string {
return filepath.Join(store.RunVMStoragePath, id, "shared") return filepath.Join(store.RunVMStoragePath(), id, "shared")
} }
func (v *VM) logger() logrus.FieldLogger { func (v *VM) logger() logrus.FieldLogger {