[pve-devel] [PATCH storage 04/11] plugin/storage: volume resize: add snapname parameter
Fiona Ebner
f.ebner at proxmox.com
Tue Dec 16 14:02:15 CET 2025
For LVM storages using 'snapshot-as-volume-chain', it's necessary to
ensure that the size for the LV of the target snapshot volume is large
enough before doing a commit operation. Allow resizing a snapshot via
the storage (plugin) API to prepare this.
Suggested-by: Fabian Grünbichler <f.gruenbichler at proxmox.com>
Signed-off-by: Fiona Ebner <f.ebner at proxmox.com>
---
src/PVE/Storage.pm | 4 ++--
src/PVE/Storage/BTRFSPlugin.pm | 3 ++-
src/PVE/Storage/ESXiPlugin.pm | 2 +-
src/PVE/Storage/ISCSIDirectPlugin.pm | 2 +-
src/PVE/Storage/ISCSIPlugin.pm | 2 +-
src/PVE/Storage/LVMPlugin.pm | 5 +++--
src/PVE/Storage/LvmThinPlugin.pm | 8 +++++++-
src/PVE/Storage/PBSPlugin.pm | 2 +-
src/PVE/Storage/Plugin.pm | 12 ++++++++----
src/PVE/Storage/RBDPlugin.pm | 4 +++-
src/PVE/Storage/ZFSPlugin.pm | 5 +++--
src/PVE/Storage/ZFSPoolPlugin.pm | 4 +++-
12 files changed, 35 insertions(+), 18 deletions(-)
diff --git a/src/PVE/Storage.pm b/src/PVE/Storage.pm
index 6e87bac..c45d35b 100755
--- a/src/PVE/Storage.pm
+++ b/src/PVE/Storage.pm
@@ -393,7 +393,7 @@ sub volume_size_info {
}
sub volume_resize {
- my ($cfg, $volid, $size, $running) = @_;
+ my ($cfg, $volid, $size, $running, $snapname) = @_;
my $padding = (1024 - $size % 1024) % 1024;
$size = $size + $padding;
@@ -402,7 +402,7 @@ sub volume_resize {
if ($storeid) {
my $scfg = storage_config($cfg, $storeid);
my $plugin = PVE::Storage::Plugin->lookup($scfg->{type});
- return $plugin->volume_resize($scfg, $storeid, $volname, $size, $running);
+ return $plugin->volume_resize($scfg, $storeid, $volname, $size, $running, $snapname);
} elsif ($volid =~ m|^(/.+)$| && -e $volid) {
die "resize file/device '$volid' is not possible\n";
} else {
diff --git a/src/PVE/Storage/BTRFSPlugin.pm b/src/PVE/Storage/BTRFSPlugin.pm
index e68d2bf..fb47aa0 100644
--- a/src/PVE/Storage/BTRFSPlugin.pm
+++ b/src/PVE/Storage/BTRFSPlugin.pm
@@ -496,10 +496,11 @@ sub volume_size_info {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
my $format = ($class->parse_volname($volname))[6];
if ($format eq 'subvol') {
+ die "resizing a snapshot is not supported for format 'subvol' in $class\n" if $snapname;
# NOTE: `btrfs send/recv` actually drops quota information so supporting subvolumes with
# quotas doesn't play nice with send/recv.
die "cannot resize subvolume - btrfs quotas are currently not supported\n";
diff --git a/src/PVE/Storage/ESXiPlugin.pm b/src/PVE/Storage/ESXiPlugin.pm
index f89e427..19f23bb 100644
--- a/src/PVE/Storage/ESXiPlugin.pm
+++ b/src/PVE/Storage/ESXiPlugin.pm
@@ -556,7 +556,7 @@ sub volume_import {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
die "resizing volumes is not supported for $class\n";
}
diff --git a/src/PVE/Storage/ISCSIDirectPlugin.pm b/src/PVE/Storage/ISCSIDirectPlugin.pm
index 62e9026..f976c31 100644
--- a/src/PVE/Storage/ISCSIDirectPlugin.pm
+++ b/src/PVE/Storage/ISCSIDirectPlugin.pm
@@ -227,7 +227,7 @@ sub volume_size_info {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
die "volume resize is not possible on iscsi device\n";
}
diff --git a/src/PVE/Storage/ISCSIPlugin.pm b/src/PVE/Storage/ISCSIPlugin.pm
index 30f4178..6472b2f 100644
--- a/src/PVE/Storage/ISCSIPlugin.pm
+++ b/src/PVE/Storage/ISCSIPlugin.pm
@@ -627,7 +627,7 @@ sub check_connection {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
die "volume resize is not possible on iscsi device";
}
diff --git a/src/PVE/Storage/LVMPlugin.pm b/src/PVE/Storage/LVMPlugin.pm
index aa472f5..a134334 100644
--- a/src/PVE/Storage/LVMPlugin.pm
+++ b/src/PVE/Storage/LVMPlugin.pm
@@ -987,7 +987,7 @@ sub deactivate_volume {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
my ($vtype, $name, $vmid, $basename, $basevmid, $isBase, $format) =
$class->parse_volname($volname);
@@ -995,7 +995,8 @@ sub volume_resize {
my $lvmsize = calculate_lvm_size($size / 1024, $format);
$lvmsize = "${lvmsize}k";
- my $path = $class->path($scfg, $volname);
+ my $path = $class->path($scfg, $volname, $storeid, $snapname);
+
my $cmd = ['/sbin/lvextend', '-L', $lvmsize, $path];
$class->cluster_lock_storage(
diff --git a/src/PVE/Storage/LvmThinPlugin.pm b/src/PVE/Storage/LvmThinPlugin.pm
index 2797d9e..1463335 100644
--- a/src/PVE/Storage/LvmThinPlugin.pm
+++ b/src/PVE/Storage/LvmThinPlugin.pm
@@ -355,7 +355,13 @@ sub create_base {
return $newvolname;
}
-# sub volume_resize {} reuse code from parent class
+sub volume_resize {
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
+
+ die "resizing a snapshot is not supported for $class\n" if $snapname;
+
+ return $class->SUPER::volume_resize($scfg, $storeid, $volname, $size, $running, $snapname);
+}
sub volume_snapshot {
my ($class, $scfg, $storeid, $volname, $snap) = @_;
diff --git a/src/PVE/Storage/PBSPlugin.pm b/src/PVE/Storage/PBSPlugin.pm
index 17e285a..9e5a5ec 100644
--- a/src/PVE/Storage/PBSPlugin.pm
+++ b/src/PVE/Storage/PBSPlugin.pm
@@ -977,7 +977,7 @@ sub volume_size_info {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
die "volume resize is not possible on pbs device";
}
diff --git a/src/PVE/Storage/Plugin.pm b/src/PVE/Storage/Plugin.pm
index b0d3bbf..221c872 100644
--- a/src/PVE/Storage/Plugin.pm
+++ b/src/PVE/Storage/Plugin.pm
@@ -1342,14 +1342,15 @@ sub volume_size_info {
=head3 volume_resize
- $plugin->volume_resize(\%scfg, $storeid, $volname, $size, $running);
+ $plugin->volume_resize(\%scfg, $storeid, $volname, $size, $running, $snapname);
Resize a volume to the new C<$size> in bytes. The size is guaranteed to be a multiple of C<1024>.
The implementation may pad to a larger size if required. In case of virtual machines, C<$running>
indicates that the VM is currently running and the call will be followed by a C<block_resize> QMP
command in QEMU. If resizing is supported natively via QEMU (for example, when using librbd), then
the plugin should simply return if the VM is running. For containers, C<$running> will always be
-C<0>.
+C<0>. If a snapshot name is specified via C<$snapname>, then the snapshot is the target of the
+resize operation.
C<die>s in case of errors, or if the underlying storage implementation or the volume's format
doesn't support resizing.
@@ -1359,13 +1360,16 @@ This function should not return any value.
=cut
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
die "can't resize this image format\n" if $volname !~ m/\.(raw|qcow2)$/;
return 1 if $running;
- my $path = $class->filesystem_path($scfg, $volname);
+ die "resizing a snapshot is not supported for $class without 'snapshot-as-volume-chain'\n"
+ if !$scfg->{'snapshot-as-volume-chain'} && $snapname;
+
+ my $path = $class->filesystem_path($scfg, $volname, $snapname);
my $format = ($class->parse_volname($volname))[6];
diff --git a/src/PVE/Storage/RBDPlugin.pm b/src/PVE/Storage/RBDPlugin.pm
index 7d3e7ab..b537425 100644
--- a/src/PVE/Storage/RBDPlugin.pm
+++ b/src/PVE/Storage/RBDPlugin.pm
@@ -895,7 +895,9 @@ sub volume_size_info {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
+
+ die "resizing a snapshot is not supported for $class\n" if $snapname;
return 1 if $running && !$scfg->{krbd}; # FIXME???
diff --git a/src/PVE/Storage/ZFSPlugin.pm b/src/PVE/Storage/ZFSPlugin.pm
index 99d8c8f..74e0a08 100644
--- a/src/PVE/Storage/ZFSPlugin.pm
+++ b/src/PVE/Storage/ZFSPlugin.pm
@@ -392,11 +392,12 @@ sub free_image {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
$volname = ($class->parse_volname($volname))[1];
- my $new_size = $class->SUPER::volume_resize($scfg, $storeid, $volname, $size, $running);
+ my $new_size =
+ $class->SUPER::volume_resize($scfg, $storeid, $volname, $size, $running, $snapname);
$class->zfs_resize_lu($scfg, $volname, $new_size);
diff --git a/src/PVE/Storage/ZFSPoolPlugin.pm b/src/PVE/Storage/ZFSPoolPlugin.pm
index 3b3456b..8319344 100644
--- a/src/PVE/Storage/ZFSPoolPlugin.pm
+++ b/src/PVE/Storage/ZFSPoolPlugin.pm
@@ -742,7 +742,9 @@ sub create_base {
}
sub volume_resize {
- my ($class, $scfg, $storeid, $volname, $size, $running) = @_;
+ my ($class, $scfg, $storeid, $volname, $size, $running, $snapname) = @_;
+
+ die "resizing a snapshot is not supported for $class\n" if $snapname;
my $new_size = int($size / 1024);
--
2.47.3
More information about the pve-devel
mailing list