hw_caps is normally derived during realize, at vfio_device_hiod_realize -> hiod_iommufd_vfio_realize -> iommufd_backend_get_device_info. However, this depends on the devid, which is not preserved during CPR.
Save devid in vmstate. Defer the vfio_device_hiod_realize call to post_load time, after devid has been recovered from vmstate. Signed-off-by: Steve Sistare <steven.sist...@oracle.com> --- hw/vfio/cpr-iommufd.c | 14 ++++++++++++++ hw/vfio/iommufd.c | 3 ++- 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/hw/vfio/cpr-iommufd.c b/hw/vfio/cpr-iommufd.c index 8453d76..a1ac517 100644 --- a/hw/vfio/cpr-iommufd.c +++ b/hw/vfio/cpr-iommufd.c @@ -99,12 +99,26 @@ void vfio_iommufd_cpr_unregister_container(VFIOIOMMUFDContainer *container) migration_remove_notifier(&bcontainer->cpr_reboot_notifier); } +static int vfio_device_post_load(void *opaque, int version_id) +{ + VFIODevice *vbasedev = opaque; + Error *err = NULL; + + if (!vfio_device_hiod_realize(vbasedev, &err)) { + error_report_err(err); + return false; + } + return true; +} + static const VMStateDescription vfio_device_vmstate = { .name = "vfio-iommufd-device", .version_id = 0, .minimum_version_id = 0, + .post_load = vfio_device_post_load, .needed = cpr_needed_for_reuse, .fields = (VMStateField[]) { + VMSTATE_INT32(devid, VFIODevice), VMSTATE_END_OF_LIST() } }; diff --git a/hw/vfio/iommufd.c b/hw/vfio/iommufd.c index 3fc530d..693ed19 100644 --- a/hw/vfio/iommufd.c +++ b/hw/vfio/iommufd.c @@ -536,7 +536,8 @@ static bool iommufd_cdev_attach(const char *name, VFIODevice *vbasedev, * FD to be connected and having a devid to be able to successfully call * iommufd_backend_get_device_info(). */ - if (!vfio_device_hiod_realize(vbasedev, errp)) { + if (!vbasedev->cpr.reused && + !vfio_device_hiod_realize(vbasedev, errp)) { goto err_alloc_ioas; } -- 1.8.3.1