[pve-devel] [PATCH 10/12] vm_deviceplug : implement pending change
Alexandre Derumier
aderumier at odiso.com
Thu Oct 30 13:40:31 CET 2014
1) if vm is not running, we apply pending change directly
2) for disk, we remove unused disk on succesfull hotplug
[CONF]
unused0: vm-disk-100-2.raw
[PENDING]
virtio0: vm-disk-100-2.raw
->
[CONF]
[PENDING]
virtio0: vm-disk-100-2.raw
3) for all devices, we apply the pending change to config and remove the pending value
[CONF]
[PENDING]
virtio0: vm-disk-100-2.raw
->
[CONF]
virtio0: vm-disk-100-2.raw
[PENDING]
Signed-off-by: Alexandre Derumier <aderumier at odiso.com>
---
PVE/QemuServer.pm | 64 +++++++++++++++++++++++++++++++++++++++++++++++------
1 file changed, 57 insertions(+), 7 deletions(-)
diff --git a/PVE/QemuServer.pm b/PVE/QemuServer.pm
index 52bcd1f..6f9dcd8 100644
--- a/PVE/QemuServer.pm
+++ b/PVE/QemuServer.pm
@@ -1401,6 +1401,19 @@ sub del_volume {
}
}
+sub del_unused_volume {
+ my ($conf, $volid, $storecfg) = @_;
+
+ foreach my $key (keys %$conf) {
+ next if($key !~ m/^unused/);
+ my $confdrive = PVE::QemuServer::parse_drive($key, $conf->{$key});
+ if (!PVE::QemuServer::drive_is_cdrom($confdrive)) {
+ PVE::QemuServer::cleanup_drive_path($key, $storecfg, $confdrive);
+ delete $conf->{$key} if $confdrive->{file} eq $volid;
+ }
+ }
+}
+
my $valid_smbios1_options = {
manufacturer => '\S+',
product => '\S+',
@@ -2951,19 +2964,38 @@ sub vm_devices_list {
}
sub vm_deviceplug {
- my ($storecfg, $conf, $vmid, $deviceid, $device) = @_;
+ my ($storecfg, $conf, $vmid, $deviceid, $device, $optvalue) = @_;
- return 1 if !check_running($vmid);
+ if (!check_running($vmid)){
+ if($conf->{pending}->{$deviceid}){
+ $conf->{$deviceid} = $optvalue;
+ delete $conf->{pending}->{$deviceid};
+ PVE::QemuServer::update_config_nolock($vmid, $conf, 1);
+ }
+ }
my $q35 = machine_type_is_q35($conf);
if ($deviceid eq 'tablet') {
- qemu_deviceadd($vmid, print_tabletdevice_full($conf));
+
+ eval { qemu_deviceadd($vmid, print_tabletdevice_full($conf->{pending}))};
+
+ if($conf->{pending}->{del}->{$deviceid}) {
+ delete $conf->{$deviceid};
+ delete $conf->{pending}->{del}->{$deviceid};
+ } else {
+ $conf->{$deviceid} = $conf->{pending}->{$deviceid};
+ delete $conf->{pending}->{$deviceid};
+ }
+
+ PVE::QemuServer::update_config_nolock($vmid, $conf, 1);
return 1;
}
return 1 if !$conf->{hotplug};
+ return 1 if ($deviceid =~ m/^(ide|sata)(\d+)$/);
+
my $devices_list = vm_devices_list($vmid);
return 1 if defined($devices_list->{$deviceid});
@@ -2971,12 +3003,18 @@ sub vm_deviceplug {
if ($deviceid =~ m/^(virtio)(\d+)$/) {
return undef if !qemu_driveadd($storecfg, $vmid, $device);
- my $devicefull = print_drivedevice_full($storecfg, $conf, $vmid, $device);
+ my $devicefull = print_drivedevice_full($storecfg, $conf->{pending}, $vmid, $device);
qemu_deviceadd($vmid, $devicefull);
if(!qemu_deviceaddverify($vmid, $deviceid)) {
qemu_drivedel($vmid, $deviceid);
return undef;
}
+
+ #remove unused disk
+ my $drive = PVE::QemuServer::parse_drive($deviceid, $conf->{pending}->{$deviceid});
+ PVE::QemuServer::del_unused_volume($conf, $drive->{file},$storecfg);
+ PVE::QemuServer::update_config_nolock($vmid, $conf, 1);
+
}
if ($deviceid =~ m/^(scsihw)(\d+)$/) {
@@ -2990,16 +3028,21 @@ sub vm_deviceplug {
if ($deviceid =~ m/^(scsi)(\d+)$/) {
return undef if !qemu_findorcreatescsihw($storecfg,$conf, $vmid, $device);
return undef if !qemu_driveadd($storecfg, $vmid, $device);
- my $devicefull = print_drivedevice_full($storecfg, $conf, $vmid, $device);
+ my $devicefull = print_drivedevice_full($storecfg, $conf->{pending}, $vmid, $device);
if(!qemu_deviceadd($vmid, $devicefull)) {
qemu_drivedel($vmid, $deviceid);
return undef;
}
+ #remove unused disk
+ my $drive = PVE::QemuServer::parse_drive($deviceid, $conf->{pending}->{$deviceid});
+ PVE::QemuServer::del_unused_volume($conf, $drive->{file},$storecfg);
+ PVE::QemuServer::update_config_nolock($vmid, $conf, 1);
+
}
if ($deviceid =~ m/^(net)(\d+)$/) {
- return undef if !qemu_netdevadd($vmid, $conf, $device, $deviceid);
- my $netdevicefull = print_netdevice_full($vmid, $conf, $device, $deviceid);
+ return undef if !qemu_netdevadd($vmid, $conf->{pending}, $device, $deviceid);
+ my $netdevicefull = print_netdevice_full($vmid, $conf->{pending}, $device, $deviceid);
qemu_deviceadd($vmid, $netdevicefull);
if(!qemu_deviceaddverify($vmid, $deviceid)) {
qemu_netdevdel($vmid, $deviceid);
@@ -3016,6 +3059,13 @@ sub vm_deviceplug {
return undef if !qemu_deviceaddverify($vmid, $deviceid);
}
+ #delete pending device after hotplug
+ if($conf->{pending}->{$deviceid}){
+ $conf->{$deviceid} = $optvalue;
+ delete $conf->{pending}->{$deviceid};
+ PVE::QemuServer::update_config_nolock($vmid, $conf, 1);
+ }
+
return 1;
}
--
1.7.10.4
More information about the pve-devel
mailing list