diff mbox series

vfio: Fix unregister SaveVMHandler in vfio_migration_finalize

Message ID 20210527123101.289-1-jiangkunkun@huawei.com
State New
Headers show
Series vfio: Fix unregister SaveVMHandler in vfio_migration_finalize | expand

Commit Message

Kunkun Jiang May 27, 2021, 12:31 p.m. UTC
In the vfio_migration_init(), the SaveVMHandler is registered for
VFIO device. But it lacks the operation of 'unregister'. It will
lead to 'Segmentation fault (core dumped)' in
qemu_savevm_state_setup(), if performing live migration after a
VFIO device is hot deleted.

Fixes: 7c2f5f75f94 (vfio: Register SaveVMHandlers for VFIO device)
Reported-by: Qixin Gan <ganqixin@huawei.com>
Signed-off-by: Kunkun Jiang <jiangkunkun@huawei.com>
---
 hw/vfio/migration.c | 1 +
 1 file changed, 1 insertion(+)

Comments

Philippe Mathieu-Daudé May 27, 2021, 1:44 p.m. UTC | #1
On 5/27/21 2:31 PM, Kunkun Jiang wrote:
> In the vfio_migration_init(), the SaveVMHandler is registered for
> VFIO device. But it lacks the operation of 'unregister'. It will
> lead to 'Segmentation fault (core dumped)' in
> qemu_savevm_state_setup(), if performing live migration after a
> VFIO device is hot deleted.
> 
> Fixes: 7c2f5f75f94 (vfio: Register SaveVMHandlers for VFIO device)
> Reported-by: Qixin Gan <ganqixin@huawei.com>
> Signed-off-by: Kunkun Jiang <jiangkunkun@huawei.com>

Cc: qemu-stable@nongnu.org

> ---
>  hw/vfio/migration.c | 1 +
>  1 file changed, 1 insertion(+)
> 
> diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
> index 201642d75e..ef397ebe6c 100644
> --- a/hw/vfio/migration.c
> +++ b/hw/vfio/migration.c
> @@ -892,6 +892,7 @@ void vfio_migration_finalize(VFIODevice *vbasedev)
>  
>          remove_migration_state_change_notifier(&migration->migration_state);
>          qemu_del_vm_change_state_handler(migration->vm_state);
> +        unregister_savevm(VMSTATE_IF(vbasedev->dev), "vfio", vbasedev);
Hmm what about devices using "%s/vfio" id?

>          vfio_migration_exit(vbasedev);
>      }
>  
>
Kunkun Jiang May 28, 2021, 2:04 a.m. UTC | #2
Hi Philippe,

On 2021/5/27 21:44, Philippe Mathieu-Daudé wrote:
> On 5/27/21 2:31 PM, Kunkun Jiang wrote:
>> In the vfio_migration_init(), the SaveVMHandler is registered for
>> VFIO device. But it lacks the operation of 'unregister'. It will
>> lead to 'Segmentation fault (core dumped)' in
>> qemu_savevm_state_setup(), if performing live migration after a
>> VFIO device is hot deleted.
>>
>> Fixes: 7c2f5f75f94 (vfio: Register SaveVMHandlers for VFIO device)
>> Reported-by: Qixin Gan <ganqixin@huawei.com>
>> Signed-off-by: Kunkun Jiang <jiangkunkun@huawei.com>
> Cc: qemu-stable@nongnu.org
>
>> ---
>>   hw/vfio/migration.c | 1 +
>>   1 file changed, 1 insertion(+)
>>
>> diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
>> index 201642d75e..ef397ebe6c 100644
>> --- a/hw/vfio/migration.c
>> +++ b/hw/vfio/migration.c
>> @@ -892,6 +892,7 @@ void vfio_migration_finalize(VFIODevice *vbasedev)
>>   
>>           remove_migration_state_change_notifier(&migration->migration_state);
>>           qemu_del_vm_change_state_handler(migration->vm_state);
>> +        unregister_savevm(VMSTATE_IF(vbasedev->dev), "vfio", vbasedev);
> Hmm what about devices using "%s/vfio" id?
The unregister_savevm() needs 'VMSTATEIf *obj'. If we pass a non-null 'obj'
to unregister_svevm(), it will handle the devices using "%s/vfio" id with
the following code:
>     if (obj) {
>         char *oid = vmstate_if_get_id(obj);
>         if (oid) {
>             pstrcpy(id, sizeof(id), oid);
>             pstrcat(id, sizeof(id), "/");
>             g_free(oid);
>         }
>     }
>     pstrcat(id, sizeof(id), idstr);

By the way, I'm puzzled that register_savevm_live() and unregister_savevm()
handle devices using "%s/vfio" id differently. So I learned the commit
history of register_savevm_live() and unregister_savevm().

In the beginning, both them need 'DeviceState *dev', which are replaced
with VMStateIf in 3cad405babb. Later in ce62df5378b, the 'dev' was removed,
because no caller of register_savevm_live() need to pass a non-null 'dev'
at that time.

So now the vfio devices need to handle the 'id' first and then call
register_savevm_live(). I am wondering whether we need to add
'VMSTATEIf *obj' in register_savevm_live(). What do you think of this?

