diff --git a/src/runtime/virtcontainers/qemu.go b/src/runtime/virtcontainers/qemu.go index 5e2bb85932..9f00a12a44 100644 --- a/src/runtime/virtcontainers/qemu.go +++ b/src/runtime/virtcontainers/qemu.go @@ -1924,7 +1924,7 @@ func (q *qemu) addDevice(ctx context.Context, devInfo interface{}, devType devic vhostDev.SocketPath = sockPath vhostDev.DevID = id - q.qemuConfig.Devices, err = q.arch.appendVhostUserDevice(q.qemuConfig.Devices, vhostDev) + q.qemuConfig.Devices, err = q.arch.appendVhostUserDevice(ctx, q.qemuConfig.Devices, vhostDev) } else { q.Logger().WithField("volume-type", "virtio-9p").Info("adding volume") q.qemuConfig.Devices, err = q.arch.append9PVolume(ctx, q.qemuConfig.Devices, v) @@ -1939,7 +1939,7 @@ func (q *qemu) addDevice(ctx context.Context, devInfo interface{}, devType devic case config.BlockDrive: q.qemuConfig.Devices, err = q.arch.appendBlockDevice(ctx, q.qemuConfig.Devices, v) case config.VhostUserDeviceAttrs: - q.qemuConfig.Devices, err = q.arch.appendVhostUserDevice(q.qemuConfig.Devices, v) + q.qemuConfig.Devices, err = q.arch.appendVhostUserDevice(ctx, q.qemuConfig.Devices, v) case config.VFIODev: q.qemuConfig.Devices = q.arch.appendVFIODevice(q.qemuConfig.Devices, v) default: diff --git a/src/runtime/virtcontainers/qemu_arch_base.go b/src/runtime/virtcontainers/qemu_arch_base.go index ae0ce3a13e..d2ffac4a1d 100644 --- a/src/runtime/virtcontainers/qemu_arch_base.go +++ b/src/runtime/virtcontainers/qemu_arch_base.go @@ -96,7 +96,7 @@ type qemuArch interface { appendBlockDevice(ctx context.Context, devices []govmmQemu.Device, drive config.BlockDrive) ([]govmmQemu.Device, error) // appendVhostUserDevice appends a vhost user device to devices - appendVhostUserDevice(devices []govmmQemu.Device, drive config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) + appendVhostUserDevice(ctx context.Context, devices []govmmQemu.Device, drive config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) // appendVFIODevice appends a VFIO device to devices appendVFIODevice(devices []govmmQemu.Device, vfioDevice config.VFIODev) []govmmQemu.Device @@ -633,7 +633,7 @@ func (q *qemuArchBase) appendBlockDevice(_ context.Context, devices []govmmQemu. return devices, nil } -func (q *qemuArchBase) appendVhostUserDevice(devices []govmmQemu.Device, attr config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) { +func (q *qemuArchBase) appendVhostUserDevice(ctx context.Context, devices []govmmQemu.Device, attr config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) { qemuVhostUserDevice := govmmQemu.VhostUserDevice{} switch attr.Type { diff --git a/src/runtime/virtcontainers/qemu_arch_base_test.go b/src/runtime/virtcontainers/qemu_arch_base_test.go index d4aba54fac..3db561c9f8 100644 --- a/src/runtime/virtcontainers/qemu_arch_base_test.go +++ b/src/runtime/virtcontainers/qemu_arch_base_test.go @@ -224,7 +224,7 @@ func testQemuArchBaseAppend(t *testing.T, structure interface{}, expected []govm case config.VFIODev: devices = qemuArchBase.appendVFIODevice(devices, s) case config.VhostUserDeviceAttrs: - devices, err = qemuArchBase.appendVhostUserDevice(devices, s) + devices, err = qemuArchBase.appendVhostUserDevice(context.Background(), devices, s) } assert.NoError(err) diff --git a/src/runtime/virtcontainers/qemu_s390x.go b/src/runtime/virtcontainers/qemu_s390x.go index 01968b6b1f..effced44b0 100644 --- a/src/runtime/virtcontainers/qemu_s390x.go +++ b/src/runtime/virtcontainers/qemu_s390x.go @@ -13,6 +13,7 @@ import ( govmmQemu "github.com/kata-containers/govmm/qemu" "github.com/kata-containers/kata-containers/src/runtime/virtcontainers/device/config" "github.com/kata-containers/kata-containers/src/runtime/virtcontainers/types" + "github.com/kata-containers/kata-containers/src/runtime/virtcontainers/utils" ) type qemuS390x struct { @@ -152,10 +153,33 @@ func (q *qemuS390x) appendCCWBlockDevice(ctx context.Context, devices []govmmQem return devices, nil } -// appendVhostUserDevice throws an error if vhost devices are tried to be used. -// See issue https://github.com/kata-containers/runtime/issues/659 -func (q *qemuS390x) appendVhostUserDevice(devices []govmmQemu.Device, attr config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) { - return nil, fmt.Errorf("No vhost-user devices supported on s390x") +func (q *qemuS390x) appendVhostUserDevice(ctx context.Context, devices []govmmQemu.Device, attr config.VhostUserDeviceAttrs) ([]govmmQemu.Device, error) { + if attr.Type != config.VhostUserFS { + return devices, fmt.Errorf("vhost-user device of type %s not supported on s390x, only vhost-user-fs-ccw is supported", attr.Type) + } + + addr, b, err := q.addDeviceToBridge(ctx, attr.DevID, types.CCW) + if err != nil { + return devices, fmt.Errorf("Failed to append vhost user device: %s", err) + } + var devno string + devno, err = b.AddressFormatCCW(addr) + if err != nil { + return devices, fmt.Errorf("Failed to append vhost user device: %s", err) + } + + qemuVhostUserDevice := govmmQemu.VhostUserDevice{ + SocketPath: attr.SocketPath, + CharDevID: utils.MakeNameID("char", attr.DevID, maxDevIDSize), + TypeDevID: utils.MakeNameID("fs", attr.DevID, maxDevIDSize), + Tag: attr.Tag, + CacheSize: attr.CacheSize, + VhostUserType: govmmQemu.VhostUserFS, + DevNo: devno, + } + + devices = append(devices, qemuVhostUserDevice) + return devices, nil } // supportGuestMemoryHotplug return false for s390x architecture. The pc-dimm backend device for s390x diff --git a/src/runtime/virtcontainers/qemu_s390x_test.go b/src/runtime/virtcontainers/qemu_s390x_test.go index 70ddf3ff21..7b8067bee4 100644 --- a/src/runtime/virtcontainers/qemu_s390x_test.go +++ b/src/runtime/virtcontainers/qemu_s390x_test.go @@ -6,11 +6,14 @@ package virtcontainers import ( + "context" "fmt" "testing" govmmQemu "github.com/kata-containers/govmm/qemu" "github.com/stretchr/testify/assert" + + "github.com/kata-containers/kata-containers/src/runtime/virtcontainers/device/config" ) func newTestQemu(assert *assert.Assertions, machineType string) qemuArch { @@ -54,15 +57,47 @@ func TestQemuS390xMemoryTopology(t *testing.T) { } func TestQemuS390xAppendVhostUserDevice(t *testing.T) { - macAddress := "00:11:22:33:44:55:66" - qemu := qemuS390x{} assert := assert.New(t) + qemu := newTestQemu(assert, QemuCCWVirtio) - vhostUserDevice := config.VhostUserDeviceAttrs{ - Type: config.VhostUserNet, - MacAddress: macAddress, + // test devices that should not work + for _, deviceType := range []config.DeviceType{config.VhostUserSCSI, config.VhostUserNet, config.VhostUserBlk} { + vhostUserDevice := config.VhostUserDeviceAttrs{ + Type: deviceType, + } + _, err := qemu.appendVhostUserDevice(context.Background(), nil, vhostUserDevice) + assert.Error(err) } - _, err := qemu.appendVhostUserDevice(nil, vhostUserDevice) - assert.Error(err) + // test vhost user fs (virtio-fs) + socketPath := "nonexistentpath.sock" + id := "deadbeef" + tag := "shared" + var cacheSize uint32 = 0 + + expected := []govmmQemu.Device{ + govmmQemu.VhostUserDevice{ + SocketPath: socketPath, + CharDevID: fmt.Sprintf("char-%s", id), + TypeDevID: fmt.Sprintf("fs-%s", id), + Tag: tag, + CacheSize: cacheSize, + VhostUserType: govmmQemu.VhostUserFS, + DevNo: "fe.0.0001", + }, + } + + vhostUserDevice := config.VhostUserDeviceAttrs{ + DevID: id, + SocketPath: socketPath, + Type: config.VhostUserFS, + Tag: tag, + CacheSize: cacheSize, + } + + var devices []govmmQemu.Device + devices, err := qemu.appendVhostUserDevice(context.Background(), devices, vhostUserDevice) + + assert.NoError(err) + assert.Equal(devices, expected) }