> -----Original Message----- > From: liulongfang <liulongfang@xxxxxxxxxx> > Sent: Thursday, March 13, 2025 7:20 AM > To: alex.williamson@xxxxxxxxxx; jgg@xxxxxxxxxx; Shameerali Kolothum > Thodi <shameerali.kolothum.thodi@xxxxxxxxxx>; Jonathan Cameron > <jonathan.cameron@xxxxxxxxxx> > Cc: kvm@xxxxxxxxxxxxxxx; linux-kernel@xxxxxxxxxxxxxxx; > linuxarm@xxxxxxxxxxxxx; liulongfang <liulongfang@xxxxxxxxxx> > Subject: [PATCH v5 5/5] hisi_acc_vfio_pci: bugfix live migration function > without VF device driver > > If the VF device driver is not loaded in the Guest OS and we attempt to > perform device data migration, the address of the migrated data will > be NULL. > The live migration recovery operation on the destination side will > access a null address value, which will cause access errors. > > Therefore, live migration of VMs without added VF device drivers > does not require device data migration. > In addition, when the queue address data obtained by the destination > is empty, device queue recovery processing will not be performed. > > Fixes: b0eed085903e ("hisi_acc_vfio_pci: Add support for VFIO live > migration") > Signed-off-by: Longfang Liu <liulongfang@xxxxxxxxxx> > --- > .../vfio/pci/hisilicon/hisi_acc_vfio_pci.c | 25 +++++++++++++------ > 1 file changed, 18 insertions(+), 7 deletions(-) > > diff --git a/drivers/vfio/pci/hisilicon/hisi_acc_vfio_pci.c > b/drivers/vfio/pci/hisilicon/hisi_acc_vfio_pci.c > index cadc82419dca..44fa2d16bbcc 100644 > --- a/drivers/vfio/pci/hisilicon/hisi_acc_vfio_pci.c > +++ b/drivers/vfio/pci/hisilicon/hisi_acc_vfio_pci.c > @@ -426,13 +426,6 @@ static int vf_qm_check_match(struct > hisi_acc_vf_core_device *hisi_acc_vdev, > return -EINVAL; > } > > - ret = qm_write_regs(vf_qm, QM_VF_STATE, &vf_data->vf_qm_state, > 1); > - if (ret) { > - dev_err(dev, "failed to write QM_VF_STATE\n"); > - return ret; > - } > - > - hisi_acc_vdev->vf_qm_state = vf_data->vf_qm_state; > hisi_acc_vdev->match_done = true; > return 0; > } > @@ -498,6 +491,13 @@ static int vf_qm_load_data(struct > hisi_acc_vf_core_device *hisi_acc_vdev, > if (migf->total_length < sizeof(struct acc_vf_data)) > return -EINVAL; > > + ret = qm_write_regs(qm, QM_VF_STATE, &vf_data->vf_qm_state, 1); > + if (ret) { > + dev_err(dev, "failed to write QM_VF_STATE\n"); > + return -EINVAL; > + } > + hisi_acc_vdev->vf_qm_state = vf_data->vf_qm_state; > + > qm->eqe_dma = vf_data->eqe_dma; > qm->aeqe_dma = vf_data->aeqe_dma; > qm->sqc_dma = vf_data->sqc_dma; > @@ -506,6 +506,12 @@ static int vf_qm_load_data(struct > hisi_acc_vf_core_device *hisi_acc_vdev, > qm->qp_base = vf_data->qp_base; > qm->qp_num = vf_data->qp_num; > > + if (!vf_data->eqe_dma || !vf_data->aeqe_dma || > + !vf_data->sqc_dma || !vf_data->cqc_dma) { > + dev_err(dev, "resume dma addr is NULL!\n"); > + return -EINVAL; > + } > + > ret = qm_set_regs(qm, vf_data); > if (ret) { > dev_err(dev, "set VF regs failed\n"); > @@ -726,8 +732,12 @@ static int hisi_acc_vf_load_state(struct > hisi_acc_vf_core_device *hisi_acc_vdev) > { > struct device *dev = &hisi_acc_vdev->vf_dev->dev; > struct hisi_acc_vf_migration_file *migf = hisi_acc_vdev- > >resuming_migf; > + struct acc_vf_data *vf_data = &migf->vf_data; > int ret; > > + if (vf_data->vf_qm_state != QM_READY) > + return 0; I don't think we need to check the above. In vf_qm_satte_save(), If vf_qm_state != QM_READY, we set the migf->total_length = QM_MATCH_SIZE. Hence it will return 0 in the below vf_qm_load_data() anyway. With that corrected, Reviewed-by: Shameer Kolothum <shameerali.kolothum.thodi@xxxxxxxxxx> Thanks, Shameer > + > /* Recover data to VF */ > ret = vf_qm_load_data(hisi_acc_vdev, migf); > if (ret) { > @@ -1531,6 +1541,7 @@ static int hisi_acc_vfio_pci_migrn_init_dev(struct > vfio_device *core_vdev) > hisi_acc_vdev->vf_id = pci_iov_vf_id(pdev) + 1; > hisi_acc_vdev->pf_qm = pf_qm; > hisi_acc_vdev->vf_dev = pdev; > + hisi_acc_vdev->vf_qm_state = QM_NOT_READY; > mutex_init(&hisi_acc_vdev->state_mutex); > mutex_init(&hisi_acc_vdev->open_mutex); > > -- > 2.24.0