Thanks,
Kunkun Jiang
>
>>           vfio_migration_exit(vbasedev);
>>       }
>>   
>>
> .
Kirti Wankhede May 28, 2021, 6:27 p.m. UTC | #3
On 5/28/2021 7:34 AM, Kunkun Jiang wrote:
> Hi Philippe,
> 
> On 2021/5/27 21:44, Philippe Mathieu-Daudé wrote:
>> On 5/27/21 2:31 PM, Kunkun Jiang wrote:
>>> In the vfio_migration_init(), the SaveVMHandler is registered for
>>> VFIO device. But it lacks the operation of 'unregister'. It will
>>> lead to 'Segmentation fault (core dumped)' in
>>> qemu_savevm_state_setup(), if performing live migration after a
>>> VFIO device is hot deleted.
>>>
>>> Fixes: 7c2f5f75f94 (vfio: Register SaveVMHandlers for VFIO device)
>>> Reported-by: Qixin Gan <ganqixin@huawei.com>
>>> Signed-off-by: Kunkun Jiang <jiangkunkun@huawei.com>
>> Cc: qemu-stable@nongnu.org
>>
>>> ---
>>>   hw/vfio/migration.c | 1 +
>>>   1 file changed, 1 insertion(+)
>>>
>>> diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
>>> index 201642d75e..ef397ebe6c 100644
>>> --- a/hw/vfio/migration.c
>>> +++ b/hw/vfio/migration.c
>>> @@ -892,6 +892,7 @@ void vfio_migration_finalize(VFIODevice *vbasedev)
>>>           
>>> remove_migration_state_change_notifier(&migration->migration_state);
>>>           qemu_del_vm_change_state_handler(migration->vm_state);
>>> +        unregister_savevm(VMSTATE_IF(vbasedev->dev), "vfio", vbasedev);
>> Hmm what about devices using "%s/vfio" id?
> The unregister_savevm() needs 'VMSTATEIf *obj'. If we pass a non-null 'obj'
> to unregister_svevm(), it will handle the devices using "%s/vfio" id with
> the following code:
>>     if (obj) {
>>         char *oid = vmstate_if_get_id(obj);
>>         if (oid) {
>>             pstrcpy(id, sizeof(id), oid);
>>             pstrcat(id, sizeof(id), "/");
>>             g_free(oid);
>>         }
>>     }
>>     pstrcat(id, sizeof(id), idstr);

This fix seems fine to me.

> 
> By the way, I'm puzzled that register_savevm_live() and unregister_savevm()
> handle devices using "%s/vfio" id differently. So I learned the commit
> history of register_savevm_live() and unregister_savevm().
> 
> In the beginning, both them need 'DeviceState *dev', which are replaced
> with VMStateIf in 3cad405babb. Later in ce62df5378b, the 'dev' was removed,
> because no caller of register_savevm_live() need to pass a non-null 'dev'
> at that time.
> 
> So now the vfio devices need to handle the 'id' first and then call
> register_savevm_live(). I am wondering whether we need to add
> 'VMSTATEIf *obj' in register_savevm_live(). What do you think of this?
> 

I think proposed change above is independent of this fix. I'll defer to 
other experts.

Reviewed by: Kirti Wankhede <kwankhede@nvidia.com>
Kunkun Jiang June 15, 2021, 11:42 a.m. UTC | #4
Kindly ping,

Hi everyone,

Will this patch be picked up soon, or is there any other work for me to do?

Best Regards,
Kunkun Jiang

On 2021/5/27 20:31, Kunkun Jiang wrote:
> In the vfio_migration_init(), the SaveVMHandler is registered for
> VFIO device. But it lacks the operation of 'unregister'. It will
> lead to 'Segmentation fault (core dumped)' in
> qemu_savevm_state_setup(), if performing live migration after a
> VFIO device is hot deleted.
>
> Fixes: 7c2f5f75f94 (vfio: Register SaveVMHandlers for VFIO device)
> Reported-by: Qixin Gan <ganqixin@huawei.com>
> Signed-off-by: Kunkun Jiang <jiangkunkun@huawei.com>
> ---
>   hw/vfio/migration.c | 1 +
>   1 file changed, 1 insertion(+)
>
> diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
> index 201642d75e..ef397ebe6c 100644
> --- a/hw/vfio/migration.c
> +++ b/hw/vfio/migration.c
> @@ -892,6 +892,7 @@ void vfio_migration_finalize(VFIODevice *vbasedev)
>   
>           remove_migration_state_change_notifier(&migration->migration_state);
>           qemu_del_vm_change_state_handler(migration->vm_state);
> +        unregister_savevm(VMSTATE_IF(vbasedev->dev), "vfio", vbasedev);
>           vfio_migration_exit(vbasedev);
>       }
>
diff mbox series

Patch

diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
index 201642d75e..ef397ebe6c 100644
--- a/hw/vfio/migration.c
+++ b/hw/vfio/migration.c
@@ -892,6 +892,7 @@  void vfio_migration_finalize(VFIODevice *vbasedev)
 
         remove_migration_state_change_notifier(&migration->migration_state);
         qemu_del_vm_change_state_handler(migration->vm_state);
+        unregister_savevm(VMSTATE_IF(vbasedev->dev), "vfio", vbasedev);
         vfio_migration_exit(vbasedev);
     }