The VFIO AP matrix mediated device driver provides an ioctl interface to configure the APM, ADM and APM fields contained in the CRYCB referenced by the guest's SIE state description. The mask values are specified in the mediated AP matrix device's sysfs attribute files. Configuring a KVM guest's AP matrix grants direct access to the AP adapters, domains and control domains specified in the matrix configuration. Signed-off-by: Tony Krowiak <akrowiak@xxxxxxxxxxxxxxxxxx> --- hw/vfio/ap-matrix.c | 45 ++++++++++++++++++++++++++++++++++++++++++++ linux-headers/linux/vfio.h | 1 + 2 files changed, 46 insertions(+), 0 deletions(-) diff --git a/hw/vfio/ap-matrix.c b/hw/vfio/ap-matrix.c index eeaa439..ce87c05 100644 --- a/hw/vfio/ap-matrix.c +++ b/hw/vfio/ap-matrix.c @@ -85,6 +85,35 @@ static VFIOGroup *vfio_ap_matrix_get_group(VFIOAPMatrixDevice *vapmdev, return vfio_get_group(groupid, &address_space_memory, errp); } +static int vfio_ap_matrix_configure(VFIOAPMatrixDevice *vapmdev, + APMatrixMasks *masks, Error **errp) +{ + size_t i; + struct vfio_ap_matrix_config config; + int ret; + + config.argsz = sizeof(config); + config.flags = 0; + + ret = ioctl(vapmdev->vdev.fd, VFIO_AP_MATRIX_CONFIGURE, &config); + if (ret) { + error_setg_errno(errp, ret, + "%s: Error configuring matrix for device %s", + TYPE_VFIO_AP_MATRIX_DEVICE, vapmdev->vdev.name); + return -EFAULT; + } + + for (i = 0; i < VFIO_AP_MATRIX_MASK_INDICES; i++) { + if (i < AP_MATRIX_MASK_INDICES) { + masks->apm[i] = config.apm[i]; + masks->aqm[i] = config.aqm[i]; + masks->adm[i] = config.adm[i]; + } + } + + return 0; +} + static void vfio_ap_matrix_realize(DeviceState *dev, Error **errp) { VFIODevice *vbasedev; @@ -92,8 +121,11 @@ static void vfio_ap_matrix_realize(DeviceState *dev, Error **errp) APMatrixDevice *apmdev = DO_UPCAST(APMatrixDevice, parent_obj, dev); S390APMatrixDevice *sapmdev = DO_UPCAST(S390APMatrixDevice, parent_obj, apmdev); + S390APMatrixDeviceClass *csapmdev = + S390_AP_MATRIX_DEVICE_GET_CLASS(sapmdev); VFIOAPMatrixDevice *vapmdev = DO_UPCAST(VFIOAPMatrixDevice, apmdev, sapmdev); + APMatrixMasks masks; char *mdevid; Error *local_err = NULL; @@ -121,8 +153,21 @@ static void vfio_ap_matrix_realize(DeviceState *dev, Error **errp) goto out_device_err; } + if (csapmdev->realize) { + if (vfio_ap_matrix_configure(vapmdev, &masks, &local_err)) { + goto out_realize_err; + } + + csapmdev->realize(sapmdev, &masks, &local_err); + if (local_err) { + goto out_realize_err; + } + } + return; +out_realize_err: + vfio_put_device(vapmdev); out_device_err: vfio_put_group(vfio_group); out_err: diff --git a/linux-headers/linux/vfio.h b/linux-headers/linux/vfio.h index 2d96c57..bf1e25d 100644 --- a/linux-headers/linux/vfio.h +++ b/linux-headers/linux/vfio.h @@ -736,6 +736,7 @@ struct vfio_ap_matrix_config { __u64 aqm[VFIO_AP_MATRIX_MASK_INDICES]; __u64 adm[VFIO_AP_MATRIX_MASK_INDICES]; }; + /* ***************************************************************** */ #endif /* _UAPIVFIO_H */ -- 1.7.1