qemuDomainRemoveDiskDevice() called qemuBlockStorageSourceChainDetachPrepareBlockdev() unconditionally. A CD-ROM with no media has an empty source (path == NULL), for which virStorageSourceIsEmpty() returns true while virStorageSourceIsBacking() still returns true, so the chain walk prepared a blockdev-del for a node that was never created in QEMU. Detaching such a device produced an internal error, either "Failed to find node with node-name='libvirt-N-storage'" (when a prior eject had left a stale node name in the source) or "argument key 'node-name' must not have null value".
Guard the detach preparation with virStorageSourceIsEmpty(), as the old-media detach in qemuDomainChangeMediaBlockdev() already does. The following qemuBlockStorageSourceChainDetach() and access revoke are already guarded by a non-NULL diskBackend, so an empty source is left untouched. Signed-off-by: Mitsuru Kariya <[email protected]> --- src/qemu/qemu_hotplug.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/qemu/qemu_hotplug.c b/src/qemu/qemu_hotplug.c index 5be567b510..c2cd5496e0 100644 --- a/src/qemu/qemu_hotplug.c +++ b/src/qemu/qemu_hotplug.c @@ -4861,7 +4861,8 @@ qemuDomainRemoveDiskDevice(virQEMUDriver *driver, diskPriv->blockjob->disk = NULL; g_clear_pointer(&diskPriv->blockjob, virObjectUnref); } else { - if (!(diskBackend = qemuBlockStorageSourceChainDetachPrepareBlockdev(disk->src))) + if (!virStorageSourceIsEmpty(disk->src) && + !(diskBackend = qemuBlockStorageSourceChainDetachPrepareBlockdev(disk->src))) goto cleanup; } -- 2.43.0
